zoukankan      html  css  js  c++  java
  • 2020.03.17 springboot缓存相关

    出自尚硅谷雷峰阳老师讲解的Spring Boot整合篇,地址:

    http://www.atguigu.com/download_detail.shtml?v=38

    1、JSR107规范

    CachingProvider【管理CacheManager】、CacheManager【管理Cache】、Cache【一个cache仅被一个CacheManager管理】、Entry【一个个缓存的内容】、Expiry【有效期】
    2、Spring的缓存抽象
    注意两点:
    ①确定方法需要被缓存以及他们的缓存策略    
    ②从缓存中读取之前缓存存储的数据
    缓存注解及作用:
    @EnableCaching:开启基于注解的缓存
    @Cacheable:主要针对方法配置,能够根据方法的请求参数对其结果进行缓存【主要用于查询】
    @CachePut:保证方法被调用,又希望结果被缓存。【主要用于修改】
    @CacheEvict:清空缓存【主要用于删除】
    SPEL表达式:
    名字
    位置
    描述
    示例
    methodName 
    root object 当前被调用的方法名 #root.methodName
    result 
    evaluation context
    方法执行后的返回值(仅当方法执行之后的判断有效,如‘unless’,’cache put’的表达式 ’cache evict’的表达式beforeInvocation=false) 
    #result 
    argument name
    evaluation context 
    方法参数的名字. 可以直接 #参数名 ,也可以使用 #p0或#a0 的形式,0代表参数的索引; 
    #iban 、 #a0 、 #p0

    3、缓存使用

    pom文件:

    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
             xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
        <modelVersion>4.0.0</modelVersion>
        <parent>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-parent</artifactId>
            <version>1.5.12.RELEASE</version>
            <relativePath/> <!-- lookup parent from repository -->
        </parent>
        <groupId>com.study.springboot</groupId>
        <artifactId>cache-study</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <name>cache-study</name>
        <description>Demo project for Spring Boot</description>
    
        <properties>
            <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
            <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
            <java.version>1.8</java.version>
        </properties>
    
        <dependencies>
            <!-- 缓存相关 -->
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-cache</artifactId>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-web</artifactId>
            </dependency>
    
            <!-- 数据库相关 -->
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
                <scope>runtime</scope>
            </dependency>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-jdbc</artifactId>
            </dependency>
    
            <!-- mybatis和springboot整合 -->
            <dependency>
                <groupId>org.mybatis.spring.boot</groupId>
                <artifactId>mybatis-spring-boot-starter</artifactId>
                <version>1.3.0</version>
            </dependency>
    
            <!-- 数据库连接池 -->
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>druid-spring-boot-starter</artifactId>
                <version>1.1.16</version>
            </dependency>
    
            <!-- 日志 -->
            <dependency>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
                <optional>true</optional>
            </dependency>
    
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-test</artifactId>
                <scope>test</scope>
                <exclusions>
                    <exclusion>
                        <groupId>org.junit.vintage</groupId>
                        <artifactId>junit-vintage-engine</artifactId>
                    </exclusion>
                </exclusions>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-devtools</artifactId>
                <scope>runtime</scope>
                <optional>true</optional>
            </dependency>
    
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-redis</artifactId>
            </dependency>
    
        </dependencies>
    
        <build>
            <plugins>
                <plugin>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-maven-plugin</artifactId>
                </plugin>
            </plugins>
        </build>
    
    </project>

    主启动类:

    package com.study.springboot.cache;
    
    import org.springframework.boot.SpringApplication;
    import org.springframework.boot.autoconfigure.SpringBootApplication;
    import org.springframework.cache.annotation.EnableCaching;
    
    @SpringBootApplication
    @EnableCaching
    public class CacheStudyApplication {
    
    	public static void main(String[] args) {
    		SpringApplication.run(CacheStudyApplication.class, args);
    	}
    
    }

    yml文件:

    server:
      port: 8001
      tomcat:
        uri-encoding: UTF-8
    spring:
      application:
        name: springboot-cache
      datasource:
        type: com.alibaba.druid.pool.DruidDataSource
        driver-class-name: com.mysql.jdbc.Driver
        url: jdbc:mysql://localhost:3306/springboot-cache?useUnicode=true&characterEncoding-utf-8&useSSL=false&serverTimezone=UTC #需要加时区
        username: root
        password: 自己的密码
        initialSize: 5
        minIdle: 5
        maxActive: 20
        maxWait: 60000
        timeBetweenEvictionRunsMillis: 60000
        minEvictableIdleTimeMillis: 300000
        validationQuery: SELECT 1 FROM DUAL
        testWhileIdle: true
        testOnBorrow: false
        testOnReturn: false
        poolPreparedStatements: true
    #   配置监控统计拦截的filters,去掉后监控界面sql无法统计,'wall'用于防火墙
        filters: stat,wall,log4j
        maxPoolPreparedStatementPerConnectionSize: 20
        useGlobalDataSourceStat: true
        connectionProperties: druid.stat.mergeSql=true;druid.stat.slowSqlMillis=500
    
      http:
        encoding:
          charset: utf-8
          force: true
          enabled: true
      redis:
        host: 192.168.213.128#自己的redis主机
    mybatis:
      mapperLocations: classpath:mapper/*.xml
      type-aliases-package: com.atguigu.springcloud.entities
      configuration:
        map-underscore-to-camel-case: true
    

      

    controller:

    package com.study.springboot.cache.controller;
    
    import com.study.springboot.cache.entity.Employee;
    import com.study.springboot.cache.service.EmployeeService;
    import lombok.extern.slf4j.Slf4j;
    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
    @Slf4j
    public class EmpController {
    
        @Autowired
        private EmployeeService employeeService;
    
    
        @GetMapping("/emp/{id}")
        public Employee getEmpById(@PathVariable("id") Integer id){
            return employeeService.queryById(id);
        }
    }

    ------------------------------------------------------------------------------
     
    package com.study.springboot.cache.controller;


    import com.study.springboot.cache.entity.Department;
    import com.study.springboot.cache.service.DepartmentService;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.cache.annotation.CacheConfig;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.PathVariable;
    import org.springframework.web.bind.annotation.RestController;


    @RestController
    public class DepartmentController {

    @Autowired
    private DepartmentService departmentService;

    @GetMapping("/dept/{id}")
    public Department getDeptById(@PathVariable("id") Integer id){
    return departmentService.getDeptById(id);
    }
    }
     

    service

    package com.study.springboot.cache.service;
    
    import com.study.springboot.cache.entity.Employee;
    import com.study.springboot.cache.mapper.EmployeeMapper;
    import lombok.extern.slf4j.Slf4j;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.cache.annotation.Cacheable;
    import org.springframework.cache.annotation.Caching;
    import org.springframework.stereotype.Service;
    
    @Service
    @Slf4j
    public class EmployeeService {
    
        @Autowired
        private EmployeeMapper employeeMapper;
    
    
        @Caching(
                cacheable = @Cacheable(value="emp",cacheManager = "employmentRedisCacheManager")
        )
        public Employee queryById(Integer id){
            log.info("查询id为:"+id+"数据");
            return employeeMapper.selectEmp(id);
        }
    }

    ------------------------------------------------------------------------------
    package com.study.springboot.cache.mapper;


    import com.study.springboot.cache.entity.Department;
    import org.apache.ibatis.annotations.Mapper;
    import org.apache.ibatis.annotations.Param;

    @Mapper
    public interface DepartmentMapper {

    public Department selectDeptById(@Param("id") Integer id);
    }
     

    mapper:

    package com.study.springboot.cache.mapper;
    
    import com.study.springboot.cache.entity.Employee;
    import org.apache.ibatis.annotations.Mapper;
    import org.apache.ibatis.annotations.Param;
    
    @Mapper
    public interface EmployeeMapper {
    
        //根据id查询
        public Employee selectEmp(@Param("id") Integer id);
    
        //修改
        public void updateEmp(Employee employee);
    
    }

    ------------------------------------------------------------------------------

    package com.study.springboot.cache.mapper;


    import com.study.springboot.cache.entity.Department;
    import org.apache.ibatis.annotations.Mapper;
    import org.apache.ibatis.annotations.Param;

    @Mapper
    public interface DepartmentMapper {

    public Department selectDeptById(@Param("id") Integer id);
    }
     

    mapper.xml

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE mapper
            PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
            "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <mapper namespace="com.study.springboot.cache.mapper.EmployeeMapper">
    
    
    
        <!--public Employee selectEmp(@Param("id") Integer id);-->
        <select id="selectEmp" parameterType="Integer" resultMap="BaseResultMap">
            select * from employee where id = #{id}
        </select>
    
        <!-- public void updateEmp(Employee employee); -->
        <update id="updateEmp" parameterType="com.study.springboot.cache.entity.Employee">
            update employee set
            lastName = #{lastName},
            email = #{email},
            gender = #{gender},
            d_id = #{dId}
            where
            id = #{id}
        </update>
    
        <resultMap id="BaseResultMap" type="com.study.springboot.cache.entity.Employee" autoMapping="true">
    
        </resultMap>
        
    </mapper>

    ------------------------------------------------------------------------------

    <?xml version="1.0" encoding="UTF-8" ?>
    <!DOCTYPE mapper
    PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
    "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <mapper namespace="com.study.springboot.cache.mapper.DepartmentMapper">



    <!--public Department selectDeptById(@Param("id") Integer id);-->
    <select id="selectDeptById" parameterType="Integer" resultMap="BaseResultMap">
    select * from department where id = #{id}
    </select>

    <resultMap id="BaseResultMap" type="com.study.springboot.cache.entity.Department" autoMapping="true">

    </resultMap>

    </mapper>

    只有springboot版本为1.xx时才能自定义,版本为2.xx时没找到对应的构造函数 个人观点【没找到对应的构造函数】

    自定义缓存管理器时注意别写get

     1 import com.study.springboot.cache.entity.Department;
     2 import com.study.springboot.cache.entity.Employee;
     3 import org.springframework.context.annotation.Bean;
     4 import org.springframework.context.annotation.Configuration;
     5 import org.springframework.context.annotation.Primary;
     6 import org.springframework.data.redis.cache.RedisCacheManager;
     7 import org.springframework.data.redis.connection.RedisConnectionFactory;
     8 import org.springframework.data.redis.core.RedisTemplate;
     9 import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
    10 
    11 import java.net.UnknownHostException;
    12 
    13 
    14 @Configuration
    15 public class MyRedisConfig {
    16 
    17 
    18     @Bean
    19     public RedisTemplate<Object,Employee> getEmployeeRedisTemplate(RedisConnectionFactory redisConnectionFactory) throws UnknownHostException {
    20         RedisTemplate<Object,Employee> template = new RedisTemplate<Object,Employee>();
    21         template.setConnectionFactory(redisConnectionFactory);
    22         //自己配置序列化器
    23         Jackson2JsonRedisSerializer<Employee> serializer = new Jackson2JsonRedisSerializer<Employee>(Employee.class);
    24         template.setDefaultSerializer(serializer);
    25         return template;
    26     }
    27 
    28     @Bean
    29     public RedisTemplate<Object,Department> getDepartmentRedisTemplate(RedisConnectionFactory redisConnectionFactory) throws UnknownHostException {
    30         RedisTemplate<Object,Department> template = new RedisTemplate<Object,Department>();
    31         template.setConnectionFactory(redisConnectionFactory);
    32         //自己配置序列化器
    33         Jackson2JsonRedisSerializer<Department> serializer = new Jackson2JsonRedisSerializer<Department>(Department.class);
    34         template.setDefaultSerializer(serializer);
    35         return template;
    36     }
    37 
    38     @Bean
    39     public RedisCacheManager employmentRedisCacheManager(RedisTemplate<Object,Employee> employeeRedisTemplate){
    40         RedisCacheManager redisCacheManager = new RedisCacheManager(employeeRedisTemplate);
    41         redisCacheManager.setUsePrefix(true);
    42 
    43         return redisCacheManager;
    44     }
    45 
    46     @Primary
    47     @Bean
    48     public RedisCacheManager departmentRedisCacheManager(RedisTemplate<Object,Department> departmentRedisTemplate){
    49         RedisCacheManager redisCacheManager = new RedisCacheManager(departmentRedisTemplate);
    50         redisCacheManager.setUsePrefix(true);
    51 
    52         return redisCacheManager;
    53     }
    54 }

    测试类:

    redis命令网址:http://www.redis.cn/commands.html

    package com.study.springboot.cache;
    
    import com.study.springboot.cache.entity.Employee;
    import com.study.springboot.cache.service.EmployeeService;
    import org.junit.Test;
    import org.junit.runner.RunWith;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.boot.test.context.SpringBootTest;
    import org.springframework.data.redis.core.RedisTemplate;
    import org.springframework.data.redis.core.StringRedisTemplate;
    import org.springframework.data.redis.core.ValueOperations;
    import org.springframework.test.context.junit4.SpringRunner;
    
    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class CacheStudyApplicationTests {
    
        @Test
        public void contextLoads() {
        }
    
        @Autowired
        private StringRedisTemplate stringRedisTemplate;
    
        @Autowired
        private EmployeeService employeeService;
    
        @Autowired
        private RedisTemplate<Object,Employee> employeeRedisTemplate;
    
        @Test
        public void testRedis(){
            ValueOperations<String, String> stringValueOperations = stringRedisTemplate.opsForValue();
            //stringValueOperations.append("msg","hello");
    
            Employee employee = employeeService.queryById(2);
            //stringValueOperations.append("emp:1",employee.toString());
    
            employeeRedisTemplate.opsForValue().set("emp:1",employee);
    
        }
    
    }

    建表sql(老师提供的课件中有):

    /*
    Navicat MySQL Data Transfer
    
    Source Server         : 本地
    Source Server Version : 50528
    Source Host           : 127.0.0.1:3306
    Source Database       : springboot_cache
    
    Target Server Type    : MYSQL
    Target Server Version : 50528
    File Encoding         : 65001
    
    Date: 2018-04-27 14:54:04
    */
    
    SET FOREIGN_KEY_CHECKS=0;
    
    -- ----------------------------
    -- Table structure for department
    -- ----------------------------
    DROP TABLE IF EXISTS `department`;
    CREATE TABLE `department` (
      `id` int(11) NOT NULL AUTO_INCREMENT,
      `departmentName` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Table structure for employee
    -- ----------------------------
    DROP TABLE IF EXISTS `employee`;
    CREATE TABLE `employee` (
      `id` int(11) NOT NULL AUTO_INCREMENT,
      `lastName` varchar(255) DEFAULT NULL,
      `email` varchar(255) DEFAULT NULL,
      `gender` int(2) DEFAULT NULL,
      `d_id` int(11) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
     
  • 相关阅读:
    Study Plan The Twelfth Day
    Study Plan The Fifteenth Day
    Study Plan The Seventeenth Day
    Study Plan The Tenth Day
    Study Plan The Eighth Day
    Study Plan The Eleventh Day
    Study Plan The Sixteenth Day
    Study Plan The Thirteenth Day
    Study Plan The Fourteenth Day
    Study Plan The Ninth Day
  • 原文地址:https://www.cnblogs.com/lxw-all/p/12512149.html
Copyright © 2011-2022 走看看