1.前期准备:
现在的网站,越来越多的人开始使用验证码的方式来进行验证,下面将粗略的展示一下。
收费标准:可以直接参考阿里云给出的官方价格。小于70字的价格0.045元/条。
在自己的阿里云账户里边,要先先充值一点钱,这样在后面代码开发测试的时候,不会出现报错的现象。
1)充值:
2)准备AccessKey和密码:(这个涉及到个人隐私,大家一定需要保护好,如果发现泄漏的,可以及时在阿里云平台做出对应的措施。)
3)生成AccessKey和密码:(此处本人踩了第一个坑,大家一定要注意)
如果发现自己的账号存在了异常发送,可以点击后面的禁用或者删除(这一步一定要记住)
3)设置签名:
注意:此处审核是人工审核,一定不要随便填写,如果审核失败了,过半小时再去填写一次。签名针对普通用户只能设置一次,一定不要乱写,请认真对待哟。
显示上面的通过,就表明成功了一半了。
4)设置模版:
注意:和上面的签名是一样的,但是模版是可以设置多个的。人工审核,一定要认真填写。
在编码的时候,会用到模版名称,模版CODE。
2.代码测试:
官网的Demo:https://api.aliyun.com/new?spm=a2c4g.11186623.2.12.14d019d9YM6YOp#/?product=Dysmsapi
class AlibabaSmsApplicationTests {
/*官方给的依赖
pom.xml
<dependency>
<groupId>com.aliyun</groupId>
<artifactId>aliyun-java-sdk-core</artifactId>
<version>4.5.0</version>
</dependency>
*/
@Test
void contextLoads() {
//连接阿里云服务器
DefaultProfile profile = DefaultProfile.getProfile("cn-hangzhou", "<accessKeyId>","上面设置了AccessKey,里边有密码,直接填写就好");
IAcsClient client = new DefaultAcsClient(profile);
//构建请求
CommonRequest request = new CommonRequest();
request.setSysMethod(MethodType.POST);
request.setSysDomain("dysmsapi.aliyuncs.com");//此处禁止修改
request.setSysVersion("2017-05-25");//此处禁止修改
request.setSysAction("SendSms");
//自定义的参数(手机号,验证码,签名,模版)
request.putQueryParameter("PhoneNumbers", "要发送的手机号");
request.putQueryParameter("SignName", "上面设置的签名名称");
request.putQueryParameter("TemplateCode", "上面审核通过的模版");
//构建一个短信验证码:
HashMap<String,Object> map = new HashMap<>();
map.put("code", UUID.randomUUID().toString().substring(0,4));//随机生成的验证码
request.putQueryParameter("TemplateParam", JSONObject.toJSONString(map));
try {
CommonResponse response = client.getCommonResponse(request);
System.out.println(response.getData());
} catch (ServerException e) {
e.printStackTrace();
} catch (ClientException e) {
e.printStackTrace();
}
}
}
3.自己在使用的时候踩过的坑:
com.aliyuncs.exceptions.ClientException: SignatureDoesNotMatch : Specified signature is not matched with our calculation. (是因为上面在连接阿里云服务器的时候,我的连接密码错了,不是登录密码,是个人设置的AccessKey的密码)
com.aliyuncs.exceptions.ClientException: MissingPhoneNumbers : PhoneNumbers is mandatory for this action.(有几个地方一定要注意:自定义的参数,参数名一定要用阿里官方提供的,否则就会报错)
4.阿里云短信服务结合redis使用:
我们都知道,redis在保存数据的时候,有一个时效性。我们可以利用这点完成对验证的保存。
直接上代码:
1)service的接口phoneNum:是手机号;templateCode模版编号;code验证码
public interface SendSms {
public boolean send(String phoneNum, String templateCode, Map<String,String> code);
}
2)service的实现类:
@Service
public class SendSmsImpl implements SendSms {
@Override
public boolean send(String phoneNum, String templateCode, Map<String, String> code) {
//连接阿里云服务器
DefaultProfile profile = DefaultProfile.getProfile("cn-hangzhou", "<accessKeyId>","上面设置了AccessKey,里边有密码,直接填写就好");
IAcsClient client = new DefaultAcsClient(profile);
//构建请求
CommonRequest request = new CommonRequest();
request.setSysMethod(MethodType.POST);
request.setSysDomain("dysmsapi.aliyuncs.com");//此处禁止修改
request.setSysVersion("2017-05-25");//此处禁止修改
request.setSysAction("SendSms");
//自定义的参数(手机号,验证码,签名,模版)
request.putQueryParameter("PhoneNumbers", phoneNum);
request.putQueryParameter("SignName",templateCode);
request.putQueryParameter("TemplateCode",code);
try {
CommonResponse response = client.getCommonResponse(request);
System.out.println(response.getData());
return response.getHttpResponse().isSuccess();
} catch (ServerException e) {
e.printStackTrace();
} catch (ClientException e) {
e.printStackTrace();
}
return false;
}
}
3)逻辑层:
@RestController
@CrossOrigin//跨域的支持
public class SmsApiController {
@Autowired
private SendSms sendSms;
@Autowired
private RedisTemplate<String,String> redisTemplate;
@GetMapping("/send/{phone}")
public String code(@PathVariable("phone")String phone){
String code = redisTemplate.opsForValue().get(phone);
if(!StringUtils.isEmpty(code)){
return phone+":"+code+"已经存在,还可以正常使用";
}
//直接生成验证码
code = UUID.randomUUID().toString().substring(0, 4);
HashMap<String, String> param = new HashMap<>();
param.put("code",code);
boolean isSend = sendSms.send(phone, "模版编号", param);
if(isSend){//设置有效时间
redisTemplate.opsForValue().set(phone,code,5, TimeUnit.SECONDS);
return "发送成功";
}
return "发送失败";
}
}
4)配置文件:
redis的配置文件需要设置:
spring.redis.host=192.168.80.137
spring.redis.port=6379