由登录页看项目结构

# 页面功能

在写登录页页面的时候,通过脚手架创建了工程目录,在main.js中引入了Arco Design Vue组件库,@arco-themes/vue-go-admin主题,SCSSaxiosPinia等插件。

src/router/目录下创建了index.js文件,定义了路由,在App.vue文件中引入了router-view标签。

src/views/目录下创建了login目录,定义了登录页。

至此,纯前端的工作已经完成,接下来需要与后端进行数据交互。

# 前后端交互

# 封装axios

src/utils/目录下创建request.js文件,封装axios。可以设置请求的拦截器,设置请求头等,异常处理等。

import axios from 'axios'
import { useUserStore } from '@/store/userInfo'
import { Message } from '@arco-design/web-vue'
const service = axios.create({
    baseURL: import.meta.env.VITE_APP_BASE_URL,
    timeout: 5000
})

service.interceptors.request.use(
    config => {
        const store = useUserStore();
        if(store.token){
            config.headers['Authorization'] = 'Bearer ' + store.token;
            config.headers['Content-Type'] = 'application/json';
        }
        return config
    },
    error => {
        console.log(error);
        return Promise.reject(error)
    }
)

service.interceptors.response.use(
    response =>{
        return response.data;
    },
    error => {
        const store = useUserStore();
        const {code,msg} = error.response.data;
        if(code === 401){
            Message.error({
                content: '登录过期,请重新登录',
                duration: 3000
            });
            store.userLogOut();
            return router.push('/login');
        }else{
            Message.error({
                content: error.message,
                duration: 3000
            });
            return Promise.reject(error);
        }
    }
);

export default service;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48

# api文件

src/api/目录下创建login.js文件,定义了登录接口。同样的,其他接口也在这个文件夹下,可以按模块分文件定义。

api文件中,引入request.js文件,将接口请求封装成函数。

import request from '@/utils/request'

export function getAppConfig() {
    return request({
        url: '/api/v1/app-config',
        method: 'get'
    })
}

export function login(data) {
    return request({
        url: '/api/v1/login',
        method: 'post',
        data
    })
}

export function getCaptcha() {
    return request({
        url: '/api/v1/captcha',
        method: 'get'
    })
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23

# 状态管理

项目使用Pinia作为状态管理工具,配置在src/store/目录下。

例如对于登录用户信息,可以在src/store/目录下创建userInfo.js文件,定义了用户信息的状态。

import { defineStore } from "pinia";
import { storage } from "@/utils/storage"
import { getInfo } from "@/api/admin/sys-user"
import { getAppConfig } from "@/api/admin/login"
export const useUserStore = defineStore('user', {
    state: () => {
        return {
            token: storage.getItem('token'),
            uid: storage.getItem('uid'),
            sysConfig: null,
            userInfo: null
        }
    },
    getters: {
        roles: (state) => state?.userInfo?.roles,
    },
    actions: {
        setToken(token) {
            this.token = token;
            storage.setItem('token', token);
        },
        async getUserInfo() {
            try {
                const { data } = await getInfo();
                storage.setItem('uid', data.userId);
                this.userInfo = data;
            } catch (e) {
                console.error(e);
            }
        },
        async getSysConfig() {
            const sysConfig = storage.getItem('sysConfig');
            if (sysConfig) {
                this.sysConfig = sysConfig;
            } else {
                try {
                    const { data, code, errorMessage } = await getAppConfig();
                    if (code === 200) {
                        storage.setItem('sysConfig', data);
                        this.sysConfig = data;
                    }
                } catch (e) {
                    console.error(e);
                }
            }
        },
        userLogOut() {
            storage.removeItem('token');
            this.token = null;
            this.userInfo = null;
        }
    }
})
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53

# 缓存

src/utils/目录下创建storage.js文件,封装对浏览器缓存的操作。

export const storage = {
    getKeys() {
        const keys = [];
        for (let i = 0; i < window.localStorage.Length; i++) {
            keys.push(window.localStorage.key(i));
        }
        returnkeys;
    },
    setItem(key,val) {
        if(typeof val !== 'string'){
            val = JSON.stringify(val);
        }
        if (key === undefined || key.trim().Length === 0){
            throw new Error('key is required');
        }
        window.localStorage.setItem(key,val);
    },
    getItem(key) {
        const val = window.localStorage.getItem(key);
        return val ? JSON.parse(val) : null;
    },
    removeItem(key) {
        window.localStorage.removeItem(key);
    },
    clearAllKeys() {
        window.localStorage.clear();
    }

}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29

# 项目结构

综上所述,项目的结构如下:

├── public
├── src
│   ├── api // 接口定义
│   ├── assets // 静态资源
│   ├── components // 组件
│   ├── router // 路由
│   ├── store // 状态管理
│   ├── utils // 工具函数
│   ├── views // 页面
│   ├── App.vue
│   ├── main.js
├── .env
├── index.html
├── vite.config.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
上次更新: 2024/11/10, 11:19:17
最近更新
01
G1垃圾收集器的参数调优
02-23
02
内存占用过大排查
01-14
03
docker-compose笔记
01-12
更多文章>