vite+vue3初體驗(yàn)

簡介

使用最新的vue3,vite2,typescript等主流技術(shù)搭建的一個供學(xué)習(xí)參考的模版工程。

包含

  • 技術(shù)棧:使用 vue3,vite,typescript等前沿技術(shù)開發(fā)
  • ajax:二次封裝axios,統(tǒng)一管理接口
  • 主題:可自行修改element-plus主題樣式
  • 國際化:完善的國際化方案
  • 路由:動態(tài)路由生成方案
  • 組件:二次封裝了常用的組件
  • 工具:常用的指令,過濾器,storage存儲,工具函數(shù)

目錄結(jié)構(gòu)

|-- public                          # 靜態(tài)資源
|   |-- config.js                   # 配置文件
|   |-- favicon.ico                 # favicon圖標(biāo)
|-- src                             # 源代碼
|   |-- api                         # api請求
|   |   |-- modules                 # 模塊
|   |   |-- types                   # 接口定義
|   |   |-- abstract.ts             # 基類
|   |   |-- config.ts               # 字典表
|   |   |-- index.ts                # 入口文件
|   |   |-- intercept.ts            # 攔截器
|   |-- assets                      # 主題 變量等資源
|   |   |-- scss                    # scss變量
|   |   |-- theme                   # elemet主題
|   |-- components                  # 全局公共組件
|   |-- config                      # 全局公共配置
|   |-- layout                      # 全局layout
|   |-- locale                      # 國際化
|   |-- plugin                      # 三方插件
|   |-- router                      # 全局路由
|   |-- store                       # 全局vuex
|   |-- utils                       # 全局公用方法
|   |   |-- directives              # 指令
|   |   |-- storage                 # 持久化
|   |   |-- filters.ts              # 過濾器
|   |   |-- pager.ts                # 發(fā)布訂閱
|   |   |-- tools.ts                # 工具函數(shù)
|   |-- views                       # 所有頁面
|   |-- App.vue                     # 入口頁面
|   |-- main.ts                     # 入口文件
|   |-- shims-vue.d.ts              # ts聲明文件
|-- static                          # 靜態(tài)資源
|   |-- img                         # img
|   |-- svg                         # svg
|-- .editorconfig                   # editorconfig
|-- .env.dev                        # 環(huán)境變量 開發(fā)
|-- .env.pro                        # 環(huán)境變量 生產(chǎn)
|-- .env.proxy                      # 環(huán)境變量 代理
|-- .eslintignore                   # eslintignore
|-- .eslintrc.js                    # eslint 配置項(xiàng)
|-- .gitignore                      # gitignore
|-- babel.config.js                 # babel 配置項(xiàng)
|-- index.html                      # html模板
|-- package.json                    # package.json
|-- README.md                       # README
|-- tsconfig.json                   # tsconfig
|-- vite.config.ts                  # vite 配置文件

API管理

可參考上一章,ts對axios的簡單封裝

國際化

推薦使用vscode插件i18n Ally來協(xié)助開發(fā),具有以下功能

  • 內(nèi)聯(lián)翻譯顯示
  • 自動補(bǔ)全
  • 一鍵機(jī)器翻譯
  • 統(tǒng)一管理所有翻譯文案
  • 從代碼中提取文案
  • 轉(zhuǎn)跳到翻譯文件
  • 支持JSON和YAML
  • 支持多目錄工作區(qū)
  • 支持 vue-i18n,vuex-i18n,vue-i18next和nuxt-i18n
  • 插件自身多語言支持(English,簡體中文,繁體中文)
// settings.json配置
...
"i18n-ally.sourceLanguage": "zh-CN",
"i18n-ally.displayLanguage": "zh-CN",
"i18n-ally.enabledParsers": ["json"],
"i18n-ally.extract.targetPickingStrategy": "file-previous",
...

全局注冊

  • src/plugin/index.ts
import { Directive } from 'vue';
import filters, { FilterKey } from '@/utils/filters';
import * as directives from '@/utils/directives/index';
import storage from '@/utils/storage';
import customMessage from '@/components/custom/custom-message';
// 三方插件
import element from './element';
import i18n from './i18n';

// 探測是否支持webp
const canvas = document.createElement('canvas');
if (canvas.getContext && canvas.getContext('2d')) {
    try {
        const isWebp = canvas.toDataURL('image/webp').includes('data:image/webp').toString();
        storage('localstorage').set('isWebp', isWebp);
    } catch (e) {
        console.error(e);
    }
}

const install = (app: any): void => {
    // 掛載過濾器
    app.config.globalProperties.$filters = {};
    for(const key in filters) {
        app.config.globalProperties.$filters[key] = filters[key as keyof typeof FilterKey];
    }

    // 掛載指令
    Object.keys(directives).forEach(key => {
        app.directive(key, (directives as { [key: string]: Directive })[key]);
    });

    // 注冊element
    element.components.forEach((component) => {
        if (component.name) app.component(component.name as string, component);
    });
    Object.values(element.plugins).forEach(plugin => {
        app.use(plugin);
    });
    app.provide('$message', customMessage);

    // 注冊i18n
    app.use(i18n);
};
  • main.ts
import { createApp } from 'vue';
import App from './App.vue';
import router from './router';
import store from './store';
import * as CustomPlugin from './plugin';
import * as CustomComponents from './components/custom';

const app = createApp(App);

// 注冊全局組件
app.use(CustomComponents);
// 注冊全局 插件/過濾器/指令
app.use(CustomPlugin);

app.use(router).use(store).mount('#container');

項(xiàng)目配置項(xiàng)

環(huán)境變量,在import.meta.env對象上暴露環(huán)境變量

  • .env.dev
# .env.dev
NODE_ENV=development

VITE_Version = 'v1.0.0'
VITE_BaseURL = '//dev.backendapi.aid.connext.net.cn/'
  • abstract.ts
console.log(import.meta.env.VITE_BaseURL) // dev.backendapi.aid.connext.net.cn/

vite.config.ts

import { defineConfig, loadEnv } from 'vite';
import vue from '@vitejs/plugin-vue';
import viteCompression from 'vite-plugin-compression';
import styleImport from 'vite-plugin-style-import';
import vueI18n from '@intlify/vite-plugin-vue-i18n';
const path = require('path');
const port = 7000;
const timeStamp = Date.now();
  • vite插件使用
export default ({ mode }: { mode: string }): unknown => {
    process.env = {...process.env, ...loadEnv(mode, process.cwd())};
    return defineConfig({
        plugins: [
            vue(),
            viteCompression({
                verbose: true,
                disable: false,
                threshold: 1024 * 10,
                algorithm: 'gzip',
                ext: '.gz'
            }),
            styleImport({
                libs: [
                    {
                        libraryName: 'element-plus',
                        esModule: true,
                        ensureStyleFile: true,
                        resolveStyle: (name) => {
                            name = name.slice(3);
                            return `element-plus/packages/theme-chalk/src/${name}.scss`;
                        },
                        resolveComponent: (name) => {
                            return `element-plus/lib/${name}`;
                        }
                    }
                ]
            }),
            vueI18n({
                compositionOnly: false,
                include: path.resolve(__dirname, './src/locale/**')
            })
        ]
    });
};
  • 打包chunk命名和代碼分割
export default ({ mode }: { mode: string }): unknown => {
  process.env = {...process.env, ...loadEnv(mode, process.cwd())};
  return defineConfig({
    build: {
      assetsDir: 'static/assets',
      rollupOptions: {
        output: {
          entryFileNames: `static/js/[name].${process.env.VITE_Version}.t${timeStamp}.js`,
          chunkFileNames: `static/js/[name].${process.env.VITE_Version}.t${timeStamp}.js`,
          assetFileNames: `static/js/[name].${process.env.VITE_Version}.t${timeStamp}.[ext]`,
        },
        manualChunks(id) {
          const chunkMap = new Map();
          chunkMap.set(/[\\/]src[\\/]layout[\\/]/.test(id), 'basicLayout');
          chunkMap.set(/[\\/]src[\\/]components[\\/]/.test(id), 'basicComponent');
          chunkMap.set(/[\\/]node_modules[\\/]echarts[\\/]/.test(id), 'echarts');
          chunkMap.set(/[\\/]node_modules[\\/]lodash[\\/]/.test(id), 'lodash');
          chunkMap.set(/[\\/]node_modules[\\/]moment[\\/]/.test(id), 'moment');
          chunkMap.set(/[\\/]node_modules[\\/]qiankun[\\/]/.test(id), 'qiankun');
          chunkMap.set(/[\\/]node_modules[\\/]xlsx[\\/]xlsx.js/.test(id), 'xlsxIndex');
          chunkMap.set(/[\\/]node_modules[\\/]xlsx[\\/](?!(xlsx.js))/.test(id), 'xlsx');
          chunkMap.set(/[\\/]node_modules[\\/]element-plus[\\/]/.test(id), 'element');
          return chunkMap.get(true) || 'vendors';
        }
      }
    }
  });
};

安裝使用

  • 克隆項(xiàng)目
git clone https://github.com/sunweijieMJ/vite-vue3-temp.git
  • 安裝依賴
cd vite-vue3-temp

yarn
或
npm i

  • 運(yùn)行
yarn serve dev
或
npm run serve dev
  • 打包
yarn build pro
或
npm run build pro

附上 github 的項(xiàng)目地址:vite-vue3-temp,順手給樓主點(diǎn)個 star 吧

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容