Vue3问题:如何实现短信验证码登录?前后端! | 您所在的位置:网站首页 › qq不用手机验证码登录怎么登录 › Vue3问题:如何实现短信验证码登录?前后端! |
前端功能问题系列文章,点击上方合集↑ 序言大家好,我是大澈! 本文约3400+字,整篇阅读大约需要4分钟。 本文主要内容分三部分,第一部分是需求分析,第二部分是实现步骤,第三部分是问题详解。 如果您只需要解决问题,请阅读第一、二部分即可。 如果您有更多时间,进一步学习问题相关知识点,请阅读至第三部分。 1. 需求分析点击发送验证码按钮,获取手机短信验证码。此时,发送验证码按钮进入倒计时状态,且不可被点击。 成功获取到短信验证码并输入,点击登录按钮,完成页面跳转。 短信验证码登录功能的实现,借助了阿里云短信业务API,我们可以使用阿里云的短信服务向用户发送验证码、通知、营销等不同类型的短信。 总体实现步骤如下: 创建阿里云账号:如果您还没有阿里云账号,需要先注册一个账号并完成身份验证。 开通短信服务:登录阿里云控制台,找到短信服务并进行开通,然后完善相关信息,包括资质、签名、模板等,最后还需要购买短信套餐包。 这里解释一下两个概念: 短信签名:短信签名是您发送短信时用于展示发送方身份的标识,需要在阿里云短信控制台进行申请和审核。 短信模板:短信模板是您发送短信时所使用的短信内容模板,需要在阿里云短信控制台进行申请和审核。 获取API凭证:在阿里云控制台中,创建 AccessKey,并确保该密钥对拥有短信发送的权限。 编写后端接口调用对应API:使用选择的编程语言和相关 SDK,调用阿里云短信业务API中相应的接口,如发送短信、查询发送记录等。 编写前端代码:发送短信并验证登录。 下面是具体的代码实现,包括前端、后端两方面。 2.2 编写前端代码对于前端来说,所做的操作并不算多,无非是要实现点击发送短信验证码后的倒计时效果,以及两个接口的调用。 对于倒计时效果,就是利用了定时器,去控制发送验证码按钮的状态。 对于调用的两个接口,一个是发送短信接口,一个是短信验证及登录接口。 相关代码实例请继续往下看,每个地方基本都给大家做了详细的注释。 模版代码: {{ countdown > 0 ? `重新发送(${countdown})` : '发送验证码' }} 登录逻辑代码: import {reactive, ref} from 'vue' import Axios from '../api/axios'; import {ElMessage} from "element-plus"; const dataForm = reactive({ phone: '123456', code: '', }) let isSendingCode = ref(false); let countdown = ref(0); // 发送验证码,调验证码接口 const sendVerificationCode = () => { // 检查手机号是否有效 // ... // 调发送短信接口 Axios.get('/admin/send', { params: { phone: dataForm.phone, } }) .then(res => { ElMessage.success(res.data) }) .catch(error => { console.error(error); }); isSendingCode.value = true; // 设置倒计时时间,这里假设为10秒 countdown.value = 10; // 倒计时效果 const countdownInterval = setInterval(() => { countdown.value--; if (countdown.value { // 调发送短信接口 Axios.post('/admin/checkLogin', { phoneNumber: dataForm.phone, code: dataForm.code, }) .then(res => { ElMessage.success(res.data) }) .catch(error => { console.error(error); }); } 2.3 编写后端接口对于后端实现,要先引入阿里云短信业务依赖,再封装短信发送工具类,再编写两个接口,一个是发送短信接口,一个是短信验证及登录接口。 在发送短信接口业务层中,生成随机字符串,传入并调用短信发送工具类方法发送验证码,并把验证码存入Redis中。 在短信验证及登录接口业务层中,将前端传过来的验证码与Redis中存的验证码进行比较,校验成功执行下一步登录操作。 相关代码实例请继续往下看,每个地方基本都给大家做了详细的注释。 Pom.xml中引入依赖代码: org.springframework.boot spring-boot-starter-data-redis com.aliyun aliyun-java-sdk-core 4.6.0 com.aliyun aliyun-java-sdk-dysmsapi 1.1.0 com.alibaba fastjson 1.2.76短信发送服务工具类代码: package com.dache.base.common.util; import com.alibaba.fastjson.JSONObject; import com.aliyuncs.DefaultAcsClient; import com.aliyuncs.IAcsClient; import com.aliyuncs.dysmsapi.model.v20170525.SendSmsRequest; import com.aliyuncs.dysmsapi.model.v20170525.SendSmsResponse; import com.aliyuncs.exceptions.ClientException; import com.aliyuncs.exceptions.ServerException; import com.aliyuncs.profile.DefaultProfile; import com.google.gson.Gson; import java.util.HashMap; /** * @Description 短信发送服务 */ public class SmsUtil { public static String toSendMes(String phoneNumber,String code) { //1.连接阿里云 /** "", // The region ID 地区标识 "", // The AccessKey ID of the RAM account RAM账户的AccessKey ID 阿里云账号可查 "", // The AccessKey Secret of the RAM account RAM 账户的 AccessKey Secret 阿里云账号可查 **/ DefaultProfile profile = DefaultProfile.getProfile("cn-beijing", "your-access-key-id", "your-access-key-secret"); IAcsClient client = new DefaultAcsClient(profile); //2.构建请求 自定义参数 SendSmsRequest request = new SendSmsRequest(); //接收短信的手机号码 request.setPhoneNumbers(phoneNumber); //短信签名名称 request.setSignName("阿里云短信测试"); //短信模板CODE request.setTemplateCode("SMS_154SECRET9"); //模版内容:您正在使用阿里云短信测试服务,体验验证码是:${code},如非本人操作,请忽略本短信! //短信模板变量对应的实际值 //("{\"code\":\"1234\"}"); HashMap param=new HashMap(); param.put("code",code); request.setTemplateParam(JSONObject.toJSONString(param)); SendSmsResponse response = new SendSmsResponse(); try { //3.发送请求 response = client.getAcsResponse(request); } catch (ServerException e) { e.printStackTrace(); } catch (ClientException e) { System.out.println("ErrCode:" + e.getErrCode()); System.out.println("ErrMsg:" + e.getErrMsg()); System.out.println("RequestId:" + e.getRequestId()); } //短信成功返回json { "RequestId": "614048FB-0619-4439-A1D5-AA8B218A****", "Message": "OK", "BizId": "386715418801811068^0", "Code": "OK"} return response.getMessage(); } }接口Controller层代码: /** * 发送短信 */ @ApiOperation(value = "发送短信") @GetMapping("/send") public CommonResult toSendMessage(@RequestParam("phone") String phone){ String message = adminService.toSendMessage(phone); return CommonResult.success(message); } /** * 检验验证码和密码,校验成功后登录 */ @ApiOperation(value = "检验验证码和密码,校验成功后登录") @PostMapping("/checkLogin") public CommonResult checkLogin(@RequestBody ToCheckLoginDTO toCheckLogin){ String checkLogin = adminService.checkLogin(toCheckLogin.getPhoneNumber(), toCheckLogin.getCode()); // 省略用户密码加密校验 // ... // 省略JWT认证 // ... return CommonResult.success(checkLogin); }接口Service层代码: /** * 发送短信 */ @Override public String toSendMessage(String phoneNumber) { //扩展 可以验证该电话号码是否注册 //1.判定验证码是否过期 String code = redisTemplate.opsForValue().get(phoneNumber); if (!StringUtils.isEmpty(code)){ return phoneNumber+":"+"验证码未过期"; } //2.已过期/无验证码 生成验证码 //随机生成字符串 做验证码 int toCode = (int) (Math.random() * (50000 - 40000) + 40000); code=Integer.toString(toCode); String toSendMes = SmsUtil.toSendMes(phoneNumber, code); if (ComConstants.OK.equals(toSendMes)){ //redis 中存放 5分钟过期 redisTemplate.opsForValue().set(phoneNumber,code,ComConstants.NUM_FIVE, TimeUnit.MINUTES); //3.发送短信 return "短信发送成功"; } return "短信发送异常"; } /** * 检验手机验证码并登录 */ @Override public String checkLogin(String phoneNumber, String code) { //1.redis 验证码校验 String redisCode = redisTemplate.opsForValue().get(phoneNumber); if (code.equals(redisCode)){ return "登入成功"; } return "登入失败"; }当然,上述前端和后端代码的实现中,必然会存在一些缺陷,因为它只是一个实例,具体的实现还需要在项目中根据需求进行完善。 3. 问题详解 3.1 常见短信服务API文档地址整理阿里云短信服务API文档地址:https://help.aliyun.com/document_detail/101414.html。 以下是一些其它常见短信服务供应商: 腾讯云短信服务API:腾讯云提供了短信服务API,用于发送短信验证码和推广短信。文档地址:https://cloud.tencent.com/document/product/382。 云片网短信API:云片网是国内的一家短信服务提供商,他们提供了简单易用的短信API接口,用于发送验证码、通知短信等。文档地址:https://www.yunpian.com/doc/zh_CN/introduction/index.html。 极光短信API:极光推送是一家提供多种推送服务的服务提供商,其中包括短信推送服务。他们提供了短信API,可以用于发送短信验证码和通知短信。文档地址:https://docs.jiguang.cn/jpush/server/push/rest_api_v3_sms/。 结语建立这个平台的初衷: 打造一个仅包含前端问题的问答平台,让大家高效搜索处理同样问题。 通过不断积累问题,一起练习逻辑思维,并顺便学习相关的知识点。 遇到难题,遇到有共鸣的问题,一起讨论,一起沉淀,一起成长。 感谢关注微信公众号:“程序员大澈”,然后加入问答群,让我们一起解决实现所有BUG! |
CopyRight 2018-2019 实验室设备网 版权所有 |