第八节:Element Plus 基础、封装通用组件 + 路由守卫
本节目标:
- 写全局路由守卫,未登录拦截跳登录页
- Pinia 数据持久化(刷新页面 token 不丢失)
- 封装一个简单全局通用组件示例
- 完善退出登录功能
步骤 1:Pinia 持久化(本地存储 localStorage)
修改 src/stores/user.js
import { defineStore } from 'pinia'
export const useUserStore = defineStore('user', {
state: () => ({
token: localStorage.getItem('token') || '',
username: localStorage.getItem('username') || ''
}),
getters: {
isLogin: (state) => !!state.token
},
actions: {
setUserInfo(token, username) {
this.token = token
this.username = username
// 存入本地存储
localStorage.setItem('token', token)
localStorage.setItem('username', username)
},
logout() {
this.token = ''
this.username = ''
localStorage.removeItem('token')
localStorage.removeItem('username')
}
}
})
步骤 2:配置全局路由守卫 src/router/index.js
在文件末尾追加守卫代码
// 路由守卫
router.beforeEach((to, from, next) => {
const userStore = useUserStore()
// 访问登录页直接放行
if (to.path === '/login') {
next()
} else {
// 判断是否有token
if (userStore.isLogin) {
next()
} else {
// 没有token跳登录
next('/login')
}
}
})
export default router
⚠️注意:需要在 router 顶部导入 userStore
import { useUserStore } from '@/stores/user'
完整的 src/router/index.js 头部片段:
import { createRouter, createWebHistory } from 'vue-router'
import { useUserStore } from '@/stores/user'
// 布局组件
const Layout = () => import('@/layout/index.vue')
步骤 3:封装一个全局通用组件示例
新建 src/components/PageCard.vue,后台页面通用卡片容器,components 与 layout 同级
<template>
<el-card class="page-card">
<template #header>
<div class="card-header">
<span>{{ title }}</span>
</div>
</template>
<slot></slot>
</el-card>
</template>
<script setup>
defineProps({
title: {
type: String,
default: ''
}
})
</script>
<style scoped>
.page-card {
margin: 10px;
}
.card-header {
font-weight: bold;
font-size: 16px;
}
</style>
修改后台首页 src/views/dashboard/index.vue,测试我们封装的 PageCard 组件
<template>
<div>
<PageCard title="系统首页看板">
<p>欢迎进入仿若依Vue3 Setup后台管理系统</p>
<el-button type="danger" @click="handleLogout">退出登录</el-button>
</PageCard>
</div>
</template>
<script setup>
import { useUserStore } from '@/stores/user'
import { useRouter } from 'vue-router'
const userStore = useUserStore()
const router = useRouter()
const handleLogout = () => {
userStore.logout()
ElMessage.success('已退出登录')
router.push('/login')
}
</script>
因为配置了 unplugin 自动导入,
PageCard组件不需要手动 import,直接使用。
✅第八节测试
- 重启
pnpm dev - 直接在浏览器地址栏访问
/dashboard/index- 没有登录,自动拦截跳转
/login✔
- 没有登录,自动拦截跳转
- 使用账号
admin / 123456登录成功,进入首页 - 刷新浏览器页面:token、用户信息不会丢失(localStorage 持久化生效)✔
- 首页看到封装的 PageCard 卡片,点击【退出登录】,清空信息,跳回登录页 ✔
- F12 控制台无报错。
注意:此时 Layout 布局还只是简单占位,下一节正式开发完整 Layout(侧边栏、头部、折叠按钮)。
