Vue组件开发之LeanCloud带图形校验码的短信发送功能


Posted in Javascript onNovember 07, 2017

有15万开发者使用LeanCloud服务,其中不乏知乎、懂球帝、爱范儿、拉卡拉等知名应用,LeanCloud提供了数据存储、即时消息……等一站式服务,并从常用的用户管理需求出发,提供了邮箱验证、短信验证……等用户账户相关的服务。

为防止攻击者恶意发送海量短信造成用户账户损失并影响正常业务,LeanCloud推出了免费图形校验码服务,并且可以在应用设置中设置“强制短信验证服务使用图形校验码”。

Vue组件开发之LeanCloud带图形校验码的短信发送功能

Vue是目前使用较广泛的三大前端框架之一,其数据驱动及组件化的特性使得前端开发更为快捷便利。

LeanCloud提供的由客户发起的短信发送场景主要有用户验证、用户密码重置,虽然不是很多场景,但如果每个场景下都单独进行图形校验码相关开发,则费时费力且对一些需要统一设置的参数调整不够灵活。

组件命名为Mobile,基于Element-UI的Form组件和Input组件进行开发,如果用户对布局和样式有特殊要求,只需要改为自己相应的组件,或者使用原生HTML元素并设置样式即可,同时需要将Element-UI提供的$message改为自己相应的API调用。

组件行为

开发的Mobile组件用于发送短信验证码,因此需要能够输入手机号码和图形校验码,并可触发发送短信的动作,触发发送短信动作成功后,需要禁用发送短信功能,并进行倒计时,倒计时结束后才能重新发送短信。

因此具体的组件行为主要是以下几点:

  • 提供一个输入手机号的输入框,该输入框内容可以由用户输入,也可以从用户信息中获取。
  • 提供一个输入图形校验码的输入框。
  • 页面加载完毕显示图形校验码。
  • 提供一个发送短信的按钮,用户点击发送短信的按钮,校验图形校验码,若校验通过,使用手机号码,并以图形校验码校验返回的validataionToken作为option参数发送短信。
  • 短信发送成功,禁用发送短信的按钮,启动定时器进行倒计时,倒计时结束后恢复发送短信的按钮。
  • 组件使用Element-UI的Form组件的布局,需要考虑el-form的labelWidth标签宽度设置与父组件中的el-form匹配。

其中发送短信的行为必须调用不同场景下的API,因此我们需要将此按钮绑定的事件emit到父组件,由父组件决定具体调用哪个API。

组件props

从上述组件行为出发,分析需要传入组件的props:

  • 表示手机号码属性。我们发送短信验证码的目的是最终用于后续的验证或密码重置操作,可以从外部传入,并且能够在组件内部修改后返回父组件,因此该属性必须是双向绑定的,Vue组件中双向绑定的属性有两种,一是自定义v-model,属性名必须是value,一是可以使用.sync修饰符绑定的属性,这里将手机号码属性设置为Mobile组件的v-model属性,属性名为value。
  • 通知Mobile组件短信已发送的属性。属性名为smsSent,类型为Boolean,以禁用发送短信的按钮,并启动倒计时。
  • el-form的labelWidth属性。设置默认值,并接受来自父组件中传递的数据以保持与父组件中其他元素/组件布局一致。

组件的props选项如下:

props: {
 labelWidth: {
 type: String,
 default: '100px'
 },
 value: String,
 smsSent: Boolean
},

组件模板中,与props相关的考量主要有如下三方面:

组件的根元素是一个el-form组件,其label-width属性绑定到来自父组件的labelWidth属性, <el-form ref="mobile-form">

手机号码输入框使用el-input组件,绑定到value属性,要实现双向绑定,不能直接使用v-model进行数据绑定,而是要将v-model绑定转换为v-bind:value属性绑定和@input事件绑定, <el-input :value="value" @input="value => $emit('input', value)"> ,这样就可以实现“v-model透传”。

(间接)发送短信按钮的禁用状态。发送短信按钮的禁用状态由倒计时的计数器组件data数据触发,当该数据不为0时,发送短信的按钮禁用。倒计时触发方式是通过父组件中绑定的smsSent属性,因此需要在子组件中watch该属性,并在该值为真是设置倒计时计数器,并通过setInterval进行倒计时。

图形校验码加载

为在组件加载时显示图形校验码,需要在组件的mounted生命周期钩子中调用LeanCloud的API。

AV.Captcha.request()的回调中绑定校验码输入框、图形校验码元素以及发送短信按钮元素,绑定参数对象的三个属性均可以是表示元素id的string或实际HTMLElement,由于我们创建的是Vue组件,因此直接使用组件的$refs属性来指定实际HTMLElement,需要注意的是,el-input中input元素是ref的$el属性的children[0],而el-button中button元素是ref的$el。

绑定函数还需要传入第二个参数,这是一个含有success和error方法的对象,用于提供图形校验码校验成功和失败的操作。

发送短信验证码

发送短信验证码在传递的第二个参数对象的success方法中进行,在这里,我们首先更新组件的smsSent属性为false,这样,当在父组件中实际完成短信发送之后设置smsSent为true时才会触发针对smsSent属性的watcher,同时,需要注意在父组件中绑定smsSent属性时,必须使用.sync修饰符。然后向父组件emit自定义sendSmsCode事件,并将success回调时的validateToken参数透传过去。

mounted () {
 this.$emit('update:smsSent', false)
 AV.Captcha.request().then((captcha) => {
 captcha.bind({
 textInput: this.$refs.captcha.$el.children[0],
 image: this.$refs.captchaImage,
 verifyButton: this.$refs.sendSms.$el
 }, {
 success: (validateToken) => {
 this.$emit('sendSmsCode', validateToken)
 },
 error: () => {
 this.$message.error('请输入正确的图形校验码!')
 }
 })
 })
}

组件使用

首先在父组件的组件选项中添加包含Mobile组件的components,然后在模板中添加mobile组件。

<mobile v-model="mobileForm.mobile"
 :sms-sent.sync="mobileForm.smsSent"
 @sendSmsCode="sendSms"></mobile>

其中绑定sendSmsCode事件的方法如下:

sendSms (validateToken) {
 this.sendSmsCode({
 mobile: this.mobileForm.mobile,
 validateToken
 }).then(() => {
 this.mobileForm.smsSent = true
 })
},

完整组件代码

<template>
 <el-form class="mobile-form"
  :label-width="labelWidth"
  ref="mobile-form">
 <el-form-item label="手机号码" prop="mobile">
 <el-input :value="value"
  @input="value => $emit('input', value)"
  :maxlength="11"
  type="tel">
 </el-input>
 </el-form-item>
 <el-form-item label="图形校验码">
 <el-input type="text" ref="captcha"></el-input>
 <img ref="captchaImage">
 </el-form-item>
 <el-form-item>
 <el-button type="info"
   ref="sendSms"
   :disabled="smsCodeCountingDown > 0 ||
    value.length !== 11">
 发送验证码
 </el-button>
 <span v-if="smsCodeCountingDown > 0">
   {{smsCodeCountingDown}} 秒后重新发送
  </span>
 </el-form-item>
 </el-form>
</template>
<script>
 import AV from 'leancloud-storage'
 export default {
 data () {
 return {
 smsCodeCountingDown: 0
 }
 },
 props: {
 labelWidth: {
 type: String,
 default: '100px'
 },
 value: String,
 smsSent: Boolean
 },
 watch: {
 smsSent (val) {
 if (val) {
  this.smsCodeCountingDown = 30
  let countingDownInterval = setInterval(() => {
  this.smsCodeCountingDown--
  if (this.smsCodeCountingDown === 0) {
  clearInterval(countingDownInterval)
  }
  }, 1000)
 }
 }
 },
 mounted () {
 AV.Captcha.request().then((captcha) => {
 captcha.bind({
  textInput: this.$refs.captcha.$el.children[0],
  image: this.$refs.captchaImage,
  verifyButton: this.$refs.sendSms.$el
 }, {
  success: (validateToken) => {
  this.$emit('update:smsSent', false)
leancloud  this.$emit('sendSmsCode', validateToken)
  },
  error: () => {
  this.$message.error('请输入正确的图形校验码!')
  }
 })
 })
 }
 }
</script>
<style scoped>
 .sms-code-form {
 width: 360px;
 }
</style>

总结

以上所述是小编给大家介绍的Vue组件开发之LeanCloud带图形校验码的短信发送功能,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
js checkbox(复选框) 使用集锦
Apr 28 Javascript
jquery 学习笔记 传智博客佟老师附详细注释
Sep 12 Javascript
Prototype源码浅析 Number部分
Jan 16 Javascript
js动态添加onload、onresize、onscroll事件(另类方法)
Dec 26 Javascript
js中Math之random,round,ceil,floor的用法总结
Dec 26 Javascript
JavaScript实现网页加载进度条代码超简单
Sep 21 Javascript
javascript弹出窗口实现代码
Nov 12 Javascript
JavaScript进阶练习及简单实例分析
Jun 03 Javascript
Vue学习笔记进阶篇之多元素及多组件过渡
Jul 19 Javascript
详解vue-router 初始化时做了什么
Jun 11 Javascript
使用vue-router为每个路由配置各自的title
Jul 30 Javascript
简单易扩展可控性强的Jquery转盘抽奖程序
Mar 16 jQuery
EasyUI实现下拉框多选功能
Nov 07 #Javascript
ES6中字符串string常用的新增方法小结
Nov 07 #Javascript
ES6中数组array新增方法实例总结
Nov 07 #Javascript
vue组件父子间通信详解(三)
Nov 07 #Javascript
浅谈ES6 模板字符串的具体使用方法
Nov 07 #Javascript
微信小程序上传图片到服务器实例代码
Nov 07 #Javascript
解决Vue使用mint-ui loadmore实现上拉加载与下拉刷新出现一个页面使用多个上拉加载后冲突问题
Nov 07 #Javascript
You might like
phpmyadmin中配置文件现在需要绝密的短语密码的解决方法
2007/02/11 PHP
Smarty中调用FCKeditor的方法
2014/10/27 PHP
php对二维数组进行相关操作(排序、转换、去空白等)
2015/11/04 PHP
php使用get_class_methods()函数获取分类的方法
2016/07/20 PHP
javascript RadioButtonList获取选中值
2009/04/09 Javascript
javaScript 页面自动加载事件详解
2014/02/10 Javascript
jQuery对val和atrr(&quot;value&quot;)赋值的区别介绍
2014/09/26 Javascript
Bootstrap每天必学之简单入门
2015/11/19 Javascript
require、backbone等重构手机图片查看器
2016/11/17 Javascript
利用CSS、JavaScript及Ajax实现图片预加载的方法
2016/11/29 Javascript
jQuery Ajax 实现在html页面实时显示用户登录状态
2016/12/30 Javascript
原生js jquery ajax请求以及jsonp的调用方法
2017/08/04 jQuery
vue实现打印功能的两种方法
2018/09/07 Javascript
Vue 解决父组件跳转子路由后当前导航active样式消失问题
2020/07/21 Javascript
详解JavaScript原型与原型链
2020/11/16 Javascript
[01:56]2014DOTA2西雅图邀请赛 MVP外卡赛老队长精辟点评
2014/07/09 DOTA
[03:11]DOTA2上海特锦赛小组赛第一日recap精彩回顾
2016/02/28 DOTA
python自动发送邮件脚本
2018/06/20 Python
python3实现随机数
2018/06/25 Python
python安装scipy的方法步骤
2019/06/26 Python
python  logging日志打印过程解析
2019/10/22 Python
python剪切视频与合并视频的实现
2020/03/03 Python
Python timeit模块原理及使用方法
2020/10/10 Python
HTTP状态码详解
2021/03/18 杂记
基于HTML5 Canvas的3D动态Chart图表的示例
2017/11/02 HTML / CSS
Canvas实现放大镜效果完整案例分析(附代码)
2020/11/26 HTML / CSS
有趣、实用和鼓舞人心的产品:Inspire Uplift
2019/11/05 全球购物
幼儿园教师工作感言
2014/02/15 职场文书
《要下雨了》教学反思
2014/02/17 职场文书
计算机专业毕业生自荐书
2014/06/02 职场文书
四风查摆问题及整改措施
2014/10/10 职场文书
2014年设备管理工作总结
2014/11/26 职场文书
入团介绍人意见范文
2015/06/04 职场文书
校园安全主题班会
2015/08/12 职场文书
2016大学先进团支部事迹材料
2016/03/01 职场文书
详解在OpenCV中如何使用图像像素
2022/03/03 Python