【qiankun接入教程】umi项目与非umi项目接入

简介

qiankun 是一个基于 single-spa 的微前端实现库,旨在帮助大家能更简单、无痛的构建一个生产可用微前端架构系统。

什么是微前端(官网抄的)

微前端架构具备以下几个核心价值:

技术栈无关 主框架不限制接入应用的技术栈,微应用具备完全自主权

独立开发、独立部署 微应用仓库独立,前后端可独立开发,部署完成后主框架自动完成同步更新

增量升级

在面对各种复杂场景时,我们通常很难对一个已经存在的系统做全量的技术栈升级或重构,而微前端是一种非常好的实施渐进式重构的手段和策略

独立运行时 每个微应用之间状态隔离,运行时状态不共享

微前端架构旨在解决单体应用在一个相对长的时间跨度下,由于参与的人员、团队的增多、变迁,从一个普通应用演变成一个巨石应用( Frontend Monolith)后,随之而来的应用不可维护的问题。这类问题在企业级 Web 应用中尤其常见。

qiankun接入核心

  1. 基座应用与子应用都需要安装qiankun依赖
  2. 基座应用注册子应用
  3. 子应用修改打包输出为umd、同时解决dev环境跨域问题(cors方案,可参考qiankun官方文档)
javascript 复制代码
const { name } = require('./package');
module.exports = {
devServer: {
  headers: {
    'Access-Control-Allow-Origin': '*',
  },
},
configureWebpack: {
  output: {
    library: `${name}-[name]`,
    libraryTarget: 'umd', // 把微应用打包成 umd 库格式
    jsonpFunction: `webpackJsonp_${name}`, // webpack 5 需要把 jsonpFunction 替换成 chunkLoadingGlobal
  },
},
};
  1. 子应用暴露qiankun生命周期钩子

接入场景与接入流程

接入场景主要分为umi项目和非umi项目,原因是因为umi提供了@umijs/plugin-qiankun插件一键开启微前端。

场景一

  • 基座应用与子应用都非umi项目

接入流程

  1. 主子应用安装qiankun依赖
  2. 主应用在项目入口文件中注入子应用
js 复制代码
import {registerMicroApps, start} from 'qiankun';

registerMicroApps([{
  name: 'child', // app name registered
  entry: '//localhost:8080', //子应用项目入口地址
  container: '#container',    //微前端挂在节点
  activeRule: '/',            //匹配路由
  props: {                    //初始化通信数据
    eventName: "TransferValue",
  }
}]);
start();   //开启qiankun
  1. 子应用入口文件暴露qiankun生命周期钩子函数
js 复制代码
export async function bootstrap() {
  console.log(' react app bootstraped');
}

export async function mount(props) {
}

export async function unmount(props) {
}
  1. 子应用需要在mountunmount去找到应用的挂在点和应用的卸载点
js 复制代码
function render(props) {
  const {container} = props;
  ReactDOM.render(<App/>, container ? container.querySelector('#root') : document.querySelector('#root'));
}

if (!window.__POWERED_BY_QIANKUN__) {
  render({});
}               //判断应用是否为qiankun挂在

export async function mount(props) {
  console.log(props)
  render(props);
}

export async function unmount(props) {
  const {container} = props;
  ReactDOM.unmountComponentAtNode(container ? container.querySelector('#root') : document.querySelector('#root'));
}
  1. 修改webpack(vite同理)打包配置,以下以create-react-app脚手架项目为例;安装react-app-rewired 依赖,然后在项目目录下新建config-overrides.js文件,配置打包,修改启动脚本。

6. 完成接入

场景二

  • 基座应用非umi项目
  • 子应用umi4

接入流程

  1. 基座应用接入流程不变
  2. 子应用umi4分为umi-maxumi-simple-appumi-simple-app子应用接入为例
  3. umi-simple-app安装umi插件集@umijs/plugins
  4. 在umi配置文件中开启qiankkun插件并且开启子应用qiankun配置
js 复制代码
export default defineConfig({
  plugins: ["@umijs/plugins/dist/qiankun"],
  qiankun:{
    slave:{}
  },
});
  1. app.js文件中开启qiankun生命周期
js 复制代码
export const qiankun = {
    // 应用加载之前
    async bootstrap(props: any) {
        console.log('app2 bootstrap', props);
    },
    // 应用 render 之前触发
    async mount(props: any) {
        console.log('app2 mount', props);
    },
    // 应用卸载之后触发
    async unmount(props: any) {
        console.log('app2 unmount', props);
    },
};
  1. 接入完成(umi-max内部集成qiankun插件、直接启动qiankun配置、暴漏出qiankun生命周期钩子即可)

场景三

  • 基座应用与子应用都是umi4

接入流程

  1. 基座应用和子应用同时安装@umijs/plugins,在umi配置文件中开启qiankun插件配置
js 复制代码
 plugins: ["@umijs/plugins/dist/qiankun"]

umi-max跳过此步骤、umi-max集成了此插件

  1. 基座应用开启qiankun配置
js 复制代码
   qiankun: {
        master: {
            apps: [
                {
                    name: "child1",
                    entry: "//localhost:3010"
                },
            ]
        }
    }
  1. 基座应用注入路由使用microApp匹配子应用
js 复制代码
 routes: [{path: "/child1", microApp: "child1"}]

基座应用配置完毕

  1. 子应用开启qiankun配置、并注入路由
js 复制代码
export default defineConfig({
  plugins: ["@umijs/plugins/dist/qiankun"],
  qiankun:{
    slave:{}
  },
  base:"/child2",
  routes: [
    { path: "/", component: "index" },
  ],
  npmClient: 'pnpm',
});
  1. 在app.js入口文件中暴漏qiankun生命周期
js 复制代码
export const qiankun = {
    // 应用加载之前
    async bootstrap(props: any) {
        console.log('app2 bootstrap', props);
    },
    // 应用 render 之前触发
    async mount(props: any) {
        console.log('app2 mount', props);
    },
    // 应用卸载之后触发
    async unmount(props: any) {
        console.log('app2 unmount', props);
    },
};
  1. 接入流程完毕

小结

  • qiankun的使用场景主要分为umi项目或者非umi项目
  • umi项目无论基座应用还是子应用都可以使用umi自动封装的插件快速开启微前端配置
  • umi无论基座应用还是子应用都可以根据qiankun官方文档开启微前端配置
  • 基座应用和子应用可根据上面场景灵活搭配

通信

基座应用在app.js中暴漏出的useQiankunStateForSlave函数

js 复制代码
export function useQiankunStateForSlave() {
  const [globalState, setGlobalState] = useState<any>({
    slogan: 'Hello MicroFrontend',
  });

  return {
    globalState,
    setGlobalState,
  };
}

子应用在需要使用的地方直接通过以下使用

js 复制代码
const masterProps = useModel('@@qiankunStateFromMaster');

子应用打包成静态资源引入场景场景

qiankun的文档中entry支持配置成对象,html一定是html字符串,script可以配置为需要注入的脚本地址 如以下所示:

js 复制代码
fetch('http://localhost:7001/dist/index.html') // 配置静态资源地址
  .then(response => response.text())
  .then(htmlString => {
    console.log(htmlString)
    registerMicroApps([{
      name: 'qiankun', // app name registered
      entry: {
        html: htmlString,
        scripts: ["http://localhost:7001/dist/umi.js", "http://localhost:7001/dist/p__index.async.js"] //需要注入的脚本地址
      },
      container: '#root-subapp-container', activeRule: '/test',
    }]);
    start();
  })
  .catch(error => {
    console.error('Error fetching the HTML file:', error);
  });

注意

  • 基座应用与子应用路由的模式需要同一,比如基座应用是hash路由,子应用也需要配置hash路由
  • 路由路径要同一(因为子应用需要基座应用注入的路由去进行匹配)
相关推荐
知否技术4 小时前
知道这10个npm工具包,开发效率提高好几倍!第2个大家都用过!
前端·npm
希希不嘻嘻~傻希希4 小时前
CSS 字体与文本样式笔记
开发语言·前端·javascript·css·ecmascript
石小石Orz5 小时前
分享10个吊炸天的油猴脚本,2025最新!
前端
爷_5 小时前
Nest.js 最佳实践:异步上下文(Context)实现自动填充
前端·javascript·后端
爱上妖精的尾巴6 小时前
3-19 WPS JS宏调用工作表函数(JS 宏与工作表函数双剑合壁)学习笔记
服务器·前端·javascript·wps·js宏·jsa
草履虫建模6 小时前
Web开发全栈流程 - Spring boot +Vue 前后端分离
java·前端·vue.js·spring boot·阿里云·elementui·mybatis
—Qeyser6 小时前
让 Deepseek 写电器电费计算器(html版本)
前端·javascript·css·html·deepseek
UI设计和前端开发从业者6 小时前
从UI前端到数字孪生:构建数据驱动的智能生态系统
前端·ui
Junerver7 小时前
Kotlin 2.1.0的新改进带来哪些改变
前端·kotlin
千百元8 小时前
jenkins打包问题jar问题
前端