微前端框架 single-spa
对于时刻将 “没有 js 做不到的事情” 视为座右铭的前端程序员们是不可能不造轮子的,鼎鼎大名的 single-spa 就这么被造出来了。
借助 single-spa,开发者可以为不同的子应用使用不同的技术栈,比如子应用 A 使用 vue 开发,子应用 B 使用 react 开发,完全没有历史债务。
single-spa 的实现原理并不难,从架构上来讲可以分为两部分:子应用和容器应用。
子应用与传统的单页应用的区别在于
- 不需要 HTML 入口文件,
- js 入口文件导出的模块,必须包括 bootstrap、mount 和 unmount 三个方法。
容器应用主要负责注册应用,当 url 命中子应用的路由时激活并挂载子应用,或者当子应用不处于激活状态时,将子应用从页面中移除卸载。其核心方法有两个:
registerApplication
注册并下载子应用
start
启动处于激活状态的子应用。
以下是 single-spa 的简单示例:
容器应用代码
<html> <body> <script src="single-spa-config.js"></script> </body> </html>
single-spa-config.js
代码如下:
import * as singleSpa from 'single-spa'; const appName = 'app1'; const app1Url = 'http://app1.com/app1.js' singleSpa.registerApplication('app1',() => loadJS(app1Url), location => location.pathname.startsWith('/app1')) singleSpa.start();
loadJS 方法是伪代码,表示加载 app1.js。开发者需要自己实现,或者借助 systemJS 来实现。
子应用代码:
//app1.js let domEl; export function bootstrap(props) { return Promise .resolve() .then(() => { domEl = document.createElement('div'); domEl.id = 'app1'; document.body.appendChild(domEl); }); } export function mount(props) { return Promise .resolve() .then(() => { domEl.textContent = 'App 1 is mounted!' }); } export function unmount(props) { return Promise .resolve() .then(() => { domEl.textContent = ''; }) }
优点
- 纯前端解决方案
- 可以使用多种技术栈
- 完善的生态
缺点
- 上手成本高
- 需要改造现有应用
- 跨应用的联调变得复杂
适用场景
以上介绍了三种常见的微前端架构方式。天生喜爱新事物的前端同学,早就想要一试了。那么问题来了。哪些场景适合微前端架构?采用哪种微前端实现方式?我的看法很简单:
- 业务模块相对独立的复杂单体应用
- 综合考虑团队技术能力和业务现状选择适合的方式
总结
以上介绍了三种常见的微前端实现方式:
- 使用 iframe 组合
- 服务端模板渲染组合
- 微前端框架 single-spa
接下来还会继续分享关于微前端在项目中应用,微前端框架 single-spa 的实现原理解析等微前端系列内容,敬请关注。