vue3 + h5 构建流程

发布时间 2023-08-08 18:37:26作者: 半截肥皂

目录

初始化项目架构

一步一步搭建自己的Vue3 h5项目架构

备注:文档编写时间为 2023-8-8 注意依赖版本!
项目源码???

技术栈

工具类

  • NodeJs V16.20.0
  • Npm V8.19.4
  • Vite V4.4.8
  • Eslint V8.45.0
  • TypeScript V5.0.2
  • Vscode

环境

  • Vue V3.3.4
  • vue-router V4.2.4
  • Vuex V4.0.2
  • axios V1.4.0

搭建流程

初始化项目

yarn create vite my-vue-app --template vue-ts

初始化git

cd my-vue-app
git init
git add .
git commit -m "init"

运行项目

yarn
yarn dev

配置 server环境

vite.config.ts

// vite.config.ts
...
base: "./", // 打包路径
server: {
    port: 9999, // 服务端口号
    open: true, // 服务启动时是否自动打开浏览器
    cors: true, // 允许跨域
    host: "192.168.7.52" // 本机的局域网IP
}
...

配置项目环境

增加三个文件

修改package.json脚本

...
 "scripts": {
    "dev": "vite --mode dev",
    "test": "vue-tsc && vite build --mode test",
    "build": "vue-tsc && vite build --mode prot",
    "preview": "vite preview"
  },
  ...

如何使用

import.meta.env.VITE_BASE_URL

重新启动

yarn dev

配置 Eslint

***配置完成 Eslint 最好重新启动 Vscode!!!
yarn add -D eslint vite-plugin-eslint
yarn add -D eslint-plugin-vue
yarn add -D @typescript-eslint/eslint-plugin
yarn add -D @typescript-eslint/parser

增加文件 .eslintrc.cjs

具体文件在末尾

对 vite.config.ts 修改

***配置完成 Eslint 最好重新启动 Vscode!!!
import eslint from "vite-plugin-eslint";
// vite.config.ts
plugins: [vue(), eslint()],

重新启动

yarn dev

增加vue-router

yarn add vue-router@4

App.vue

<!-- src/App.vue -->
<template>
  <router-view />
</template>

router

// src/router/index.ts
import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";
import Home from "../pages/home/index.vue";
const routes: Array<RouteRecordRaw> = [
  {
    path: "/",
    name: "Home",
    component: Home,
    meta: {
      title: "首页"
    }
  }
];

const router = createRouter({
  history: createWebHistory(),
  routes
});

export default router;


home

<!-- src/pages/home/index.vue -->
<template>
  <p>home</p>
</template>
<script lang="ts" setup></script>
<style scoped></style>

main.ts引用 router

// ...
import router from "./router";
createApp(App).use(router).mount("#app");

重新启动

yarn dev

配置 src/@ 别名

对 vite.config.ts 修改

// vite.config.ts
import path from "path";
declare const __dirname: string;
// ...
resolve: {
    alias: {
        "@": path.resolve(__dirname, "src")
    }
},
// ...

对 tsconfig.ts 修改

"compilerOptions":{
    "baseUrl": ".",
    "paths": {
        "@/*": [
        "src/*"
        ]
    },
}
// ...

使用 @

// src/router/index.ts
// ...
import Home from "@/pages/home/index.vue";
// ...

关于类型设计

以模块的形式

对 tsconfig.ts修改

// 新增 typings/**/*.ts
// ...
 "include": ["src/**/*.ts", "src/**/*.d.ts", "src/**/*.tsx", "src/**/*.vue", "typings/**/*.ts"],
// ...

增加axios

官方文档介绍比较详细,点击下方???
***简单的http封装(文章末尾)

关于接口设计

接口设计思路,以模块的形式,比如 user是一个模块,商品是一个模块,订单是一个模块 目录结构 ???

.eslintrc.cjs


module.exports = {
  env: {
    browser: true,
    es2021: true
  },
  extends: [
    "eslint:recommended",
    "plugin:@typescript-eslint/recommended",
    "plugin:vue/vue3-essential"
  ],
  overrides: [
    {
      env: {
        node: true
      },
      files: [".eslintrc.{js,cjs}"],
      parserOptions: {
        sourceType: "script"
      }
    }
  ],
  parser: "vue-eslint-parser", // 新增
  parserOptions: {
    ecmaVersion: "latest",
    parser: "@typescript-eslint/parser",
    sourceType: "module"
  },
  plugins: ["@typescript-eslint", "vue"],
  rules: {
    "no-console": process.env.NODE_ENV === "production" ? "warn" : "off", //生产模式不允许使用log
    "no-debugger": "error", //生产默认不允许使用debugger
    "@typescript-eslint/no-explicit-any": "off",
    "vue/multi-word-component-names": "off",
    "vue/no-mutating-props": "off",
    "@typescript-eslint/no-unused-vars": "error",
    "generator-star-spacing": "off",
    indent: "off",
    "space-before-function-paren": "off",
    "vue/html-end-tags": "error", //标签必须闭合
    camelcase: "error", // 强制驼峰法命名
    eqeqeq: "error", // 要求使用 === 和 !==
    "no-eq-null": "error", // 禁止对null使用==或!=运算符
    "no-extra-parens": "error", // 禁止非必要的括号
    "no-extra-semi": "error", // 禁止多余的冒号
    "no-invalid-regexp": "error", // 禁止无效的正则表达式
    "no-multi-spaces": "error", // 不能用多余的空格
    "vue/require-v-for-key": "error", // vue的for循环是否必须有key
    "no-var": "off", // 禁用var,用let和const代替
    "no-self-compare": "error", // 不能比较自身
    "no-redeclare": "error", // 禁止重复声明变量
    quotes: [2, "double"], // 必须使用双引号
    semi: [2, "always"], // 语句强制分号结尾
    "comma-dangle": [2, "never"], // 数组和对象键值对最后一个逗号, never参数:不能带末尾的逗号, always参数:必须带末尾的逗号
    "no-undef": "off"
  }
};

axios简单封装

// src/tools/http.ts
import axios from "axios";
// 创建 axios 实例
const service = axios.create({
  /* 基础地址 一般都是动态的 */
  baseURL: GLOBAL_API_URL,
  /* 请求类型定义 */
  // headers: {
  //   'Content-Type': 'application/x-www-form-urlencoded;charset=UTF-8'
  // },
  /* 如果用的JSONP,可以配置此参数带上cookie凭证,如果是代理和CORS不用设置 */
  withCredentials: false,
  /* 请求超时时间 */
  timeout: 6000
});

/**
 * http request 拦截器
 */
service.interceptors.request.use(
  (config) => {
    const token = localStorage.getItem("szd_token"); /* 获取token */
    if (token) {
      /* 让每个请求携带自定义 token 请根据实际情况自行修改 */
      config.headers["token"] = `${token}`;
    }
    if (config.method === "get") {
      /* 让每个请求都携带一个不同的时间参数,防止浏览器缓存不发送请求 */
      config.params = {
        ...config.params
      };
    }

    return config;
  },
  (error) => {
    return Promise.reject(error);
  }
);

/**
 * http response 拦截器
 */
service.interceptors.response.use(
  (response) => {
    return response.data;
  },
  (error) => {
    console.log("请求出错:", error);
  }
);

export default service;