文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

基于Vue3和elementplus如何实现登录功能

2023-07-05 09:38

关注

这篇文章主要介绍了基于Vue3和elementplus如何实现登录功能的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇基于Vue3和elementplus如何实现登录功能文章都会有所收获,下面我们一起来看看吧。

登录页面:

基于Vue3和elementplus如何实现登录功能

注册页面:

基于Vue3和elementplus如何实现登录功能

(1)引入element-plus组件库

引入组件库的方式有好多种,在这里我就在main.js全局引入了.

npm i element-plus -S

main.js中代码:

import { createApp } from "vue";//element-plusimport ElementPlus from "element-plus";import "element-plus/dist/index.css";import App from "./App.vue";import router from "./router";import axios from "axios";import store from "./store";//创建实例const app = createApp(App);//全局应用配置app.config.globalProperties.$axios = axios; app.use(ElementPlus).use(store).use(router).mount("#app");

引入之后自己可以用几个按钮测试一下是否引入成功.

(2)登录及注册页面

html部分

views/account/Login.vue

<template>  <div id="login">    <div>      <div class="form-wrap">        <ul class="menu-tab">          <li            :class="{ current: current_menu === item.type }"            v-for="item in data.tab_menu"            :key="item.type"            @click="toggleMenu(item.type)"          >            {{ item.label }}          </li>        </ul>        <el-form          :model="data.form"          ref="account_form"          :rules="data.form_rules"          label-width="80px"        >          <el-form-item prop="username">            <label class="form-label">用户名</label>            <el-input type="password" v-model="data.form.username" />          </el-form-item>          <el-form-item prop="password">            <label class="form-label">密码</label>            <el-input type="password" v-model="data.form.password" />          </el-form-item>          <el-form-item v-show="current_menu === 'register'" prop="passwords ">            <label class="form-label">确认密码</label>            <el-input type="password" v-model="data.form.passwords" />          </el-form-item>          <el-form-item prop="code">            <label class="form-label">验证码</label>            <el-row :gutter="10">              <el-col :span="14">                <el-input v-model="data.form.code"></el-input>              </el-col>              <el-col :span="10">                <el-button                  type="success"                  class="el-button-block"                  @click="handleGetCode"                  >获取验证码</el-button                ></el-col              >            </el-row>          </el-form-item>          <el-form-item>            <el-button              type="danger"              class="el-button-block"              :disabled="data.submit_button_disabled"              :loading="data.submit_button_loading"              @click="submitForm"              >{{ current_menu === "login" ? "登录" : "注册" }}</el-button            >          </el-form-item>        </el-form>      </div>    </div>  </div></template>

js部分

<script>import { reactive, ref, getCurrentInstance, onBeforeUnmount } from "vue";import {  validate_email,  validate_password,  validate_code,} from "@/utils/validate";import { GetCode } from "@/api/common";import { Register, Login } from "@/api/account";import sha1 from "js-sha1"; //密码加密// ErrorHttpexport default {  setup() {    const instance = getCurrentInstance();    const { proxy } = getCurrentInstance();    console.log("instance", instance);    // console.log("proxy", proxy);    // 用户名校验    const validate_name_rules = (rule, value, callback) => {      let regEmail = validate_email(value);      if (value === "") {        callback(new Error("请输入邮箱"));      } else if (!regEmail) {        callback(new Error("邮箱格式不正确"));      } else {        callback();      }    };     //获取验证码    const handleGetCode = () => {      const username = data.form.username;      const password = data.form.password;      const passwords = data.form.passwords;      //校验用户名      if (!validate_email(username)) {        proxy.$message({          message: "用户名不能为空 或 格式不正确",          type: "error",        });        return false;      }       //校验密码      if (!validate_password(password)) {        proxy.$message({          message: "密码不能为空 或 格式不正确",          type: "error",        });        return false;      }       //判断为注册时,校验两次密码      if (data.current_menu === "redister" ** (password !== passwords)) {        proxy.$message({          message: "两次密码不一致",          type: "error",        });        return false;      }      //获取验证码接口      const requestData = {        username: data.form.username,        module: "register",      };       data.code_button_loading = true;      data.code_button_text = "发送中";      GetCode(requestData)        .then((res) => {          // console.log("123", res.data);验证码          // const data=res.resCode           const data = res;          if (data.resCode === 1024) {            proxy.$message.error(data.message);            return false;          }          // 成功 Elementui 提示          proxy.$message({            message: data.message,            type: "success",          });          //执行倒计时          countdown();        })        .catch((err) => {          console.log(err);          data.code_button_loading = false;          data.code_button_text = "发送验证码";        });       // ErrorHttp(requestData)      //   .then((res) => {      //     console.log(res.data);      //     // const data=res.resCode      //     const data = res.data;      //     if (data.resCode === 1024) {      //       proxy.$message.error(data.message);      //       return false;      //     }      //     // 成功 Elementui 提示      //     proxy.$message({      //       message: data.message,      //       type: "success",      //     });      //     //执行倒计时      //     countdown();      //   })      //   .catch((err) => {      //     console.log(err);      //     data.code_button_loading = false;      //     data.code_button_text = "发送验证码";      //   });    };         const countdown = (time) => {      if (time && typeof time !== "number") {        return false;      }      let second = time || 60; // 默认时间      data.code_button_loading = false; // 取消加载      data.code_button_disabled = true; // 禁用按钮      data.code_button_text = `倒计进${second}秒`; // 按钮文本      // 判断是否存在定时器,存在则先清除      if (data.code_button_timer) {        clearInterval(data.code_button_timer);      }      // 开启定时器      data.code_button_timer = setInterval(() => {        second--;        data.code_button_text = `倒计进${second}秒`; // 按钮文本        if (second <= 0) {          data.code_button_text = `重新获取`; // 按钮文本          data.code_button_disabled = false; // 启用按钮          clearInterval(data.code_button_timer); // 清除倒计时        }      }, 1000);    };     // 组件销毁之前 - 生命周期    onBeforeUnmount(() => {      clearInterval(data.code_button_timer); // 清除倒计时    });     // 校验确认密码    const validate_password_rules = (rule, value, callback) => {      let regPassword = validate_password(value);      if (value === "") {        callback(new Error("请输入密码"));      } else if (!regPassword) {        callback(new Error("请输入>=6并且<=20位的密码,包含数字、字母"));      } else {        callback();      }    };     // 校验确认密码    const validate_passwords_rules = (rule, value, callback) => {      // 如果是登录,不需要校验确认密码,默认通过      if (data.current_menu === "login") {        callback();      }      let regPassword = validate_password(value);      // 获取“密码”      const passwordValue = data.form.password;      if (value === "") {        callback(new Error("请输入密码"));      } else if (!regPassword) {        callback(new Error("请输入>=6并且<=20位的密码,包含数字、字母"));      } else if (passwordValue && passwordValue !== value) {        callback(new Error("两次密码不一致"));      } else {        callback();      }    };     const validate_code_rules = (rule, value, callback) => {      let regCode = validate_code(value);      // 激活提交按钮      data.submit_button_disabled = false;      if (value === "") {        callback(new Error("请输入验证码"));      } else if (!regCode) {        callback(new Error("请输入6位的验证码"));      } else {        callback();      }    };     // 提交表单    const submitForm = () => {      // let res = proxy.$refs.account_form;      proxy.$refs.account_form.validate((valid) => {        if (valid) {          console.log("提交表单", current_menu.value);          current_menu.value === "login" ? login() : register();          // register();        } else {          alert("error submit!");          return false;        }      });      // console.log(" 提交表单", res);    };        const login = () => {      const requestData = {        username: data.form.username,        password: sha1(data.form.password),        code: data.form.code,      };      data.submit_button_loading = true;      Login(requestData)        .then((response) => {          console.log("login", response);          data.submit_button_loading = false;          proxy.$message({            message: response.message,            type: "success",          });           reset();        })        .catch((error) => {          console.log("登录失败", error);          data.submit_button_loading = false;        });    };    //注册    const register = () => {      const requestData = {        username: data.form.username,        password: sha1(data.form.password),        code: data.form.code,      };      data.submit_button_loading = true;      Register(requestData)        .then((res) => {          proxy.$message({            message: res.message,            type: "success",          });        })        .catch((error) => {          console.log("注册错误", error);          data.submit_button_loading = false;        });    };         const reset = () => {      // 重置表单      proxy.$refs.form.resetFields();      // 切回登录模式      data.current_menu = "login";      // 清除定时器      data.code_button_timer && clearInterval(data.code_button_timer);      // 获取验证码重置文本      data.code_button_text = "获取验证码";      // 获取验证码激活      data.code_button_disabled = false;      // 禁用提交按钮      data.submit_button_disabled = true;      // 取消提交按钮加载      data.submit_button_loading = false;    };     const data = reactive({      form_rules: {        username: [{ validator: validate_name_rules, trigger: "change" }],        password: [{ validator: validate_password_rules, trigger: "change" }],        passwords: [{ validator: validate_passwords_rules, trigger: "change" }],        code: [{ validator: validate_code_rules, trigger: "change" }],      },      form: {        username: "", // 用户名        password: "", // 密码        passwords: "", // 确认密码        code: "", // 验证码      },      tab_menu: [        { type: "login", label: "登录" },        { type: "register", label: "注册" },      ],            code_button_disabled: false,      code_button_loading: false,      code_button_text: "获取验证码",      code_button_timer: null,      // 提交按钮      submit_button_disabled: true,    });     const toggleMenu = (type) => {      current_menu.value = type;    };    let current_menu = ref(data.tab_menu[0].type);    // const dataItem = toRefs(data);    return {      // ...dataItem,      data,      current_menu,      toggleMenu,      handleGetCode,      submitForm,      register,      reset,      login,    };  },};</script>

css部分(使用了scss)

<style lang="scss" scoped>#login {  height: 100vh;  background-color: #344a5f;}.form-wrap {  width: 320px;  padding-top: 100px;  margin: auto;}.menu-tab {  text-align: center;  li {    display: inline-block;    padding: 10px 24px;    margin: 0 10px;    color: #fff;    font-size: 14px;    border-radius: 5px;    cursor: pointer;    &.current {      background-color: rgba(0, 0, 0, 0.1);    }  }}.form-label {  display: block;  color: #fff;  font-size: 14px;}</style>

(3)封装一些公共方法及样式

新建styles文件夹,然后新建几个样式文件:

normalize.scss

    html, body, span, applet, object, iframe, h2, h3, h4, h5, h6, h7, p, blockquote, pre, a, abbr, acronym, address, big, cite, code, del, dfn, em, img, ins, kbd, q, s, samp, small, strike, strong, sub, sup, tt, var, b, u, i, center, dl, dt, dd, ol, ul, fieldset, form, legend, table, caption, tbody, tfoot, thead, tr, th, td, article, aside, canvas, details, embed,  figure, figcaption, footer, header, hgroup,  menu, nav, output, ruby, section, summary, time, mark, audio, video {   margin: 0;   padding: 0;   font-size: 100%;   font: inherit;   vertical-align: baseline; }  article, aside, details, figcaption, figure,  footer, header, hgroup, menu, nav, section {   display: block; } html {    line-height: 1.15;     -webkit-text-size-adjust: 100%;   }            body {    margin: 0;    font-family: 'Microsoft YaHei';    font-size: 14px;  }        main {    display: block;  }                  hr {    box-sizing: content-box;     height: 0;     overflow: visible;   }        pre {    font-family: monospace, monospace;     font-size: 1em;   }            a {    background-color: transparent;    text-decoration: none;  }         abbr[title] {    border-bottom: none;     text-decoration: underline;     text-decoration: underline dotted;   }        b,  strong {    font-weight: bolder;  }        code,  kbd,  samp {    font-family: monospace, monospace;     font-size: 1em;   }        small {    font-size: 80%;  }        sub,  sup {    font-size: 75%;    line-height: 0;    position: relative;    vertical-align: baseline;  }    sub {    bottom: -0.25em;  }    sup {    top: -0.5em;  }            img {    display: block;    border-style: none;  }            button,  input,  optgroup,  select,  textarea {    font-family: inherit;     font-size: 100%;     margin: 0;   }        button,  input {     overflow: visible;  }        button,  select {     text-transform: none;  }        button,  [type="button"],  [type="reset"],  [type="submit"] {    -webkit-appearance: button;  }        button::-moz-focus-inner,  [type="button"]::-moz-focus-inner,  [type="reset"]::-moz-focus-inner,  [type="submit"]::-moz-focus-inner {    border-style: none;    padding: 0;  }        button:-moz-focusring,  [type="button"]:-moz-focusring,  [type="reset"]:-moz-focusring,  [type="submit"]:-moz-focusring {    outline: 1px dotted ButtonText;  }        fieldset {    padding: 0.35em 0.75em 0.625em;  }        legend {    box-sizing: border-box;     color: inherit;     display: table;     max-width: 100%;     padding: 0;     white-space: normal;   }        progress {    vertical-align: baseline;  }        textarea {    overflow: auto;  }        [type="checkbox"],  [type="radio"] {    box-sizing: border-box;     padding: 0;   }        [type="number"]::-webkit-inner-spin-button,  [type="number"]::-webkit-outer-spin-button {    height: auto;  }        [type="search"] {    -webkit-appearance: textfield;     outline-offset: -2px;   }        [type="search"]::-webkit-search-decoration {    -webkit-appearance: none;  }        ::-webkit-file-upload-button {    -webkit-appearance: button;     font: inherit;   }            details {    display: block;  }        summary {    display: list-item;  }            template {    display: none;  }        [hidden] {    display: none;  }   ul, li { list-style: none; }

elementui.scss(当时测试时用的)

.el-button-block{    display: block;    width: 100%;}

新建main.scss(引入上方两个样式文件)

@import "./normalize.scss";@import './elementui.scss'

vue.config.js配置一下样式文件

  css: {    // 是否使用css分离插件 ExtractTextPlugin    extract: true,    // 开启 CSS source maps?    sourceMap: false,    // css预设器配置项    loaderOptions: {      scss: {        additionalData: `@import "./src/styles/main.scss";`,      },    },    // requireModuleExtension: true,  },

登录中封装的校验方法

新建utils文件夹,

a.validate.js

// 校验邮箱export function validate_email(value) {  let regEmail = /^([a-zA-Z]|[0-9])(\w|\-)+@[a-zA-Z0-9]+\.([a-zA-Z]{2,4})$/;  return regEmail.test(value);} // 校验密码export function validate_password(value) {  let regPassword = /^(?!\D+$)(?![^a-zA-Z]+$)\S{6,20}$/;  return regPassword.test(value);} // 校验验证码export function validate_code(value) {  let regCode = /^[a-z0-9]{6}$/;  return regCode.test(value);}

封装请求方法

npm i axios -S

记得先在main.js中引入axios

import axios from "axios";

utils中新建request.js

import axios from "axios";//引入element-plusimport { ElMessage } from "element-plus";console.log("11", process.env.VUE_APP_API); //undefined?? //创建实例const service = axios.create({  baseURL: "/devApi", //请求地址  timeout: 5000, //超时}); //添加请求拦截器service.interceptors.request.use(  function (config) {    //在发送请求之前做些什么    return config;  },  function (error) {    console.log(error.request);    const errorData = JSON.parse(error.request.response);    if (errorData.message) {      //判断是否具有message属性      ElMessage({        message: errorData.message,        type: "error",      });    }    //对请求错误做些什么    return Promise.reject(errorData);  }); //添加响  应拦截器service.interceptors.response.use(  function (response) {    //对响应数据做些什么    console.log("响应数据", response);    const data = response.data;    if (data.resCode === 0) {      return Promise.resolve(data);    } else {      ElMessage({        message: data.message,        type: "error",      });      return Promise.reject(data);    }  },  function (error) {    //对响应错误做些什么    const errorData = JSON.parse(error.request.response);    if (errorData.message) {      //判断是否具有message属性      ElMessage({        message: errorData.message,        type: "error",      });    }     return Promise.reject(errorData);  }); //暴露serviceexport default service;

(4)配置环境变量

和项目根路径同级,新建几个文件:

.env.development

VUE_APP_API = '/devApi'

可以自定义,但是必须是VUE_APP_XXX的格式

.env.production

VUE_APP_API = '/production'

.env.test

VUE_APP_API = '/test'

配置完后记得在axios文件中打印一下,看下能输出自己配置的环境变量吗.

基于Vue3和elementplus如何实现登录功能

(5)配置代理(跨域)

基本大同小异,代理地址改成自己的就可以了.

  devServer: {    open: false, //编译完成是否自动打开网页    host: "0.0.0.0", //指定使用地址,默认是localhost,0.0.0.0代表可以被外界访问    port: 8080,    proxy: {      "/devApi": {        target: "http://v3.web-jshtml.cn/api", //(必选)API服务器的地址        changeOrigin: true, //(必选) 是否允许跨域        ws: false, //(可选) 是否启用websockets        secure: false, //(可选) 是否启用https接口        pathRewrite: {          "^/devApi": "", //匹配开头为/devApi的字符串,并替换成空字符串        },      },    },  },

关于“基于Vue3和elementplus如何实现登录功能”这篇文章的内容就介绍到这里,感谢各位的阅读!相信大家对“基于Vue3和elementplus如何实现登录功能”知识都有一定的了解,大家如果还想学习更多知识,欢迎关注编程网行业资讯频道。

阅读原文内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     807人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     351人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     314人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     433人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     221人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯