一、前言 之前分享过关于Redis集群如何搭建的,最近有小伙伴儿说分享一下Redis如何使用SpringBoot的整合,项目中经常使用的就是Redis,本次整合的是Redis单机版,后续会分享Redis集群版本,请多提出自己的意见。
二、开始整合 1.首先需要搭建Redis服务器,可参考之前的博客() 2019/04/26/Redis的搭建(win和linux版) 
2.搭建SpringBoot工程,参考之前的博客 SpringBoot工程搭建 
3.在pom文件加入redis的依赖和Json相关依赖 1 2 3 4 5 6 7 8 9 10 <dependency >     <groupId > org.springframework.boot</groupId >      <artifactId > spring-boot-starter-data-redis</artifactId >  </dependency > <dependency >     <groupId > com.alibaba</groupId >      <artifactId > fastjson</artifactId >      <version > 1.2.38</version >  </dependency > 
 
4.创建项目结构,结构如下图所示 
5.项目全局配置文件application.properties文件配置Redis的相关配置 如下问全部的配置,因为我的redis没有设置密码,故password被我注释掉了
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 #项目启动端口 server.port=8088 #应用上下文 server.context-path = /SpringBootRedis #redis相关配置 # Redis数据库索引(默认为0) spring.redis.database=0 # Redis服务器地址 spring.redis.host=127.0.0.1 # Redis服务器连接端口 spring.redis.port=6379 # Redis服务器连接密码(默认为空) #spring.redis.password= # 连接池最大连接数(使用负值表示没有限制) spring.redis.pool.max-active=200 # 连接池最大阻塞等待时间(使用负值表示没有限制) spring.redis.pool.max-wait=-1 # 连接池中的最大空闲连接 spring.redis.pool.max-idle=10 # 连接池中的最小空闲连接 spring.redis.pool.min-idle=0 # 连接超时时间(毫秒) spring.redis.timeout=1000 
 
6.配置redis的配置文件,使用RedisTemplate进行操作,需要将数据的进行序列化,才不会出现乱码 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 package  com.yang.config.redis;import  com.fasterxml.jackson.annotation.JsonAutoDetect;import  com.fasterxml.jackson.annotation.PropertyAccessor;import  com.fasterxml.jackson.databind.ObjectMapper;import  org.springframework.context.annotation.Bean;import  org.springframework.context.annotation.Configuration;import  org.springframework.data.redis.connection.RedisConnectionFactory;import  org.springframework.data.redis.core.RedisTemplate;import  org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;import  org.springframework.data.redis.serializer.StringRedisSerializer;@Configuration public  class  RedisConfig   {    @Bean      public  RedisTemplate<String, Object> redisTemplate (RedisConnectionFactory factory)   {         RedisTemplate<String, Object> template = new  RedisTemplate<String, Object>();         template.setConnectionFactory(factory);         Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new  Jackson2JsonRedisSerializer(Object.class);         ObjectMapper om = new  ObjectMapper();         om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);         om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);         jackson2JsonRedisSerializer.setObjectMapper(om);         StringRedisSerializer stringRedisSerializer = new  StringRedisSerializer();                  template.setKeySerializer(stringRedisSerializer);                  template.setHashKeySerializer(stringRedisSerializer);                  template.setValueSerializer(jackson2JsonRedisSerializer);                  template.setHashValueSerializer(jackson2JsonRedisSerializer);         template.afterPropertiesSet();         return  template;     } } 
 
7.编写redis工具类,供开发使用,注入RedisTemplate进行操作 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 package  com.yang.config.redis;import  org.springframework.beans.factory.annotation.Autowired;import  org.springframework.context.annotation.Configuration;import  org.springframework.data.redis.core.RedisTemplate;import  java.util.concurrent.TimeUnit;@Configuration public  class  RedisUtil   {    @Autowired      private  RedisTemplate<String,Object> redisTemplate;          public  void  set (String key , Object value)  {         redisTemplate.opsForValue().set(key,value);     }          public  void  set (String key , Object value , int  exp,TimeUnit s)  {         if ( s==null  ){             s = TimeUnit.SECONDS;         }         redisTemplate.opsForValue().set(key,value,exp, s);     }          public  <T>T get (String key)  {         return  (T)redisTemplate.opsForValue().get(key);     } } 
 
8.编写RedisController,编写set和get,使用请求来存储redis的值和获取redis的值 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 package  com.yang.controller;import  com.yang.config.redis.RedisUtil;import  org.springframework.beans.factory.annotation.Autowired;import  org.springframework.web.bind.annotation.GetMapping;import  org.springframework.web.bind.annotation.RequestMapping;import  org.springframework.web.bind.annotation.RequestParam;import  org.springframework.web.bind.annotation.RestController;@RestController @RequestMapping ("/redis" )public  class  RedisController   {    @Autowired      private  RedisUtil redisUtil;          @GetMapping ("/get" )     public  String get (@RequestParam(value="key" )  String key) {         return  redisUtil.get(key).toString();     }          @GetMapping ("/put" )     public  String put (@RequestParam(value="key" )  String key,@RequestParam (value="value" )  String value) {         redisUtil.set(key,value);         return  "success" ;     } } 
 
9.使用浏览器访问接口保存数据,并查询数据 
三、加载机制剖析 1.经过查看,Redis的包中,包含RedisAutoConfiguration这个配置类,使用了Configuration注解,SpringBoot会自动加载     
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 package  org.springframework.boot.autoconfigure.data.redis;import  java.net.URI;import  java.net.URISyntaxException;import  java.net.UnknownHostException;import  java.util.ArrayList;import  java.util.List;import  org.apache.commons.pool2.impl.GenericObjectPool;import  org.springframework.beans.factory.ObjectProvider;import  org.springframework.boot.autoconfigure.condition.ConditionalOnClass;import  org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;import  org.springframework.boot.autoconfigure.data.redis.RedisProperties.Cluster;import  org.springframework.boot.autoconfigure.data.redis.RedisProperties.Pool;import  org.springframework.boot.autoconfigure.data.redis.RedisProperties.Sentinel;import  org.springframework.boot.context.properties.EnableConfigurationProperties;import  org.springframework.context.annotation.Bean;import  org.springframework.context.annotation.Configuration;import  org.springframework.data.redis.connection.RedisClusterConfiguration;import  org.springframework.data.redis.connection.RedisConnectionFactory;import  org.springframework.data.redis.connection.RedisNode;import  org.springframework.data.redis.connection.RedisSentinelConfiguration;import  org.springframework.data.redis.connection.jedis.JedisConnection;import  org.springframework.data.redis.connection.jedis.JedisConnectionFactory;import  org.springframework.data.redis.core.RedisOperations;import  org.springframework.data.redis.core.RedisTemplate;import  org.springframework.data.redis.core.StringRedisTemplate;import  org.springframework.util.Assert;import  org.springframework.util.StringUtils;import  redis.clients.jedis.Jedis;import  redis.clients.jedis.JedisPoolConfig;@Configuration @ConditionalOnClass ({JedisConnection.class, RedisOperations.class, Jedis.class})@EnableConfigurationProperties ({RedisProperties.class})public  class  RedisAutoConfiguration   {    public  RedisAutoConfiguration ()   {     }     @Configuration      protected  static  class  RedisConfiguration   {         protected  RedisConfiguration ()   {         }         @Bean          @ConditionalOnMissingBean (             name = {"redisTemplate" }         )         public  RedisTemplate<Object, Object> redisTemplate (RedisConnectionFactory redisConnectionFactory)  throws  UnknownHostException  {             RedisTemplate<Object, Object> template = new  RedisTemplate();             template.setConnectionFactory(redisConnectionFactory);             return  template;         }         @Bean          @ConditionalOnMissingBean ({StringRedisTemplate.class})         public  StringRedisTemplate stringRedisTemplate (RedisConnectionFactory redisConnectionFactory)  throws  UnknownHostException  {             StringRedisTemplate template = new  StringRedisTemplate();             template.setConnectionFactory(redisConnectionFactory);             return  template;         }     }     @Configuration      @ConditionalOnClass ({GenericObjectPool.class})     protected  static  class  RedisConnectionConfiguration   {         private  final  RedisProperties properties;         private  final  RedisSentinelConfiguration sentinelConfiguration;         private  final  RedisClusterConfiguration clusterConfiguration;         public  RedisConnectionConfiguration (RedisProperties properties, ObjectProvider<RedisSentinelConfiguration> sentinelConfiguration, ObjectProvider<RedisClusterConfiguration> clusterConfiguration)   {             this .properties = properties;             this .sentinelConfiguration = (RedisSentinelConfiguration)sentinelConfiguration.getIfAvailable();             this .clusterConfiguration = (RedisClusterConfiguration)clusterConfiguration.getIfAvailable();         }         @Bean          @ConditionalOnMissingBean ({RedisConnectionFactory.class})         public  JedisConnectionFactory redisConnectionFactory ()  throws  UnknownHostException  {             return  this .applyProperties(this .createJedisConnectionFactory());         }         protected  final  JedisConnectionFactory applyProperties (JedisConnectionFactory factory)   {             this .configureConnection(factory);             if  (this .properties.isSsl()) {                 factory.setUseSsl(true );             }             factory.setDatabase(this .properties.getDatabase());             if  (this .properties.getTimeout() > 0 ) {                 factory.setTimeout(this .properties.getTimeout());             }             return  factory;         }         private  void  configureConnection (JedisConnectionFactory factory)   {             if  (StringUtils.hasText(this .properties.getUrl())) {                 this .configureConnectionFromUrl(factory);             } else  {                 factory.setHostName(this .properties.getHost());                 factory.setPort(this .properties.getPort());                 if  (this .properties.getPassword() != null ) {                     factory.setPassword(this .properties.getPassword());                 }             }         }         private  void  configureConnectionFromUrl (JedisConnectionFactory factory)   {             String url = this .properties.getUrl();             if  (url.startsWith("rediss://" )) {                 factory.setUseSsl(true );             }             try  {                 URI uri = new  URI(url);                 factory.setHostName(uri.getHost());                 factory.setPort(uri.getPort());                 if  (uri.getUserInfo() != null ) {                     String password = uri.getUserInfo();                     int  index = password.lastIndexOf(":" );                     if  (index >= 0 ) {                         password = password.substring(index + 1 );                     }                     factory.setPassword(password);                 }             } catch  (URISyntaxException var6) {                 throw  new  IllegalArgumentException("Malformed 'spring.redis.url' "  + url, var6);             }         }         protected  final  RedisSentinelConfiguration getSentinelConfig ()   {             if  (this .sentinelConfiguration != null ) {                 return  this .sentinelConfiguration;             } else  {                 Sentinel sentinelProperties = this .properties.getSentinel();                 if  (sentinelProperties != null ) {                     RedisSentinelConfiguration config = new  RedisSentinelConfiguration();                     config.master(sentinelProperties.getMaster());                     config.setSentinels(this .createSentinels(sentinelProperties));                     return  config;                 } else  {                     return  null ;                 }             }         }         protected  final  RedisClusterConfiguration getClusterConfiguration ()   {             if  (this .clusterConfiguration != null ) {                 return  this .clusterConfiguration;             } else  if  (this .properties.getCluster() == null ) {                 return  null ;             } else  {                 Cluster clusterProperties = this .properties.getCluster();                 RedisClusterConfiguration config = new  RedisClusterConfiguration(clusterProperties.getNodes());                 if  (clusterProperties.getMaxRedirects() != null ) {                     config.setMaxRedirects(clusterProperties.getMaxRedirects().intValue());                 }                 return  config;             }         }         private  List<RedisNode> createSentinels (Sentinel sentinel)   {             List<RedisNode> nodes = new  ArrayList();             String[] var3 = StringUtils.commaDelimitedListToStringArray(sentinel.getNodes());             int  var4 = var3.length;             for (int  var5 = 0 ; var5 < var4; ++var5) {                 String node = var3[var5];                 try  {                     String[] parts = StringUtils.split(node, ":" );                     Assert.state(parts.length == 2 , "Must be defined as 'host:port'" );                     nodes.add(new  RedisNode(parts[0 ], Integer.valueOf(parts[1 ]).intValue()));                 } catch  (RuntimeException var8) {                     throw  new  IllegalStateException("Invalid redis sentinel property '"  + node + "'" , var8);                 }             }             return  nodes;         }         private  JedisConnectionFactory createJedisConnectionFactory ()   {             JedisPoolConfig poolConfig = this .properties.getPool() != null  ? this .jedisPoolConfig() : new  JedisPoolConfig();             if  (this .getSentinelConfig() != null ) {                 return  new  JedisConnectionFactory(this .getSentinelConfig(), poolConfig);             } else  {                 return  this .getClusterConfiguration() != null  ? new  JedisConnectionFactory(this .getClusterConfiguration(), poolConfig) : new  JedisConnectionFactory(poolConfig);             }         }         private  JedisPoolConfig jedisPoolConfig ()   {             JedisPoolConfig config = new  JedisPoolConfig();             Pool props = this .properties.getPool();             config.setMaxTotal(props.getMaxActive());             config.setMaxIdle(props.getMaxIdle());             config.setMinIdle(props.getMinIdle());             config.setMaxWaitMillis((long )props.getMaxWait());             return  config;         }     } } 
 
2.配置了EnableConfigurationProperties,配置了RedisProperties,而RedisProperties则使用了ConfigurationProperties,加载了前缀为spring.redis的所有配置,故读取了application.properties文件中的内容。 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 package  org.springframework.boot.autoconfigure.data.redis;import  java.util.List;import  org.springframework.boot.context.properties.ConfigurationProperties;@ConfigurationProperties (prefix = "spring.redis" )public  class  RedisProperties   {	 	private  int  database = 0 ; 	 	private  String url; 	 	private  String host = "localhost" ; 	 	private  String password; 	 	private  int  port = 6379 ; 	 	private  boolean  ssl; 	 	private  int  timeout; 	private  Pool pool; 	private  Sentinel sentinel; 	private  Cluster cluster; 	public  int  getDatabase ()   { 		return  this .database; 	} 	public  void  setDatabase (int  database)   { 		this .database = database; 	} 	public  String getUrl ()   { 		return  this .url; 	} 	public  void  setUrl (String url)   { 		this .url = url; 	} 	public  String getHost ()   { 		return  this .host; 	} 	public  void  setHost (String host)   { 		this .host = host; 	} 	public  String getPassword ()   { 		return  this .password; 	} 	public  void  setPassword (String password)   { 		this .password = password; 	} 	public  int  getPort ()   { 		return  this .port; 	} 	public  void  setPort (int  port)   { 		this .port = port; 	} 	public  boolean  isSsl ()   { 		return  this .ssl; 	} 	public  void  setSsl (boolean  ssl)   { 		this .ssl = ssl; 	} 	public  void  setTimeout (int  timeout)   { 		this .timeout = timeout; 	} 	public  int  getTimeout ()   { 		return  this .timeout; 	} 	public  Sentinel getSentinel ()   { 		return  this .sentinel; 	} 	public  void  setSentinel (Sentinel sentinel)   { 		this .sentinel = sentinel; 	} 	public  Pool getPool ()   { 		return  this .pool; 	} 	public  void  setPool (Pool pool)   { 		this .pool = pool; 	} 	public  Cluster getCluster ()   { 		return  this .cluster; 	} 	public  void  setCluster (Cluster cluster)   { 		this .cluster = cluster; 	} 	 	public  static  class  Pool   { 		 		private  int  maxIdle = 8 ; 		 		private  int  minIdle = 0 ; 		 		private  int  maxActive = 8 ; 		 		private  int  maxWait = -1 ; 		public  int  getMaxIdle ()   { 			return  this .maxIdle; 		} 		public  void  setMaxIdle (int  maxIdle)   { 			this .maxIdle = maxIdle; 		} 		public  int  getMinIdle ()   { 			return  this .minIdle; 		} 		public  void  setMinIdle (int  minIdle)   { 			this .minIdle = minIdle; 		} 		public  int  getMaxActive ()   { 			return  this .maxActive; 		} 		public  void  setMaxActive (int  maxActive)   { 			this .maxActive = maxActive; 		} 		public  int  getMaxWait ()   { 			return  this .maxWait; 		} 		public  void  setMaxWait (int  maxWait)   { 			this .maxWait = maxWait; 		} 	} 	 	public  static  class  Cluster   { 		 		private  List<String> nodes; 		 		private  Integer maxRedirects; 		public  List<String> getNodes ()   { 			return  this .nodes; 		} 		public  void  setNodes (List<String> nodes)   { 			this .nodes = nodes; 		} 		public  Integer getMaxRedirects ()   { 			return  this .maxRedirects; 		} 		public  void  setMaxRedirects (Integer maxRedirects)   { 			this .maxRedirects = maxRedirects; 		} 	} 	 	public  static  class  Sentinel   { 		 		private  String master; 		 		private  String nodes; 		public  String getMaster ()   { 			return  this .master; 		} 		public  void  setMaster (String master)   { 			this .master = master; 		} 		public  String getNodes ()   { 			return  this .nodes; 		} 		public  void  setNodes (String nodes)   { 			this .nodes = nodes; 		} 	} } 
 
四、源码地址 点我查看