springboot手机验证码

Posted mandy3651423

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了springboot手机验证码相关的知识,希望对你有一定的参考价值。

阿里短信平台

accessKeyId和accessKeySecret这两个参数是需要项目组提供

 

下面是pom导入阿里的sdk包

<dependency>
    <groupId>com.aliyun</groupId>
    <artifactId>aliyun-java-sdk-core</artifactId>
    <version>4.1.0</version>
</dependency>

之后写一个配置类 配置发送手机验证码的相关参数

private  static final String product = "Dysmsapi";
    //产品域名,开发者无需替换
    private  static final String domain = "dysmsapi.aliyuncs.com";

    private  static final String accessKeyId = "keyId填写自己的";
    private  static final String accessKeySecret = "KeySercret填写自己的";

    public SendSmsResponse sendALiSms(String telephone, String code)throws Exception{
        System.setProperty("sun.net.client.defaultConnectTimeout", "10000");
        System.setProperty("sun.net.client.defaultReadTimeout", "10000");
        //初始化acsClient,暂不支持region化
        IClientProfile profile = DefaultProfile.getProfile("cn-hangzhou", accessKeyId, accessKeySecret);
        DefaultProfile.addEndpoint("cn-hangzhou", "cn-hangzhou", product, domain);
        IAcsClient acsClient = new DefaultAcsClient(profile);
        //组装请求对象-具体描述见控制台-文档部分内容
        SendSmsRequest request = new SendSmsRequest();
        //必填:待发送手机号
        request.setPhoneNumbers(telephone);
        //必填:短信签名-可在短信控制台中找到
        request.setSignName("短信签名");
        //必填:短信模板-可在短信控制台中找到
        request.setTemplateCode("SMS_157975162");
        //可选:模板中的变量替换JSON串,如模板内容为"亲爱的${name},您的验证码为${code}"时,此处的值为
//        request.setTemplateParam("{"name":"Tom", "code":"123"}");
        request.setTemplateParam("{"code":"" + code + ""}");
        //选填-上行短信扩展码(无特殊需求用户请忽略此字段)
        //request.setSmsUpExtendCode("90997");
        //可选:outId为提供给业务方扩展字段,最终在短信回执消息中将此值带回给调用者
        request.setOutId("yourOutId");
        //hint 此处可能会抛出异常,注意catch
        SendSmsResponse sendSmsResponse = acsClient.getAcsResponse(request);
        return sendSmsResponse;

以上keyId和keySercret可以写在配置文件里

然后可以对这个方法封装一下 当然不封装直接调用也可以

public SendSmsResponse sendSms(String telephone,String code)throws Exception{
    AliSmsConfig aliSmsConfig=new AliSmsConfig();
    SendSmsResponse response=aliSmsConfig.sendALiSms(telephone,code);
    return response;
}

之后写Service层 下面直接贴出impl代码

@Override
public int sendSms(String telephone) {
    //这里生成六位随机数
    Integer random=(int)((Math.random()*9+1)*100000);
    String code=random.toString();
    AliSmsUtil aliSmsUtil=new AliSmsUtil();
    SendSmsResponse response = null;
    try {
        response=  aliSmsUtil.sendSms(telephone,code);
    }catch (Exception e){
        e.printStackTrace();
    }
    if (response!=null&&response.getCode().equals("OK")){
        return 0;
    }
    //TODO 在此 验证码应存入数据库
    /*
     * 加一个存库方法 用于之后验证
     *
     */
    return 500;
}

上面那个方法生成了6位随机数 这里根据需求生成不同长度的随机数

最后用controller层调用service层

@Resource
SmsService smsService;

@GetMapping("/sendSms")
public CommonResult companyApproveList(@RequestParam(value = "phone") String phone) {
    //再次验证手机号是否有误
    if (PhoneUtil.confPhone(phone)){
        int sms=smsService.sendSms(phone);
        if (sms==0){
            return CommonResult.success(null);
        }else {
            return CommonResult.error(501,"短信发送失败");
        }
    }else {
        return CommonResult.error(500,"请填写正确的手机号");
    }
}

controller层: 前端传入一个手机号 虽然这个手机号经过了前端的判断 但是我们还是需要再次判断一下 这里写一个判断手机号的方法 之后手机号都可以放进这里验证

确定这个手机号是可用的以后就可以将这个手机号传到service层 进行发送验证码

 

之后处理可以将这个验证码存到redis或者数据库中 当用户手机接收到验证码并填写给前端的时候 根据存到redis/mysql中的数据 进行判断验证码是否正确 等等操作

PhoneUtils.confPhone()这个方法跳过也可以 这就是一个判断手机号是否正确的工具

public static boolean confPhone(String phone){
    if (phone.length() != 11)
    {
        return false;
    }else{
        /**
         * 移动号段正则表达式
         */
        String pat1 = "^((13[4-9])|(147)|(15[0-2,7-9])|(178)|(18[2-4,7-8]))\d{8}|(1705)\d{7}$";
        /**
         * 联通号段正则表达式
         */
        String pat2  = "^((13[0-2])|(145)|(15[5-6])|(176)|(18[5,6]))\d{8}|(1709)\d{7}$";
        /**
         * 电信号段正则表达式
         */
        String pat3  = "^((133)|(153)|(177)|(18[0,1,9])|(149))\d{8}$";
        /**
         * 虚拟运营商正则表达式
         */

        String pat4 = "^((170))\d{8}|(1718)|(1719)\d{7}$";

        Pattern pattern1 = Pattern.compile(pat1);
        Matcher match1 = pattern1.matcher(phone);
        boolean isMatch1 = match1.matches();
        if(isMatch1){
            return true;
        }
        Pattern pattern2 = Pattern.compile(pat2);
        Matcher match2 = pattern2.matcher(phone);
        boolean isMatch2 = match2.matches();
        if(isMatch2){
            return true;
        }
        Pattern pattern3 = Pattern.compile(pat3);
        Matcher match3 = pattern3.matcher(phone);
        boolean isMatch3 = match3.matches();
        if(isMatch3){
            return true;
        }
        Pattern pattern4 = Pattern.compile(pat4);
        Matcher match4 = pattern4.matcher(phone);
        boolean isMatch4 = match4.matches();
        if(isMatch4){
            return true;
        }
        return false;
    }
}

这个工具的返回值是boolean 调用这个方法就是判断手机号是否正确 如果正确我就可以进行下一步的操作 如果错误就返回给前端 这个手机号是错误的

以上是关于springboot手机验证码的主要内容,如果未能解决你的问题,请参考以下文章

springboot验证码重构

springboot手机验证码

手机验证发送及其验证(基于springboot+redis)保姆级

腾讯云短信服务实现 Java 发送手机验证码(SpringBoot+Redis 实现)

SpringBoot使用第三方工具实现手机短信发送验证码(榛子云)

springboot系列(二十):如何通过redis实现手机号验证码功能 |超级详细,建议收藏