短信失效验证判断

本章节主要描述短信15分钟内有效验证,过期则验证失败,以阿里云短信(java ssm)为例,如果不知道如何发送短信验证码的请看上一个章节。

验证码发送

  1. 添加VerificationCode类

此类用于接收code验证码和手机号,因为业务需要,验证完验证码之后需要手机号进行业务操作,这里不做解释,根据自己需求而定

package com.rxys.util;


import java.util.Random;
import java.util.TimerTask;
import java.util.concurrent.Callable;
import java.util.concurrent.Delayed;
import java.util.concurrent.TimeUnit;

//必须实现Runnable方法,后面会使用到ScheduledThreadPool线程池
public class VerificationCode implements Runnable {

    public String code;

    public String phone;

    private char[] array = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'};


    public VerificationCode(String phone){
        this.phone=phone;
    }
	
	//获取验证码
    public String getCode() {
        setCode();
        return this.code;
    }
	
	//创建6位数验证码交给成员变量code
    public void setCode() {
        StringBuffer stringBuffer = new StringBuffer();
        int i = 0;
        while (i < 6) {
            stringBuffer.append(array[new Random().nextInt(10)]);
            i++;
        }
        this.code = stringBuffer.toString();
    }

	//过期后将该实例验证码为空值
    @Override
    public void run() {
        this.code = "";
    }

    @Override
    public String toString() {
        return "VerificationCode=[code="+code+",phone="+phone+"]";
    }
}

  1. 发送验证码controller层
	//ParamVo主要接受前端参数,主要有phoneNumber和sessionId
	//因为项目原因特殊,sessionId需要前端发送,这里可以用session.getId()获取。不懂的可以留言。
	@PostMapping("/getCode")
    public JsonResult getCode(@RequestBody ParamVo paramVo) {
        return new JsonResult (phoneService.getCode(paramVo.getPhoneNumbers(),paramVo.getSessionId()));
    }

  1. 发送验证码service层

    成员中变量加上ScheduledThreadPool和hashmap

	//ScheduledThreadPool是用来进行延迟任务,这里调用他的schedule()进行短信过期,ScheduledThreadPool还有几种方法大家可以百度查阅作为扩展知识
    private ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(Integer.MAX_VALUE);

    //创建map用于根据sessionId存储VerificationCode实例,
    private HashMap<String,VerificationCode> map=new HashMap<>();

getCode业务逻辑

	/*此代码抛出ServiceException被@ExceptionHandler做了异常处理,可以跟根据自己业务修改返回错误*/
    @Override
    public String getCode(String phoneNumbers,String sessionId) {
    	//判断手机号是否为空
        if (phoneNumbers == null || phoneNumbers.equals("")) {
            throw new ServiceException("手机号码为空");
        }
        //创建verificationCode对象,将手机号存入实例
        VerificationCode verificationCode=new VerificationCode(phoneNumbers);
        //将verificationCode存入成员变量map中,sessionId为key
        map.put(sessionId,verificationCode);
        //获取验证码
        String code = verificationCode.getCode();
        //SendSmsUtil为阿里云验证工具类,不了解的请看上一个章节
        //此处返回发送验证码回调信息
        String result = SendSmsUtil.sendMeg(phoneNumbers, code);
        //15分钟后执行verificationCode的run方法,设置code为空值(调用verificationCode的run方法,TimeUnit.MINUTES表示以分钟计时,15分钟后执行)
        scheduledExecutorService.schedule(verificationCode, 15, TimeUnit.MINUTES);
        //打印回到信息
        System.out.println(result);
        //将回调信息用map接收,此处使用阿里的JSON类
        Map<String, String> map = JSON.parseObject(result, Map.class);
        String message = map.get("Message");
        //如果message不等于OK,则抛出异常。message不等于Ok则为异常信息
        if (!message.equals("OK")) {
            throw new ServiceException(message);
        }
        return "验证码发送成功";
    }
  1. 接口测试

此时调用接口,短信发送成功(已收到短信)
短信失效验证判断_第1张图片

验证码有效期验证

  1. controller层
	//因为项目原因特殊,sessionId需要前端发送,这里可以用session.getId()获取。不懂的可以留言。
    @PostMapping("/judgeCode")
    public JsonResult judgeCode(@RequestBody ParamVo paramVo) {
        return new JsonResult (phoneService.judgeCode(paramVo.getCode(),paramVo.getSessionId()));
    }
  1. service层
	/*此代码抛出ServiceException被@ExceptionHandler做了异常处理,可以跟根据自己业务修改返回错误*/
    @Override
    public String judgeCode(String code, String sessionId) {
        //获取map中的verificationCode实例,sessionId为key获取
        VerificationCode verificationCode=map.get(sessionId);
        //如果verificationCode为null则验证码已被移除或者没有发送手机验证
        if(verificationCode==null){
            throw new ServiceException("请获取验证码");
        }
         //如果verificationCode为空字符则验证码失效,说明该实例的run方法已被ScheduledThreadPool调用
        if (verificationCode.code.equals("")) {
            throw new ServiceException("验证码过期");
        }
         //如果verificationCode与传入的code值不相等,则抛出验证码错误异常
        if (!verificationCode.code.equals(code)) {
            throw new ServiceException("验证码错误");
        }
		//以上判断顺序不可修改
        //获取map中的校验成功后移除map中verificationCode对象
        map.remove(sessionId);
        return "验证成功";
    }
  1. 接口测试

    失效测试
    短信失效验证判断_第2张图片
    校验成功测试
    短信失效验证判断_第3张图片
    未发送测试
    短信失效验证判断_第4张图片

你可能感兴趣的:(短信验证)