前言:vue3+ts+vite大家已經(jīng)都開始用了,最近也在學(xué)習(xí),基本上是零基礎(chǔ)開始ts的學(xué)習(xí),很多語法知識是邊寫邊查,沒有系統(tǒng)的學(xué)習(xí)ts。此處展示從零開始,搭建的一個框架,方便拿來即用!
1. 初始化一個vite項目
npm create vite@latest
其中框架選擇vue,語言選擇typeScript
2. 啟動項目
npm install
npm run dev
項目啟動成功以后如下所示:
3. 修改目錄
為了方便日常工作中的框架使用,在此處對剛初始化好的框架進(jìn)行改造,在原有框架的基礎(chǔ)上,添加store,router,layout,utils,views等文件夾,其中的作用將在后面進(jìn)行說明。如圖所示:
4. 配置router
首先安裝vue-router的依賴
npm install vue-router
在router文件夾下創(chuàng)建index.ts文件,配置如下:
import { createRouter, createWebHashHistory, RouteRecordRaw } from 'vue-router';
const routes: Array<RouteRecordRaw> = [
// 項目打開后進(jìn)入的默認(rèn)地址
{
path: '/',
redirect: '/login'
},
{
path: '/login',
component: () => import('../views/login/login.vue')
},
{
path: '/home',
component: () => import('../views/home/home.vue')
}
]
const router = createRouter({
history: createWebHashHistory(), // 本項目采用了哈希模式
routes
})
export default router
路由文件配置以后,需要在main.ts文件中進(jìn)行引用,如下所示:
import { createApp } from 'vue'
import './style.css'
import App from './App.vue'
const app = createApp(App)
// 路由設(shè)置
import router from './router/index'
app.use(router)
app.mount('#app')
修改app.vue文件,根據(jù)實際情況進(jìn)行修改,本項目中不需要初始化的helloWord組件,所以修改如下所示:
<script setup lang="ts">
</script>
<template>
<div>
<router-view></router-view>
</div>
</template>
<style scoped>
</style>
在views文件夾中創(chuàng)建login.vue文件,并重新啟動項目,如圖所示,跳轉(zhuǎn)到登陸頁面后表示路由配置成功:
vue文件中使用路由的方法如下:
import { useRouter, useRoute} from 'vue-router'
const router = useRouter()
const route = useRoute()
// 路由跳轉(zhuǎn)
router.push('/xxx')
**補充:**路由hash模式與history模式的區(qū)別
- hash模式
示例:http://localhost:5173/#/login
原理:利用window監(jiān)聽的onhashchange事件,不會包含在http請求中,對后端完全沒有影響。 - history模式
示例:http://localhost:5173/login
原理:地址發(fā)生改變后,會按照改變后的地址向服務(wù)端發(fā)送請求,需要后端配合處理,做地址映射。
5.配置vuex(pinia)
pinia 是一個擁有組合式API的狀態(tài)管理庫。
pinia官網(wǎng): https://pinia.vuejs.org/zh/introduction.html
首先安裝pinia的依賴
npm install pinia
在store文件夾中創(chuàng)建index.ts,具體內(nèi)容如下:
import type {App} from 'vue'
import { createPinia } from "pinia";
const store = createPinia()
export function setupStore(app:App<Element>) {
app.use(store)
}
export {store}
然后在store文件夾中創(chuàng)建modules文件夾,并創(chuàng)建user.ts 文件,用來保存用戶的基本信息。
import { defineStore } from 'pinia'
import { store } from '../index'
interface userInfoType {
username: string,
age: number,
gender: string
}
export const useUserStore = defineStore('user', () => {
// 此處使用的是組合式API的方式,更多情況可查看官網(wǎng)
let userInfo: userInfoType = {
username: '小明',
age: 18,
gender: '男'
}
return {
userInfo
}
},
)
// 最后到處定義的useUserStore
export function useUserStoreHook() {
return useUserStore(store)
}
store的基本信息配置好以后,需要在main.ts問價中掛載到app組件上,如下:
import { setupStore } from './store'
// 掛載store
setupStore(app);
存儲在vuex中的數(shù)據(jù)使用方式如下:
// login.vue 文件
<script setup lang="ts">
import { useUserStore } from '../../store/modules/user'
const userStore = useUserStore()
let userInfo = userStore.userInfo
</script>
<template>
<div class="login-wrap">
<p>登錄頁面</p>
{{ userInfo.username }}的年齡是{{ userInfo.age }}
</div>
</template>
<style scoped>
.login-wrap {
width: 100%;
height: 100vh;
background-size: 100% 100%;
position: relative;
box-sizing: border-box;
}
</style>
效果如下:
6. element-plus 的基本使用
首先安裝依賴
npm install element-plus
官網(wǎng): https://element-plus.org/zh-CN/guide/design.html
本項目中使用的是方法是在main.ts文件中完整導(dǎo)入!main.ts文件如下:
// element-plus
import ElementPlus from 'element-plus'
import 'element-plus/dist/index.css'
// 導(dǎo)入所有的icon圖標(biāo)
import * as ElementPlusIconsVue from '@element-plus/icons-vue'
app.use(ElementPlus)
for (const [key, component] of Object.entries(ElementPlusIconsVue)) {
app.component(key, component)
}
在vue文件中基本使用方法:
import { ElMessage } from 'element-plus'
ElMessage('你好')
7. axios封裝
對于前后分離的項目來說,綁定后端提供的接口進(jìn)行數(shù)據(jù)增刪改查是業(yè)務(wù)中較為重要的部分,此處對axios的使用進(jìn)行封裝,方便向服務(wù)斷發(fā)送請求。
依舊是安裝axios的依賴:
npm install axios
axios的接口封裝文件如下:
import axios from 'axios';
import type { AxiosInstance, AxiosRequestConfig, AxiosResponse, AxiosError } from 'axios'
import {getCookie,setCookie} from '../../utils/cookie'
const service: AxiosInstance = axios.create({
baseURL: import.meta.env.VITE_APP_API_BASEURL,
timeout: 15000,
headers: {
'Content-Type': 'application/json'
},
});
interface requestConfig extends AxiosRequestConfig {
headers?: any
}
// axios實例攔截請求
service.interceptors.request.use(
(config: requestConfig) => {
const token = getCookie('token');
if (token) {
config.headers.token = token
}
return config;
},
(error: AxiosError) => {
return Promise.reject(error);
},
);
// axios實例攔截響應(yīng)
service.interceptors.response.use(
(response: AxiosResponse) => {
if (response.status === 200) {
return response;
}
return response;
},
// 請求失敗
(error: any) => {
const { response } = error;
if (response) {
// 請求已發(fā)出,但是不在2xx的范圍
return Promise.reject(response.data);
}
},
);
/***
* post 方法封裝
*/
export function postMethod<T>(url:string,params?:any):Promise<T> {
return new Promise((resolve, reject) => {
service.post(url,params).then((res:any) => {
if(res.data.code === 200 && res.headers['token']) {
setCookie('token',res.headers['token'],21600)
}
resolve(res.data)
}).catch((err) => {
reject(err)
})
})
}
/***
* get 方法封裝
*/
export function getMethod<T>(url:string,params?:any):Promise<T> {
return new Promise((resolve, reject) => {
service.get(url,params).then((res:any) => {
if(res.data.code === 200 && res.headers['token']) {
setCookie('token',res.headers['token'],21600)
}
resolve(res.data)
}).catch((err) => {
reject(err)
})
})
}
/**
* 文件上傳 方法封裝
* 上傳文件傳參方式注意為form-data格式
*/
export function uploadFile<T>(url:string,uploadForm:any):Promise<T>{
const fd = new FormData()
fd.append('fileName', uploadForm.projectId)
fd.append('file', uploadForm.file)
return new Promise((resolve, reject) => {
service.post(url,fd,{
headers: {
'Content-Type': 'multipart/form-data'
}
}).then((res:any) => {
if(res.data.code === 200 && res.headers['token']) {
setCookie('token',res.headers['token'],21600)
}
resolve(res.data)
}).catch((err) => {
reject(err)
})
})
}
8. cookie封裝
用戶登錄的時候,提交表單信息,需要對接口返回的token進(jìn)行存儲,此處使用了cookie進(jìn)行存儲,可以利用js-cookie庫進(jìn)行cookie存儲,也可自己封裝方法,此處是封裝cookie的方法進(jìn)行cookie的存儲,獲取,以及清除,如下所示:
// cookie.ts
/**
* cookie 瀏覽器緩存
*/
const domain = ''
// 時間單位為秒
export function setCookie(c_name: string, value: any, expire?: any) {
var date: any = new Date()
date.setSeconds(date.getSeconds() + expire)
document.cookie = c_name + '=' + escape(value) + '; expires=' + date.toGMTString() + '; domain=' + domain + ';path=/'
}
export function getCookie(c_name: string) {
let c_start: number
let c_end: number
if (document.cookie.length > 0) {
c_start = document.cookie.indexOf(c_name + '=')
if (c_start != -1) {
c_start = c_start + c_name.length + 1
c_end = document.cookie.indexOf(';', c_start)
if (c_end == -1) c_end = document.cookie.length
return unescape(document.cookie.substring(c_start, c_end))
}
}
return ''
}
export function delCookie(c_name:string) {
setCookie(c_name, '', -1)
}
9. localStorage 使用
在獲取localStorage存儲信息時,發(fā)現(xiàn)存在一個問題,在vue文件中的setup的語法糖中,直接使用JSON的序列化方法會標(biāo)紅,可以正常使用,但是存在類型問題。將其進(jìn)行封裝后,發(fā)現(xiàn)這個問題不在出現(xiàn),在vue文件中使用時,直接引入即可。如下所示:文章來源:http://www.zghlxwxcb.cn/news/detail-464394.html
// localStorage.ts
/**
* window.localStorage 瀏覽器永久緩存
*/
export const localStorage = {
// 設(shè)置永久緩存
set(key: string, val: any) {
window.localStorage.setItem(key, JSON.stringify(val));
},
// 獲取永久緩存
get(key: string) {
const json: any = window.localStorage.getItem(key);
return JSON.parse(json);
},
// 移除永久緩存
remove(key: string) {
window.localStorage.removeItem(key);
},
// 移除全部永久緩存
clear() {
window.localStorage.clear();
}
};
10. 框架地址
gitee地址: https://gitee.com/free_project/vue3_ts_frame.git
目前只有一個空架子,針對表單的使用等還未進(jìn)行展示;因為對ts不熟,好多類型都設(shè)置了any。若有問題還請指出!文章來源地址http://www.zghlxwxcb.cn/news/detail-464394.html
到了這里,關(guān)于從0開始搭建一個vue3+vite+ts+pinia+element-plus的項目的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!