micro.jpeg
前言
微前端是一種多個(gè)團(tuán)隊(duì)通過(guò)獨(dú)立發(fā)布功能的方式來(lái)共同構(gòu)建現(xiàn)代化 web 應(yīng)用的技術(shù)手段及方法策略授段。
quankun 微前端架構(gòu)
quankun + vue 前端微應(yīng)用化實(shí)現(xiàn)
案例代碼中有詳細(xì)注釋說(shuō)明
github下載地址 front-micro-app
項(xiàng)目結(jié)構(gòu)
├── portal 主應(yīng)用
├── product 產(chǎn)品業(yè)務(wù)子應(yīng)用
├── trade 訂單業(yè)務(wù)子應(yīng)用
主應(yīng)用
1瓣赂、安裝 qiankun
yarn add qiankun # 或者 npm i qiankun -S
2、在主應(yīng)用中注冊(cè)微應(yīng)用
import { registerMicroApps, start ,setDefaultMountApp} from 'qiankun';
/**
* [基于路由配置]
* 通過(guò)將微應(yīng)用關(guān)聯(lián)到一些 url 規(guī)則的方式蚌父,實(shí)現(xiàn)當(dāng)瀏覽器 url 發(fā)生變化時(shí)植酥,自動(dòng)加載相應(yīng)的微應(yīng)用的功能会放。
* registerMicroApps(apps, lifeCycles?)
*/
registerMicroApps(
// apps - Array<RegistrableApp> - 必選著摔,
[
{
name: 'product', // 微應(yīng)用名稱布蔗,確保微應(yīng)用唯一
entry: '//localhost:7702', // 微應(yīng)用入口地址
container: '#container', // 微應(yīng)用的容器節(jié)點(diǎn)的選擇器或者 Element 實(shí)例
activeRule: '/product', // 微應(yīng)用的激活規(guī)則 (支持直接配置字符串或字符串?dāng)?shù)組衅码,當(dāng)配置為字符串時(shí)會(huì)直接跟 url 中的路徑部分做前綴匹配拯刁,匹配成功表明當(dāng)前應(yīng)用會(huì)被激活。)
},
{
name: 'trade',
entry: '//localhost:7703',
container: '#container',
activeRule: location => location.pathname.startsWith('/trade')
},
],
// 微應(yīng)用的一些注冊(cè)信息 lifeCycles - LifeCycles - 可選逝段,全局的微應(yīng)用生命周期鉤子
{
beforeLoad: app => console.log('before load', app.name),
beforeMount: [
app => console.log('before mount', app.name),
],
}
);
// 設(shè)置主應(yīng)用啟動(dòng)后默認(rèn)進(jìn)入的微應(yīng)用
setDefaultMountApp('/product');
/**
* prefetch - boolean | 'all' | string[] | (( apps: RegistrableApp[] ) => { criticalAppNames: string[]; minorAppsName: string[] }) - 可選垛玻,是否開(kāi)啟預(yù)加載,默認(rèn)為 true奶躯。
* 配置為 true 則會(huì)在第一個(gè)微應(yīng)用 mount 完成后開(kāi)始預(yù)加載其他微應(yīng)用的靜態(tài)資源帚桩,配置為 'all' 則主應(yīng)用 start 后即開(kāi)始預(yù)加載所有微應(yīng)用靜態(tài)資源。
* 配置為 'all' 則主應(yīng)用 start 后即開(kāi)始預(yù)加載所有微應(yīng)用靜態(tài)資源嘹黔。
* 配置為 string[] 則會(huì)在第一個(gè)微應(yīng)用 mounted 后開(kāi)始加載數(shù)組內(nèi)的微應(yīng)用資源
* 配置為 function 則可完全自定義應(yīng)用的資源加載時(shí)機(jī) (首屏應(yīng)用及次屏應(yīng)用)
* sandbox - boolean | { strictStyleIsolation?: boolean } - 可選账嚎,是否開(kāi)啟沙箱,默認(rèn)為 true儡蔓。
* 當(dāng)配置為 { strictStyleIsolation: true } 表示開(kāi)啟嚴(yán)格的樣式隔離模式郭蕉。這種模式下 qiankun 會(huì)為每個(gè)微應(yīng)用的容器包裹上一個(gè) shadow dom 節(jié)點(diǎn),從而確保微應(yīng)用的樣式不會(huì)對(duì)全局造成影響喂江。
* singular - boolean | ((app: RegistrableApp<any>) => Promise<boolean>); - 可選召锈,是否為單實(shí)例場(chǎng)景,默認(rèn)為 true获询。
* fetch - Function - 可選涨岁,自定義的 fetch 方法拐袜。
* getPublicPath - (url: string) => string - 可選
* getTemplate - (tpl: string) => string - 可選
*/
start({
singular: true
});
子應(yīng)用
1、main.js 導(dǎo)出相應(yīng)的生命周期鉤子
/**
* 微應(yīng)用靜態(tài)資源一定要支持跨域
* qiankun 將會(huì)在微應(yīng)用 bootstrap 之前注入一個(gè)運(yùn)行時(shí)的 publicPath 變量
* runtime publicPath 主要解決的是微應(yīng)用動(dòng)態(tài)載入的 腳本梢薪、樣式蹬铺、圖片 等地址不正確的問(wèn)題。
*/
if (window.__POWERED_BY_QIANKUN__) {
__webpack_public_path__ = window.__INJECTED_PUBLIC_PATH_BY_QIANKUN__
}
let router = null; // 路由
let instance = null; // vue實(shí)例
// 微應(yīng)用渲染方法
function render() {
router = new VueRouter({
base: window.__POWERED_BY_QIANKUN__ ? '/product' : '/',
mode: 'history',
routes,
});
router.beforeEach((to, from, next) => {
const title = to.meta && to.meta.title;
if (title) {
document.title = title;
}
next();
});
instance = new Vue({
router,
render: h => h(App),
}).$mount('#app');
}
// 獨(dú)立項(xiàng)目運(yùn)行時(shí) 渲染
if (!window.__POWERED_BY_QIANKUN__) {
render();
}
/**
* bootstrap 只會(huì)在微應(yīng)用初始化的時(shí)候調(diào)用一次沮尿,下次微應(yīng)用重新進(jìn)入時(shí)會(huì)直接調(diào)用 mount 鉤子丛塌,不會(huì)再重復(fù)觸發(fā) bootstrap。
* 通常我們可以在這里做一些全局變量的初始化畜疾,比如不會(huì)在 unmount 階段被銷毀的應(yīng)用級(jí)別的緩存等赴邻。
*/
export async function bootstrap() {
console.log('產(chǎn)品微應(yīng)用初始化 bootstrap');
}
/**
* 應(yīng)用每次進(jìn)入都會(huì)調(diào)用 mount 方法,通常我們?cè)谶@里觸發(fā)應(yīng)用的渲染方法
*/
export async function mount(props) {
console.log('產(chǎn)品微應(yīng)用渲染', props);
render();
}
/**
* 應(yīng)用每次 切出/卸載 會(huì)調(diào)用的方法啡捶,通常在這里我們會(huì)卸載微應(yīng)用的應(yīng)用實(shí)例
*/
export async function unmount() {
console.log('產(chǎn)品微應(yīng)用卸載');
instance.$destroy();
instance = null;
router = null;
}
/**
* 可選生命周期鉤子姥敛,僅使用 loadMicroApp(手動(dòng)加載) 方式加載微應(yīng)用時(shí)生效
*/
export async function update(props) {
console.log('update props', props);
}
2、vue.config.js 配置微應(yīng)用的打包工具
const packageName = require('./package.json').name;
module.exports = {
output: {
library: `${packageName}-[name]`,
libraryTarget: 'umd',
jsonpFunction: `webpackJsonp_${packageName}`,
},
};
The end ??
Thank you for reading
如果覺(jué)得文章對(duì)你有所幫助瞎暑,點(diǎn)個(gè)贊吧??