# vueTs **Repository Path**: lyfcloud/vue-ts ## Basic Information - **Project Name**: vueTs - **Description**: 使用vue3.0 + ts 构建的后台系统 - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 2 - **Forks**: 0 - **Created**: 2021-05-05 - **Last Updated**: 2022-05-25 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README ## 一、技术栈 - 开发环境:[Node](https://nodejs.org/en/) - 代码管理:[Git ](https://git-scm.com/) - 构建工具:[Vite 2.x](https://vitejs.dev/) - 前端框架:[Vue3.x](https://v3.vuejs.org/) - 编程语言:[TypeScript](https://www.typescriptlang.org/) - 路由工具:[Vue Router 4.x](https://next.router.vuejs.org/) - 状态管理:[Pinia]() - UI 框架:[Ant-Design-Vue](https://2x.antdv.com/docs/vue/introduce-cn/) - CSS 预编译:[Less](http://lesscss.cn/) - HTTP 工具:[Axios](https://axios-http.com/) ## 二、`vite` + `Ts` + `vue3.0`搭建 #### 1. 初始化 - 使用`npm` ```javascript npm init @vitejs/app ``` - 输入项目名`Project name`: `vue-ts` - 选择`vue` - 选择`Typescript` #### 2. 项目目录 ``` vue-ts | └───build -- 打包文件 │ │ util.ts -- 打包时的公共方法 │ node_modules -- 项目依赖包的目录 └───public -- 项目公用文件 │ │ favicon.ico -- 网站地址栏前面的小图标 └───src -- 源文件目录 │ │ assets -- 静态文件目录,图片图标,比如网站logo │ │ components -- Vue3.x的自定义组件目录 │ │ router -- 路由文件 │ │ views -- 视图文件 │ │ App.vue -- 项目的根组件,单页应用都需要的 │ │ main.ts -- 项目入口文件 │ │ shims-vue.d.ts -- tS识别.vue的辅助文件 │ .gitignore -- git忽略提交文件 │ index.html -- 首页入口文件 │ package-lock.json -- 项目配置文件,锁定版本号 │ package.json -- 项目配置文件 │ tsconfig.json -- ts配置文件 │ vite.config.ts -- vite配置文件 ``` #### 3. 配置环境变量 - 创建环境变量 ```jade # .env文件 是所有的env公共配置文件 VITE_PORT=9527 ``` ```jade # .env.development 开发环境配置 # 环境名称 VITE_GLOB_NAME = DEVELOPMENT # 是否删除Console.log VITE_DROP_CONSOLE = false ``` ```jade # .env.production 生产环境配置 # 环境名称 VITE_GLOB_NAME = PRODUCTION # 是否删除Console.log VITE_DROP_CONSOLE = true ``` ```jade # .env.test 测试环境配置 # 环境名称 VITE_GLOB_NAME = TEST # 是否删除Console.log VITE_DROP_CONSOLE = false ``` - 修改`package.json`文件 ```json { "scripts": { "dev": "vite", "build:test": "vue-tsc --noEmit && vite build --mode test", "build:prod": "vue-tsc --noEmit && vite build --mode production", "serve": "vite preview" } } ``` - 修改`vite.config.ts`文件, 增加以下配置 ```typescript import type { UserConfig, ConfigEnv } from 'vite' import { loadEnv } from 'vite' import { wrapperEnv } from './build/util' /** * @description 获取当前目录 */ const root: string = process.cwd() // https://vitejs.dev/config/ export default ({ command, mode }: ConfigEnv): UserConfig => { const env = loadEnv(mode, root) const viteEnv = wrapperEnv(env) const { VITE_PORT } = viteEnv return { root, server: { port: VITE_PORT } } } ``` - 创建`build`文件夹,并在下面创建一个`util.ts`文件 ```typescript export interface ViteEnv { VITE_PORT: number VITE_GLOB_NAME: string VITE_DROP_CONSOLE: boolean } /** * 读取env环境的配置,并配置到node的全局变量中 */ export function wrapperEnv(envConfig: any): ViteEnv { const ret: any = {} for (const envName of Object.keys(envConfig)) { ret[envName] = envConfig[envName] } process.env = { ...process.env, ...envConfig } return ret } ``` #### 4. 配置`alias` - 在`vite.config.ts`中配置 ```typescript resolve: { alias: { "@": resolve(__dirname, "src"), }, }, ``` - 在`tsconfig.json`中 配置 ```json { "baseUrl": ".", "paths": { "@/*": ["src/*"] } } ``` #### 5. 配置路由` vue-router@4` - 安装 ```javascript npm i vue-router@4 ``` - 创建`src/router/index.ts`文件 ```typescript /** * 路由 */ import type { RouteRecordRaw } from 'vue-router' import { createRouter, createWebHistory } from 'vue-router' const routes: RouteRecordRaw[] = [ { path: '/login', name: 'Login', component: () => import('@/views/login/index.vue') }, { path: '/', name: 'Dashboard', component: () => import('@/views/dashboard/index.vue') } ] const router = createRouter({ history: createWebHistory(), routes }) export default router ``` - 在`main.ts`中引入 ```typescript import router from '@/router/index' const app = createApp(App) app.use(router) app.mount('#app') ``` - 修改`App.vue`文件 ```vue ``` #### 6. 配置状态管理`pinia` - [文档地址](https://pinia.esm.dev/introduction.html) - 安装 ```javascript npm i pinia@next ``` - 创建`src/store/index.ts`文件 ```typescript import type { App } from 'vue' import { createPinia } from 'pinia' const store = createPinia() export function setupStore(app: App) { app.use(store) } export { store } ``` - 创建`src/store/modules/user.ts`文件 ```typescript import { defineStore } from 'pinia' export const useUserStore = defineStore({ id: 'app-user', state: () => ({ token: '11111111' }), getters: { getToken(): string { return this.token } }, actions: { setToken(info: string) { this.token = info } } }) ``` - 在`main.ts`中引入 ```typescript import { createApp } from 'vue' import { setupStore } from '@/store/index' const app = createApp(App) setupStore(app) app.mount('#app') ``` #### 7. 安装`UI`组件`antd` - 安装 ```js npm i ant-design-vue@next // UI npm i vite-plugin-style-import -D // 安装样式按需加载组件 ``` - 修改 vite.config.ts ```ts import styleImport from 'vite-plugin-style-import' export default ({ command, mode }: ConfigEnv): UserConfig => { return { ... plugins: [ ... styleImport({ libs: [ { libraryName: 'ant-design-vue', esModule: true, resolveStyle: (name) => { return `ant-design-vue/es/${name}/style/index` } } ] }) ] } } ``` - 创建 antd.ts ```ts /** * @description 按需引入antd */ import { Button } from 'ant-design-vue' import { App } from 'vue' const components = [Button] export function registerAntdComp(app: App) { components.forEach((comp: any) => { app.component(comp.name || comp.displayName, comp) }) } ``` - 使用 ```vue ``` - 在`main.ts`中引入样式 ```ts import { registerAntdComp } from '@/antd' registerAntdComp(app) ``` #### 8. 安装`css`预处理器`Less` - 安装 ```js npm i less -D ``` - 更改`main.ts`中`antd`样式的引入 ```ts import('ant-design-vue/dist/antd.less') // 注意:加上之后`vite`终端会报错 // 报错信息如下:[vite] Internal server error: Inline JavaScript is not enabled. Is it set in your options? ``` - 解决报错, 修改`vite.config.ts`文件,T 添加下面配置 ``` css: { preprocessorOptions: { less: { javascriptEnabled: true } } } ``` #### 9. 安装`axios` - 安装 ```js npm i axios ``` - 新建`src/utils/axios.ts` ```ts import Axios from 'axios' const baseURL = 'https://www.baidu.com' const axios = Axios.create({ baseURL, timeout: 20000 }) // 请求拦截 axios.interceptors.request.use( (response) => { // 可以根据请求数据进行处理 return response }, (error) => { return Promise.reject(error) } ) // 响应拦截 axios.interceptors.response.use( (response) => { // 对返回数据进行统一处理 return response }, (error) => { return Promise.reject(error) } ) ``` ## 三、代码规范 #### 1. 集成`Prettier`配置 - 安装`Prettier` ``` npm i prettier -D ``` - 创建`Prettier`的配置文件 `.prettierrc.js` - 配置`.prettierrc.js` ```js module.exports = { useTabs: false, tabWidth: 2, printWidth: 100, singleQuote: true, trailingComma: 'none', bracketSpacing: true, semi: false } ``` - 使用命令格式化代码 ``` npx prettier -w . ``` #### 2. 集成`ESLint` - 安装 ``` npm i eslint -D ``` - 配置`ESLint` - 执行`npx eslint --init`创建配置文件 - How would you like to use ESLint? **To check syntax, find problems, and enforce code style** - What type of modules does your project use? **JavaScript modules (import/export)** - Which framework does your project use? **Vue.js** - Does your project use TypeScript? **Yes** - Where does your code run? **Browser 和 Node** - How would you like to define a style for your project? **Use a popular style guide** - Which style guide do you want to follow? **Airbnb** - What format do you want your config file to be in? **JavaScript** - 生成`ESLint`的配置文件 ```js module.exports = { env: { browser: true, es2021: true, node: true }, extends: ['plugin:vue/essential', 'airbnb-base'], parserOptions: { ecmaVersion: 12, parser: '@typescript-eslint/parser', sourceType: 'module' }, plugins: ['vue', '@typescript-eslint'], rules: {} } ``` #### 3. 解决`Prettier`和`ESLint`冲突 - 安装`eslint-plugin-prettier`将 `Prettier `的规则设置到 `ESLint` 的规则中 - 安装`eslint-config-prettier` 关闭 ESLint 中与 Prettier 中会发生冲突的规则 ``` npm i eslint-plugin-prettier eslint-config-prettier -D ``` - 最后形成优先级:`Prettier 配置规则` > `ESLint 配置规则` - 在`.eslintrc.js`中添加`prettier`插件 ```js module.exports = { ... extends: [ 'plugin:vue/essential', 'airbnb-base', 'plugin:prettier/recommended' // 添加 prettier 插件 ], ... } ```