Docker · Spring Boot · Kotlin · 微服务SpringBoot极简教程 · Spring Boot JVM · Java虚拟机原理 · JVM上语言·框架· 生态系统

Spring Boot之集成Redis(二):集成Redis

2020-10-31  本文已影响0人  狄仁杰666

前言

来啦老铁!

笔者学习Spring Boot有一段时间了,附上Spring Boot系列学习文章,欢迎取阅、赐教:

  1. 5分钟入手Spring Boot;
  2. Spring Boot数据库交互之Spring Data JPA;
  3. Spring Boot数据库交互之Mybatis;
  4. Spring Boot视图技术;
  5. Spring Boot之整合Swagger;
  6. Spring Boot之junit单元测试踩坑;
  7. 如何在Spring Boot中使用TestNG;
  8. Spring Boot之整合logback日志;
  9. Spring Boot之整合Spring Batch:批处理与任务调度;
  10. Spring Boot之整合Spring Security: 访问认证;
  11. Spring Boot之整合Spring Security: 授权管理;
  12. Spring Boot之多数据库源:极简方案;
  13. Spring Boot之使用MongoDB数据库源;
  14. Spring Boot之多线程、异步:@Async;
  15. Spring Boot之前后端分离(一):Vue前端;
  16. Spring Boot之前后端分离(二):后端、前后端集成;
  17. Spring Boot之前后端分离(三):登录、登出、页面认证;
  18. Spring Boot之面向切面编程:Spring AOP;
  19. Spring Boot之集成Redis(一):Redis初入门;

在上一篇文章Spring Boot之集成Redis(一):Redis初入门中,我们初步入门了Redis,熟悉了Redis的安装、配置、本数据类型以及基本操作。今天,我们一起来尝试在Spring Boot项目中集成Redis,一起在Spring Boot完成一些Redis基本操作吧!

项目代码已上传Git Hub仓库,欢迎取阅:

基本步骤

  1. 安装Redis依赖;
  2. 配置application.properties;
  3. 使用StringRedisTemplate操作Redis;

1. 安装Redis依赖;

在项目的pom.xml文件内的dependencies节点内添加redis依赖:

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
记得安装一下依赖:
mvn install -Dmaven.test.skip=true -Dmaven.wagon.http.ssl.insecure=true -Dmaven.wagon.http.ssl.allowall=true

2. 配置application.properties;

这里作用主要是配置Redis服务端的连接,配置如下:

#Redis服务端的host和port
spring.redis.host=127.0.0.1
spring.redis.port=6379
#Redis服务端的密码
spring.redis.password=Redis!123
#Redis最大连接数
spring.redis.pool.max-active=8
#Redis连接超时时间,单位 ms(毫秒)
spring.redis.timeout=5000

其中spring.redis.pool.max-active指定了Spring Boot应用的最大连接数,若设置为0,则表示无限制。

3. 使用StringRedisTemplate操作Redis;

我的思路是创建一个API,在该API内使用Redis的基本命令,进而演示在Spring Boot项目中与Redis的交互过程。

(我们先来演示Redis数据类型为String的)

1). 创建controller包,并在包内创建RedisStringController类;
2). 创建domain包,并创建实体类RedisStringCache,用于声明Redis String缓存对象格式;

代码如下:

package com.github.dylanz666.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.stereotype.Component;

import java.io.Serializable;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@NoArgsConstructor
@AllArgsConstructor
@Data
@Component
public class RedisStringCache implements Serializable {
    private static final long serialVersionUID = 1L;

    private String key;
    private String value;

    @Override
    public String toString() {
        return "{" +
                "\"key\":\"" + key + "\"," +
                "\"value\":" + value + "" +
                "}";
    }
}
3). 在RedisStringController类内添加演示用的API,代码如下:
package com.github.dylanz666.controller;

import com.github.dylanz666.domain.RedisStringCache;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.web.bind.annotation.*;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@RestController
@RequestMapping("/api/cache")
public class RedisStringController {
    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    @PostMapping("/string")
    public @ResponseBody RedisStringCache redisStringCache(@RequestBody RedisStringCache redisStringCache) {
        String key = redisStringCache.getKey();
        String value = redisStringCache.getValue();

        stringRedisTemplate.opsForValue().set(key, value);
        String cachedValue = stringRedisTemplate.opsForValue().get(key);

        RedisStringCache cached = new RedisStringCache();
        cached.setKey(key);
        cached.setValue(cachedValue);
        return cached;
    }
}

项目整体结构:

项目整体结构

上述步骤完成后,我们开始来做演示:

(1). 启动Redis服务端;
启动Redis服务端
(2). 启动Spring Boot应用;
启动Spring Boot应用
(3). 调用API进行Redis交互演示;

请求API:http://127.0.0.1:8080/api/cache/string

请求API
(4). 通过redis-cli方式,再次验证是否缓存成功;
再次验证是否缓存成功

可见,我们已在Spring Boot项目中与Redis服务端交互成功啦!

stringRedisTemplate.opsForValue().set(key, value);

上面这一行代码,相当于redis-cli连接Redis服务端方式的 set key value 操作;

stringRedisTemplate.opsForValue().get(key);

上面这一行代码,相当于redis-cli连接Redis服务端方式的 get key 操作;

接下来,我们一起来尝试在Spring Boot项目中做更多的Redis基本操作!

(演示Redis数据类型为hash的)

1). domain包内创建RedisHashCache实体类,用于声明Redis hash缓存对象格式;
package com.github.dylanz666.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.stereotype.Component;

import java.io.Serializable;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@NoArgsConstructor
@AllArgsConstructor
@Data
@Component
public class RedisHashCache implements Serializable {
    private static final long serialVersionUID = 1L;

    private String key;
    private String field;
    private String value;

    @Override
    public String toString() {
        return "{" +
                "\"key\":\"" + key + "\"," +
                "\"field\":\"" + field + "\"," +
                "\"value\":" + value + "" +
                "}";
    }
}
2). RedisStringController内编写演示API:
@PostMapping("/hash")
public @ResponseBody RedisHashCache redisHashCache(@RequestBody RedisHashCache redisHashCache) {
    String key = redisHashCache.getKey();
    String field = redisHashCache.getField();
    String value = redisHashCache.getValue();

    stringRedisTemplate.opsForHash().put(key, field, value);
    String cachedValue = Objects.requireNonNull(stringRedisTemplate.opsForHash().get(key, field)).toString();

    RedisHashCache cached = new RedisHashCache();
    cached.setKey(key);
    cached.setField(field);
    cached.setValue(cachedValue);
    return cached;
}
stringRedisTemplate.opsForHash().put(key, field, value);

上面这行代码等同于redis-cli中使用命令:hset key field value;

stringRedisTemplate.opsForHash().get(key, field);

上面这行代码等同于redis-cli中使用命令:hget key field;

(3). 调用API进行Redis交互演示;

请求API:http://127.0.0.1:8080/api/cache/hash

请求API

(演示Redis数据类型为list的)

1). domain包内创建RedisListCache实体类,用于声明Redis list缓存对象格式;
package com.github.dylanz666.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.stereotype.Component;

import java.io.Serializable;
import java.util.List;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@NoArgsConstructor
@AllArgsConstructor
@Data
@Component
public class RedisListCache implements Serializable {
    private static final long serialVersionUID = 1L;

    private String key;
    private List<String> list;

    @Override
    public String toString() {
        return "{" +
                "\"key\":\"" + key + "\"," +
                "\"list\":" + list + "" +
                "}";
    }
}
2). RedisStringController内编写演示API:
@PostMapping("/list")
public @ResponseBody RedisListCache redisListCache(@RequestBody RedisListCache redisListCache) {
    String key = redisListCache.getKey();
    List<String> list = redisListCache.getList();

    stringRedisTemplate.opsForList().leftPushAll(key, list);
    List<String> cachedList = stringRedisTemplate.opsForList().range(key, 0, -1);

    RedisListCache cached = new RedisListCache();
    cached.setKey(key);
    cached.setList(cachedList);
    return cached;
}
stringRedisTemplate.opsForList().leftPushAll(key, list);

上面这行代码等同于redis-cli中使用命令:lpush key value...;

stringRedisTemplate.opsForList().range(key, 0, -1);

上面这行代码等同于redis-cli中使用命令:lrange key 0 -1;

(3). 调用API进行Redis交互演示;

请求API:http://127.0.0.1:8080/api/cache/list

请求API

(演示Redis数据类型为set的)

1). domain包内创建RedisSetCache实体类,用于声明Redis set缓存对象格式;
package com.github.dylanz666.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.stereotype.Component;

import java.io.Serializable;
import java.util.Arrays;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@NoArgsConstructor
@AllArgsConstructor
@Data
@Component
public class RedisSetCache implements Serializable {
    private static final long serialVersionUID = 1L;

    private String key;
    private String[] sets;

    @Override
    public String toString() {
        return "{" +
                "\"key\":\"" + key + "\"," +
                "\"sets\":" + Arrays.toString(sets) + "" +
                "}";
    }
}
2). RedisStringController内编写演示API:
@PostMapping("/set")
public @ResponseBody RedisSetCache redisSetCache(@RequestBody RedisSetCache redisSetCache) {
    String key = redisSetCache.getKey();
    String[] sets = redisSetCache.getSets();

    stringRedisTemplate.opsForSet().add(key, sets);
    Set<String> cacheSets = stringRedisTemplate.opsForSet().members(key);

    RedisSetCache cached = new RedisSetCache();
    cached.setKey(key);
    assert cacheSets != null;
    cached.setSets(cacheSets.toArray(sets));
    return cached;
}
stringRedisTemplate.opsForSet().add(key, sets);

上面这行代码等同于redis-cli中使用命令:sadd key value...;

stringRedisTemplate.opsForSet().members(key);

上面这行代码等同于redis-cli中使用命令:smembers key;

(3). 调用API进行Redis交互演示;

请求API:http://127.0.0.1:8080/api/cache/set

请求API

(演示Redis数据类型为zset的)

1). domain包内创建RedisZsetCache实体类,用于声明Redis zset缓存对象格式;
package com.github.dylanz666.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.stereotype.Component;

import java.io.Serializable;
import java.util.Set;

/**
 * @author : dylanz
 * @since : 10/28/2020
 */
@NoArgsConstructor
@AllArgsConstructor
@Data
@Component
public class RedisZsetCache implements Serializable {
    private static final long serialVersionUID = 1L;

    private String key;
    private String value;
    private double score;
    private Set<String> zset;


    @Override
    public String toString() {
        return "{" +
                "\"key\":\"" + key + "\"," +
                "\"value\":\"" + value + "\"," +
                "\"score\":\"" + score + "\"," +
                "\"zset\":" + zset + "" +
                "}";
    }
}
2). RedisStringController内编写演示API:
@PostMapping("/zset")
public @ResponseBody RedisZsetCache redisZsetCache(@RequestBody RedisZsetCache redisZsetCache) {
    String key = redisZsetCache.getKey();
    String value = redisZsetCache.getValue();
    double score = redisZsetCache.getScore();

    stringRedisTemplate.opsForZSet().add(key, value, score);

    Set<String> cachedZset = stringRedisTemplate.opsForZSet().rangeByScore(key, score, score);

    RedisZsetCache cached = new RedisZsetCache();
    cached.setKey(key);
    cached.setValue(value);
    cached.setScore(score);
    cached.setZset(cachedZset);
    return cached;
}
stringRedisTemplate.opsForZSet().add(key, value, score);

上面这行代码等同于redis-cli中使用命令:zadd key score value;

stringRedisTemplate.opsForZSet().rangeByScore(key, score, score);

上面这行代码等同于redis-cli中使用命令:zrangebyscore key min max;

(3). 调用API进行Redis交互演示;

请求API:http://127.0.0.1:8080/api/cache/zset

请求API

最后,来演示设置一个会过期的Redis缓存(演示缓存2分钟):

@PostMapping("/expire/string")
public @ResponseBody RedisStringCache redisStringCacheWithExpireTime(@RequestBody RedisStringCache redisStringCache) {
    String key = redisStringCache.getKey();
    String value = redisStringCache.getValue();

    stringRedisTemplate.opsForValue().set(key, value, Duration.ofMinutes(2));
    String cachedValue = stringRedisTemplate.opsForValue().get(key);

    RedisStringCache cached = new RedisStringCache();
    cached.setKey(key);
    cached.setValue(cachedValue);
    return cached;
}
缓存2分钟

通过这样的Redis操作,我们设置了一个2分钟后失效的String类型的Redis缓存,并且的确2分钟后缓存失效了!

更多操作和redis接口,可直接使用stringRedisTemplate,获取代码建议:
redis接口

以上是我们使用StringRedisTemplate来与Redis进行交互的过程,涉及存、取数据,读者可自行根据StringRedisTemplate提供的接口,对Redis进行增删改查。

实际使用场景中,通常是在第一次存到其他数据库时,会缓存到Redis,并设置一定的缓存过期时间,而后续的请求会先从Redis缓存中获取,减少数据库访问次数,降低数据库服务器的压力!

使用StringRedisTemplate来与Redis进行交互的过程是正确、灵活的,这一点毋庸置疑,但整体代码还是比较多的,略显臃肿,其实有更简约的方式来操作Redis,这里剧透一下:

下一篇文章我将介绍基于Spring Cache方式操作Redis,操作Redis缓存也能用注解的方式,敬请期待!

如果本文对您有帮助,麻烦点赞、关注!

谢谢!

上一篇下一篇

猜你喜欢

热点阅读