springboot搭建redis-cluster客户端

·  阅读 1678

上一篇文章介绍了如何搭建redis集群,现在我们搭建一个客户端去连接redis集群并使用它去操作redis集群。上一篇文章:搭建redis集群-超详细的配置

1. 初始化一个springboot项目

https://start.spring.io
复制代码

2. pom.xml添加依赖

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-redis</artifactId>
    <version>2.1.6.RELEASE</version>
</dependency>
<dependency>
    <groupId>redis.clients</groupId>
    <artifactId>jedis</artifactId>
    <version>3.1.0</version>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-configuration-processor</artifactId>
    <optional>true</optional>
</dependency>
复制代码

3. application.yml相关配置

jedis:
  cluster:
    nodes: 192.168.1.1:6379, 192.168.1.2:6379, 192.168.1.3:6379, 192.168.1.4:6379, 192.168.1.5:6379, 192.168.1.6:6379
    timeout: 3000
    pool:
      max-total: 800
      max-idle: 100
      min-idle: 50
      block-when-exhausted: true
      max-wait-millis: 1500
      test-on-borrow: false
      test-on-return: false
      test-while-idle: true
      time-between-eviction-runs-millis: 30000
      min_evictable_idle_time_millis: 1860000
      num_tests_per_eviction_run: 4
复制代码

4. 编写RedisClusterProperty.java

@Configuration
@ConfigurationProperties(prefix = "jedis.cluster")
public class RedisClusterProperty {

    /**
     * 节点列表
     */
    private List<String> nodes;

    /**
     * 连接过期时间
     */
    private Integer timeout;
}
复制代码

5. 编写RedisClusterPoolProperty.java

@Configuration
@ConfigurationProperties(prefix = "jedis.cluster.pool")
public class RedisClusterPoolProperty {

    /**
     * 池中最多能有几个连接,这个值跟并发量有关
     *
     * 假如一次命令平均耗时是10ms,那么一秒能执行100次命令
     * 业务要求的并发量达到1000
     * 则maxTotal = 1000 / 100 = 10
     */
    private Integer maxTotal;

    /**
     * 池中最多能有几个空闲连接
     *
     * 这个值设置和maxTotal相差无几,防止maxTotal和maxTotal相差太多而频繁创建和销毁连接
     */
    private Integer maxIdle;

    /**
     * 池中最小能有几个空闲连接
     */
    private Integer minIdle;

    /**
     * 当池中没有连接可用的时候,是否等待
     */
    private Boolean blockWhenExhausted;

    /**
     * 当池中没有连接可用的时候,最多能等待多久
     */
    private Integer maxWaitMillis;

    /**
     * 向池中拿连接的时候,是否会检测连接是否可用(ping)
     * 建议设置为false
     */
    private Boolean testOnBorrow;

    /**
     * 向池中归还连接的时候,是否会检测连接是否可用(ping)
     * 建议设置为false
     */
    private Boolean testOnReturn;

    /**
     * 是否开启空闲连接检测
     * 建议设置为true
     */
    private Boolean testWhileIdle;

    /**
     * 空闲资源的检测周期
     */
    private Integer timeBetweenEvictionRunsMillis;

    /**
     * 资源池中资源最小空闲时间,达到此值后空闲资源被移除 默认30分钟
     */
    private Long minEvictableIdleTimeMillis;

    /**
     * 做空闲资源检测时,每次的采样数 默认3个
     */
    private Integer numTestsPerEvictionRun;

    /**
     * 构建GenericObjectPoolConfig
     */
    @Bean
    public GenericObjectPoolConfig getGenericObjectPoolConfig() {
        GenericObjectPoolConfig poolConfig = new GenericObjectPoolConfig();
        poolConfig.setMaxTotal(maxTotal);
        poolConfig.setMaxIdle(maxIdle);
        poolConfig.setMinIdle(minIdle);
        poolConfig.setBlockWhenExhausted(blockWhenExhausted);
        poolConfig.setMaxWaitMillis(maxWaitMillis);
        poolConfig.setTestOnBorrow(testOnBorrow);
        poolConfig.setTestOnReturn(testOnReturn);
        poolConfig.setTestWhileIdle(testWhileIdle);
        poolConfig.setTimeBetweenEvictionRunsMillis(timeBetweenEvictionRunsMillis);
        poolConfig.setMinEvictableIdleTimeMillis(minEvictableIdleTimeMillis);
        poolConfig.setNumTestsPerEvictionRun(numTestsPerEvictionRun);
        return poolConfig;
    }

}
复制代码

6. 编写RedisService.java

@Service
public class RedisService {

    /**
     * redis集群节点参数
     */
    private RedisClusterProperty redisClusterProperty;

    /**
     * 连接池配置文件
     */
    private GenericObjectPoolConfig poolConfig;

    private JedisCluster jedisCluster;

    private Jedis jedis;

    /**
     * 构造函数
     * @param redisClusterProperty redis集群节点参数
     * @param poolConfig 连接池配置文件
     */
    public RedisService(RedisClusterProperty redisClusterProperty, GenericObjectPoolConfig poolConfig) {
        this.redisClusterProperty = redisClusterProperty;
        this.poolConfig = poolConfig;
    }

    /**
     * 初始化方法
     */
    @PostConstruct
    public void init() {

        Set<HostAndPort> hostAndPorts = new HashSet<>();

        List<String> nodes = redisClusterProperty.getNodes();
    
        if (CollectionUtils.isNotEmpty(nodes)) {
            if (nodes.size() == 1) {
                String[] hostAndPostStr = nodes.get(0).split(":");
                if (StringUtils.isNotBlank(hostAndPostStr[0]) && StringUtils.isNotBlank(hostAndPostStr[1])) {
                    jedis = new Jedis(hostAndPostStr[0], Integer.parseInt(hostAndPostStr[1]));
                }
            } else {
                for (String node : nodes) {
                    if (StringUtils.contains(node, ":")) {
                        String[] hostAndPostStr = node.split(":");
                        if (StringUtils.isNotBlank(hostAndPostStr[0]) && StringUtils.isNotBlank(hostAndPostStr[1])) {
                            hostAndPorts.add(new HostAndPort(hostAndPostStr[0], Integer.parseInt(hostAndPostStr[1])));
                        }
                    }
                }
            }
            this.jedisCluster = new JedisCluster(hostAndPorts, redisClusterProperty.getTimeout(), poolConfig);
        }
    }
    
    /**
     * redis集群的配置
     */
    @Bean
    public RedisClusterConfiguration redisClusterConfiguration() {

        RedisClusterConfiguration redisClusterConfiguration = new RedisClusterConfiguration();

        List<String> nodes = redisClusterProperty.getNodes();

        if (CollectionUtils.isNotEmpty(nodes)) {
            for (String node : nodes) {
                if (StringUtils.contains(node, ":")) {
                    String[] hostAndPostStr = node.split(":");
                    redisClusterConfiguration.addClusterNode(new RedisClusterNode(hostAndPostStr[0], Integer.parseInt(hostAndPostStr[1])));
                }
            }
        }

        return redisClusterConfiguration;
    }
    
    /**
     * 字符串:获取
     * 时间复杂度:O(1)
     */
    public String get(String key) {
        return jedisCluster.get(key);
    }
}
复制代码

7. 使用RedisService去连接redis集群

@Service
public class TestService {
    
    @Autowired
    private RedisService redisService;
    
    public String get(String key) {
        return redisService.get(key);
    }
}

复制代码
分类:
后端
标签:
分类:
后端
标签: