vue 專案打包通過命令修改 vue-router 模式,修改 API 介面字首
需求說明:
在開發 vue 專案的過程中遇到的需求是要把 api 介面字首暴露在命令列,通過 npm run build apiUrl 即可修改介面入口,用於從 docker 部署到不同的測試伺服器上,其次是路由模式的問題,部署到測試伺服器上的需要是 history 模式,但是產品是用 electron + vue 開發的桌面應用,electron 硬性要求 vue-router 的路由模式是 hash 模式,所以命令列需新增一個配置項 mode ,mode 可選值有 history 、hash
最終結果:
npm run build '' hash ---> 使用原始碼中寫死的 api 入口 ,vue-router 模式是 hash 模式
npm run build https://192.168.166.101:8444 history ---> 使用 https://192.168.166.101:8444 作為 api 入口,vue-router 模式是 history 模式
實現:
1.新建 base/config.js 用於存放從 webpack.prod.conf.js 裡寫入的資料
2.新建 base/index.js 用於將從 base/config.js 裡匯出的 config 掛載在 Vue 原型的 $config 物件上
3.新建 build/apiConfig.js 用於封裝 fs-extra 對檔案的讀寫
4.在 webpack.prod.conf.js 將命令列中敲入的命令寫入 base/config.js 裡
5.在 main.js 中將 base/index.js 丟擲的 install 掛載到 Vue 上
6.在 Login.vue 和 router/index.js 裡引入 this.$config.host 以及 base/config.js 即可
關鍵程式碼:
2.新建 base/index.js 用於將從 base/config.js 裡匯出的 config 掛載在 Vue 原型的 $config 物件上
// 將 config 封裝成外掛 // example this.$config // 匯入所有介面 import config from './config'; const install = Vue => { if(install.installed) return; install.installed = true; Object.defineProperties(Vue.prototype, { // 此處掛載在 Vue 原型的 $config 物件上 $config:{ get(){ return config; } } }) } export default install;
3.新建 build/apiConfig.js 用於封裝 fs-extra 對檔案的讀寫
const fs = require("fs-extra");
const path = require("path");
var _path = path.join(__dirname, "../src/base/host.js");
if (!fs.pathExistsSync(_path)) {
// 如果不存在路徑
fs.mkdirpSync(_path); // 就建立
}
module.exports = {
read: function() {
let filesData = fs.readFileSync(_path, "utf-8", function(e, data) {
if (e) throw e;
return data;
});
return filesData;
},
write: function(writeStr) {
fs.open(_path, "w", function(e, fd) {
if (e) throw e;
fs.write(fd, writeStr, 0, "utf8", function(e) {
if (e) throw e;
fs.closeSync(fd);
});
});
}
};
4.在 webpack.prod.conf.js 將命令列中敲入的命令寫入 base/config.js 裡
const apiConfig = require('./apiConfig');
apiConfig.read();
apiConfig.write(
`export const host = '${process.argv[2]}';
export const mode = '${process.argv[3]}';
// 預設全部倒出
// 根絕需要進行
export default {
host,
mode
}`
);
5.在 main.js 中將 base/index.js 丟擲的 install 掛載到 Vue 上
import host from './base/index';
Vue.use(host);
6.在 Login.vue 裡引入 this.$config.host
this.$store.set("presetPort", this.$config.host ? this.$config.host.split(":")[2] : "443"); // 設定預置埠
this.$store.set("presetHost", this.$config.host ? this.$config.host.split(":")[0] : "https"); // 設定預置協議
this.$store.set("presetIP", this.$config.host ? this.$config.host.split(":")[1].split("/")[2] : "192.168.166.109"); // 設定預置IP
6.在 router/index.js 裡引入 base/config.js
import { mode } from '@/base/config';
let router = null;
let routes = [
{
path: 'xxx',
name: 'xxx',
component: xxx
}...];
mode === 'history' ? routes.push({path:"*",component:xxx}) : "";
router = new Router({
mode: mode,
routes:routes
})
export default router;