微前端
的核心理念是将前端应用程序看作是一个整体,由多个独立的部分组成。每个部分被视为一个微前端应用
,它们可以具有自己的技术栈、开发流程和团队组织。这种方式使得团队可以独立开发和部署各个子应用,减少了协调和合并的复杂性。
为了解决团队平台系统多且相互独立,系统体量大且页面多,开发效率低、接入成本高。
当前应用痛点:
最早也是最熟悉的解决方案就是通过iframe
显著的优点:
1.非常简单,无需任何改造
2.完美隔离,JS、CSS 都是独立的运行环境
3.不限制使用,页面上可以放多个 iframe 来组合业务
缺点非常突出:
1.无法保持路由状态,刷新后路由状态就丢失
2.完全的隔离导致与子应用的交互变得极其困难,只能采用postMessage
方式。
3.iframe 中的弹窗无法突破其本身
整个应用全量资源加载,加载太慢
qiankun
是一个基于 single-spa
的微前端实现库:qiankun文档
vue create mian
vue create sbuapp
npm i qiankun -S
main.js:
import Vue from 'vue'
import App from './App.vue'
Vue.config.productionTip = false
//qiankun配置
import { registerMicroApps, start } from 'qiankun';
//子应用列表
let apps = [
{
name:'subapp',
entry:'//localhost:8080',//子应用的地址,这里演示是本地启动的地址。
container:'#app',//子应用的容器节点的选择器(vue一般为app)
activeRule:'/subapp',//访问子应用的规则,比如:主应用为localhost:8081,那访问该子应用的url应为localhost:8081/subapp
}
]
//注册子应用
registerMicroApps(apps);
//启动
start();
new Vue({
render: h => h(App),
}).$mount('#app')
根目录创建public-path.js文件
//public-path.js
if (window.POWERED_BY_QIANKUN) {
webpack_public_path = window.INJECTED_PUBLIC_PATH_BY_QIANKUN;
}
main.js:
import Vue from 'vue'
import App from './App.vue'
Vue.config.productionTip = false
let instance = null;
function render(props = {}) {
const { container } = props;
instance = new Vue({
render: (h) => h(App),
}).$mount(container ? container.querySelector('#app') : '#app');
}
// 独立运行时
if (!window.POWERED_BY_QIANKUN) {
render();
}
export async function bootstrap() {
console.log('[vue] vue app bootstraped');
}
export async function mount(props) {
console.log('[vue] props from main framework', props);
render(props);
}
export async function unmount() {
instance.$destroy();
instance.$el.innerHTML = '';
instance = null;
}
这里先启动子应用,然后启动主应用,访问主应用OK:http://localhost:8084,然后著应用地址+/subapp 访问子应用:http://localhost:8084/subapp
跨域报错:
解决跨域问题
qiankun官网早就给出来了 https://qiankun.umijs.org/zh/guide/tutorial#vue-%E5%BE%AE%E5%BA%94%E7%94%A8
copy到子应用vue.config.js:
const { defineConfig } = require('@vue/cli-service')
const { name } = require('./package');
module.exports = defineConfig({
transpileDependencies: true,
devServer: {
headers: {
'Access-Control-Allow-Origin': '*',
},
},
configureWebpack: {
output: {
library: ${name}-[name],
libraryTarget: 'umd', // 把微应用打包成 umd 库格式
jsonpFunction: webpackJsonp_${name},