starter机制
Spring Boot Starter机制是Spring Boot项目中的一个重要概念,它主要用于简化Maven或Gradle等构建工具中的依赖管理。每个Starter都包含了实现特定功能所需的库和组件,以及相应的配置文件。开发者只需在项目中引入相应的Starter依赖,即可快速搭建起具备该功能的项目骨架。
自定义starter好处
简化依赖管理:与Spring Boot内置的Starter类似,自定义Starter同样可以隐藏底层库的复杂依赖关系,使开发者只需关注业务逻辑,而无需担心底层的依赖问题。这有助于降低项目的复杂性,提升开发效率。
统一配置和自动装配:自定义Starter可以包含默认的配置信息和自动装配类,使得相关功能或组件的集成更加统一和便捷。开发者无需为每个项目重复编写相同的配置代码,只需引入自定义Starter即可实现快速集成。
提高可复用性:通过自定义Starter,可以将一些通用的功能或组件进行封装,使得这些功能或组件可以在多个项目之间共享和复用。这不仅可以减少代码冗余,还可以确保不同项目之间的功能实现保持一致。
扩展性和灵活性:自定义Starter允许开发者根据实际需求进行定制和扩展。开发者可以添加自己的配置项和默认配置值,以满足特定的业务需求。此外,自定义Starter还可以与其他第三方组件或库进行集成,以提供更加丰富的功能。
易于维护:由于自定义Starter对底层依赖进行了封装和统一配置,因此在维护和升级时只需关注自定义Starter的变更,而无需对每个使用到该Starter的项目进行逐一修改。这大大简化了维护工作,提高了开发效率。
综上所述,自定义Spring Boot Starter通过简化依赖管理、统一配置和自动装配、提高可复用性、扩展性和灵活性以及易于维护等好处,为开发者提供了一种高效、便捷的方式来构建和集成Spring Boot应用程序中的特定功能或组件。
使用场景
在日常开发工作中,如统一整合redis,mq,minIO,鉴权,日志等,用于框架集成,供自己和公司其他团队使用,通过简化配置来提高开发效率。
实现原理
具体来说,Spring Boot Starter通过自动配置(Auto-configuration)和依赖管理来实现其机制。自动配置类使用@Configuration注解进行标记,并通过条件注解(如@ConditionalOnClass、@ConditionalOnBean、@ConditionalOnProperty等)来确定是否应用自动配置。当在Spring Boot应用的pom.xml文件中添加了一个Starter的依赖时,它会触发Spring Boot的自动配置机制。自动配置类中的配置将被应用于应用程序上下文,并根据需要创建和配置相关的Bean。
实现步骤
源码地址:https://github.com/mikewuhao/redis-spring-boot-starter
项目结构
RedisConfiguration
java">package com.wuhao.redis.config;import com.wuhao.redis.utils.RedisUtils;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.StringUtils;
import redis.clients.jedis.JedisPoolConfig;/*** Copyright 2022 skyworth** @Author: wuhao* @CreateTime: 2024-04-22 11:51* @Description: redis配置类* @Version: 1.0**/
@Configuration
@EnableConfigurationProperties(RedisProperties.class)
public class RedisConfiguration {private final RedisProperties properties;public RedisConfiguration(RedisProperties redisProperties) {this.properties = redisProperties;}@Bean(name = "redisHandler")@ConditionalOnMissingBean(RedisUtils.class)public RedisUtils redisUtils() {JedisPoolConfig poolConfig = new JedisPoolConfig();//最大连接数poolConfig.setMaxTotal(properties.getMaxTotal());//最多空闲数poolConfig.setMaxIdle(properties.getMaxIdLe());//当池中没有连接时,最多等待5秒poolConfig.setMaxWaitMillis(properties.getMaxWaitMillis());String pw = StringUtils.isEmpty(properties.getPassword()) ? null : properties.getPassword();return new RedisUtils(poolConfig, properties.getHost(), properties.getPort(), properties.getTimeOut(), pw, properties.getDatabase());}
}
RedisProperties
java">
package com.wuhao.redis.config;import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;/*** Copyright 2022 skyworth** @Author: wuhao* @CreateTime: 2024-04-22 11:51* @Description: redis配置属性* @Version: 1.0**/
@ConfigurationProperties("spring.redis")
public class RedisProperties {@Value("${host:127.0.0.1}")private String host;@Value("${port:6379}")private int port;@Value("${database:0}")private int database;@Value("${password:}")private String password;@Value("${timeOut:3000}")private int timeOut;@Value("${maxTotal:10000}")private int maxTotal;@Value("${maxIdLe:50}")private int maxIdLe;@Value("${maxWaitMillis:5000}")private long maxWaitMillis;public String getHost() {return host;}public void setHost(String host) {this.host = host;}public int getPort() {return port;}public void setPort(int port) {this.port = port;}public int getDatabase() {return database;}public void setDatabase(int database) {this.database = database;}public String getPassword() {return password;}public void setPassword(String password) {this.password = password;}public int getTimeOut() {return timeOut;}public void setTimeOut(int timeOut) {this.timeOut = timeOut;}public int getMaxTotal() {return maxTotal;}public void setMaxTotal(int maxTotal) {this.maxTotal = maxTotal;}public int getMaxIdLe() {return maxIdLe;}public void setMaxIdLe(int maxIdLe) {this.maxIdLe = maxIdLe;}public long getMaxWaitMillis() {return maxWaitMillis;}public void setMaxWaitMillis(long maxWaitMillis) {this.maxWaitMillis = maxWaitMillis;}
}
RedisUtils
java">package com.wuhao.redis.utils;import org.apache.commons.pool2.impl.GenericObjectPoolConfig;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.Pipeline;
import redis.clients.jedis.Tuple;import java.util.*;/*** Copyright 2022 skyworth** @Author: wuhao* @CreateTime: 2024-04-22 11:51* @Description: redis工具类* @Version: 1.0**/
public final class RedisUtils {/*除了该工具类提供的方法外,还可以在外面调用getJedis()方法,获取到jedis实例后,调用它原生的api来操作*/private final JedisPool jedisPool;static final Long OPERATE_SUCCESS = 1L;/*** 定义获取锁的lua脚本*/static final String LOCK_LUA_SCRIPT = "if redis.call('setnx', KEYS[1], ARGV[1]) == 1 then return redis.call('expire', KEYS[1], ARGV[2]) else return 0 end";/*** 定义释放锁的lua脚本*/static final String UNLOCK_LUA_SCRIPT = "if redis.call('get',KEYS[1]) == ARGV[1] then return redis.call('del',KEYS[1]) else return -1 end";/*** 获取jedis对象,并选择redis库。jedis默认是0号库,可传入1-16之间的数选择库存放数据* 原则上使用一个redis库存放数据,通过特定的key的命令规则来区分不同的数据就行了。** @param index redis库号。使用可变参数的目的就是该参数可传可不传。* @return 返回jedis对象*/public Jedis getJedis(int... index) {Jedis jedis = jedisPool.getResource();if (index != null && index.length > 0) {if (index[0] > 0 && index[0] <= 16) {jedis.select(index[0]);}}return jedis;}/*######################## key的操作 ################################*//*** 删除一个或多个key** @param key 一个或多个key*/public Long del(String... key) {try (Jedis jedis = getJedis()) {return jedis.del(key);}}/*** 批量删除** @param keyList 要删除的key的集合*/public void mDel(List<String> keyList) {Jedis jedis = getJedis();//获取pipelinePipeline pipeline = jedis.pipelined();for (String key : keyList) {pipeline.del(key);}//执行结果同步,这样才能保证结果的正确性。实际上不执行该方法也执行了上面的命令,但是结果确不一定完全正确。//注意pipeline.sync();//关闭连接jedis.close();}/*** 判断某个key是否还存在** @param key key*/public Boolean exists(String key) {try (Jedis jedis = getJedis()) {return jedis.exists(key);}}/*** 设置某个key的过期时间,单位秒** @param key key* @param seconds 过期时间秒*/public void expire(String key, int seconds) {try (Jedis jedis = getJedis()) {jedis.expire(key, seconds);}}/*** 设置某个key的过期时间,单位秒** @param key key* @param seconds 过期时间秒*/public void expire(String key, Long seconds) {try (Jedis jedis = getJedis()) {jedis.expire(key, seconds.intValue());}}/*** 设置某个key的过期时间,单位毫秒** @param key key* @param seconds 过期时间秒*/public void expireAt(String key, long seconds) {try (Jedis jedis = getJedis()) {jedis.expireAt(key, seconds);}}/*** 查看某个key还有几秒过期,-1表示永不过期 ,-2表示已过期*/public Long ttl(String key) {try (Jedis jedis = getJedis()) {return jedis.ttl(key);}}/*** 查看某个key对应的value的类型*/public String type(String key) {try (Jedis jedis = getJedis()) {return jedis.type(key);}}/*######################## string(字符串)的操作 ####################*//*** 获取某个key的value,类型要对,只能value是string的才能获取*/public String get(String key) {try (Jedis jedis = getJedis()) {return jedis.get(key);}}/*** 设置某个key的value*/public String set(String key, String value) {try (Jedis jedis = getJedis()) {return jedis.set(key, value);}}/*** 设置某个key的value*/public String set(String key, String value, int expireSeconds) {try (Jedis jedis = getJedis()) {return jedis.setex(key, expireSeconds, value);}}/*** 设置某个key的value*/public String set(String key, String value, Long expireSeconds) {try (Jedis jedis = getJedis()) {return jedis.setex(key, expireSeconds.intValue(), value);}}public String set(String key, String value, String nxxx, String expx, long time) {try (Jedis jedis = getJedis()) {return jedis.set(key, value, nxxx, expx, time);}}/*** 字符串后追加内容** @param key key* @param appendContent 要追加的内容*/public Long append(String key, String appendContent) {try (Jedis jedis = getJedis()) {return jedis.append(key, appendContent);}}/*** 返回key的value的长度*/public Long strLen(String key) {try (Jedis jedis = getJedis()) {return jedis.strlen(key);}}/*** value 加1 必* 须是字符型数字*/public Long incr(String key) {try (Jedis jedis = getJedis()) {return jedis.incr(key);}}/*** value* 须是字符型数字*/public Long incr(String key, int num) {try (Jedis jedis = getJedis()) {return jedis.incrBy(key, num);}}/*** value 减1 必须是字符型数字*/public Long decr(String key) {try (Jedis jedis = getJedis()) {return jedis.decr(key);}}/*** value 加increment*/public Long incrBy(String key, int increment) {try (Jedis jedis = getJedis()) {return jedis.incrBy(key, increment);}}public Double incrByFloat(String key, double increment) {try (Jedis jedis = getJedis()) {return jedis.incrByFloat(key, increment);}}/*** value 加increment*/public Long incrBy(String key, Long increment) {try (Jedis jedis = getJedis()) {return jedis.incrBy(key, increment);}}/*** value 减increment*/public Long decrBy(String key, int increment) {try (Jedis jedis = getJedis()) {return jedis.decrBy(key, increment);}}/*** 给某个key设置过期时间和value,成功返回OK** @param key key* @param seconds 过期时间秒* @param value 设置的值*/public String setEx(String key, int seconds, String value) {try (Jedis jedis = getJedis()) {return jedis.setex(key, seconds, value);}}/*######################## list(列表)的操作 #######################*//*** 从左边向列表中添加值*/public void lPush(String key, String str) {try (Jedis jedis = getJedis()) {jedis.lpush(key, str);}}/*** 从左边向列表中添加值*/public void lPushAll(String key, String... strings) {try (Jedis jedis = getJedis()) {jedis.lpush(key, strings);}}public void rPushAll(String key, String... strings) {try (Jedis jedis = getJedis()) {jedis.rpush(key, strings);}}/*** 从右边向列表中添加值*/public void rPush(String key, String str) {try (Jedis jedis = getJedis()) {jedis.rpush(key, str);}}/*** 从左边取出一个列表中的值*/public String lPop(String key) {try (Jedis jedis = getJedis()) {return jedis.lpop(key);}}/*** 从右边取出一个列表中的值*/public String rPop(String key) {try (Jedis jedis = getJedis()) {return jedis.rpop(key);}}/*** 取出列表中指定范围内的值,0 到 -1 表示全部*/public List<String> lRange(String key, int startIndex, int endIndex) {try (Jedis jedis = getJedis()) {return jedis.lrange(key, startIndex, endIndex);}}/*** 返回某列表指定索引位置的值*/public String lIndex(String key, int index) {try (Jedis jedis = getJedis()) {return jedis.lindex(key, index);}}/*** 返回某列表的长度*/public Long lLen(String key) {try (Jedis jedis = getJedis()) {return jedis.llen(key);}}/*** 给某列表指定位置设置为指定的值*/public String lSet(String key, Long index, String str) {try (Jedis jedis = getJedis()) {return jedis.lset(key, index, str);}}/*** 对列表进行剪裁,保留指定闭区间的元素(索引位置也会重排)*/public void ltrim(String key, Integer startIndex, Integer endIndex) {try (Jedis jedis = getJedis()) {jedis.ltrim(key, startIndex, endIndex);}}/*** 从列表的左边阻塞弹出一个元素*/public List<String> blpop(String key, Integer timeout) {try (Jedis jedis = getJedis()) {return jedis.blpop(timeout, key);}}/*** 从列表的右边阻塞弹出一个元素*/public List<String> brpop(String key, Integer timeout) {try (Jedis jedis = getJedis()) {return jedis.brpop(timeout, key);}}/*######################## hash(哈希表)的操作 #######################*///hset hget hmset hmget hgetall hdel hkeys hvals hexists hincrby/*** 给某个hash表设置一个键值对*/public void hset(String key, String field, String value) {try (Jedis jedis = getJedis()) {jedis.hset(key, field, value);}}/*** 取出某个hash表中某个field对应的value*/public String hget(String key, String field) {try (Jedis jedis = getJedis()) {return jedis.hget(key, field);}}/*** 某个hash表设置一个或多个键值对*/public void hmset(String key, Map<String, String> kvMap) {try (Jedis jedis = getJedis()) {jedis.hmset(key, kvMap);}}/*** 取出某个hash表中任意多个key对应的value的集合*/public List<String> hmget(String key, String... fields) {try (Jedis jedis = getJedis()) {return jedis.hmget(key, fields);}}/*** 取出某个hash表中所有的键值对*/public Map<String, String> hgetAll(String key) {try (Jedis jedis = getJedis()) {return jedis.hgetAll(key);}}/*** 判断某个hash表中的某个key是否存在*/public Boolean hexists(String key, String field) {try (Jedis jedis = getJedis()) {return jedis.hexists(key, field);}}/*** 返回某个hash表中所有的key*/public Set<String> hkeys(String key) {try (Jedis jedis = getJedis()) {return jedis.hkeys(key);}}/*** 返回某个hash表中所有的value*/public List<String> hvals(String key) {try (Jedis jedis = getJedis()) {return jedis.hvals(key);}}/*** 删除某个hash表中的一个或多个键值对*/public Long hdel(String key, String... fields) {try (Jedis jedis = getJedis()) {return jedis.hdel(key, fields);}}/*** 给某个hash表中的某个field的value增加多少*/public Long hincrBy(String key, String field, Long increment) {try (Jedis jedis = getJedis()) {return jedis.hincrBy(key, field, increment);}}/*** 给某个hash表中的某个field的value增加多少*/public Long hincrBy(String key, String field, Integer increment) {try (Jedis jedis = getJedis()) {return jedis.hincrBy(key, field, increment);}}/*** 给某个hash表中的某个field的value增加多少*/public Long hdecrBy(String key, String field, Integer increment) {try (Jedis jedis = getJedis()) {return jedis.hincrBy(key, field, -increment);}}public Double hincrByFloat(String key, String field, Double increment) {try (Jedis jedis = getJedis()) {return jedis.hincrByFloat(key, field, increment);}}/*######################## set(集合)的操作 ###########################*//*** 往set集合中添加一个或多个元素*/public Long sadd(String key, String... members) {try (Jedis jedis = getJedis()) {return jedis.sadd(key, members);}}/*** 返回set集合中的所有元素,顺序与加入时的顺序一致*/public Set<String> smembers(String key) {try (Jedis jedis = getJedis()) {return jedis.smembers(key);}}/*** 判断集合中是否存在某个元素*/public Boolean sismember(String key, String member) {try (Jedis jedis = getJedis()) {return jedis.sismember(key, member);}}/*** 返回set集合的长度*/public Long scard(String key) {try (Jedis jedis = getJedis()) {return jedis.scard(key);}}/*** 删除set集合中指定的一个或多个元素*/public Long srem(String key, String... members) {try (Jedis jedis = getJedis()) {return jedis.srem(key, members);}}/*** 将key1中的元素key1Member移动到key2中*/public Long smove(String key1, String key2, String key1Member) {try (Jedis jedis = getJedis()) {return jedis.smove(key1, key2, key1Member);}}/*** 随机查询返回集合中的指定个数的元素(若count为负数,返回的元素可能会重复)*/public List<String> srandmember(String key, int count) {try (Jedis jedis = getJedis()) {return jedis.srandmember(key, count);}}/*** 从set集合中随机弹出指定个数个元素** @param key key* @param count 要弹出的个数* @return 随机弹出的元素*/public Set<String> spop(String key, int count) {try (Jedis jedis = getJedis()) {return jedis.spop(key, count);}}/*** 求交集,返回多个set集合相交的部分*/public Set<String> sinter(String... setKeys) {try (Jedis jedis = getJedis()) {return jedis.sinter(setKeys);}}/*** 求并集,求几个set集合的并集(因为set中不会有重复的元素,合并后的集合也不会有重复的元素)*/public Set<String> sunion(String... setKeys) {try (Jedis jedis = getJedis()) {return jedis.sunion(setKeys);}}/*** 求差集,求几个集合之间的差集*/public Set<String> sdiff(String... setKeys) {try (Jedis jedis = getJedis()) {return jedis.sdiff(setKeys);}}/*######################## zset(有序集合)的操作 #######################*//*** 添加一个元素到zset*/public Long zadd(String key, double score, String member) {try (Jedis jedis = getJedis()) {return jedis.zadd(key, score, member);}}/*** 添加一个或多个元素到zset*/public Long zadd(String key, Map<String, Double> memberScores) {try (Jedis jedis = getJedis()) {return jedis.zadd(key, memberScores);}}/*** 查询指定闭区间的元素(根据分数升序)* (0,-1表示全部)*/public Set<String> zrange(String key, long start, long end) {try (Jedis jedis = getJedis()) {return jedis.zrange(key, start, end);}}/*** 查询指定闭区间的元素,带着分数* (0,-1表示全部)*/public Set<Tuple> zrangeWithScores(String key, long start, long end) {try (Jedis jedis = getJedis()) {return jedis.zrangeWithScores(key, start, end);}}/*** 查询指定索引闭区间的元素(根据分数降序)* (0,-1表示全部)*/public Set<String> zrevrange(String key, long start, long end) {try (Jedis jedis = getJedis()) {return jedis.zrevrange(key, start, end);}}/*** 查询指定索引闭区间的元素,带着分数(根据分数降序)* (0,-1表示全部)*/public Set<Tuple> zrevrangeWithScores(String key, long start, long end) {try (Jedis jedis = getJedis()) {return jedis.zrevrangeWithScores(key, start, end);}}/*** 返回有序集合(zset)中的元素个数*/public Long zcard(String key) {try (Jedis jedis = getJedis()) {return jedis.zcard(key);}}/*** 返回指定分数区间的元素个数(闭区间)*/public Long zcount(String key, Long startScore, Long endScore) {try (Jedis jedis = getJedis()) {return jedis.zcount(key, startScore, endScore);}}/*** 返回某元素在集合中的排名(根据分数降序排列时)*/public Long zrevrank(String key, String member) {try (Jedis jedis = getJedis()) {return jedis.zrevrank(key, member);}}/*** 返回某元素在集合中的排名(根据分数升序排列时)*/public Long zrank(String key, String member) {try (Jedis jedis = getJedis()) {return jedis.zrank(key, member);}}/*** 升序查询指定分数闭区间的元素*/public Set<String> zrangeByScore(String key, double min, double max) {try (Jedis jedis = getJedis()) {return jedis.zrangeByScore(key, min, max);}}/*** 升序查询指定分数闭区间的元素,并指定偏移量*/public Set<String> zrangeByScore(String key, double min, double max, int offset, int size) {try (Jedis jedis = getJedis()) {return jedis.zrangeByScore(key, min, max, offset, size);}}/*** 升序查询指定分数闭区间的元素,带着分数*/public Set<Tuple> zrangeByScoreWithScores(String key, double min, double max) {try (Jedis jedis = getJedis()) {return jedis.zrangeByScoreWithScores(key, min, max);}}/*** 升序查询指定分数闭区间的元素,并指定偏移量,带着分数*/public Set<Tuple> zrangeByScoreWithScores(String key, double min, double max, int offset, int size) {try (Jedis jedis = getJedis()) {return jedis.zrangeByScoreWithScores(key, min, max, offset, size);}}/*** 降序查询指定分数闭区间的元素*/public Set<String> zrevrangebyscore(String key, double max, double min) {try (Jedis jedis = getJedis()) {return jedis.zrevrangeByScore(key, max, min);}}/*** 降序查询指定分数闭区间的元素,并指定偏移量*/public Set<String> zrevrangebyscore(String key, double max, double min, int offset, int size) {try (Jedis jedis = getJedis()) {return jedis.zrevrangeByScore(key, max, min, offset, size);}}/*** 降序查询指定分数闭区间的元素,并带着分数*/public Set<Tuple> zrevrangeByScoreWithScores(String key, double max, double min) {try (Jedis jedis = getJedis()) {return jedis.zrevrangeByScoreWithScores(key, max, min);}}/*** 降序查询指定分数闭区间的元素,并指定偏移量,带着分数*/public Set<Tuple> zrevrangeByScoreWithScores(String key, double max, double min, int offset, int size) {try (Jedis jedis = getJedis()) {return jedis.zrevrangeByScoreWithScores(key, min, max, offset, size);}}/*** 有序集合中指定删除一或多个元素*/public Long zrem(String key, String... member) {try (Jedis jedis = getJedis()) {return jedis.zrem(key, member);}}/*** 分数升序排名时,删除指定索引区间的元素*/public Long zremrangebyrank(String key, long start, long end) {try (Jedis jedis = getJedis()) {return jedis.zremrangeByRank(key, start, end);}}/*** 分数升序排名时,删除指定分数区间的元素*/public Long zremrangeByScore(String key, long min, long max) {try (Jedis jedis = getJedis()) {return jedis.zremrangeByScore(key, min, max);}}/*** 查询有序集合中某元素的分数*/public Double zscore(String key, String member) {try (Jedis jedis = getJedis()) {return jedis.zscore(key, member);}}/*** 给有序集合中某元素的分数增加(正数)或减少(负数)*/public Double zincrby(String key, double score, String member) {try (Jedis jedis = getJedis()) {return jedis.zincrby(key, score, member);}}/*######################## lock 相关 #######################*//*** 获取一把锁*/public boolean lock(String key, String lockValue, int expire) {if (key == null || lockValue == null) {return false;}try (Jedis jedis = getJedis()) {List<String> args = new ArrayList<>();args.add(lockValue);args.add(String.valueOf(expire));Object res = jedis.eval(LOCK_LUA_SCRIPT, Collections.singletonList(key), args);return res != null && res.equals(OPERATE_SUCCESS);} catch (Exception e) {return false;}}/*** 获取一把锁*/public boolean lock(String key, String lockValue, long expire) {if (key == null || lockValue == null) {return false;}try (Jedis jedis = getJedis()) {List<String> args = new ArrayList<>();args.add(lockValue);args.add(String.valueOf(expire));Object res = jedis.eval(LOCK_LUA_SCRIPT, Collections.singletonList(key), args);return res != null && res.equals(OPERATE_SUCCESS);} catch (Exception e) {return false;}}public boolean releaseLock(String key, String lockValue) {if (key == null || lockValue == null) {return false;}try (Jedis jedis = getJedis()) {Object res = jedis.eval(UNLOCK_LUA_SCRIPT, Collections.singletonList(key), Collections.singletonList(lockValue));return res != null && res.equals(OPERATE_SUCCESS);} catch (Exception e) {return false;}}/*** 私有化构造器,不让实例化对象*/public RedisUtils(final GenericObjectPoolConfig poolConfig, final String host, int port, int timeout, final String password, int database) {this.jedisPool = new JedisPool(poolConfig, host, port, timeout, password, database);}
}
spring.factories
org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.wuhao.redis.config.RedisConfiguration
pom.xml
<?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><groupId>com.wuhao</groupId><artifactId>redis-spring-boot-starter</artifactId><version>1.0-SNAPSHOT</version><properties><revision>2.0.2.RELEASE</revision><redis.revision>2.9.0</redis.revision><maven.compiler.source>8</maven.compiler.source><maven.compiler.target>8</maven.compiler.target><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding></properties><dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId><version>${revision}</version></dependency><dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId><version>${redis.revision}</version></dependency></dependencies></project>
对starter打jar包
先clean,再install安装到本地仓库
外部引用
pom文件加入依赖的starter的jar包
配置文件填写redis的配置信息
注入依赖redis工具类,写业务代码