SpringBoot緩存技術整合SpringData Redis


首先說明一下,這里使用的是Springboot2.2.6.RELEASE版本,由於Springboot迭代很快,所以要注意版本問題。

1、SpringData Redis是屬於SpringData下的一個模塊。作用就是簡化對於redis的操作。SpringData JPA為了簡化對數據庫的操作。修改pom文件添加SpringData Redis的坐標。

 1 <?xml version="1.0" encoding="UTF-8"?>
 2 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
 3          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
 4     <modelVersion>4.0.0</modelVersion>
 5     <parent>
 6         <groupId>org.springframework.boot</groupId>
 7         <artifactId>spring-boot-starter-parent</artifactId>
 8         <version>2.2.6.RELEASE</version>
 9         <relativePath/> <!-- lookup parent from repository -->
10     </parent>
11     <groupId>com.bie.springboot</groupId>
12     <artifactId>springdata-redis</artifactId>
13     <version>0.0.1-SNAPSHOT</version>
14     <name>springdata-redis</name>
15     <description>Demo project for Spring Boot</description>
16 
17     <properties>
18         <java.version>1.8</java.version>
19     </properties>
20 
21     <dependencies>
22         <!-- thymeleaf的啟動器 -->
23         <dependency>
24             <groupId>org.springframework.boot</groupId>
25             <artifactId>spring-boot-starter-thymeleaf</artifactId>
26         </dependency>
27         <!-- springBoot的啟動器 -->
28         <dependency>
29             <groupId>org.springframework.boot</groupId>
30             <artifactId>spring-boot-starter-web</artifactId>
31         </dependency>
32 
33         <!-- springBoot測試的啟動器 -->
34         <dependency>
35             <groupId>org.springframework.boot</groupId>
36             <artifactId>spring-boot-starter-test</artifactId>
37             <scope>test</scope>
38             <!--<exclusions>
39                 <exclusion>
40                     <groupId>org.junit.vintage</groupId>
41                     <artifactId>junit-vintage-engine</artifactId>
42                 </exclusion>
43             </exclusions>-->
44         </dependency>
45         <!-- SpringData Redis的啟動器 -->
46         <dependency>
47             <groupId>org.springframework.boot</groupId>
48             <artifactId>spring-boot-starter-data-redis</artifactId>
49         </dependency>
50         <!-- jedis是操作redis的工具依賴包 -->
51         <dependency>
52             <groupId>redis.clients</groupId>
53             <artifactId>jedis</artifactId>
54             <version>2.9.0</version>
55         </dependency>
56     </dependencies>
57 
58     <build>
59         <plugins>
60             <plugin>
61                 <groupId>org.springframework.boot</groupId>
62                 <artifactId>spring-boot-maven-plugin</artifactId>
63             </plugin>
64         </plugins>
65     </build>
66 
67 </project>

編寫SpringData Redis的配置類,替代了之前的配置文件。

  1 package com.bie.springboot.config;
  2 
  3 import org.springframework.context.annotation.Bean;
  4 import org.springframework.context.annotation.Configuration;
  5 import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
  6 import org.springframework.data.redis.connection.jedis.JedisClientConfiguration;
  7 import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
  8 import org.springframework.data.redis.core.RedisTemplate;
  9 import org.springframework.data.redis.serializer.StringRedisSerializer;
 10 import redis.clients.jedis.JedisPoolConfig;
 11 
 12 /**
 13  * 完成對Redis的整合的一些配置。
 14  * 1、JedisConnectionFacotory從SpringData Redis 2.0開始已經不推薦直接顯示設置連接的信息了,
 15  * 一方面為了使配置信息與建立連接工廠解耦,另一方面抽象出Standalone、Sentinel、RedisCluster
 16  * 三種模式的環境配置類和一個統一的jedis客戶端連接配置類(用於配置連接池和SSL連接),
 17  * 使得我們可以更加靈活方便根據實際業務場景需要來配置連接信息。
 18  */
 19 @Configuration
 20 public class RedisConfig {
 21 
 22     /**
 23      * 1.創建JedisPoolConfig對象。在該對象中完成一些鏈接池配置,連接池配置信息。
 24      *
 25      * @return
 26      */
 27     @Bean
 28     public JedisPoolConfig jedisPoolConfig() {
 29         // 創建JedisPoolConfig對象
 30         JedisPoolConfig config = new JedisPoolConfig();
 31         // 最大空閑數
 32         config.setMaxIdle(10);
 33         // 最小空閑數
 34         config.setMinIdle(5);
 35         // 最大鏈接數
 36         config.setMaxTotal(20);
 37         //當池內沒有可用的連接時,最大等待時間
 38         config.setMaxWaitMillis(10000);
 39         return config;
 40     }
 41 
 42     /**
 43      * 2.創建JedisConnectionFactory,配置redis鏈接信息。
 44      *
 45      * @param config 從IOC容器中將連接池拿去出來
 46      * @return
 47      */
 48     @Bean
 49     public JedisConnectionFactory jedisConnectionFactory(JedisPoolConfig config) {
 50         // 關聯鏈接池的配置對象,不推薦使用了
 51         // factory.setPoolConfig(config);
 52         // 配置鏈接Redis的信息
 53         // 主機地址,不推薦使用了
 54         // factory.setHostName("192.168.70.128");
 55         // 端口,不推薦使用了
 56         // factory.setPort(6379);
 57 
 58         // 創建RedisStandaloneConfiguration對象
 59         RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration();
 60         // 然后根據該配置實例來初始化jedis連接工廠。
 61         // 設置ip主機地址
 62         redisStandaloneConfiguration.setHostName("192.168.110.140");
 63         // 設置在第幾號redis數據庫操作,默認操作第0個數據庫
 64         redisStandaloneConfiguration.setDatabase(0);
 65         // 設置redis的密碼
 66         // redisStandaloneConfiguration.setPassword(RedisPassword.of("123456"));
 67         // 設置端口號
 68         redisStandaloneConfiguration.setPort(6379);
 69 
 70 
 71         // 獲得默認的連接池構造器
 72         JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = JedisClientConfiguration.builder().usePooling();
 73 
 74         // 指定jedisPoolConifig來修改默認的連接池構造器
 75         jpcb.poolConfig(config);
 76         // 通過構造器來構造jedis客戶端配置
 77         JedisClientConfiguration jedisClientConfiguration = jpcb.build();
 78 
 79         // 將設置好的數據庫鏈接傳遞到JedisConnectionFactory構造方法里面
 80         // JedisConnectionFactory factory = new JedisConnectionFactory(redisStandaloneConfiguration);
 81 
 82         // 返回,注入到ioc容器中
 83         // 單機配置 + 客戶端配置 = jedis連接工廠
 84         return new JedisConnectionFactory(redisStandaloneConfiguration, jedisClientConfiguration);
 85     }
 86 
 87 
 88     /**
 89      * 3.創建RedisTemplate模板對象,用於執行Redis操作的方法。
 90      *
 91      * @param jedisConnectionFactory
 92      *
 93      * @return
 94      */
 95     @Bean
 96     public RedisTemplate<String, Object> redisTemplate(JedisConnectionFactory jedisConnectionFactory) {
 97         // 創建RedisTemplate對象
 98         RedisTemplate<String, Object> template = new RedisTemplate<>();
 99         // 關聯,鏈接連接池工廠,RedisTemplate與JedisConnectionFactory關聯
100         template.setConnectionFactory(jedisConnectionFactory);
101         // 為key設置序列化器
102         template.setKeySerializer(new StringRedisSerializer());
103         // 為value設置序列化器
104         template.setValueSerializer(new StringRedisSerializer());
105         return template;
106     }
107 
108 
109     /**
110      * jedis連接工廠
111      *
112      * @param jedisPoolConfig
113      * @return
114      */
115 //    @Bean
116 //    public RedisConnectionFactory redisConnectionFactory(JedisPoolConfig jedisPoolConfig) {
117 //        // 單機版jedis
118 //        RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration();
119 //        // 設置redis服務器的host或者ip地址
120 //        redisStandaloneConfiguration.setHostName("192.168.110.140");
121 //        // 設置默認使用的數據庫
122 //        redisStandaloneConfiguration.setDatabase(0);
123 //        // 設置密碼
124 //        // redisStandaloneConfiguration.setPassword(RedisPassword.of("123456"));
125 //        // 設置redis的服務的端口號
126 //        redisStandaloneConfiguration.setPort(6379);
127 //        // 獲得默認的連接池構造器
128 //        // JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = (JedisClientConfiguration.JedisPoolingClientConfigurationBuilder) JedisClientConfiguration.builder();
129 //
130 //        // 獲得默認的連接池構造器
131 //        JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = JedisClientConfiguration.builder().usePooling();
132 //
133 //        // 指定jedisPoolConifig來修改默認的連接池構造器
134 //        jpcb.poolConfig(jedisPoolConfig);
135 //        // 通過構造器來構造jedis客戶端配置
136 //        JedisClientConfiguration jedisClientConfiguration = jpcb.build();
137 //        // 單機配置 + 客戶端配置 = jedis連接工廠
138 //        return new JedisConnectionFactory(redisStandaloneConfiguration, jedisClientConfiguration);
139 //    }
140 
141 
142 }

編寫測試代碼,測試整合環境。

 1 package com.bie.springboot;
 2 
 3 import org.junit.jupiter.api.Test;
 4 import org.junit.runner.RunWith;
 5 import org.springframework.beans.factory.annotation.Autowired;
 6 import org.springframework.boot.test.context.SpringBootTest;
 7 import org.springframework.data.redis.core.RedisTemplate;
 8 import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
 9 
10 @RunWith(SpringJUnit4ClassRunner.class)
11 @SpringBootTest(classes = SpringdataRedisApplication.class)
12 class SpringdataRedisApplicationTests {
13 
14     @Autowired
15     private RedisTemplate<String, Object> redisTemplate;
16 
17     /*** 添加一個字符串 */
18     @Test
19     public void testSet() {
20         this.redisTemplate.opsForValue().set("key", "我想要學好springboot");
21     }
22 
23     /*** 獲取一個字符串 */
24     @Test
25     public void testGet() {
26         String value = (String) this.redisTemplate.opsForValue().get("key");
27         System.out.println(value);
28     }
29 
30 }

如果報了下面所示的錯誤,如下所示:

  1   .   ____          _            __ _ _
  2  /\\ / ___'_ __ _ _(_)_ __  __ _ \ \ \ \
  3 ( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
  4  \\/  ___)| |_)| | | | | || (_| |  ) ) ) )
  5   '  |____| .__|_| |_|_| |_\__, | / / / /
  6  =========|_|==============|___/=/_/_/_/
  7  :: Spring Boot ::        (v2.2.6.RELEASE)
  8 
  9 2020-05-16 23:19:54.910  INFO 5476 --- [           main] c.b.s.SpringdataRedisApplicationTests    : Starting SpringdataRedisApplicationTests on DESKTOP-V37QSSE with PID 5476 (started by biehl in D:\program\idea\IntelliJ IDEA 2019.1.3\workspace_idea\springdata-redis)
 10 2020-05-16 23:19:54.914  INFO 5476 --- [           main] c.b.s.SpringdataRedisApplicationTests    : No active profile set, falling back to default profiles: default
 11 2020-05-16 23:19:56.826  INFO 5476 --- [           main] .s.d.r.c.RepositoryConfigurationDelegate : Multiple Spring Data modules found, entering strict repository configuration mode!
 12 2020-05-16 23:19:56.830  INFO 5476 --- [           main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data Redis repositories in DEFAULT mode.
 13 2020-05-16 23:19:56.887  INFO 5476 --- [           main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 29ms. Found 0 Redis repository interfaces.
 14 2020-05-16 23:19:57.186 ERROR 5476 --- [           main] o.s.boot.SpringApplication               : Application run failed
 15 
 16 java.lang.NoClassDefFoundError: redis/clients/jedis/util/Pool
 17     at java.lang.Class.getDeclaredConstructors0(Native Method) ~[na:1.8.0_191]
 18     at java.lang.Class.privateGetDeclaredConstructors(Class.java:2671) ~[na:1.8.0_191]
 19     at java.lang.Class.getDeclaredConstructors(Class.java:2020) ~[na:1.8.0_191]
 20     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.findConstructorBindingAnnotatedConstructor(ConfigurationPropertiesBindConstructorProvider.java:62) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 21     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.getBindConstructor(ConfigurationPropertiesBindConstructorProvider.java:48) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 22     at org.springframework.boot.context.properties.ConfigurationPropertiesBean$BindMethod.forType(ConfigurationPropertiesBean.java:311) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 23     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.validate(ConfigurationPropertiesBeanDefinitionValidator.java:63) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 24     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.postProcessBeanFactory(ConfigurationPropertiesBeanDefinitionValidator.java:45) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 25     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:286) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 26     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:174) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 27     at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:706) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 28     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:532) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 29     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:747) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 30     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:397) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 31     at org.springframework.boot.SpringApplication.run(SpringApplication.java:315) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 32     at org.springframework.boot.test.context.SpringBootContextLoader.loadContext(SpringBootContextLoader.java:126) [spring-boot-test-2.2.6.RELEASE.jar:2.2.6.RELEASE]
 33     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContextInternal(DefaultCacheAwareContextLoaderDelegate.java:99) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 34     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContext(DefaultCacheAwareContextLoaderDelegate.java:124) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 35     at org.springframework.test.context.support.DefaultTestContext.getApplicationContext(DefaultTestContext.java:123) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 36     at org.springframework.test.context.web.ServletTestExecutionListener.setUpRequestContextIfNecessary(ServletTestExecutionListener.java:190) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 37     at org.springframework.test.context.web.ServletTestExecutionListener.prepareTestInstance(ServletTestExecutionListener.java:132) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 38     at org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:244) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 39     at org.springframework.test.context.junit.jupiter.SpringExtension.postProcessTestInstance(SpringExtension.java:98) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
 40     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$5(ClassBasedTestDescriptor.java:337) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 41     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.executeAndMaskThrowable(ClassBasedTestDescriptor.java:342) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 42     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$6(ClassBasedTestDescriptor.java:337) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 43     at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193) ~[na:1.8.0_191]
 44     at java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:175) ~[na:1.8.0_191]
 45     at java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1382) ~[na:1.8.0_191]
 46     at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481) ~[na:1.8.0_191]
 47     at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471) ~[na:1.8.0_191]
 48     at java.util.stream.StreamSpliterators$WrappingSpliterator.forEachRemaining(StreamSpliterators.java:312) ~[na:1.8.0_191]
 49     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:743) ~[na:1.8.0_191]
 50     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:742) ~[na:1.8.0_191]
 51     at java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:580) ~[na:1.8.0_191]
 52     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.invokeTestInstancePostProcessors(ClassBasedTestDescriptor.java:336) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 53     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.instantiateAndPostProcessTestInstance(ClassBasedTestDescriptor.java:259) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 54     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$2(ClassBasedTestDescriptor.java:252) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 55     at java.util.Optional.orElseGet(Optional.java:267) ~[na:1.8.0_191]
 56     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$3(ClassBasedTestDescriptor.java:251) [junit-jupiter-engine-5.5.2.jar:5.5.2]
 57     at org.junit.jupiter.engine.execution.TestInstancesProvider.getTestInstances(TestInstancesProvider.java:29) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
 58     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$prepare$0(TestMethodTestDescriptor.java:106) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
 59     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 60     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:105) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
 61     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:69) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
 62     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$prepare$1(NodeTestTask.java:107) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 63     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 64     at org.junit.platform.engine.support.hierarchical.NodeTestTask.prepare(NodeTestTask.java:107) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 65     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:75) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 66     at java.util.ArrayList.forEach(ArrayList.java:1257) ~[na:1.8.0_191]
 67     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 68     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 69     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 70     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 71     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 72     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 73     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 74     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 75     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 76     at java.util.ArrayList.forEach(ArrayList.java:1257) ~[na:1.8.0_191]
 77     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 78     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 79     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 80     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 81     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 82     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 83     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 84     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 85     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 86     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.submit(SameThreadHierarchicalTestExecutorService.java:32) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 87     at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:57) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 88     at org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:51) ~[junit-platform-engine-1.5.2.jar:1.5.2]
 89     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:229) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
 90     at org.junit.platform.launcher.core.DefaultLauncher.lambda$execute$6(DefaultLauncher.java:197) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
 91     at org.junit.platform.launcher.core.DefaultLauncher.withInterceptedStreams(DefaultLauncher.java:211) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
 92     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:191) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
 93     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:128) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
 94     at com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:69) ~[junit5-rt.jar:na]
 95     at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47) ~[junit-rt.jar:na]
 96     at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242) ~[junit-rt.jar:na]
 97     at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70) ~[junit-rt.jar:na]
 98 Caused by: java.lang.ClassNotFoundException: redis.clients.jedis.util.Pool
 99     at java.net.URLClassLoader.findClass(URLClassLoader.java:382) ~[na:1.8.0_191]
100     at java.lang.ClassLoader.loadClass(ClassLoader.java:424) ~[na:1.8.0_191]
101     at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349) ~[na:1.8.0_191]
102     at java.lang.ClassLoader.loadClass(ClassLoader.java:357) ~[na:1.8.0_191]
103     ... 81 common frames omitted
104 
105 2020-05-16 23:19:57.189 ERROR 5476 --- [           main] o.s.test.context.TestContextManager      : Caught exception while allowing TestExecutionListener [org.springframework.test.context.web.ServletTestExecutionListener@4738a206] to prepare test instance [com.bie.springboot.SpringdataRedisApplicationTests@4e2c95ee]
106 
107 java.lang.NoClassDefFoundError: redis/clients/jedis/util/Pool
108     at java.lang.Class.getDeclaredConstructors0(Native Method) ~[na:1.8.0_191]
109     at java.lang.Class.privateGetDeclaredConstructors(Class.java:2671) ~[na:1.8.0_191]
110     at java.lang.Class.getDeclaredConstructors(Class.java:2020) ~[na:1.8.0_191]
111     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.findConstructorBindingAnnotatedConstructor(ConfigurationPropertiesBindConstructorProvider.java:62) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
112     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.getBindConstructor(ConfigurationPropertiesBindConstructorProvider.java:48) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
113     at org.springframework.boot.context.properties.ConfigurationPropertiesBean$BindMethod.forType(ConfigurationPropertiesBean.java:311) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
114     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.validate(ConfigurationPropertiesBeanDefinitionValidator.java:63) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
115     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.postProcessBeanFactory(ConfigurationPropertiesBeanDefinitionValidator.java:45) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
116     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:286) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
117     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:174) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
118     at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:706) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
119     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:532) ~[spring-context-5.2.5.RELEASE.jar:5.2.5.RELEASE]
120     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:747) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
121     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:397) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
122     at org.springframework.boot.SpringApplication.run(SpringApplication.java:315) ~[spring-boot-2.2.6.RELEASE.jar:2.2.6.RELEASE]
123     at org.springframework.boot.test.context.SpringBootContextLoader.loadContext(SpringBootContextLoader.java:126) ~[spring-boot-test-2.2.6.RELEASE.jar:2.2.6.RELEASE]
124     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContextInternal(DefaultCacheAwareContextLoaderDelegate.java:99) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
125     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContext(DefaultCacheAwareContextLoaderDelegate.java:124) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
126     at org.springframework.test.context.support.DefaultTestContext.getApplicationContext(DefaultTestContext.java:123) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
127     at org.springframework.test.context.web.ServletTestExecutionListener.setUpRequestContextIfNecessary(ServletTestExecutionListener.java:190) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
128     at org.springframework.test.context.web.ServletTestExecutionListener.prepareTestInstance(ServletTestExecutionListener.java:132) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
129     at org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:244) ~[spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
130     at org.springframework.test.context.junit.jupiter.SpringExtension.postProcessTestInstance(SpringExtension.java:98) [spring-test-5.2.5.RELEASE.jar:5.2.5.RELEASE]
131     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$5(ClassBasedTestDescriptor.java:337) [junit-jupiter-engine-5.5.2.jar:5.5.2]
132     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.executeAndMaskThrowable(ClassBasedTestDescriptor.java:342) [junit-jupiter-engine-5.5.2.jar:5.5.2]
133     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$6(ClassBasedTestDescriptor.java:337) [junit-jupiter-engine-5.5.2.jar:5.5.2]
134     at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193) ~[na:1.8.0_191]
135     at java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:175) ~[na:1.8.0_191]
136     at java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1382) ~[na:1.8.0_191]
137     at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481) ~[na:1.8.0_191]
138     at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471) ~[na:1.8.0_191]
139     at java.util.stream.StreamSpliterators$WrappingSpliterator.forEachRemaining(StreamSpliterators.java:312) ~[na:1.8.0_191]
140     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:743) ~[na:1.8.0_191]
141     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:742) ~[na:1.8.0_191]
142     at java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:580) ~[na:1.8.0_191]
143     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.invokeTestInstancePostProcessors(ClassBasedTestDescriptor.java:336) [junit-jupiter-engine-5.5.2.jar:5.5.2]
144     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.instantiateAndPostProcessTestInstance(ClassBasedTestDescriptor.java:259) [junit-jupiter-engine-5.5.2.jar:5.5.2]
145     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$2(ClassBasedTestDescriptor.java:252) [junit-jupiter-engine-5.5.2.jar:5.5.2]
146     at java.util.Optional.orElseGet(Optional.java:267) ~[na:1.8.0_191]
147     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$3(ClassBasedTestDescriptor.java:251) [junit-jupiter-engine-5.5.2.jar:5.5.2]
148     at org.junit.jupiter.engine.execution.TestInstancesProvider.getTestInstances(TestInstancesProvider.java:29) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
149     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$prepare$0(TestMethodTestDescriptor.java:106) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
150     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
151     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:105) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
152     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:69) ~[junit-jupiter-engine-5.5.2.jar:5.5.2]
153     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$prepare$1(NodeTestTask.java:107) ~[junit-platform-engine-1.5.2.jar:1.5.2]
154     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
155     at org.junit.platform.engine.support.hierarchical.NodeTestTask.prepare(NodeTestTask.java:107) ~[junit-platform-engine-1.5.2.jar:1.5.2]
156     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:75) ~[junit-platform-engine-1.5.2.jar:1.5.2]
157     at java.util.ArrayList.forEach(ArrayList.java:1257) ~[na:1.8.0_191]
158     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38) ~[junit-platform-engine-1.5.2.jar:1.5.2]
159     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139) ~[junit-platform-engine-1.5.2.jar:1.5.2]
160     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
161     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125) ~[junit-platform-engine-1.5.2.jar:1.5.2]
162     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135) ~[junit-platform-engine-1.5.2.jar:1.5.2]
163     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123) ~[junit-platform-engine-1.5.2.jar:1.5.2]
164     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
165     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122) ~[junit-platform-engine-1.5.2.jar:1.5.2]
166     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80) ~[junit-platform-engine-1.5.2.jar:1.5.2]
167     at java.util.ArrayList.forEach(ArrayList.java:1257) ~[na:1.8.0_191]
168     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38) ~[junit-platform-engine-1.5.2.jar:1.5.2]
169     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139) ~[junit-platform-engine-1.5.2.jar:1.5.2]
170     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
171     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125) ~[junit-platform-engine-1.5.2.jar:1.5.2]
172     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135) ~[junit-platform-engine-1.5.2.jar:1.5.2]
173     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123) ~[junit-platform-engine-1.5.2.jar:1.5.2]
174     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73) ~[junit-platform-engine-1.5.2.jar:1.5.2]
175     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122) ~[junit-platform-engine-1.5.2.jar:1.5.2]
176     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80) ~[junit-platform-engine-1.5.2.jar:1.5.2]
177     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.submit(SameThreadHierarchicalTestExecutorService.java:32) ~[junit-platform-engine-1.5.2.jar:1.5.2]
178     at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:57) ~[junit-platform-engine-1.5.2.jar:1.5.2]
179     at org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:51) ~[junit-platform-engine-1.5.2.jar:1.5.2]
180     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:229) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
181     at org.junit.platform.launcher.core.DefaultLauncher.lambda$execute$6(DefaultLauncher.java:197) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
182     at org.junit.platform.launcher.core.DefaultLauncher.withInterceptedStreams(DefaultLauncher.java:211) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
183     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:191) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
184     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:128) ~[junit-platform-launcher-1.5.2.jar:1.5.2]
185     at com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:69) ~[junit5-rt.jar:na]
186     at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47) ~[junit-rt.jar:na]
187     at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242) ~[junit-rt.jar:na]
188     at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70) ~[junit-rt.jar:na]
189 Caused by: java.lang.ClassNotFoundException: redis.clients.jedis.util.Pool
190     at java.net.URLClassLoader.findClass(URLClassLoader.java:382) ~[na:1.8.0_191]
191     at java.lang.ClassLoader.loadClass(ClassLoader.java:424) ~[na:1.8.0_191]
192     at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349) ~[na:1.8.0_191]
193     at java.lang.ClassLoader.loadClass(ClassLoader.java:357) ~[na:1.8.0_191]
194     ... 81 common frames omitted
195 
196 
197 java.lang.NoClassDefFoundError: redis/clients/jedis/util/Pool
198 
199     at java.lang.Class.getDeclaredConstructors0(Native Method)
200     at java.lang.Class.privateGetDeclaredConstructors(Class.java:2671)
201     at java.lang.Class.getDeclaredConstructors(Class.java:2020)
202     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.findConstructorBindingAnnotatedConstructor(ConfigurationPropertiesBindConstructorProvider.java:62)
203     at org.springframework.boot.context.properties.ConfigurationPropertiesBindConstructorProvider.getBindConstructor(ConfigurationPropertiesBindConstructorProvider.java:48)
204     at org.springframework.boot.context.properties.ConfigurationPropertiesBean$BindMethod.forType(ConfigurationPropertiesBean.java:311)
205     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.validate(ConfigurationPropertiesBeanDefinitionValidator.java:63)
206     at org.springframework.boot.context.properties.ConfigurationPropertiesBeanDefinitionValidator.postProcessBeanFactory(ConfigurationPropertiesBeanDefinitionValidator.java:45)
207     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:286)
208     at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:174)
209     at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:706)
210     at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:532)
211     at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:747)
212     at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:397)
213     at org.springframework.boot.SpringApplication.run(SpringApplication.java:315)
214     at org.springframework.boot.test.context.SpringBootContextLoader.loadContext(SpringBootContextLoader.java:126)
215     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContextInternal(DefaultCacheAwareContextLoaderDelegate.java:99)
216     at org.springframework.test.context.cache.DefaultCacheAwareContextLoaderDelegate.loadContext(DefaultCacheAwareContextLoaderDelegate.java:124)
217     at org.springframework.test.context.support.DefaultTestContext.getApplicationContext(DefaultTestContext.java:123)
218     at org.springframework.test.context.web.ServletTestExecutionListener.setUpRequestContextIfNecessary(ServletTestExecutionListener.java:190)
219     at org.springframework.test.context.web.ServletTestExecutionListener.prepareTestInstance(ServletTestExecutionListener.java:132)
220     at org.springframework.test.context.TestContextManager.prepareTestInstance(TestContextManager.java:244)
221     at org.springframework.test.context.junit.jupiter.SpringExtension.postProcessTestInstance(SpringExtension.java:98)
222     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$5(ClassBasedTestDescriptor.java:337)
223     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.executeAndMaskThrowable(ClassBasedTestDescriptor.java:342)
224     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$invokeTestInstancePostProcessors$6(ClassBasedTestDescriptor.java:337)
225     at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193)
226     at java.util.stream.ReferencePipeline$2$1.accept(ReferencePipeline.java:175)
227     at java.util.ArrayList$ArrayListSpliterator.forEachRemaining(ArrayList.java:1382)
228     at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:481)
229     at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:471)
230     at java.util.stream.StreamSpliterators$WrappingSpliterator.forEachRemaining(StreamSpliterators.java:312)
231     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:743)
232     at java.util.stream.Streams$ConcatSpliterator.forEachRemaining(Streams.java:742)
233     at java.util.stream.ReferencePipeline$Head.forEach(ReferencePipeline.java:580)
234     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.invokeTestInstancePostProcessors(ClassBasedTestDescriptor.java:336)
235     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.instantiateAndPostProcessTestInstance(ClassBasedTestDescriptor.java:259)
236     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$2(ClassBasedTestDescriptor.java:252)
237     at java.util.Optional.orElseGet(Optional.java:267)
238     at org.junit.jupiter.engine.descriptor.ClassBasedTestDescriptor.lambda$testInstancesProvider$3(ClassBasedTestDescriptor.java:251)
239     at org.junit.jupiter.engine.execution.TestInstancesProvider.getTestInstances(TestInstancesProvider.java:29)
240     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.lambda$prepare$0(TestMethodTestDescriptor.java:106)
241     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
242     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:105)
243     at org.junit.jupiter.engine.descriptor.TestMethodTestDescriptor.prepare(TestMethodTestDescriptor.java:69)
244     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$prepare$1(NodeTestTask.java:107)
245     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
246     at org.junit.platform.engine.support.hierarchical.NodeTestTask.prepare(NodeTestTask.java:107)
247     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:75)
248     at java.util.ArrayList.forEach(ArrayList.java:1257)
249     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38)
250     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139)
251     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
252     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125)
253     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135)
254     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123)
255     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
256     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122)
257     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80)
258     at java.util.ArrayList.forEach(ArrayList.java:1257)
259     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.invokeAll(SameThreadHierarchicalTestExecutorService.java:38)
260     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$5(NodeTestTask.java:139)
261     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
262     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$7(NodeTestTask.java:125)
263     at org.junit.platform.engine.support.hierarchical.Node.around(Node.java:135)
264     at org.junit.platform.engine.support.hierarchical.NodeTestTask.lambda$executeRecursively$8(NodeTestTask.java:123)
265     at org.junit.platform.engine.support.hierarchical.ThrowableCollector.execute(ThrowableCollector.java:73)
266     at org.junit.platform.engine.support.hierarchical.NodeTestTask.executeRecursively(NodeTestTask.java:122)
267     at org.junit.platform.engine.support.hierarchical.NodeTestTask.execute(NodeTestTask.java:80)
268     at org.junit.platform.engine.support.hierarchical.SameThreadHierarchicalTestExecutorService.submit(SameThreadHierarchicalTestExecutorService.java:32)
269     at org.junit.platform.engine.support.hierarchical.HierarchicalTestExecutor.execute(HierarchicalTestExecutor.java:57)
270     at org.junit.platform.engine.support.hierarchical.HierarchicalTestEngine.execute(HierarchicalTestEngine.java:51)
271     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:229)
272     at org.junit.platform.launcher.core.DefaultLauncher.lambda$execute$6(DefaultLauncher.java:197)
273     at org.junit.platform.launcher.core.DefaultLauncher.withInterceptedStreams(DefaultLauncher.java:211)
274     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:191)
275     at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:128)
276     at com.intellij.junit5.JUnit5IdeaTestRunner.startRunnerWithArgs(JUnit5IdeaTestRunner.java:69)
277     at com.intellij.rt.execution.junit.IdeaTestRunner$Repeater.startRunnerWithArgs(IdeaTestRunner.java:47)
278     at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:242)
279     at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:70)
280 Caused by: java.lang.ClassNotFoundException: redis.clients.jedis.util.Pool
281     at java.net.URLClassLoader.findClass(URLClassLoader.java:382)
282     at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
283     at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:349)
284     at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
285     ... 81 more
286 
287 
288 Process finished with exit code -1

是Jedis版本問題:將Jedis改為 3.0.0版本或者2.10.1版本后即可解決。我是將Jedis2.9.0版本改為了Jedis3.0.0版本解決了問題。

1 <!-- jedis是操作redis的工具依賴包 -->
2 <dependency>
3     <groupId>redis.clients</groupId>
4     <artifactId>jedis</artifactId>
5     <version>3.0.0</version>
6 </dependency>

提取redis的配置信息,在application.properties配置文件中新增配置信息。 

 1 # 最大空閑數,最后綴必須固定
 2 spring.redis.jedis.pool.max-idle=10
 3 # 最小空閑數,連接池中最小空閑連接
 4 spring.redis.jedis.pool.min-idle=10
 5 # 最大鏈接數,連接池最大連接數(使用負值表示沒有限制)
 6 spring.redis.jedis.pool.max-active=8
 7 # 當池內沒有可用的連接時,最大等待時間
 8 spring.redis.jedis.pool.max-wait=-1ms
 9 
10 
11 
12 # 設置redis的主機
13 spring.redis.hostName=192.168.110.140
14 # 設置redis的端口號
15 spring.redis.port=6379
16 # 設置操作第一個數據庫
17 spring.redis.database=0

修改配置類,配置屬性在application.properties進行設置。

  1 package com.bie.springboot.config;
  2 
  3 import org.springframework.boot.context.properties.ConfigurationProperties;
  4 import org.springframework.context.annotation.Bean;
  5 import org.springframework.context.annotation.Configuration;
  6 import org.springframework.data.redis.connection.RedisStandaloneConfiguration;
  7 import org.springframework.data.redis.connection.jedis.JedisClientConfiguration;
  8 import org.springframework.data.redis.connection.jedis.JedisConnectionFactory;
  9 import org.springframework.data.redis.core.RedisTemplate;
 10 import org.springframework.data.redis.serializer.StringRedisSerializer;
 11 import redis.clients.jedis.JedisPoolConfig;
 12 
 13 /**
 14  * 完成對Redis的整合的一些配置。
 15  * 1、JedisConnectionFacotory從SpringData Redis 2.0開始已經不推薦直接顯示設置連接的信息了,
 16  * 一方面為了使配置信息與建立連接工廠解耦,另一方面抽象出Standalone、Sentinel、RedisCluster
 17  * 三種模式的環境配置類和一個統一的jedis客戶端連接配置類(用於配置連接池和SSL連接),
 18  * 使得我們可以更加靈活方便根據實際業務場景需要來配置連接信息。
 19  */
 20 @Configuration
 21 public class RedisConfig {
 22 
 23     /**
 24      * 1.創建JedisPoolConfig對象。在該對象中完成一些鏈接池配置,連接池配置信息。
 25      *
 26      * @return
 27      * @ConfigurationProperties:會將前綴相同的內容創建一個實體。
 28      */
 29     @Bean
 30     @ConfigurationProperties(prefix = "spring.redis.jedis.pool")
 31     public JedisPoolConfig jedisPoolConfig() {
 32         // 創建JedisPoolConfig對象
 33         JedisPoolConfig config = new JedisPoolConfig();
 34         // 最大空閑數
 35         // config.setMaxIdle(10);
 36         // 最小空閑數
 37         // config.setMinIdle(5);
 38         // 最大鏈接數
 39         // config.setMaxTotal(20);
 40         // 當池內沒有可用的連接時,最大等待時間
 41         // config.setMaxWaitMillis(10000);
 42 
 43         System.out.println("最大空閑數,redis默認值:" + config.getMaxIdle());
 44         System.out.println("最小空閑數,redis默認值:" + config.getMinIdle());
 45         System.out.println("最大鏈接數,redis默認值:" + config.getMaxTotal());
 46         System.out.println("當池內沒有可用的連接時,最大等待時間,redis默認值:" + config.getMaxWaitMillis());
 47         System.out.println();
 48         return config;
 49     }
 50 
 51     /**
 52      * 2.創建JedisConnectionFactory,配置redis鏈接信息。
 53      *
 54      * @param config 從IOC容器中將連接池拿去出來
 55      * @return
 56      */
 57     @Bean
 58     @ConfigurationProperties(prefix = "spring.redis")
 59     public JedisConnectionFactory jedisConnectionFactory(JedisPoolConfig config) {
 60         // 關聯鏈接池的配置對象,不推薦使用了
 61         // factory.setPoolConfig(config);
 62         // 配置鏈接Redis的信息
 63         // 主機地址,不推薦使用了
 64         // factory.setHostName("192.168.70.128");
 65         // 端口,不推薦使用了
 66         // factory.setPort(6379);
 67         System.out.println("最大空閑數,redis配置完畢:" + config.getMaxIdle());
 68         System.out.println("最小空閑數,redis配置完畢:" + config.getMinIdle());
 69         System.out.println("最大鏈接數,redis配置完畢:" + config.getMaxTotal());
 70         System.out.println("當池內沒有可用的連接時,最大等待時間,redis配置完畢:" + config.getMaxWaitMillis());
 71         System.out.println();
 72 
 73         // 創建RedisStandaloneConfiguration對象
 74         RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration();
 75         // 然后根據該配置實例來初始化jedis連接工廠。
 76         // 設置ip主機地址
 77         // redisStandaloneConfiguration.setHostName("192.168.110.140");
 78         // 設置在第幾號redis數據庫操作,默認操作第0個數據庫
 79         // redisStandaloneConfiguration.setDatabase(0);
 80         // 設置redis的密碼
 81         // redisStandaloneConfiguration.setPassword(RedisPassword.of("123456"));
 82         // 設置端口號
 83         // redisStandaloneConfiguration.setPort(6379);
 84         System.out.println("配置文件application.properties設置在第幾號redis數據庫操作,默認值:" + redisStandaloneConfiguration.getHostName());
 85         System.out.println("配置文件application.properties設置ip主機地址,默認值:" + redisStandaloneConfiguration.getDatabase());
 86         System.out.println("配置文件application.properties設置端口號,默認值:" + redisStandaloneConfiguration.getPort());
 87         System.out.println();
 88 
 89         // 獲得默認的連接池構造器
 90         JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = JedisClientConfiguration.builder().usePooling();
 91 
 92         // 指定jedisPoolConifig來修改默認的連接池構造器
 93         jpcb.poolConfig(config);
 94         // 通過構造器來構造jedis客戶端配置
 95         JedisClientConfiguration jedisClientConfiguration = jpcb.build();
 96 
 97         // 將設置好的數據庫鏈接傳遞到JedisConnectionFactory構造方法里面
 98         // JedisConnectionFactory factory = new JedisConnectionFactory(redisStandaloneConfiguration);
 99 
100         // 返回,注入到ioc容器中
101         // 單機配置 + 客戶端配置 = jedis連接工廠
102         return new JedisConnectionFactory(redisStandaloneConfiguration, jedisClientConfiguration);
103     }
104 
105 
106     /**
107      * 3.創建RedisTemplate模板對象,用於執行Redis操作的方法。
108      *
109      * @param jedisConnectionFactory
110      * @return
111      */
112     @Bean
113     public RedisTemplate<String, Object> redisTemplate(JedisConnectionFactory jedisConnectionFactory) {
114         System.out.println("配置文件application.properties設置在第幾號redis數據庫操作,配置完畢:" + jedisConnectionFactory.getHostName());
115         System.out.println("配置文件application.properties設置ip主機地址,配置完畢:" + jedisConnectionFactory.getDatabase());
116         System.out.println("配置文件application.properties設置端口號,配置完畢:" + jedisConnectionFactory.getPort());
117         System.out.println();
118 
119         // 創建RedisTemplate對象
120         RedisTemplate<String, Object> template = new RedisTemplate<>();
121         // 關聯,鏈接連接池工廠,RedisTemplate與JedisConnectionFactory關聯
122         template.setConnectionFactory(jedisConnectionFactory);
123         // 為key設置序列化器
124         template.setKeySerializer(new StringRedisSerializer());
125         // 為value設置序列化器
126         template.setValueSerializer(new StringRedisSerializer());
127         return template;
128     }
129 
130 
131     /**
132      * jedis連接工廠
133      *
134      * @param jedisPoolConfig
135      * @return
136      */
137 //    @Bean
138 //    public RedisConnectionFactory redisConnectionFactory(JedisPoolConfig jedisPoolConfig) {
139 //        // 單機版jedis
140 //        RedisStandaloneConfiguration redisStandaloneConfiguration = new RedisStandaloneConfiguration();
141 //        // 設置redis服務器的host或者ip地址
142 //        redisStandaloneConfiguration.setHostName("192.168.110.140");
143 //        // 設置默認使用的數據庫
144 //        redisStandaloneConfiguration.setDatabase(0);
145 //        // 設置密碼
146 //        // redisStandaloneConfiguration.setPassword(RedisPassword.of("123456"));
147 //        // 設置redis的服務的端口號
148 //        redisStandaloneConfiguration.setPort(6379);
149 //        // 獲得默認的連接池構造器
150 //        // JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = (JedisClientConfiguration.JedisPoolingClientConfigurationBuilder) JedisClientConfiguration.builder();
151 //
152 //        // 獲得默認的連接池構造器
153 //        JedisClientConfiguration.JedisPoolingClientConfigurationBuilder jpcb = JedisClientConfiguration.builder().usePooling();
154 //
155 //        // 指定jedisPoolConifig來修改默認的連接池構造器
156 //        jpcb.poolConfig(jedisPoolConfig);
157 //        // 通過構造器來構造jedis客戶端配置
158 //        JedisClientConfiguration jedisClientConfiguration = jpcb.build();
159 //        // 單機配置 + 客戶端配置 = jedis連接工廠
160 //        return new JedisConnectionFactory(redisStandaloneConfiguration, jedisClientConfiguration);
161 //    }
162 
163 
164 }

使用上面的測試類進行測試,觀察控制台,可以看出一些配置信息。

Spring Boot整合Spring Data Redis,來進行存取Java對象。Spring Data Redis 操作實體對象。創建實體類,方便進行存儲對象。

 1 package com.bie.springboot.po;
 2 
 3 import java.io.Serializable;
 4 
 5 public class Users implements Serializable {
 6 
 7     private Integer id;
 8     private String name;
 9     private Integer age;
10 
11     public Integer getId() {
12         return id;
13     }
14 
15     public void setId(Integer id) {
16         this.id = id;
17     }
18 
19     public String getName() {
20         return name;
21     }
22 
23     public void setName(String name) {
24         this.name = name;
25     }
26 
27     public Integer getAge() {
28         return age;
29     }
30 
31     public void setAge(Integer age) {
32         this.age = age;
33     }
34 
35     public Users(Integer id, String name, Integer age) {
36         this.id = id;
37         this.name = name;
38         this.age = age;
39     }
40 
41     @Override
42     public String toString() {
43         return "Users{" +
44                 "id=" + id +
45                 ", name='" + name + '\'' +
46                 ", age=" + age +
47                 '}';
48     }
49 
50     public Users() {
51     }
52 }

使用測試類,開始進行測試。

 1 package com.bie.springboot;
 2 
 3 import com.bie.springboot.po.Users;
 4 import org.junit.jupiter.api.Test;
 5 import org.junit.runner.RunWith;
 6 import org.springframework.beans.factory.annotation.Autowired;
 7 import org.springframework.boot.test.context.SpringBootTest;
 8 import org.springframework.data.redis.core.RedisTemplate;
 9 import org.springframework.data.redis.serializer.JdkSerializationRedisSerializer;
10 import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
11 
12 @RunWith(SpringJUnit4ClassRunner.class)
13 @SpringBootTest(classes = SpringdataRedisApplication.class)
14 class SpringdataRedisApplicationTests {
15 
16     @Autowired
17     private RedisTemplate<String, Object> redisTemplate;
18 
19     /**
20      * 添加一個字符串
21      */
22     @Test
23     public void testSet() {
24         this.redisTemplate.opsForValue().set("key", "我想要學好springboot");
25     }
26 
27     /**
28      * 獲取一個字符串
29      */
30     @Test
31     public void testGet() {
32         String value = (String) this.redisTemplate.opsForValue().get("key");
33         System.out.println(value);
34     }
35 
36     /**
37      * 添加 Users 對象
38      */
39     @Test
40     public void testSetUsers() {
41         // 該實體類要實現序列號接口的
42         Users users = new Users(1, "張颯颯", 24);
43         // 實體類重新設置序列化器
44         this.redisTemplate.setValueSerializer(new JdkSerializationRedisSerializer());
45         // 將實體類序列話后存儲到redis中
46         this.redisTemplate.opsForValue().set("users", users);
47     }
48 
49     /**
50      * 獲取 Users 對象
51      */
52     @Test
53     public void testGetUsers() {
54         // 重新設置序列化器
55         this.redisTemplate.setValueSerializer(new JdkSerializationRedisSerializer());
56         Users users = (Users) this.redisTemplate.opsForValue().get("users");
57         System.out.println("users: " + users);
58     }
59 
60 }

Spring Boot整合Spring Data Redis,來進行存取JSON格式Java對象。實體類直接序列化存儲比實體類轉換為json格式存儲要大,所以也可以選擇以json格式進行存儲實體類對象,以 JSON 格式存儲實體對象。

 1 package com.bie.springboot;
 2 
 3 import com.bie.springboot.po.Users;
 4 import org.junit.jupiter.api.Test;
 5 import org.junit.runner.RunWith;
 6 import org.springframework.beans.factory.annotation.Autowired;
 7 import org.springframework.boot.test.context.SpringBootTest;
 8 import org.springframework.data.redis.core.RedisTemplate;
 9 import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
10 import org.springframework.data.redis.serializer.JdkSerializationRedisSerializer;
11 import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
12 
13 @RunWith(SpringJUnit4ClassRunner.class)
14 @SpringBootTest(classes = SpringdataRedisApplication.class)
15 class SpringdataRedisApplicationTests {
16 
17     @Autowired
18     private RedisTemplate<String, Object> redisTemplate;
19 
20     /**
21      * 添加一個字符串
22      */
23     @Test
24     public void testSet() {
25         this.redisTemplate.opsForValue().set("key", "我想要學好springboot");
26     }
27 
28     /**
29      * 獲取一個字符串
30      */
31     @Test
32     public void testGet() {
33         String value = (String) this.redisTemplate.opsForValue().get("key");
34         System.out.println(value);
35     }
36 
37     /**
38      * 添加 Users 對象
39      */
40     @Test
41     public void testSetUsers() {
42         // 該實體類要實現序列號接口的
43         Users users = new Users(1, "張颯颯", 24);
44         // 實體類重新設置序列化器
45         this.redisTemplate.setValueSerializer(new JdkSerializationRedisSerializer());
46         // 將實體類序列話后存儲到redis中
47         this.redisTemplate.opsForValue().set("users", users);
48     }
49 
50     /**
51      * 獲取 Users 對象
52      */
53     @Test
54     public void testGetUsers() {
55         // 重新設置序列化器
56         this.redisTemplate.setValueSerializer(new JdkSerializationRedisSerializer());
57         Users users = (Users) this.redisTemplate.opsForValue().get("users");
58         System.out.println("users: " + users);
59     }
60 
61     /**
62      * 基於 JSON 格式存 Users 對象
63      */
64     @Test
65     public void testSetUsersUseJSON() {
66         // 創建實體類對象
67         Users users = new Users(1, "張颯颯", 24);
68         // 將指定的實體類轉換為json格式
69         this.redisTemplate.setValueSerializer(new Jackson2JsonRedisSerializer<>(Users.class));
70         // 將轉換為json格式的實體類存儲到redis中
71         this.redisTemplate.opsForValue().set("users_json", users);
72     }
73 
74     /**
75      * 基於 JSON 格式取 Users 對象
76      */
77     @Test
78     public void testGetUseJSON() {
79         // 反序列化,將指定的實體類以json格式進行反序列化
80         this.redisTemplate.setValueSerializer(new Jackson2JsonRedisSerializer<>(Users.class));
81         Users users = (Users) this.redisTemplate.opsForValue().get("users_json");
82         System.out.println("users_json: " + users);
83     }
84 
85 }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM