Kaynağa Gözat

fix: 修改密码/手机/邮箱增加人机校验

周玉环 3 gün önce
ebeveyn
işleme
9d64ea5527

+ 2 - 2
xinkeaboard-web/assets/language/en.js

@@ -37,7 +37,7 @@ export const lang_en = {
     '请输入账号/手机号': 'Please enter the account number / mobile phone number',
     '请输入手机号': 'Please enter phone number',
     '请输入验证码': 'Please enter verification code',
-    '获取验证码': 'get verification code',
+    '获取验证码': 'get code',
     's后获取': 'After obtaining s',
     '请输入正确的账号/手机号': 'Please enter the correct account number / mobile phone number',
     '请输入账号': 'Please enter your account',
@@ -630,7 +630,7 @@ export const lang_en = {
 
     //邮箱管理
     '请输入邮箱号': 'Please enter the mailbox number',
-    '请输入邮箱验证码': 'Please enter the mailbox codes,only accept numbers',
+    '请输入邮箱验证码': 'Please enter the mailbox codes',
     '请输入正确的邮箱验证码': 'Please enter a valid email address Verification Code',
 
     //设置登陆密码

+ 92 - 44
xinkeaboard-web/pages/member/email.vue

@@ -27,7 +27,7 @@
               :placeholder="L['请输入邮箱验证码']"
               type="number"
             ></el-input>
-            <div class="get_sms pointer" @click="getSmsCode">
+            <div class="get_sms pointer" @click="showHMVerify">
               {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
             </div>
           </div>
@@ -55,9 +55,9 @@
               :placeholder="L['请输入邮箱验证码']"
               type="number"
             ></el-input>
-            <div class="get_sms pointer" @click="getSmsCode">
+            <el-button :disabled="countDownM" :loading="getSmsLoading" class="get_sms pointer" @click="showHMVerify">
               {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
-            </div>
+            </el-button>
           </div>
           <el-input
             v-if="step == 2"
@@ -66,6 +66,13 @@
             :placeholder="L['请输入新邮箱']"
           >
           </el-input>
+          <div class="error_tip" v-if="emailErrorMsg">
+            <span
+              style="color: #e1251b; font-size: 14px"
+              class="iconfont icon-jubao"
+            ></span>
+            {{ emailErrorMsg }}
+          </div>
           <div
             v-if="step == 2"
             class="sms_code_con flex_row_center_center margin"
@@ -75,9 +82,9 @@
               :placeholder="L['请输入邮箱验证码']"
               maxlength="6"
             ></el-input>
-            <div class="get_sms pointer" @click="getSmsCode">
+            <el-button :disabled="countDownM" :loading="getSmsLoading" class="get_sms pointer" @click="showHMVerify">
               {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
-            </div>
+            </el-button>
           </div>
           <div class="error_tip">
             <span
@@ -103,6 +110,20 @@
 <!--        </p>-->
 <!--      </div>-->
     </div>
+    <el-dialog
+      :title="L['register']['滑动验证']"
+      destroy-on-close
+      width="500px"
+      center
+      modal-class="email-verify-model"
+      v-model="modalVisible"
+    >
+      <SliderVerify
+        :slideVerifyOptions="{ show: false, w: 450, h: 220 }"
+        @onSuccess="verifySuccess"
+        @onFail="verifyFail"
+      />
+    </el-dialog>
   </div>
 </template>
 
@@ -122,15 +143,16 @@ definePageMeta({
 const { proxy } = getCurrentInstance();
 const step = ref(1);
 const errorMsg = ref("");
+const emailErrorMsg = ref("");
 const old_sms_code = ref("");
 const new_sms_code = ref("");
 const new_mobile = ref("");
 const timeOutId = ref(""); //定时器的返回值
 const countDownM = ref(0); //短信验证码倒计时
 const memberInfo = reactive({ data: filtersStore.getMemberInfo });
-const preventFre = ref(false);
 const getLatestMemberInfo = ref(false)
-
+const modalVisible = ref(false);
+const getSmsLoading = ref(false)
 
 const getMemberInfo = () => {
   get("v3/member/front/member/getInfo").then((res) => {
@@ -141,33 +163,41 @@ const getMemberInfo = () => {
     });
 }
 
-
-const getSmsCode = () => {
-  if (preventFre.value) {
-    return;
-  }
-  preventFre.value = true;
-  if (countDownM.value > 1) {
-    preventFre.value = false;
-    return;
-  } else {
-    //验证新邮箱是否正确
-    if (memberInfo.data.memberMobile && step.value == 2) {
-      if (!new_mobile.value) {
-        preventFre.value = false;
-        errorMsg.value = L["请输入邮箱号"];
+//开启人机校验
+const showHMVerify = () => {
+  //验证新邮箱是否正确
+  if (step.value == 2) {
+    if (!new_mobile.value) {
+      emailErrorMsg.value = L["请输入邮箱号"];
+      return;
+    } else {
+      let checkEmailVal = checkEmail(new_mobile.value);
+      if (checkEmailVal !== true) {
+        emailErrorMsg.value = checkEmailVal;
         return;
       } else {
-        let checkEmailVal = checkEmail(new_mobile.value);
-        if (checkEmailVal !== true) {
-          errorMsg.value = checkEmailVal;
-          preventFre.value = false;
-          return;
-        } else {
-          errorMsg.value = "";
-        }
+        emailErrorMsg.value = "";
       }
     }
+  }
+  modalVisible.value = true;
+};
+
+// 人机验证成功
+const verifySuccess = () => {
+  modalVisible.value = false;
+  getSmsCode();
+};
+
+// 人机校验失败
+const verifyFail = () => {
+  showMessage({
+    message: L["register"]["校验不通过"],
+    type: "warning",
+  });
+};
+
+const getSmsCode = () => {
     var param = {};
     param.verifyType = 1;
     //未绑定邮箱
@@ -179,34 +209,35 @@ const getSmsCode = () => {
         step.value == 1 ? memberInfo.data.memberEmail : new_mobile.value;
       param.changeType = step.value == 1 ? "old" : "new";
     }
+    getSmsLoading.value = true;
     get("v3/msg/front/commons/sendVerifyCode", param).then((res) => {
       if (res.state == 200) {
         countDownM.value = 60;
         countDown();
-        preventFre.value = false;
       } else {
         ElMessage.error(res.msg);
-        preventFre.value = false;
       }
-    });
-  }
+    }).finally(() => {
+        getSmsLoading.value = false;
+    })
+  
 };
 
 //绑定邮箱
 const bindEmail = () => {
-
   //验证邮箱是否正确
-  if (memberInfo.data.memberMobile && step.value == 2) {
+  if (step.value == 2) {
     if (!new_mobile.value) {
-      errorMsg.value = L["请输入邮箱号"];
+      emailErrorMsg.value = L["请输入邮箱号"];
       return false;
     } else {
       let checkEmailVal = checkEmail(new_mobile.value);
       if (checkEmailVal !== true) {
-        errorMsg.value = checkEmailVal;
+        emailErrorMsg.value = checkEmailVal;
         return false;
       }
     }
+    emailErrorMsg.value = ''
   }
   //验证码校验
   if (!new_sms_code.value) {
@@ -266,10 +297,8 @@ const bindEmail = () => {
     });
 };
 const next = () => {
-
   let param = {};
   let url = "";
-  preventFre.value = false;
   if (step.value == 1) {
     //验证码校验
     if (!old_sms_code.value) {
@@ -341,7 +370,6 @@ const next = () => {
 const countDown = () => {
   countDownM.value--;
   if (countDownM.value == 0) {
-    preventFre.value = false;
     clearTimeout(timeOutId.value);
   } else {
     timeOutId.value = setTimeout(countDown, 1000);
@@ -371,7 +399,19 @@ onUnmounted(() => {
 })
 
 </script>
+<style lang="scss">
+.email-verify-model {
+  .el-dialog__title {
+    font-weight: 900 !important;
+  }
 
+  .el-dialog__body {
+    display: flex;
+    justify-content: center;
+    align-items: center;
+  }
+}
+</style>
 <style lang="scss" scoped>
 .sld_email_mange {
   width: 957px;
@@ -437,17 +477,25 @@ onUnmounted(() => {
       }
 
       .sms_code_con {
+        position: relative;
         width: 100%;
 
         .get_sms {
-          width: 100px;
+          // display: flex;
+          // justify-content: center; /* 水平居中 */
+          // align-items: center; /* 垂直居中 */
+          // text-align: center; /* 多行文本居中 */
+          // position: absolute;
+          white-space: pre-wrap;
+          right: -25px;
+          top: 0;
+          width: 120px;
           height: 40px;
-          line-height: 38px;
           background: #00985e;
-          text-align: center;
           color: white;
           font-size: 14px;
           border-radius: 0 3px 3px 0;
+          padding: 5px 10px;
         }
       }
 

+ 77 - 24
xinkeaboard-web/pages/member/phone.vue

@@ -22,9 +22,9 @@
             :placeholder="L['请输入短信验证码']"
             type="number"
           ></el-input>
-          <div class="get_sms pointer" @click="getSmsCode">
+          <el-button :disabled="countDownM" :loading="getSmsLoading" class="get_sms pointer" @click="showHMVerify">
             {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
-          </div>
+          </el-button>
         </div>
         <el-input
           v-if="step == 2"
@@ -34,22 +34,28 @@
           type="number"
         >
         </el-input>
+        <div class="error_tip" v-if="newMobileErrorMsg">
+          <span
+            style="color: #e1251b; font-size: 14px"
+            class="iconfont icon-jubao"
+          ></span>
+          {{ newMobileErrorMsg }}
+        </div>
         <div
           v-if="step == 2"
-          class="sms_code_con flex_row_center_center margin"
+          class="sms_code_con margin"
         >
           <el-input
             v-model="new_sms_code"
             :placeholder="L['请输入短信验证码']"
             type="number"
           ></el-input>
-          <div class="get_sms pointer" @click="getSmsCode">
+          <el-button :disabled="countDownM" :loading="getSmsLoading" class="get_sms pointer" @click="showHMVerify">
             {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
-          </div>
+          </el-button>
         </div>
-        <div class="error_tip">
+        <div class="error_tip" v-if="errorMsg">
           <span
-            v-if="errorMsg"
             style="color: #e1251b; font-size: 14px"
             class="iconfont icon-jubao"
           ></span>
@@ -69,6 +75,20 @@
         </p>
       </div>
     </div>
+    <el-dialog
+      :title="L['register']['滑动验证']"
+      destroy-on-close
+      width="500px"
+      center
+      modal-class="phone-verify-model"
+      v-model="modalVisible"
+    >
+      <SliderVerify
+        :slideVerifyOptions="{ show: false, w: 450, h: 220 }"
+        @onSuccess="verifySuccess"
+        @onFail="verifyFail"
+      />
+    </el-dialog>
   </div>
 </template>
 
@@ -87,6 +107,7 @@ definePageMeta({
 });
 const { proxy } = getCurrentInstance();
 const errorMsg = ref("");
+const newMobileErrorMsg = ref("");
 const step = ref(1);
 const old_sms_code = ref("");
 const new_sms_code = ref("");
@@ -95,32 +116,46 @@ const timeOutId = ref(""); //定时器的返回值
 const countDownM = ref(0); //短信验证码倒计时
 const memberInfo = reactive({ data: filtersStore.getMemberInfo });
 const preventFre = ref(false);
+const getSmsLoading = ref(false)
+const modalVisible = ref(false)
 if(memberInfo.data.memberMobile == null){
   step.value = 2
 }
-const getSmsCode = () => {
-  if (preventFre.value) {
-    return false;
-  }
-  preventFre.value = true;
+
+//开启人机校验
+const showHMVerify = () => {
   if (step.value == 2) {
     //手机号验证
     if (!new_mobile.value) {
-      preventFre.value = false;
-      errorMsg.value = L["请输入手机号"];
+      newMobileErrorMsg.value = L["请输入手机号"];
       return false;
     } else {
       let checkMobileVal = checkPhone(new_mobile.value);
       if (checkMobileVal !== true) {
-        errorMsg.value = checkMobileVal;
-        preventFre.value = false;
+        newMobileErrorMsg.value = checkMobileVal;
         return false;
       }
     }
+    newMobileErrorMsg.value = ''
   }
-  if (countDownM.value) {
-    return false;
-  }
+  modalVisible.value = true;
+};
+
+// 人机验证成功
+const verifySuccess = () => {
+  modalVisible.value = false;
+  getSmsCode();
+};
+
+// 人机校验失败
+const verifyFail = () => {
+  showMessage({
+    message: L["register"]["校验不通过"],
+    type: "warning",
+  });
+};
+
+const getSmsCode = () => {
   var param = {};
   param.verifyType = 2;
   param.changeType = step.value == 1 ? "old" : "new";
@@ -133,13 +168,11 @@ const getSmsCode = () => {
       countDownM.value = 60;
       countDown();
     } else {
-      preventFre.value = false;
       ElMessage.error(res.msg);
     }
   });
 };
 const next = () => {
-  preventFre.value = false;
   if (step.value == 1) {
     //验证码校验
     if (!old_sms_code.value) {
@@ -243,7 +276,19 @@ watch([old_sms_code, new_sms_code, new_mobile], () => {
   errorMsg.value = "";
 });
 </script>
+<style lang="scss">
+.phone-verify-model {
+  .el-dialog__title {
+    font-weight: 900 !important;
+  }
 
+  .el-dialog__body {
+    display: flex;
+    justify-content: center;
+    align-items: center;
+  }
+}
+</style>
 <style lang="scss" scoped>
 .sld_phone_mange {
   width: 957px;
@@ -289,17 +334,25 @@ watch([old_sms_code, new_sms_code, new_mobile], () => {
       }
 
       .sms_code_con {
+        position: relative;
         width: 100%;
 
         .get_sms {
-          width: 100px;
+          // display: flex;
+          // justify-content: center; /* 水平居中 */
+          // align-items: center; /* 垂直居中 */
+          // text-align: center; /* 多行文本居中 */
+          // position: absolute;
+          white-space: pre-wrap;
+          right: -25px;
+          top: 0;
+          width: 120px;
           height: 40px;
-          line-height: 38px;
           background: #00985e;
-          text-align: center;
           color: white;
           font-size: 14px;
           border-radius: 0 3px 3px 0;
+          padding: 5px 10px;
         }
       }
 

+ 56 - 14
xinkeaboard-web/pages/member/pwd/login.vue

@@ -34,9 +34,9 @@
               v-model="sms_code"
               :placeholder="L[contactType === 'email' ? '请输入邮件验证码' : '请输入短信验证码']"
             ></el-input>
-            <div class="get_sms pointer" @click="getSmsCode">
+            <el-button :disabled="countDownM" :loading="getSmsLoading" class="get_sms pointer" @click="showHMVerify">
               {{ countDownM ? countDownM + L["s后获取"] : L["获取验证码"] }}
-            </div>
+            </el-button>
           </div>
           <el-input
             type="password"
@@ -81,6 +81,20 @@
       <!--        <p>• {{ L["复杂的密码可使账号更安全且建议定期更换密码。"] }}</p>-->
       <!--      </div>-->
     </div>
+    <el-dialog
+      :title="L['register']['滑动验证']"
+      destroy-on-close
+      width="500px"
+      center
+      modal-class="register-verify-model"
+      v-model="modalVisible"
+    >
+      <SliderVerify
+        :slideVerifyOptions="{ show: false, w: 450, h: 220 }"
+        @onSuccess="verifySuccess"
+        @onFail="verifyFail"
+      />
+    </el-dialog>
   </div>
 </template>
 
@@ -111,6 +125,8 @@ const countDownM = ref(0); //短信验证码倒计时
 const memberInfo = reactive({ data: {} });
 const isSmsClick = ref(false);
 const getLatestMemberInfo = ref(false);
+const modalVisible = ref(false);
+const getSmsLoading = ref(false)
 
 const getMemberInfo = () => {
   get("v3/member/front/member/getInfo").then((res) => {
@@ -123,29 +139,43 @@ const getMemberInfo = () => {
 };
 getMemberInfo();
 
+//开启人机校验
+const showHMVerify = () => {
+  modalVisible.value = true;
+};
+
+// 人机验证成功
+const verifySuccess = () => {
+  modalVisible.value = false;
+  getSmsCode();
+};
+
+// 人机校验失败
+const verifyFail = () => {
+  showMessage({
+    message: L["register"]["校验不通过"],
+    type: "warning",
+  });
+};
+
 const getSmsCode = () => {
-  if (isSmsClick.value) {
-    return;
-  } else if (countDownM.value) {
-    return;
-  }
-  isSmsClick.value = true;
   var param = {};
   param.verifyType = 1;
-  param.verifyAddr = memberInfo.data.memberEmail;
+  const verifyAddr = contactType === 'email' ? memberInfo.data.memberEmail : memberInfo.data.memberMobile
+  param.verifyAddr = verifyAddr;
+  getSmsLoading.value = true;
   get("v3/msg/front/commons/sendVerifyCode", param).then((res) => {
     if (res.state == 200) {
       countDownM.value = 60;
       countDown();
-      isSmsClick.value = false;
     } else {
       ElMessage.error(res.msg);
-      isSmsClick.value = false;
     }
-  });
+  }).finally(() => {
+    getSmsLoading.value = false;
+  })
 };
 const next = () => {
-  isSmsClick.value = false;
   let url = "";
   let param = {};
   if (memberInfo.data.hasLoginPassword) {
@@ -206,7 +236,6 @@ const next = () => {
 const countDown = () => {
   countDownM.value--;
   if (countDownM.value == 0) {
-    isSmsClick.value = false;
     clearTimeout(timeOutId.value);
   } else {
     timeOutId.value = setTimeout(countDown, 1000);
@@ -219,7 +248,19 @@ watch([old_password, password, confirm_password], () => {
   confirm_password.value = confirm_password.value.substring(0, 20);
 });
 </script>
+<style lang="scss">
+.register-verify-model {
+  .el-dialog__title {
+    font-weight: 900 !important;
+  }
 
+  .el-dialog__body {
+    display: flex;
+    justify-content: center;
+    align-items: center;
+  }
+}
+</style>
 <style lang="scss" scoped>
 @import "@/assets/style/theme.scss";
 .sld_login_password_mange {
@@ -305,6 +346,7 @@ watch([old_password, password, confirm_password], () => {
           align-items: center; /* 垂直居中 */
           text-align: center; /* 多行文本居中 */
           position: absolute;
+          white-space: pre-wrap;
           right: -25px;
           top: 0;
           width: 120px;