如何用vue3+Element plus实现一个完整登录功能

 更新时间:2024年01月23日 15:15:26   作者:czy陈泽宇  
要实现用户的登录功能,可以使用Vue3和Element Plus,下面这篇文章主要给大家介绍了关于如何基于Vue3和Element Plus组件库实现一个完整的登录功能,文中提供了详细的代码示例,需要的朋友可以参考下

一、想要实现的效果

二、搭建登录静态

1、实现左边背景和右边登录栏的总体布局布局:

<el-row class="content">
    <!--el-col 列: -->
    <el-col :span="16" :xs="0" class="content-left"></el-col>
    <el-col :span="8" :xs="24" class="content-right">
<el-row>

2、账号密码登录和手机号码登录切换使用<el-tabs>组件实现:

3、其他省略

4、全部代码:

  <el-row class="content">
    <!--el-col 列: -->
    <el-col :span="16" :xs="0" class="content-left"></el-col>
    <el-col :span="8" :xs="24" class="content-right">
      <div class="loginContent">
        <div class="loginContentTop">
          <div class="header">
            <div class="logo">
              <img src="../assets/images/logo.png" alt="" class="image" />
            </div>
            <div class="fontSize">JinPiKa</div>
          </div>
          <span class="introduce">全球最大的代码托管平台</span>
        </div>
        <div class="loginContentForm">
          <div class="loginMethods">
            <el-tabs>
              <el-tab-pane
                label="账号密码登录"
                class="toLogin"
                :class="{ option: !option }"
                @click="toOption(0)"
              >
                <!-- loginForm: 表单数据对象-->
                <el-form
                  :model="loginForm"
                  :rules="loginFormRules"
                  style="width: 208px"
                >
                  <el-form-item label="" prop="username">
                    <el-input
                      :prefix-icon="User"
                      placeholder="用户名:user"
                      v-model="loginForm.username"
                      inline-message
                    ></el-input>
                  </el-form-item>
                  <el-form-item label="" prop="password">
                    <el-input
                      :prefix-icon="Lock"
                      placeholder="密码:user"
                      show-password
                      v-model="loginForm.password"
                      inline-message
                    ></el-input>
                  </el-form-item>
                </el-form>
              </el-tab-pane>
              <el-tab-pane
                label="手机号码登录"
                class="toLogin"
                :class="{ option: !option }"
                @click="toOption(0)"
              >
                <!-- loginForm: 表单数据对象-->
                <el-form
                  :model="loginFormPhone"
                  :rules="loginFormPhoneRules"
                  style="width: 208px"
                  prop="phone"
                >
                  <el-form-item label="">
                    <el-input
                      :prefix-icon="User"
                      placeholder="请输入手机号"
                      v-model="loginFormPhone.phone"
                      inline-message
                    ></el-input>
                  </el-form-item>
                  <el-form-item label="" prop="code">
                    <el-input
                      :prefix-icon="Lock"
                      placeholder="请输入验证码"
                      v-model="loginFormPhone.code"
                      inline-message
                    ></el-input>
                  </el-form-item>
                </el-form>
              </el-tab-pane>
            </el-tabs>
          </div>
        </div>
        <div class="loginContentButton">
          <div class="buttonTop">
            <el-checkbox v-model="checked" label="自动登录" size="small" />
            <el-link type="primary" :underline="false">
              <span style="font-size: 12px">忘记密码</span>
            </el-link>
          </div>
          <el-button type="primary" class="loginButton" @click="tologin">
            登录
          </el-button>
          <el-divider>
            <span class="fengexian">其他登录方式</span>
          </el-divider>
          <div class="svgItems">
            <div class="svgItem">
              <svg-icon
                name="zhifubao"
                width="18px"
                height="18px"
                color="pink"
              ></svg-icon>
            </div>
            <div class="svgItem">
              <svg-icon
                name="taobao"
                width="18px"
                height="18px"
                color="pink"
              ></svg-icon>
            </div>
            <div class="svgItem">
              <svg-icon
                name="weibo"
                width="18px"
                height="18px"
                color="pink"
              ></svg-icon>
            </div>
          </div>
        </div>
      </div>
    </el-col>
  </el-row>

三、封装接口

1、首先需要对axios进行一个二次封装,实现请求和响应拦截器

在utils文件夹(一般用于存放封装的文件)下创建一个request.ts文件

import axios from 'axios'
const requeset=axios.create({
    baseURL: import.meta.env.BASE_URL,   //基础路径
    timeout:5000    //发请求超时时间为5s
})
//给request实例添加请求拦截器
request.interceptors.request.use((config)=>{
    // config:配置对象:里面有个headers属性请求头,经常给服务器端通过请求头携带公共参数
    return config
})
//配置响应拦截器
request.interceptors.response.use(
    //成功响应:返回服务端的数据    
    (response)=>{
        return response.data
    },
    //失败响应:会返回错误对象,用来处理http网络错误
    (error)=>{
    // 存储网络错误信息
    let message = ''
    // 根据http状态码判断网络错误
    const status = error.response.status
    switch (status) {
      case 401:
        message = '登录已过期,请重新登录'
        break
      case 403:
        message = '没有权限,请联系管理员'
        break
      case 404:
        message = '请求资源不存在'
        break
      case 500:
        message = '服务器内部错误'
        break
      default:
        // eslint-disable-next-line @typescript-eslint/no-unused-vars
        message = '网络错误'
        break
    }
    // 提示错误信息
    ElMessage({
      type: 'error',
      message,
    })
    // 返回一个失败的promise对象
    return Promise.reject(error)
    }

)

2、引入pinia

(1)在store文件夹下创建pinia仓库,

// 引入 pinia
import { createPinia } from 'pinia'
// 创建大仓库
const pinia = createPinia()
// 对外暴露
export default pinia

(2)在main.ts中,引入仓库并全局使用pinia

// 引入仓库
import pinia from './store'
// 全局使用 pinia
app.use(pinia)

3、在api文件夹下,封装登录接口,用于统一管理用户相关的接口

// 引入封装好的 request
import request from '@/plugins/request'
// 引入用户相关的 ts 类型检测
import { loginForm, loginResponseData } from './type'
//用户相关接口的请求地址
enum API{
    //用户登录的请求地址:在接口文档中,去掉默认请求地址baseURL后剩下的部分
    LOGIN='/admin/login'
}
//登录接口
export const reqLogin=(data:loginForm)=>{
    request.post<any,loginResponseData>(API.LOGIN,data)
}

或者第二种普通封装方式:

// 封装登录相关接口
import { loginForm } from '@/apis/user/type'
import request from '@/utils/request'
export function useLoginAPI(data: loginForm) {
  return request({
    url: 'http://monitor-spring.jinxinapp.cn/api/v1/admin/login',
    method: 'POST',
    data,
  })
}

4、在store文件夹下创建用户相关的小仓库

// 用户相关的小仓库
import { defineStore } from 'pinia'
//引入登录接口
import {reqLogin} from '@/api/user/index.ts'
const useUserStore=defineStore('user',{
    state:()=>{
        return{
            token:localStorage.getItem('token'),
        }
    },
    actions:{
        //用户登录的方法,data是登录时传入的账号密码
        async useLogin(data:loginForm){
            //登录请求
            const result=awiat reqLogin(data)
            if(result.code==200){
                this.token=result.data.token
                localStorage.getItem('token',result.data.token)
                   return 'ok'
            }else{
                return Promise.reject(new Error(result.data.message))
            }
        }
    },
    getters:{}
})
export default useUserStore

5、在登录页面,点击登录按钮调用tologin方法

const tologin=async ()=>{
    try{
        //调用仓库里的登录方法,传入的loginForm里面是账号密码
        await useStore.userLogin(loginForm)
        $router.push('/home')    //登录成功跳转首页,
        ElNotification({
              title: '成功',
              message: '登录成功',
              type: 'success',
        })
    }catch(error){
        ElNotification({
          message: (error as Error).message,
          type: 'error',
        })
    }
}

总结 

到此这篇关于如何用vue3+Element plus实现一个完整登录功能的文章就介绍到这了,更多相关vue3+Element plus登录功能内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Vue项目npm操作npm run serve或npm run dev报错及二者的区别

    Vue项目npm操作npm run serve或npm run dev报错及二者

    这篇文章主要介绍了Vue项目npm操作npm run serve或npm run dev报错及二者的区别说明,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-10-10
  • vue element如何添加遮罩层

    vue element如何添加遮罩层

    这篇文章主要介绍了vue element如何添加遮罩层问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-03-03
  • 基于vue2的canvas时钟倒计时组件步骤解析

    基于vue2的canvas时钟倒计时组件步骤解析

    今天给大家介绍一款基于vue2的canvas时钟倒计时组件,这个时钟倒计时组件采用canvas动画的炫酷动画效果形式,根据剩余时间的多少变换颜色和旋转扇形的速度,适合抢购、拍卖、下注等业务场景,且对移动端友好,需要的朋友可以参考下
    2018-11-11
  • vue实现电子时钟效果

    vue实现电子时钟效果

    这篇文章主要为大家详细介绍了vue实现电子时钟效果,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-08-08
  • Vue router错误跳转到首页("/")的问题及解决

    Vue router错误跳转到首页("/")的问题及解决

    这篇文章主要介绍了Vue router错误跳转到首页("/")的问题及解决方案,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-10-10
  • 关于Vue新搭档TypeScript快速入门实践

    关于Vue新搭档TypeScript快速入门实践

    这篇文章主要介绍了关于Vue新搭档TypeScript快速入门实践,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-09-09
  • vue.js内部自定义指令与全局自定义指令的实现详解(利用directive)

    vue.js内部自定义指令与全局自定义指令的实现详解(利用directive)

    这篇文章主要给大家介绍了关于vue.js内部自定义指令与全局自定义指令的实现方法,vue.js中实现自定义指令的主要是利用directive,directive这个单词是我们写自定义指令的关键字,需要的朋友们下面跟着小编来一起学习学习吧。
    2017-07-07
  • vuex中使用对象展开运算符的示例

    vuex中使用对象展开运算符的示例

    本篇文章主要介绍了vuex中使用对象展开运算符的示例,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2017-09-09
  • vue组件定义,全局、局部组件,配合模板及动态组件功能示例

    vue组件定义,全局、局部组件,配合模板及动态组件功能示例

    这篇文章主要介绍了vue组件定义,全局、局部组件,配合模板及动态组件功能,结合实例形式分析了vue.js中组件的定义、全局组件、局部组件、配合模板组件及动态组件的相关使用方法与操作注意事项,需要的朋友可以参考下
    2019-03-03
  • vue获取dom元素注意事项

    vue获取dom元素注意事项

    这篇文章主要介绍了vue获取dom元素注意事项及vue获取dom元素的内容,需要的朋友可以参考下
    2017-12-12

最新评论