写在前面

本文将在第二篇《整合Swagger-UI实现在线API文档》的基础上整合Redis,实现数据缓存这一功能。

Redis简介

Redis是一个使用C语言开发的高性能键值对数据库,可用于数据缓存,以实现大量数据的高并发负载访问。

点击 这里 下载Redis,选择3.2.100的版本进行下载:

下载之后解压到指定目录:

接着打开终端,切换到上述解压目录,执行redis启动命令:

1
redis-server.exe redis.windows.conf

可以看到此时redis就已经启动成功了。

整合Redis

第一步,复制一份shop-swagger-ui源码,将其名字修改为shop-redis,然后对应包和文件中的信息也记得修改,本篇后续所有操作均在shop-redis这一Module中进行。

第二步,在shop-redis的POM文件中新增如下依赖:

1
2
3
4
5
<!--redis依赖配置-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

第三步,往application.yml配置文件中在指定位置处新增如下配置信息。首先在spring节点下新增如下配置信息:

1
2
3
4
5
6
7
8
9
10
11
12
13
spring:
redis:
host: localhost # Redis服务器地址
database: 2 # Redis数据库索引(默认为0)
port: 6379 # Redis服务器连接端口
password: envy123 # Redis服务器连接密码(默认为空)
jedis:
pool:
max-active: 8 # 连接池最大连接数(使用负值表示没有限制)
max-wait: -1ms # 连接池最大阻塞等待时间(使用负值表示没有限制)
max-idle: 8 # 连接池中的最大空闲连接
min-idle: 0 # 连接池中的最小空闲连接
timeout: 3000ms # 连接超时时间(毫秒)

然后在根节点下添加Redis自定义key的相关配置信息:

1
2
3
4
5
6
7
# 自定义redis的key
redis:
key:
prefix:
authCode: "portal:authCode:"
expire:
authCode: 120 # 验证码超期时间,单位秒

第四步,在service包内定义一个名为RedisService的接口,用于定义一些常用的Redis操作,此处我们让对象和数组都以JSON形式进行存储:

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
/**
* Redis操作
* 对象和数组都以JSON形式进行存储
*/
public interface RedisService {
/**
* 存储数据
*/
void set(String key,String value);

/**
* 获取数据
*/
String get(String key);

/**
* 设置超期时间
*/
boolean expire(String key,long expire);

/**
* 删除数据
*/
void remove(String key);

/**
* 自增操作
* @param delta 自增步长
*/
Long increment(String key,long delta);
}

第五步,在impl包内定义一个名为RedisServiceImpl的类,这个类需要实现RedisService接口,并重写其中的方法:

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
@Service
public class RedisServiceImpl implements RedisService {
@Autowired
private StringRedisTemplate stringRedisTemplate;

@Override
public void set(String key, String value) {
stringRedisTemplate.opsForValue().set(key,value);
}

@Override
public String get(String key) {
return stringRedisTemplate.opsForValue().get(key);
}

@Override
public boolean expire(String key, long expire) {
return stringRedisTemplate.expire(key,expire, TimeUnit.SECONDS);
}

@Override
public void remove(String key) {
stringRedisTemplate.delete(key);
}

@Override
public Long increment(String key, long delta) {
return stringRedisTemplate.opsForValue().increment(key,delta);
}
}

第六步,这里我们以会员发送验证码为例来介绍如何使用Redis。在service包内定义一个名为UmsMemberService的接口,用于定义会员管理相关的接口方法:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
/**
* 会员管理Service
*/
public interface UmsMemberService {
/**
* 根据手机号生成验证码
*/
CommonResult generateAuthCode(String telephone);

/**
* 判断验证码和手机号是否匹配
*/
CommonResult verifyAuthCode(String telephone,String authCode);
}

第七步,在impl包内定义一个名为UmsMemberServiceImpl的类,这个类需要实现UmsMemberService接口,并重写其中的方法:

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
/**
* 会员管理Service实现类
*/
@Service
public class UmsMemberServiceImpl implements UmsMemberService {
@Autowired
private RedisService redisService;
@Value("${redis.key.prefix.authCode}")
private String REDIS_KEY_PREFIX_AUTH_CODE;
@Value("${redis.key.expire.authCode}")
private Long AUTH_CODE_EXPIRE_SECONDS;

@Override
public CommonResult generateAuthCode(String telephone) {
StringBuilder stringBuilder = new StringBuilder();
Random random = new Random();
for (int i = 0; i < 6; i++) {
stringBuilder.append(random.nextInt(10));
}
String authCode = stringBuilder.toString();
//验证码+手机号作为Key存储到Redis中
String redisKey = REDIS_KEY_PREFIX_AUTH_CODE + telephone;
redisService.set(redisKey,authCode);
redisService.expire(redisKey,AUTH_CODE_EXPIRE_SECONDS);
return CommonResult.success(authCode,"验证码获取成功");
}

@Override
public CommonResult verifyAuthCode(String telephone, String authCode) {
if(StringUtils.isEmpty(authCode)){
return CommonResult.failed("请输入验证码");
}
String redisKey = REDIS_KEY_PREFIX_AUTH_CODE + telephone;
String redisAuthCode = redisService.get(redisKey);
if(StringUtils.isEmpty(redisAuthCode)){
return CommonResult.failed("验证码已过期");
}
boolean result = authCode.equals(redisAuthCode);
if(result){
return CommonResult.success(null,"验证码校验成功");
}else {
return CommonResult.failed("验证码不正确");
}
}
}

第八步,在controller包内定义一个名为UmsMemberController的类,这是会员登录注册管理的Controller:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
/**
* 会员管理Controller
*/
@Api(tags = "UmsMemberController",description = "会员登录注册管理")
@RestController
@RequestMapping("/sso")
public class UmsMemberController {
@Autowired
private UmsMemberService umsMemberService;

@ApiOperation("获取验证码")
@GetMapping("/getAuthCode")
public CommonResult getAuthCode(@RequestParam @ApiParam("手机号")String telephone){
return umsMemberService.generateAuthCode(telephone);
}

@ApiOperation("校验验证码是否正确")
@PostMapping("/verifyAuthCode")
public CommonResult verifyAuthCode(@RequestParam @ApiParam("手机号")String telephone,@ApiParam("验证码")@RequestParam String authCode){
return umsMemberService.verifyAuthCode(telephone,authCode);
}
}

第九步,启动项目,访问Swagger-UI接口文档地址,即浏览器访问http://localhost:8080/swagger-ui.html链接,可以看到新的接口已经出现了:

之后测试获取验证码的接口,可以发现测试是通过的:

再来看一下校验验证码是否正确的接口,发现测试也是通过的:

这样本篇关于整合Redis实现数据缓存的学习就完成了,后续介绍如何整合SpringSecurity和JWT实现认证与授权这一功能。本篇笔记源码,可以点击 这里 进行阅读。