神奇!這款 Vue 後台框架居然不用手動配置路由
前言
做 Vue 開發脫離不了路由,尤其是中大型項目,頁面多且雜,在配置路由的時候總是會變得逐漸暴躁,因為費時,並且又沒有什麼太多技術含量,總覺得是在浪費時間。
另外如果接手了別人的項目,當業務有變更,或者測試反饋有 bug 。通常需要先要根據頁面 URL 去找到對應配置的路由,然後對照 component
參數對應的 .vue
文件,操作繁瑣,效率也不高。
那有沒有一種辦法可以根據 .vue
文件自動生成路由,並且路由的 path
就是文件所在的文件夾路徑,這樣即節省了路由配置的時間,也提高了根據 URL 定位頁面文件的效率。
經過我的一番查找,還真找到了,就是下面這兩個插件:
使用
安裝
從這兩款插件的名字可以看出,這倆是 vite 的插件,並且僅支持 Vue3 ,那我就搬出我的 Fantastic-template 項目模版拿來測試了。
首先先安裝依賴。因為模版里自帶了 vue-router ,所以不需要再安裝。
pnpm add vite-plugin-pages vite-plugin-vue-layouts -D
安裝好依賴後,需要在 vite.config.js
里進行配置,由於這兩個插件作用不同,我們一個個來介紹如何使用。
vite-plugin-pages
這個是本次介紹的核心,它能夠將文件系統生成對應的路由,從而省去手動配置路由的時間。
首先在 vite.config.js
增加以下配置:
import Pages from 'vite-plugin-pages'
export default {
plugins: [
Pages({
dirs: 'src/views', // 需要生成路由的文件目錄
exclude: ['**/components/*.vue'] // 排除在外的目錄,即不將所有 components 目錄下的 .vue 文件生成路由
})
]
}
目前只需要配置這 2 個參數就夠了,其它還有更多參數可以去 vite-plugin-pages 項目頁了解。
接着在頁面中引入就可以使用了。
import { createRouter } from 'vue-router'
import routes from '~pages'
const router = createRouter({
// ...
routes
})
沒錯,就是這麼簡單,當然也有一些高階用法。比如通過 params 傳參的路由,要怎麼配置呢?
在 vite-plugin-pages 里提供了一種專用的寫法,就是 [ ]
。例如 src/views/example/[id].vue
這個文件,最終生成的路由 path
就是 /example/:id
。
針對 404 頁面,我們可以在創建個這樣的文件 src/views/[...all].vue
,它生成的路由就是 /:all(.*)*
。
除此之外,我們還可以在 .vue
文件中增加 <route></route>
代碼塊,這裏面默認接收 json5
格式的路由配置。需要注意的是,如果在 <route></route>
里配置了 path
和 name
,將會覆蓋自動生成的 path
和 name
。
<route>
{
path: '/xxx/yyy',
name: 'zzz',
meta: {
title: 'test page'
}
}
</route>
<template>
<div>
This is a test page.
</div>
</template>
這時候似乎還缺點什麼,對的,那就是嵌套路由。通過 vite-plugin-pages 自動生成的路由,都是一級路由。而實際項目開發中,我們會使用嵌套路由的特性,搭配 <router-view></router-view>
組件實現一些布局效果。
這時候就要介紹下面這款插件了
vite-plugin-vue-layouts
首先在 vite.config.js
修改下配置:
import Pages from 'vite-plugin-pages'
import Layouts from 'vite-plugin-vue-layouts'
export default {
plugins: [
Pages({
dirs: 'src/views', // 需要生成路由的文件目錄
exclude: ['**/components/*.vue'] // 排除在外的目錄,即所有 components 目錄下的 .vue 文件都不會生成路由
}),
Layouts({
layoutsDirs: 'src/layout', // 布局文件存放目錄
defaultLayout: 'index' // 默認布局,對應 src/layout/index.vue
})
]
}
更多配置參數請查看 vite-plugin-vue-layouts 項目頁。
也還是一樣,配置好後,就可以直接使用了。
import { createRouter } from 'vue-router'
import { setupLayouts } from 'virtual:generated-layouts'
import generatedRoutes from 'virtual:generated-pages'
const routes = setupLayouts(generatedRoutes)
const router = createRouter({
// ...
routes
})
這個插件只做一件事,就是把通過 vite-plugin-pages 生成的一級路由處理成嵌套路由,大概就是這樣:
// 處理前
{
path: '/login',
component: () => import('/src/views/login.vue'),
name: 'login'
}
// 處理後
{
path: '/login',
component: () => import('/src/layout/index.vue'),
children: [
{
path: '',
component: () => import('/src/views/login.vue'),
name: 'login'
}
]
}
如果你有多種布局,可以在 <route><route>
里進行設置:
<route>
{
meta: {
layout: 'other'
}
}
</route>
甚至還可以做一些魔改,比如項目中有的路由是需要用到布局頁面的,有的則不需要,那我們可以將不需要的頁面設置為 layout: false
:
<route>
{
meta: {
layout: false
}
}
</route>
同時在路由文件處使用下面這段代碼:
import { createRouter } from 'vue-router'
import { setupLayouts } from 'virtual:generated-layouts'
import generatedRoutes from 'virtual:generated-pages'
let routes = []
generatedRoutes.forEach(v => {
routes.push(v?.meta?.layout != false ? setupLayouts([v])[0] : v)
})
const router = createRouter({
// ...
routes
})
總結
通過下面這張圖配合總結吧:
文件系統 路由地址 路由 name
views
├─ example
│ ├─ components
│ │ └─ List
│ │ └─ index.vue
│ ├─ params
│ │ └─ [id].vue /example/params/:id example-params
│ ├─ axios.vue /example/axios example-axios
│ ├─ cookie.vue /example/cookie example-cookie
│ └─ svgicon.vue /example/svgicon example-svgicon
├─ [...all].vue /:all(.*)* all
├─ index.vue / index
└─ login.vue /login login
- 使用路由參數需通過
[ ]
將參數名包裹,並設為文件名 - 文件夾不會生成路由,例如 example 文件夾並沒有生成
/example
路由 - 路由 name 會根據文件的目錄結構自動生成,並用
-
連接,可確保 name 的唯一性 - 所有 components 目錄均不會生成路由
點題
這麼好用的特性,我也是第一時間集成進了我開發的 Fantastic-admin 後台框架中,如果你感興趣,可以點我詳細了解如何使用。