SpringBoot日记——缓存的使用
SpringBoot核心技术的东西基本上都有介绍过了,接下来,进阶点~来说说缓存吧~
缓存这个词不少同学应该不会很陌生。而我们这里主要使用的就是Redis。
客户端第一次请求的时候是从库里拿出我们需要的数据,但如果每次查询都从库里拿,就会很耗时耗能。那么使用缓存以后,我们只需要第一次从库里拿完存到缓存中,只要不清除缓存,我们以后的请求都直接在缓存中拿数据,就会快很多很多。
先给出几个基础的方法,包括Mapper/Bean/Controller,不然后边说的东西估计有些人会很懵。
package com.oooodin.cache.bean;
public class Employee {
private Integer id;
private String lastName;
private String email;
private Integer gender; //性别 1男 0女
private Integer dId;
public Employee() {
super();
}
public Employee(Integer id, String lastName, String email, Integer gender, Integer dId) {
super();
this.id = id;
this.lastName = lastName;
this.email = email;
this.gender = gender;
this.dId = dId;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public Integer getGender() {
return gender;
}
public void setGender(Integer gender) {
this.gender = gender;
}
public Integer getdId() {
return dId;
}
public void setdId(Integer dId) {
this.dId = dId;
}
@Override
public String toString() {
return "Employee [id=" + id + ", lastName=" + lastName + ", email=" + email + ", gender=" + gender + ", dId="
+ dId + "]";
}
}
bean.Employee
import com.oooodin.cache.bean.Employee;
import org.apache.ibatis.annotations.Delete;
import org.apache.ibatis.annotations.Insert;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update; public interface EmployeeMapper { // 查询
@Select("SELECT * FROM employee WHERE id = #{id}")
public Employee getEmpById(Integer id); // 更新
@Update("UPDATE employee SET lastName = #{lastName},email = #{email},gender = #{gender},d_id=#{dId} WHERE id = #{id}")
public void updateEmp(Employee employee); // 删除
@Delete("DELETE FROM employee WHERE id = #{id}")
public void deleteEmpById(Integer id); // 新增
@Insert("INSERT INTO employee(lastName,email,genderm,d_id) VALUES(#{lastName},#{email},#{gender},#{dId})")
public void insertEmp(Employee employee);
}
mapper.EmployeeMapper
import com.oooodin.cache.bean.Employee;
import com.oooodin.cache.mapper.EmployeeMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.CachePut;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.stereotype.Service; @Service
public class EmployeeService { @Autowired
EmployeeMapper employeeMapper; /**
* 将方法结果进行缓存
* 再要相同数据,直接从缓存中获取,不再调用方法
*
* @param id
* @return
*/
@Cacheable(cacheNames = "emp")
public Employee getEmp(Integer id) {
System.out.println("查询" + id + "号员工");
Employee emp = employeeMapper.getEmpById(id);
return emp;
} @CachePut(cacheNames = "emp", key = "#result.id")
public Employee updateEmp(Employee employee) {
System.out.println("updateEmp:" + employee);
employeeMapper.updateEmp(employee);
return employee;
} @CacheEvict(cacheNames = "emp", key = "#id")
public void deleteEmp(Integer id) {
employeeMapper.deleteEmpById(id);
}
}
service.EmployeeService
import com.oooodin.cache.bean.Employee;
import com.oooodin.cache.service.EmployeeService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController; @RestController
public class EmployeeController { @Autowired
EmployeeService employeeService; @GetMapping("/emp/{id}")
public Employee getEmploee(@PathVariable("id") Integer id) {
Employee emp = employeeService.getEmp(id);
return emp;
} @GetMapping("/emp")
public Employee updateEmp(Employee employee) {
Employee emp = employeeService.updateEmp(employee);
return emp;
} @GetMapping("/delete")
public String deleteEmp(Integer id) {
employeeService.deleteEmp(id);
System.out.println("success");
return "success to delete EMP with id =" + id.toString();
}
}
controller.EmployeeController
基本注解
我们需要了解的一些基本注解有:
@EnableCache:开启基于注解的缓存。通常我们放在application的主方法中
@Cacheable:针对方法请求参数对结果进行缓存
@CachePut:保证方法的调用/执行,以及更新缓存
@CacheEvict:清除缓存
难么如何来使用呢?首先,在pom.xml中添加如下:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-cache</artifactId>
</dependency>
这样,我们就关联了cache缓存。
然后,我们创建数据,在数据库里录入些东西,让我们之后可以读取和展示数据。那么关于增删改查的,关于mapper/bean等方法我就不在这里写了,想了解的可以翻看前边的文章~
下边是主程序的代码,我加了一些注释,告诉大家一些基本步骤
/**
* 一、搭建环境
* 1.导入数据库文件,创建出两个表
* 2.创建javaBean封装数据库
* 3.整合Mybatis数据源信息
* 1.配置数据库
* 2.使用注解版的MyBatis
* 1)、使用@Mapper扫描包
* 2)、创建Service和Controller
* 二、缓存
* 步骤:
* 1、开启基于注解的缓存
* 2、标注缓存注解即可
* @Cacheable
* @CacheEvict
* @CachePut
*/
@MapperScan("com.oooodin.cache.mapper")
@SpringBootApplication
@EnableCaching
public class CacheApplication { public static void main(String[] args) {
SpringApplication.run(CacheApplication.class, args);
}
}
看到了吧,上边有个橙色的注解,那个就是开启了缓存的注解功能,这样我们方法中写的缓存注解就可以被识别和使用了。例如:
这个方法的结果就会被写入到缓存中,我们可以启动主程序,然后在浏览器中多访问几次,看看打印了几次,如果只有1次,说明后边的请求都是从缓存中获得,而没有运行方法去查数据库,那么就成功了。
http://localhost:8080/emp/1 <====用这个来查询1号员工,并存入缓存
@Cacheable(cacheNames = "emp")
public Employee getEmp(Integer id) {
System.out.println("查询" + id + "号员工");
Employee emp = employeeMapper.getEmpById(id);
return emp;
}
继续来看:
这个就是将缓存数据更新的作用,同时方法也一定会运行。也就是像之前那样多次请求的话,每次都会访问数据库了。那么我们为什么要用这个?
这么说吧,当我们更新数据库的同时,同样更新缓存。然后我们再次请求一次。所以我们更新以后,再用上边的地址查询一下看看是不是有更新。
http://localhost:8080/emp?id=1&lastName=张三&gender=2 <===这个是用来更新数据到数据库的,同时也可以更新缓存。
@CachePut(cacheNames = "emp")
public Employee updateEmp(Employee employee) {
System.out.println("updateEmp:" + employee);
employeeMapper.updateEmp(employee);
return employee;
}
诶?是不是发现更新没问题,但是查询发现没变啊????
来看这个参数:key。因为我们在查询的那个方法中如果没有设定key,就会默认以参数当做key值在保存。然后我们在更新的时候要对应key才行。所以(取结果的id):
这回我们再刷新和查询的时候就会有变化了吧~
@CachePut(cacheNames = "emp", key = "#employee.id")
public Employee updateEmp(Employee employee) {
System.out.println("updateEmp:" + employee);
employeeMapper.updateEmp(employee);
return employee;
}
在开发过程中,我们不光是要更新,也要清除缓存,不然一直存着也会有问题的~:
这样,我们清除缓存名未emp中key是id的那条~,再次查询的时候,你会发现,我们又需要查询数据库重新保存缓存了。
http://localhost:8080/delete?id=1 <===删除id是1的那条缓存
@CacheEvict(cacheNames = "emp", key = "#id")
public void deleteEmp(Integer id) {
employeeMapper.deleteEmpById(id);
}
当然注解和参数,还有其他很多,我们可以去进入的jar包看一下具体的都有哪些,然后自己挨个尝试一下。比如Caching。这里我就不详细来说了(其实也没说多少东西……)
对了,这里给大家推荐一下可以学习的地方。可以搜一下 尚硅谷讲的SpringBoot的搞基片(高级篇),里边讲的真的很不错,很详细。
真正的教程不是视频或者书籍,而是官方API文档和源码。看懂这两个就能基本解决所有问题了,加油!
下一篇文章,说一下redis我们是如何整合的吧~
SpringBoot日记——缓存的使用的更多相关文章
- 带着新人学springboot的应用03(springboot+mybatis+缓存 下)
springboot+mybatis+缓存,基本的用法想必是会了,现在说一说内部大概的原理. 稍微提一下mybatis,只要导入了mybatis的依赖,那么有个自动配置类就会生效,你可以去mybati ...
- SpringBoot 与缓存
1. JSR107 Java Caching 定义了5个核心接口: CachingProvider:定义了创建,配置,获取,管理和控制多个CacheManager; CacheManager:定义了创 ...
- SpringBoot 整合缓存Cacheable实战详细使用
前言 我知道在接口api项目中,频繁的调用接口获取数据,查询数据库是非常耗费资源的,于是就有了缓存技术,可以把一些不常更新,或者经常使用的数据,缓存起来,然后下次再请求时候,就直接从缓存中获取,不需要 ...
- SpringBoot日记——Cache缓存篇
通常我们访问数据的情况如下图,数据存缓存就取缓存,不存缓存就取数据库,这样可以提升效率,不用一直读取数据库的信息: 开始记录: 关于SpringBoot缓存的应用 1. 首先在pom.xml文件中添加 ...
- springboot redis 缓存对象
只要加入spring-boot-starter-data-redis , springboot 会自动识别并使用redis作为缓存容器,使用方式如下 gradle加入依赖 compile(" ...
- springboot~hazelcast缓存中间件
缓存来了 在dotnet平台有自己的缓存框架,在java springboot里当然了集成了很多,而且缓存的中间件也可以进行多种选择,向redis, hazelcast都是分布式的缓存中间件,今天主要 ...
- 带着新人学springboot的应用02(springboot+mybatis+缓存 中)
继续接着上一节,大家应该知道驼峰命名法吧!就是我们javabean中属性一般命名是lastName,userName这种类型的,而数据库中列名一般都是last_name,user_name这种的,要让 ...
- 带着新人学springboot的应用01(springboot+mybatis+缓存 上)
上一篇结束,第一次做一个这么长的系列,很多东西我也是没有说到,也许是还没有想到,哈哈哈,不过基本的东西还是说的差不多了的.假如以后碰到了不会的,随便查查资料配置一下就ok. 咳,还有大家如果把我前面的 ...
- SpringBoot Redis缓存 @Cacheable、@CacheEvict、@CachePut
文章来源 https://blog.csdn.net/u010588262/article/details/81003493 1. pom.xml <dependency> <gro ...
随机推荐
- 解决windows下vim中文乱码
解决windows下vim中文乱码 windows安装了vim8,也就是gvim后,打开带有中文的文档,显示中文是乱码. 毕竟有许多文档我是用utf-8编码的,所以解决的办法是设置一下编码为utf-8 ...
- 脱壳_00_压缩壳_ASPACK
写在前面的话: Aspack是最常见的一种压缩壳,具有较好的兼容性.压缩率和稳定性,今天我们就来一起分析一下这个壳: 零.分析压缩壳: 0.在开始动态调试前,用PEID和LoadPE查看一些信息,做到 ...
- css常见效果
1.ul li横排 /* ul li以横排显示 */ /* 所有class为menu的div中的ul样式 */ div.menu ul { list-style:none; /* 去掉ul前面的符号 ...
- 1-100求和 sum(range(101))
print(sum(range(101))) s = 0for i in range(101): s += iprint(s)
- Spring线程池配置模板设计(基于Springboot)
目录 线程池配置模板 基础的注解解释 常用配置参数 配置类设计 线程池使用 ThreadPoolTaskExecutor源码 线程池配置模板 springboot给我们提供了一个线程池的实现,它的底层 ...
- 抽象类、final关键字、多态
1.1 抽象类 1.1.1 抽象类概念 C extends B,B extends A,在继承过程中,形成一个继承金字塔,位于金字塔底部的类越来越具体(强大),位于塔顶的越来越抽象(简单). 例如:人 ...
- Net dll组件版本兼容问题
dll组件版本兼容问题,是生产开发中经常遇到的问题,常见组件兼容问题如:Newtonsoft.Json,log4net等 为了节约大家时间,想直接看解决方法的,可直接点击目录3.4 目录 1.版本兼容 ...
- day1-课堂笔记
venv 执行方法: 1,pycharm执行 2,cmd命令窗口执行:python D:\PyCharmProjects\MyProject\day1.py 回车 java原理: HW.jav ...
- leetcode 460. LFU Cache
hash:存储的key.value.freq freq:存储的freq.key,也就是说出现1次的所有key在一起,用list连接 class LFUCache { public: LFUCache( ...
- 开源http协议库curl和wget的区别和使用
curl和wget基础功能有诸多重叠,如下载等. 在高级用途上的curl由于可自定义各种请求参数所以长于模拟web请求,用于测试网页交互(浏览器):wget由于支持ftp和Recursive所以长于下 ...