springboot 2.0 自定義redis自動裝配


首先創建maven項目 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">

	<parent>
		<groupId>com.tuling</groupId>
		<artifactId>tuling-springboot</artifactId>
		<version>0.0.1-SNAPSHOT</version>
	</parent>

	<modelVersion>4.0.0</modelVersion>

	<groupId>com.hnnd</groupId>
	<artifactId>redisoper-spring-boot-autoconfiguration</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<packaging>jar</packaging>

	<name>redisoper-spring-boot-autoconfiguration</name>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
		<java.version>1.8</java.version>
	</properties>

	<dependencies>
		<dependency>
			<groupId>org.springframework.data</groupId>
			<artifactId>spring-data-redis</artifactId>
			<version>2.0.9.RELEASE</version>
		</dependency>

		<dependency>
			<groupId>redis.clients</groupId>
			<artifactId>jedis</artifactId>
			<version>2.9.0</version>
		</dependency>

		<!-- 自動配置的依賴-->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-autoconfigure</artifactId>
		</dependency>

		<!-- 實體類映射屬性文件需要的-->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-configuration-processor</artifactId>
			<optional>true</optional>
		</dependency>

		<dependency>
			<groupId>com.google.guava</groupId>
			<artifactId>guava</artifactId>
			<version>18.0</version>
		</dependency>

		<dependency>
			<groupId>org.projectlombok</groupId>
			<artifactId>lombok</artifactId>
			<optional>true</optional>
			<version>1.16.18</version>
		</dependency>

	</dependencies>


</project>

  自定義配置工程截圖:

RedisOperAutoConfiguration類 是核心類

package com.redisoper;

import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.JedisPoolConfig;
import redis.clients.jedis.JedisShardInfo;
import redis.clients.jedis.ShardedJedisPool;
import redis.clients.util.Hashing;
import redis.clients.util.Sharded;

import java.util.List;

/**
 * redis操作配置類
 * Created by Administrator on 2018/8/8.
 */
@Configuration  //開啟配置
@EnableConfigurationProperties(value = {RedisConfigProperties.class,ShardedRedisConfigProperties.class})//開啟使用映射實體對象
@ConditionalOnClass(value = {JedisPoolConfig.class, JedisPool.class})//存在JedisPoolConfig JedisPool時初始化該配置類
@Slf4j
public class RedisOperAutoConfiguration {

    @Autowired
    private RedisConfigProperties redisConfigProperties;

    @Autowired
    private ShardedRedisConfigProperties shardedRedisConfigProperties;

    public RedisOperAutoConfiguration(RedisConfigProperties redisConfigProperties,ShardedRedisConfigProperties shardedRedisConfigProperties) {
        this.redisConfigProperties = redisConfigProperties;
        this.shardedRedisConfigProperties = shardedRedisConfigProperties;
    }
  
  
   // 此處是redis集群配置,單機版可忽略 @Bean @ConditionalOnMissingBean(ShardedJedisPool.class) @ConditionalOnProperty(prefix = "spring.ha.redis",name = "USEHA",havingValue ="false") //配置文件是否存在spring.ha.redis的配置 public JedisPool jedisPool() { log.info("加載jedisPool"); JedisPoolConfig jedisPoolConfig = new JedisPoolConfig(); jedisPoolConfig.setMaxTotal(redisConfigProperties.getMaxTotal()); jedisPoolConfig.setMaxIdle(redisConfigProperties.getMaxIdel()); jedisPoolConfig.setMinIdle(redisConfigProperties.getMinIdel()); jedisPoolConfig.setTestOnBorrow(redisConfigProperties.isTestOnBorrow()); jedisPoolConfig.setTestOnReturn(redisConfigProperties.isTestOnRetrun()); JedisPool jedisPool = new JedisPool(jedisPoolConfig,redisConfigProperties.getRedis_server_ip(),redisConfigProperties.getRedis_server_port(),1000*1,redisConfigProperties.getRedis_pass()); return jedisPool; }
  // 此處是集群配置 單機版忽略 @Bean @ConditionalOnMissingBean(JedisPool.class) @ConditionalOnProperty(prefix = "spring.ha.redis",name = "USEHA",havingValue ="true") // 配置文件是否存在spring.ha.redis public ShardedJedisPool shardedJedisPool() { log.info("shardedJedisPool"); JedisPoolConfig jedisPoolConfig = new JedisPoolConfig(); jedisPoolConfig.setMaxIdle(shardedRedisConfigProperties.getMaxIdel()); jedisPoolConfig.setMaxTotal(shardedRedisConfigProperties.getMaxTotal()); jedisPoolConfig.setMinIdle(shardedRedisConfigProperties.getMinIdel()); jedisPoolConfig.setTestOnReturn(shardedRedisConfigProperties.isTestOnRetrun()); jedisPoolConfig.setTestOnBorrow(shardedRedisConfigProperties.isTestOnBorrow()); jedisPoolConfig.setBlockWhenExhausted(true); JedisShardInfo jedisShardInfo = new JedisShardInfo(shardedRedisConfigProperties.getRedis_server_ip1(),shardedRedisConfigProperties.getRedis_server_port1()); jedisShardInfo.setPassword(shardedRedisConfigProperties.getRedis_pass1()); JedisShardInfo jedisShardInfo2 = new JedisShardInfo(shardedRedisConfigProperties.getRedis_server_ip2(),shardedRedisConfigProperties.getRedis_server_port2()); jedisShardInfo2.setPassword(shardedRedisConfigProperties.getRedis_pass2()); List<JedisShardInfo> shardInfos = Lists.newArrayList(); shardInfos.add(jedisShardInfo); shardInfos.add(jedisShardInfo2); ShardedJedisPool shardingRedisPool = new ShardedJedisPool(jedisPoolConfig,shardInfos, Hashing.MURMUR_HASH, Sharded.DEFAULT_KEY_TAG_PATTERN); return shardingRedisPool; } @Bean @ConditionalOnBean(JedisPool.class) // 容器中存在JedisPool類則初始化該bean public RedisOperClient redisOperClient() { RedisOperClient redisOperClient = new RedisOperClient(jedisPool()); return redisOperClient; } @Bean @ConditionalOnBean(ShardedJedisPool.class) //一樣的道理 public ShardedRedisOperClient shardedRedisOperClient() { ShardedRedisOperClient shardedRedisOperClient = new ShardedRedisOperClient(shardedJedisPool()); return shardedRedisOperClient; } }
@Configuration:這個配置就不用多做解釋了,我們一直在使用
@EnableConfigurationProperties:這是一個開啟使用配置參數的注解,value值就是我們配置實體參數映射的ClassType,將配置實體作為配置來源。
SpringBoot內置條件注解
有關@ConditionalOnXxx相關的注解這里要系統的說下,因為這個是我們配置的關鍵,根據名稱我們可以理解為具有Xxx條件,當然它實際的意義也是如此,條件注解是一個系列,下面我們詳細做出解釋
@ConditionalOnBean:當SpringIoc容器內存在指定Bean的條件
@ConditionalOnClass:當SpringIoc容器內存在指定Class的條件
@ConditionalOnExpression:基於SpEL表達式作為判斷條件
@ConditionalOnJava:基於JVM版本作為判斷條件
@ConditionalOnJndi:在JNDI存在時查找指定的位置
@ConditionalOnMissingBean:當SpringIoc容器內不存在指定Bean的條件
@ConditionalOnMissingClass:當SpringIoc容器內不存在指定Class的條件
@ConditionalOnNotWebApplication:當前項目不是Web項目的條件
@ConditionalOnProperty:指定的屬性是否有指定的值
@ConditionalOnResource:類路徑是否有指定的值
@ConditionalOnSingleCandidate:當指定Bean在SpringIoc容器內只有一個,或者雖然有多個但是指定首選的Bean
@ConditionalOnWebApplication:當前項目是Web項目的條件
以上注解都是元注解@Conditional演變而來的,根據不用的條件對應創建以上的具體條件注解。

  RedisConfigProperties類:

package com.redisoper;


import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;

/**
 * 單機redis配置
 * Created by Administrator on 2018/8/8.
 */
@ConfigurationProperties("spring.redis")
@Data
public class RedisConfigProperties {

    /**
     * jedispool中jedis最大的可用實例
     */

    private Integer maxTotal = 50;

    /**
     * jedispool中jedis 最大空閑數
     */
    private Integer maxIdel = 20;

    /**
     * jedispool中最小空閑數
     */
    private Integer minIdel = 5;

    /**
     * 從連接池中借出的jedis都會經過測試
     */
    private boolean testOnBorrow = true;

    /**
     * 返回jedis到池中Jedis 實例都會經過測試
     */
    private boolean testOnRetrun = false;
    /**
     * IP
     */
    private String redis_server_ip;
    /**
     * port
     */
    private Integer redis_server_port;
    /**
     * 連接redis的password
     */
    private String redis_pass;

}

  RedisOperClient類:

package com.redisoper;

import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;

import java.util.Collections;

/**
 * redis操作類
 * Created by Administrator on 2018/8/8.
 */
@Slf4j
public class RedisOperClient {

    private JedisPool jedisPool;

    public RedisOperClient(JedisPool jedisPool) {
        this.jedisPool = jedisPool;
    }

    /**
     * set 操作
     *
     * @param key   鍵
     * @param value 值
     * @return result
     */
    public String set(String key, String value) {
        Jedis jedis = null;
        String result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.set(key, value);
        } catch (Exception e) {
            log.error("set key:{},value:{},error:{}", key, value, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * list接口存儲用作消息隊列
     *
     * @param queueName 隊列名稱
     * @param value     消息
     * @return 成功
     */
    public long lpush(String queueName, String value) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.lpush(queueName, value);
        } catch (Exception e) {
            log.error("lpush key:{},value:{},異常:{}", queueName, value, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 判斷是否為空
     *
     * @param queueName 隊列名稱
     * @return true|false
     */
    public boolean isEmptyQueue(String queueName) {

        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            if (jedis.llen(queueName).intValue() == 0) {
                return false;
            }
            return true;
        } catch (Exception e) {
            log.error("isEmptyQueue key:{},異常:{}", queueName, e);
            jedisPool.returnResource(jedis);
            return false;
        } finally {
            jedisPool.returnResource(jedis);
        }
    }

    /**
     * 出隊操作
     *
     * @param queueName 隊列名稱
     * @return 隊首消息
     */
    public String rpop(String queueName) {
        Jedis jedis = null;
        String result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.rpop(queueName);
        } catch (Exception e) {
            log.error("rpop key:{},異常:{}", queueName, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    public String set(String key, String value, String set_if_not_exits, String set_with_expire_time, int expire) {
        Jedis jedis = null;
        String result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.set(key, value, set_if_not_exits, set_with_expire_time, expire);
        } catch (Exception e) {
            log.error("set key:{},value:{},set_if_not_exits:{},set_with_expire_time:{},expire:{},error:{}", key, value, set_if_not_exits, set_with_expire_time, expire, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * setex 操作
     *
     * @param key        key 鍵
     * @param expireTime 過期時間(m)
     * @param value      值
     * @return String
     */
    public String setex(String key, int expireTime, String value) {
        Jedis jedis = null;
        String result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.setex(key, expireTime, value);
        } catch (Exception e) {
            log.error("setex key:{},expireTime:{},value:{},error:{}", key, expireTime, value, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * get 操作
     *
     * @param key 鍵
     * @return value
     */
    public String get(String key) {
        Jedis jedis = null;
        String result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.get(key);
        } catch (Exception e) {
            log.error("get key:{}error:{}", key, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 讓key失效
     *
     * @param key        鍵
     * @param expireTime 失效時間
     * @return Long
     */
    public Long expire(String key, int expireTime) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.expire(key, expireTime);
        } catch (Exception e) {
            log.error("expire key:{},expireTime:{},error:{}", key, expireTime, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 判斷key是否存在
     *
     * @param key 鍵
     * @return boolean
     */
    public boolean isExists(String key) {
        Jedis jedis = null;
        boolean result = false;
        try {
            jedis = jedisPool.getResource();
            result = jedis.exists(key);
        } catch (Exception e) {
            log.error("isExists key:{},error:{}", key, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }


    /**
     * 自增
     *
     * @param key key
     * @return Long
     */
    public Long incr(String key) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.incr(key);
        } catch (Exception e) {
            log.error("incr key:{},error:{}", key, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 指定步長增加
     *
     * @param key  鍵
     * @param step 步長
     * @return Long
     */
    public Long incrBy(String key, Integer step) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.incrBy(key, step);
        } catch (Exception e) {
            log.error("incrBy key:{},step:{},error:{}", key, step, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 遞減
     *
     * @param key key
     * @return Long
     */
    public Long decr(String key) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.decr(key);
        } catch (Exception e) {
            log.error("decr key:{},error:{}", key, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    /**
     * 指定步長遞減
     *
     * @param key  鍵
     * @param step 步長
     * @return Long
     */
    public Long decrBy(String key, Integer step) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.incrBy(key, step);
        } catch (Exception e) {
            log.error("decrBy key:{},step:{},error:{}", key, step, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }

    public Long del(String key) {
        Jedis jedis = null;
        Long result = null;
        try {
            jedis = jedisPool.getResource();
            result = jedis.del(key);
        } catch (Exception e) {
            log.error("del key:{},error:{}", key, e);
            jedisPool.returnResource(jedis);
            return result;
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;
    }


    public long eval(String script, String lock, String lockValue) {
        Jedis jedis = null;
        //刪除鎖失敗
        long result = 0;
        try {
            jedis = jedisPool.getResource();
            result = (Long) jedis.eval(script, Collections.singletonList(lock), Collections.singletonList(lockValue));
            return result;
        } catch (Exception e) {
            log.error("eval script:{},lock:{},lockValue:{},error:{}", script, lock, lockValue, e);
            jedisPool.returnResource(jedis);
        } finally {
            jedisPool.returnResource(jedis);
        }
        return result;

    }
}

  

至此結束配置類,然后把這個項目打包程jar。

接着新建starter maven 工程:

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.hnnd</groupId>
	<artifactId>redisoper-springboot-starter</artifactId>
	<version>0.0.1-SNAPSHOT</version>
	<packaging>jar</packaging>

	<name>redisoper-springboot-starter</name>

	<parent>
		<groupId>com.tuling</groupId>
		<artifactId>tuling-springboot</artifactId>
		<version>0.0.1-SNAPSHOT</version> <!-- lookup parent from repository -->
	</parent>

	<properties>
		<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
		<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
		<java.version>1.8</java.version>
	</properties>

	<dependencies>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter</artifactId>
		</dependency>

          <!-- 依賴剛剛自定義的配置jar--> <dependency> <groupId>com.hnnd</groupId> <artifactId>redisoper-spring-boot-autoconfiguration</artifactId> <version>0.0.1-SNAPSHOT</version> </dependency> </dependencies> </project>

  application.properties:

spring.redis.redis-server-ip=localhost
spring.redis.redis-server-port=6379
spring.redis.redis-pass=

 

  

至此starter 工程 就可以直接使用在autoConfiguration工程自己配置的RedisOperClient 類 來操作redis,如果您把starter工程jar 包放在公司私服,那么同事就都能用你配置好的組件。多爽? 你就是傳說的架構師。

歡迎來群 592495675 暢聊技術。

 
        

 


免責聲明!

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



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