springboot整合redis实现发送短信验证码

springboot-整合redis实现发送短信验证码

用户登录时可以选择使用手机号加验证码的形式进行快速验证登录。
整体逻辑,用户输入手机号,点击发送验证码;后台收到手机号,生成指定位数的验证码,存入redis中(设定过期时间)并发送短信。若在过期时间内用户再次点击发送验证码按钮,现在redis中查询当前手机号是否有验证码缓存,有的话读取缓存中验证码更新过期时间并返回,否则生成新的验证码返回。

所需软件

  1. Redis-x64-3.2.100 (我是在windows本地的,远程也可以)
  2. 阿里云短信平台(需要付费, 后边有介绍)
  3. Spring Boot项目

Redis

本地搭建,使用redis客户端
线上搭建,使用redis服务器

Windows的Redis下载

解压到一个文件夹内
VJWKSA.png
编辑一个文本文件,内容为

1
redis-server  redis.windows.conf

将文本文件名称改为:startup.bat

双击 startup.bat 看到redis启动的标志图标即为成功了。

双击redis-cli.exe可以启动redis的客户端,查看当前redis中有什么。


Ali的短信平台

短信平台是阿里云的,需要付费购买服务,购买地址:
https://common-buy.aliyun.com/?spm=5176.8195934.907839.sms6.312c4183mzE9Yb&&commodityCode=newdysmsbag#/buy

付费完成后,首先申请短信签名和短信模板:https://help.aliyun.com/document_detail/55327.html?spm=a2c4g.11186623.6.549.huzd56。

  • 短信签名: 根据用户属性来创建符合自身属性的签名信息。企业用户需要上传相关企业资质证明,个人用户需要上传证明个人身份的证明。注意:短信签名需要审核通过后才可以使用。

  • 短信模板: 短信模板,即具体发送的短信内容。短信模板可以支持验证码、短信通知、推广短信、国际/港澳台消息四种模式。验证码和短信通知,通过变量替换实现个性短信定制。推广短信不支持在模板中添加变量。短信模板需要审核通过后才可以使用。

  • 短信示例: 【阿里云】 验证码${number},您正进行支付宝的身份验证,打死不告诉别人!这里的短信签名:阿里云,短信模板: 验证码${number},您正进行支付宝的身份验证,打死不告诉别人!

  • 最后获取 asscessKeyIdaccessKeySecret 。结合阿里云提供的开发者文档即可进行接口开发,短信开发api文档:https://help.aliyun.com/product/44282.html?spm=a2c4g.750001.6.1.T84wBi


项目

创建Maven项目

VJWnWd.png

添加依赖

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

application.properties

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
#--------------------------短信--------------------------
aliyun.sms.access-key-id=****
aliyun.sms.access-key-secret=***
#短信API产品名称(短信产品名固定,无需修改)
aliyun.sms.product=Dysmsapi
#短信API产品域名(接口地址固定,无需修改)
aliyun.sms.domain=dysmsapi.aliyuncs.com
# 初始化acsClient,暂不支持region化
aliyun.sms.region-id=cn-hangzhou
aliyun.sms.endpoint-name=cn-hangzhou
#短信签名-可在短信控制台中找到
aliyun.sms.sign-name=***
aliyun.sms.date-format=yyyyMMdd
aliyun.sms.template-code=SMS_160220108

#-------------------------Redis--------------------------
spring.redis.host=127.0.0.1
spring.redis.password=
spring.redis.port=6379

#默认过期时间、如果返回值存在过期时间则使用返回值中的过期时间
ali.tokenExpire=3600
ali.refreshTokenExpire=2592000
# Redis数据库索引(默认为0)
spring.redis.database=0
# Redis服务器地址
spring.redis.host=r-2ze3ede749e90084.redis.rds.aliyuncs.com
# Redis服务器连接端口
spring.redis.port=6379
# Redis服务器连接密码(默认为空)
spring.redis.password=QTOwer*&(192
# 连接超时时间(毫秒)
spring.redis.timeout=5000
# 连接池最大连接数(使用负值表示没有限制) 默认 8
spring.redis.lettuce.pool.max-active=8
# 连接池最大阻塞等待时间(使用负值表示没有限制) 默认 -1
spring.redis.lettuce.pool.max-wait=-1
# 连接池中的最大空闲连接 默认 8
spring.redis.lettuce.pool.max-idle=8
# 连接池中的最小空闲连接 默认 0
spring.redis.lettuce.pool.min-idle=0

生成随机码的工具类

1
2
3
4
5
6
7
8
9
10
public class IdentifyCodeUtil {

public static String getRandom() {
String num = "";
for (int i = 0; i < 6; i++) {
num = num + String.valueOf((int) Math.floor(Math.random() * 9 + 1));
}
return num;
}
}

发送短信,查询短信发送情况

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
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.dysmsapi.model.v20170525.QuerySendDetailsRequest;
import com.aliyuncs.dysmsapi.model.v20170525.QuerySendDetailsResponse;
import com.aliyuncs.dysmsapi.model.v20170525.SendSmsRequest;
import com.aliyuncs.dysmsapi.model.v20170525.SendSmsResponse;
import com.aliyuncs.exceptions.ClientException;
import com.aliyuncs.profile.DefaultProfile;
import com.aliyuncs.profile.IClientProfile;
import com.qingtengcloud.daisy.utils.log.LogTypeEnum;
import com.qingtengcloud.daisy.utils.log.LogUtils;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import java.text.SimpleDateFormat;
import java.util.Date;
/**
* @version V1.0
* @author: Jelly
* @program: daisy
* @description:
* @date: 2019-03-13 12:06
**/
@Component
@Slf4j
public class AliSmsSendTool {
// 自动注册短信服务的配置
@Value("${aliyun.sms.access-key-id}")
private String accessKeyId;
@Value("${aliyun.sms.access-key-secret}")
private String accessKeySecret;
@Value("${aliyun.sms.product}")
private String product;
@Value("${aliyun.sms.domain}")
private String domain;
@Value("${aliyun.sms.region-id}")
private String regionId;
@Value("${aliyun.sms.endpoint-name}")
private String endpointName;
@Value("${aliyun.sms.sign-name}")
private String signName;
@Value("${aliyun.sms.date-format}")
private String dateFormat;
public static SMS newSMS() {
return new SMS();
}
/**
* 一个短信实体
*/
@Data
public static class SMS {
private String phoneNumbers;
private String templateParam;
private String outId;
private String templateCode;
}
/**
* 获取短信发送服务机
*
* @return
*/
private IAcsClient getClient() {
IClientProfile profile = DefaultProfile.getProfile(regionId, accessKeyId, accessKeySecret);
try {
DefaultProfile.addEndpoint(endpointName, regionId, product, domain);
} catch (ClientException e) {
e.printStackTrace();
}
return new DefaultAcsClient(profile);
}
/**
* 获取短信请求
*
* @param sms
* @return
*/
private SendSmsRequest getRequest(SMS sms) {
SendSmsRequest request = new SendSmsRequest();
if (sms.getPhoneNumbers() == null) {
LogUtils.error(AliSmsSendTool.class, LogTypeEnum.TOOLS, "接收短信手机号为空!");
return null;
}
request.setPhoneNumbers(sms.getPhoneNumbers());
request.setSignName(signName);
if (sms.getTemplateCode() == null) {
LogUtils.error(AliSmsSendTool.class, LogTypeEnum.TOOLS, "短信模板为空!");
return null;
}
request.setTemplateCode(sms.getTemplateCode());
if (sms.getTemplateParam() == null) {
LogUtils.error(AliSmsSendTool.class, LogTypeEnum.TOOLS, "模板中替换JSON串de变量为空!");
return null;
}
request.setTemplateParam(sms.getTemplateParam());
if (sms.getOutId() == null) {
LogUtils.warn(AliSmsSendTool.class, LogTypeEnum.TOOLS, "提供给业务方扩展字段 outId为空!");
} else {
request.setOutId(sms.getOutId());
}
return request;
}
@Data
public static class SendResult {
private SendSmsResponse sendSmsResponse;
private SMS sms;
}
@Data
public static class QueryResult {
private QuerySendDetailsResponse querySendDetailsResponse;
private Query query;
}
/**
* 发送短信
* <p>
* <p>
* 发送验证码类的短信时,每个号码每分钟最多发送一次,每个小时最多发送5次。
* 其它类短信频控请参考阿里云
*
* @param sms 短信
*/
public SendResult sendSms(SMS sms) {
IAcsClient acsClient = getClient();
SendSmsRequest request = getRequest(sms);
SendSmsResponse sendSmsResponse = null;
try {
if (request != null) {
sendSmsResponse = acsClient.getAcsResponse(request);
}
} catch (ClientException e) {
log.error("发送短信发生错误。错误代码是 [{}],错误消息是 [{}],错误请求ID是 [{}],错误Msg是 [{}],错误类型是 [{}]", e.getErrCode(), e.getMessage(), e.getRequestId(), e.getErrMsg(), e.getErrorType());
//错误消息是 [SDK.InvalidRegionId : Can not find endpoint to access.],错误请求ID是 [null],错误Msg是 [Can not find endpoint to access.],错误类型是 [Client]
e.printStackTrace();
}
SendResult result = new SendResult();
result.setSendSmsResponse(sendSmsResponse);
result.setSms(sms);
return result;
}
public static Query newQuery() {
return new Query();
}
// 构建一个查询器
@Data
public static class Query {
private String bizId; //业务ID
private String phoneNumber;
private Date sendDate;
private Long pageSize;
private Long currentPage;
}
/**
* 查询短信发送结果
*
* @param query 查询条件
*/
public QueryResult querySendDetails(Query query) {
IAcsClient acsClient = getClient();
QuerySendDetailsRequest request = new QuerySendDetailsRequest();
request.setPhoneNumber(query.getPhoneNumber());
request.setBizId(query.getBizId());
SimpleDateFormat ft = new SimpleDateFormat(dateFormat);
request.setSendDate(ft.format(query.getSendDate()));
request.setPageSize(query.getPageSize());
request.setCurrentPage(query.getCurrentPage());
QuerySendDetailsResponse querySendDetailsResponse = null;
try {
querySendDetailsResponse = acsClient.getAcsResponse(request);
} catch (ClientException e) {
e.printStackTrace();
}
QueryResult result = new QueryResult();
result.setQuerySendDetailsResponse(querySendDetailsResponse);
result.setQuery(query);
return result;
}
}

发送短信配置常量类

sprringboot启动类Application.java加入注解:@EnableCaching
配置redis采用缓存,设置key和value的序列化方式

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
/**
* @version V1.0
* @author: Jelly
* @description:
* @date: 2019-02-22 09:39
**/
public class Constants {
public static final int SUCCESS = 200;
public static final int FAILED = 101;
public final static String SMS_AUTH_TYPE = "sms";
public final static String SMS_AUTH_CODE = "DaisySms";
public final static String SMS_SEND_STATUS_OK = "OK";
public final static long SMS_EXPIRE_TIME = 5*60;
public final static int SMS_CODE_LENGTH = 6;
}

redis实现类

保存、获取、删除验证码接口实现方法。(可以使用spring-boot自带的 stringRedisTemplate )

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
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.*;
import org.springframework.data.redis.serializer.RedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import org.springframework.stereotype.Service;
import java.io.Serializable;
import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeUnit;
/**
* @version V1.0
* @author: Jelly
* @description: redis操作方法
* @date: 2019-03-15 11:33
**/
@Service
public class RedisService {
private RedisTemplate redisTemplate;
@Autowired(required = false)
public void setRedisTemplate(RedisTemplate redisTemplate) {
RedisSerializer stringSerializer = new StringRedisSerializer();
redisTemplate.setKeySerializer(stringSerializer);
redisTemplate.setValueSerializer(stringSerializer);
redisTemplate.setHashKeySerializer(stringSerializer);
redisTemplate.setHashValueSerializer(stringSerializer);
this.redisTemplate = redisTemplate;
}
/**
* 写入缓存
* @param key
* @param value
* @return
*/
public boolean set(final String key, Object value) {
boolean result = false;
try {
ValueOperations<Serializable, Object> operations = redisTemplate.opsForValue();
operations.set(key, value);
result = true;
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
/**
* 写入缓存设置时效时间
* @param key
* @param value
* @return
*/
public boolean set(final String key, Object value, Long expireTime) {
boolean result = false;
try {
ValueOperations<Serializable, Object> operations = redisTemplate.opsForValue();
operations.set(key, value);
redisTemplate.expire(key, expireTime, TimeUnit.SECONDS);
result = true;
} catch (Exception e) {
e.printStackTrace();
}
return result;
}
/**
* 批量删除对应的value
* @param keys
*/
public void remove(final String... keys) {
for (String key : keys) {
remove(key);
}
}
/**
* 批量删除key
* @param pattern
*/
public void removePattern(final String pattern) {
Set<Serializable> keys = redisTemplate.keys(pattern);
if (keys.size() > 0)
redisTemplate.delete(keys);
}
/**
* 删除对应的value
* @param key
*/
public void remove(final String key) {
if (exists(key)) {
redisTemplate.delete(key);
}
}
/**
* 判断缓存中是否有对应的value
* @param key
* @return
*/
public boolean exists(final String key) {
return redisTemplate.hasKey(key);
}
/**
* 读取缓存
* @param key
* @return
*/
public Object get(final String key) {
Object result = null;
ValueOperations<Serializable, Object> operations = redisTemplate.opsForValue();
result = operations.get(key);
return result;
}
/**
* 哈希 添加
* @param key
* @param hashKey
* @param value
*/
public void hmSet(String key, Object hashKey, Object value){
HashOperations<String, Object, Object> hash = redisTemplate.opsForHash();
hash.put(key,hashKey,value);
}
/**
* 哈希获取数据
* @param key
* @param hashKey
* @return
*/
public Object hmGet(String key, Object hashKey){
HashOperations<String, Object, Object> hash = redisTemplate.opsForHash();
return hash.get(key,hashKey);
}
/**
* 列表添加
* @param k
* @param v
*/
public void lPush(String k,Object v){
ListOperations<String, Object> list = redisTemplate.opsForList();
list.rightPush(k,v);
}
/**
* 列表获取
* @param k
* @param l
* @param l1
* @return
*/
public List<Object> lRange(String k, long l, long l1){
ListOperations<String, Object> list = redisTemplate.opsForList();
return list.range(k,l,l1);
}
/**
* 集合添加
* @param key
* @param value
*/
public void add(String key,Object value){
SetOperations<String, Object> set = redisTemplate.opsForSet();
set.add(key,value);
}
/**
* 集合获取
* @param key
* @return
*/
public Set<Object> setMembers(String key){
SetOperations<String, Object> set = redisTemplate.opsForSet();
return set.members(key);
}
/**
* 有序集合添加
* @param key
* @param value
* @param scoure
*/
public void zAdd(String key,Object value,double scoure){
ZSetOperations<String, Object> zset = redisTemplate.opsForZSet();
zset.add(key,value,scoure);
}
/**
* 有序集合获取
* @param key
* @param scoure
* @param scoure1
* @return
*/
public Set<Object> rangeByScore(String key,double scoure,double scoure1){
ZSetOperations<String, Object> zset = redisTemplate.opsForZSet();
return zset.rangeByScore(key, scoure, scoure1);
}
}

发送短信接口

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
46
47
48
import com.aliyuncs.dysmsapi.model.v20170525.QuerySendDetailsResponse;
import com.aliyuncs.exceptions.ClientException;
import com.qingtengcloud.daisy.protocol.Result;
import com.qingtengcloud.daisy.utils.AliSmsSendTool;
import java.security.NoSuchAlgorithmException;
/**
* @version V1.0
* @author: Jelly
* @description:
* @date: 2019-03-20 15:11
**/
public interface ISmsService {
/**
* 发送短信接口
*
* @param phoneNums 手机号码
* @param templeteCode 模板代码
* @param templateParam 模板替换参数
* @return
* @throws ClientException
*/
Object sendSms(String phoneNums, String templeteCode,
String templateParam ) throws ClientException;
/**
* 查询短信发送明细
*
* @param phoneNumber
* @param bizId 业务流水号
* @return
* @throws ClientException
*/
Result querySendDetails(String phoneNumber, String bizId) throws ClientException;
/**
* 发送短信服务
*
* @param mobile 手机号
* @return
*/
Result sendMessage(String mobile) throws NoSuchAlgorithmException;
/**
* 判断验证码是否正确
*
* @param mobile
* @param identifyCode
* @return
*/
Boolean checkIsCorrectCode(String mobile, String identifyCode) throws NoSuchAlgorithmException;
}

发送短信实现类

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
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
import com.alibaba.fastjson.JSON;
import com.aliyuncs.exceptions.ClientException;
import com.qingtengcloud.daisy.constant.Constants;
import com.qingtengcloud.daisy.constant.ErrorStatus;
import com.qingtengcloud.daisy.protocol.Result;
import com.qingtengcloud.daisy.service.ISmsService;
import com.qingtengcloud.daisy.service.RedisService;
import com.qingtengcloud.daisy.utils.AliSmsSendTool;
import com.qingtengcloud.daisy.utils.Tools;
import com.qingtengcloud.daisy.utils.log.LogTypeEnum;
import com.qingtengcloud.daisy.utils.log.LogUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.security.NoSuchAlgorithmException;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
/**
* @version V1.0
* @author: Jelly
* @description:
* @date: 2019-03-20 15:31
**/
@Service
public class SmsService implements ISmsService {
@Value("${aliyun.sms.template-code}")
private String templateCode;
@Resource
private RedisService redisService;
@Autowired
private AliSmsSendTool aliSmsSendTool;
/**
* 发送短信服务
*
* @param mobile
* @return
*/
public Result sendMessage(String mobile) throws NoSuchAlgorithmException {
if (StringUtils.isEmpty(mobile)) {
return Result.buildFailure(ErrorStatus.MISSING_ARGUMENT);
}
String identifyCode;
//1. 判断是否缓存该账号验证码
String returnCode = (String) redisService.get(Constants.SMS_AUTH_CODE + Tools.MD5(Constants.SMS_AUTH_CODE + mobile));
if (!StringUtils.isEmpty(returnCode)) {
LogUtils.info(SmsService.class, LogTypeEnum.REDIS, "Redis中存在验证码 ");
identifyCode = returnCode.substring(Constants.SMS_CODE_LENGTH);
} else {
identifyCode = Tools.smsCodeUtil();
LogUtils.info(SmsService.class, LogTypeEnum.TOOLS, "生成新的验证码 ");
}
//2.发送短信
Map<String, String> codeMap = new HashMap<>();
codeMap.put("code", identifyCode);
AliSmsSendTool.SendResult response;
try {
response = sendSms(mobile, templateCode, JSON.toJSONString(codeMap));
//短信发送成功后存入redis
if (response != null && Constants.SMS_SEND_STATUS_OK.equalsIgnoreCase(response.getSendSmsResponse().getCode())) {
boolean redis = redisService.set(Constants.SMS_AUTH_CODE + Tools.MD5(Constants.SMS_AUTH_CODE + mobile), identifyCode + mobile, Constants.SMS_EXPIRE_TIME );
if (!redis) {
LogUtils.error(SmsService.class, LogTypeEnum.REDIS, "Redis存储错误 ");
return Result.buildFailure(ErrorStatus.INTERNAL_SERVER_ERROR);
} else {
return Result.buildSuccess(response);
}
}
return Result.buildFailure(ErrorStatus.SERVICE_EXCEPTION);
} catch (Exception e) {
LogUtils.error(SmsService.class, LogTypeEnum.SMS, "sendMessage method invoke error: ", e.getMessage());
}
return Result.buildFailure(ErrorStatus.INTERNAL_SERVER_ERROR);
}
/**
* 发送短信接口
*
* @param mobile 手机号
* @param templeteCode 模板代码
* @param param 模板替换参数
* @return 发送结果
* @throws ClientException 异常
*/
@Override
public AliSmsSendTool.SendResult sendSms(String mobile, String templeteCode, String param) throws ClientException {
AliSmsSendTool.SMS sms = AliSmsSendTool.newSMS();
sms.setPhoneNumbers(mobile);
sms.setTemplateParam(param);//code有要求 "message":"params must be [a-zA-Z0-9] for verification sms"
sms.setTemplateCode(templeteCode);
AliSmsSendTool.SendResult sendResult = aliSmsSendTool.sendSms(sms);
if (sendResult == null || !sendResult.getSendSmsResponse().getCode().equals(Constants.SMS_SEND_STATUS_OK)) {
LogUtils.error(SmsService.class, LogTypeEnum.SMS, "发送短信失败 ", sendResult);
return null;
}
LogUtils.info(SmsService.class, LogTypeEnum.SMS, "发送短信 成功 ", sendResult);
return sendResult;
}
/**
* 判断验证码是否正确
*
* @param mobile
* @param identifyCode
* @return
*/
public Boolean checkIsCorrectCode(String mobile, String identifyCode) throws NoSuchAlgorithmException {
if (StringUtils.isEmpty(mobile) || StringUtils.isEmpty(identifyCode)) {
LogUtils.error(SmsService.class, LogTypeEnum.SMS, "验证码校验失败,手机号或验证码错误");
return false;
}
String returnCode = null;
returnCode = (String) redisService.get(Constants.SMS_AUTH_CODE + Tools.MD5(Constants.SMS_AUTH_CODE + mobile));
if (!StringUtils.isEmpty(returnCode) && returnCode.substring(0, Constants.SMS_CODE_LENGTH).equals(identifyCode) && returnCode.substring(Constants.SMS_CODE_LENGTH).equals(mobile)) {
LogUtils.info(SmsService.class, LogTypeEnum.SMS, "验证码校验成功");
return true;
}
LogUtils.error(SmsService.class, LogTypeEnum.SMS, "验证码校验失败");
return false;
}
/**
* 查询短信发送明细
*
* @param phoneNumber
* @param bizId
* @return
* @throws ClientException
*/
@Override
public Result querySendDetails(String phoneNumber, String bizId) throws ClientException {
AliSmsSendTool.Query query = new AliSmsSendTool.Query();
query.setBizId(bizId);
query.setCurrentPage(1L);
query.setPageSize(10L);
query.setPhoneNumber(phoneNumber);
query.setSendDate(new Date());
// // 查询发送结果
AliSmsSendTool.QueryResult queryResult = aliSmsSendTool.querySendDetails(query);
if (queryResult == null) {
LogUtils.error(SmsService.class, LogTypeEnum.SMS, "没有该短信记录 ");
return Result.buildFailure(queryResult);
}
LogUtils.info(SmsService.class, LogTypeEnum.SMS, "查找短信记录成功 ");
return Result.buildSuccess(queryResult);
}
}

发送短信controller类

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
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
import com.qingtengcloud.daisy.protocol.Result;
import com.qingtengcloud.daisy.service.ISmsService;
import com.qingtengcloud.daisy.utils.AliSmsSendTool;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.Resource;
import java.security.NoSuchAlgorithmException;
/**
* @version V1.0
* @author: Jelly
* @description:
* @date: 2019-03-13 12:31
**/
@RestController
public class AliSmsSendController {
@Autowired
private AliSmsSendTool aliSmsSendTool;
@Resource
private ISmsService smsService;
/**
* 发送短信验证码
*
* @param mobile 手机号
* @return
*/
@RequestMapping("/sms/sendMessage")
public Object sendMessage(@RequestParam String mobile) throws NoSuchAlgorithmException {
return smsService.sendMessage(mobile);
}
/**
* 判断验证码是否正确
*
* @param mobile 手机号
* @param identifyCode 确认码
* @return
*/
@RequestMapping("/sms/checkIsCorrectCode")
public Object checkIsCorrectCode(@RequestParam String mobile, @RequestParam String identifyCode) throws NoSuchAlgorithmException {
Boolean isOk = smsService.checkIsCorrectCode(mobile, identifyCode);
if (isOk){
return Result.buildSuccess("isOk");
}
return Result.buildFailure("Fail");
}
@GetMapping("/sms/auto")
public Object smsTest() {
String mobile = "18846816914";
String templateCode = "SMS_160220108";
AliSmsSendTool.SMS sms = AliSmsSendTool.newSMS();
sms.setPhoneNumbers(mobile);
sms.setTemplateParam("{\"code\":\"fwzd\"}");//code有要求 "message":"params must be [a-zA-Z0-9] for verification sms"
sms.setTemplateCode(templateCode);
AliSmsSendTool.SendResult sendResult = aliSmsSendTool.sendSms(sms);
// 由于响应不及时,不能在这里构建查询,直接查询,smsSendDetailDTOs 会获取到null,
// 可以选择在别处查询,保证用户良好体验,系统响应快。考虑异步方法 线程睡眠5秒再查询,结果保存数据库进行持久化
// // 构建查询
// AliSmsSendTool.Query query = new AliSmsSendTool.Query();
// query.setBizId(sendResult.getSendSmsResponse().getBizId());
// query.setCurrentPage(1L);
// query.setPageSize(10L);
// query.setPhoneNumber(sms.getPhoneNumbers());
// query.setSendDate(new Date());
//// // 查询发送结果
// AliSmsSendTool.QueryResult queryResult= aliSmsSendTool.querySendDetails(query);
return sendResult;
}
}