更多Spring文章,歡迎點擊 一灰灰Blog-Spring專題java
在Spring的應用中,redis能夠算是基礎操做了。那麼想要玩轉redis,咱們須要知道哪些知識點呢?git
本篇博文爲redis系列的開篇,將介紹最基本的配置github
<!-- more -->redis
最簡單的使用其實開箱便可用,添加依賴spring
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-redis</artifactId> </dependency>
本機啓動redis,一切採用默認的配置 (host:127.0.0.1, port:6379, 無密碼)apache
而後就能夠愉快的玩耍了,能夠直接注入redisTemplate
實例,進行各類讀寫操做app
@SpringBootApplication public class Application { public Application(RedisTemplate<String, String> redisTemplate) { redisTemplate.opsForValue().set("hello", "world"); String ans = redisTemplate.opsForValue().get("hello"); Assert.isTrue("world".equals(ans)); } public static void main(String[] args) { SpringApplication.run(Application.class, args); } }
前面是默認的配置參數,在實際的使用中,通常都會修改這些默認的配置項,若是個人應用中,只有一個redis,那麼徹底能夠只修改默認的配置參數ide
修改配置文件: application.yml
spring-boot
spring: redis: host: 127.0.0.1 port: 6379 password: database: 0 lettuce: pool: max-active: 32 max-wait: 300ms max-idle: 16 min-idle: 8
使用和前面沒有什麼區別,直接經過注入RedisTemplate
來操做便可,須要額外注意的是設置了鏈接池的相關參數,須要額外引入依賴學習
<dependency> <groupId>org.apache.commons</groupId> <artifactId>commons-pool2</artifactId> </dependency>
依賴多個不一樣的redis,也就是說個人項目須要從多個redis實例中獲取數據,這種時候,就不能直接使用默認的,須要咱們本身來聲明ConnectionFactory
和 RedisTemplate
配置以下
spring: redis: host: 127.0.0.1 port: 6379 password: lettuce: pool: max-active: 32 max-wait: 300 max-idle: 16 min-idle: 8 database: 0 local-redis: host: 127.0.0.1 port: 6379 database: 0 password: lettuce: pool: max-active: 16 max-wait: 100 max-idle: 8 min-idle: 4
對應的配置類,採用Lettuce,基本設置以下,套路都差很少,先讀取配置,初始化ConnectionFactory
,而後建立RedisTemplate
實例,設置鏈接工廠
@Configuration public class RedisAutoConfig { @Bean public LettuceConnectionFactory defaultLettuceConnectionFactory(RedisStandaloneConfiguration defaultRedisConfig, GenericObjectPoolConfig defaultPoolConfig) { LettuceClientConfiguration clientConfig = LettucePoolingClientConfiguration.builder().commandTimeout(Duration.ofMillis(100)) .poolConfig(defaultPoolConfig).build(); return new LettuceConnectionFactory(defaultRedisConfig, clientConfig); } @Bean public RedisTemplate<String, String> defaultRedisTemplate( LettuceConnectionFactory defaultLettuceConnectionFactory) { RedisTemplate<String, String> redisTemplate = new RedisTemplate<>(); redisTemplate.setConnectionFactory(defaultLettuceConnectionFactory); redisTemplate.afterPropertiesSet(); return redisTemplate; } @Bean @ConditionalOnBean(name = "localRedisConfig") public LettuceConnectionFactory localLettuceConnectionFactory(RedisStandaloneConfiguration localRedisConfig, GenericObjectPoolConfig localPoolConfig) { LettuceClientConfiguration clientConfig = LettucePoolingClientConfiguration.builder().commandTimeout(Duration.ofMillis(100)) .poolConfig(localPoolConfig).build(); return new LettuceConnectionFactory(localRedisConfig, clientConfig); } @Bean @ConditionalOnBean(name = "localLettuceConnectionFactory") public RedisTemplate<String, String> localRedisTemplate(LettuceConnectionFactory localLettuceConnectionFactory) { RedisTemplate<String, String> redisTemplate = new RedisTemplate<>(); redisTemplate.setConnectionFactory(localLettuceConnectionFactory); redisTemplate.afterPropertiesSet(); return redisTemplate; } @Configuration @ConditionalOnProperty(name = "host", prefix = "spring.local-redis") public static class LocalRedisConfig { @Value("${spring.local-redis.host:127.0.0.1}") private String host; @Value("${spring.local-redis.port:6379}") private Integer port; @Value("${spring.local-redis.password:}") private String password; @Value("${spring.local-redis.database:0}") private Integer database; @Value("${spring.local-redis.lettuce.pool.max-active:8}") private Integer maxActive; @Value("${spring.local-redis.lettuce.pool.max-idle:8}") private Integer maxIdle; @Value("${spring.local-redis.lettuce.pool.max-wait:-1}") private Long maxWait; @Value("${spring.local-redis.lettuce.pool.min-idle:0}") private Integer minIdle; @Bean public GenericObjectPoolConfig localPoolConfig() { GenericObjectPoolConfig config = new GenericObjectPoolConfig(); config.setMaxTotal(maxActive); config.setMaxIdle(maxIdle); config.setMinIdle(minIdle); config.setMaxWaitMillis(maxWait); return config; } @Bean public RedisStandaloneConfiguration localRedisConfig() { RedisStandaloneConfiguration config = new RedisStandaloneConfiguration(); config.setHostName(host); config.setPassword(RedisPassword.of(password)); config.setPort(port); config.setDatabase(database); return config; } } @Configuration public static class DefaultRedisConfig { @Value("${spring.redis.host:127.0.0.1}") private String host; @Value("${spring.redis.port:6379}") private Integer port; @Value("${spring.redis.password:}") private String password; @Value("${spring.redis.database:0}") private Integer database; @Value("${spring.redis.lettuce.pool.max-active:8}") private Integer maxActive; @Value("${spring.redis.lettuce.pool.max-idle:8}") private Integer maxIdle; @Value("${spring.redis.lettuce.pool.max-wait:-1}") private Long maxWait; @Value("${spring.redis.lettuce.pool.min-idle:0}") private Integer minIdle; @Bean public GenericObjectPoolConfig defaultPoolConfig() { GenericObjectPoolConfig config = new GenericObjectPoolConfig(); config.setMaxTotal(maxActive); config.setMaxIdle(maxIdle); config.setMinIdle(minIdle); config.setMaxWaitMillis(maxWait); return config; } @Bean public RedisStandaloneConfiguration defaultRedisConfig() { RedisStandaloneConfiguration config = new RedisStandaloneConfiguration(); config.setHostName(host); config.setPassword(RedisPassword.of(password)); config.setPort(port); config.setDatabase(database); return config; } } }
測試類以下,簡單的演示下兩個template的讀寫
@SpringBootApplication public class Application { public Application(RedisTemplate<String, String> localRedisTemplate, RedisTemplate<String, String> defaultRedisTemplate) throws InterruptedException { // 10s的有效時間 localRedisTemplate.delete("key"); localRedisTemplate.opsForValue().set("key", "value", 100, TimeUnit.MILLISECONDS); String ans = localRedisTemplate.opsForValue().get("key"); System.out.println("value".equals(ans)); TimeUnit.MILLISECONDS.sleep(200); ans = localRedisTemplate.opsForValue().get("key"); System.out.println("value".equals(ans) + " >> false ans should be null! ans=[" + ans + "]"); defaultRedisTemplate.opsForValue().set("key", "value", 100, TimeUnit.MILLISECONDS); ans = defaultRedisTemplate.opsForValue().get("key"); System.out.println(ans); } public static void main(String[] args) { SpringApplication.run(Application.class, args); } }
上面的代碼執行演示以下
上面的演示爲動圖,抓一下重點:
localRedisTemplate
, defaultRedisTemplate
兩個對象不相同(看debug窗口後面的@xxx
)RedisTemplate
的ConnectionFactory
也是兩個不一樣的實例(即分別對應前面配置類中的兩個Factory)Description: Parameter 0 of method redisTemplate in org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration required a single bean, but 2 were found: - defaultLettuceConnectionFactory: defined by method 'defaultLettuceConnectionFactory' in class path resource [com/git/hui/boot/redis/config/RedisAutoConfig.class] - localLettuceConnectionFactory: defined by method 'localLettuceConnectionFactory' in class path resource [com/git/hui/boot/redis/config/RedisAutoConfig.class] Action: Consider marking one of the beans as @Primary, updating the consumer to accept multiple beans, or using @Qualifier to identify the bean that should be consumed
上面表示說有多個ConnectionFactory存在,而後建立默認的RedisTemplate就不知道該選擇哪個了,有兩種方法
方法一:指定默認的ConnectionFactory
藉助@Primary
來指定默認的鏈接工廠,而後在使用工程的時候,經過@Qualifier
註解來顯示指定,我須要的工廠是哪一個(主要是localRedisTemplate
這個bean的定義,若是不加,則會根據defaultLettuceConnectionFactory
這個實例來建立Redis鏈接了)
@Bean @Primary public LettuceConnectionFactory defaultLettuceConnectionFactory(RedisStandaloneConfiguration defaultRedisConfig, GenericObjectPoolConfig defaultPoolConfig) { // ... } @Bean public RedisTemplate<String, String> defaultRedisTemplate( @Qualifier("defaultLettuceConnectionFactory") LettuceConnectionFactory defaultLettuceConnectionFactory) { // .... } @Bean @ConditionalOnBean(name = "localRedisConfig") public LettuceConnectionFactory localLettuceConnectionFactory(RedisStandaloneConfiguration localRedisConfig, GenericObjectPoolConfig localPoolConfig) { // ... } @Bean @ConditionalOnBean(name = "localLettuceConnectionFactory") public RedisTemplate<String, String> localRedisTemplate( @Qualifier("localLettuceConnectionFactory") LettuceConnectionFactory localLettuceConnectionFactory) { // ... }
方法二:忽略默認的自動配置類
既然提示的是org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration
類加載bean衝突,那麼就不加載這個配置便可
@SpringBootApplication @EnableAutoConfiguration(exclude = {RedisAutoConfiguration.class, RedisReactiveAutoConfiguration.class}) public class Application { // ... }
一灰灰的我的博客,記錄全部學習和工做中的博文,歡迎你們前去逛逛
盡信書則不如,以上內容,純屬一家之言,因我的能力有限,不免有疏漏和錯誤之處,如發現bug或者有更好的建議,歡迎批評指正,不吝感激
一灰灰blog
知識星球