微前端学习笔记(6):为什么不用iframe?Web Components最佳?
Author:zhoulujun Date:
笔记,备份稿子……
Why not iframe
iframe 最大的特性就是提供了浏览器原生的硬隔离方案,不论是样式隔离、js 隔离这类问题统统都能被完美解决。但他的最大问题也在于他的隔离性无法被突破,导致应用间上下文无法被共享,随之带来的开发体验、产品体验的问题。
UI/URL 不同步:Iframe 与上层应用并非同一个文档上下文导致。这会导致iframe 内外系统的通信、数据同步等需求,主应用的 cookie 要透传到根域名都不同的子应用中实现免登效果。具体来看:
事件冒泡不穿透到主文档树上,焦点在子应用时,事件无法传递上一个文档流
主应用劫持快捷键操作
事件无法冒泡顶层,针对整个应用统一处理失效
跳转路径无法与上层文档同步,刷新丢失路由状态
Iframe 内元素会被限制在文档树中,视窗宽高限制问题
Iframe 登录态无法共享,子应用需要重新登录
Iframe 在禁用三方 cookie 时,iframe 平台服务不可用
Iframe 应用加载失败,内容发生错误主应用无法感知
全局上下文完全隔离,内存变量不共享。
性能问题与架构问题:
内存增大:使用 Iframe 会大幅增加内存和计算资源,因为 iframe 内所承载的页面需要一个全新并且完整的文档环境
无法共享基础库进一步减少包体积,而且每次子应用进入都是一次浏览器上下文重建、资源重新加载的过程。
无法预加载缓存 iframe 内容
事件通信繁琐且限制多
正因为iframe的这些问题,很多微前端框架没有再依靠iframe去实现子应用间的隔离,其中qiankun2.0官方支持了通过Web Components的方案实现样式层面的完全隔离(qiankun1.0还是基于single-spa的技术实现)。
尽管难以将 Iframe 作为微前端应用的加载器,但是却可以参考其设计思想,一个传统的 Iframe 加载文档的能力可以分为四层:文档的加载能力、HTML 的渲染、执行 JavaScript、隔离样式和 JavaScript 运行环境。那么微前端库的基础能力也可以参考其设计思想。 从设计层面采取的是基座+子应用分治的概念,部署平台负责进行服务发现和服务注册,将注册的应用列表信息下发至基座,通过基座来动态控制子系统的渲染和销毁,并提供集中式的模式来完成应用间的通信和应用的公共依赖管理
加载器(Loader)
HTML 入口类型,拆解 HTML Dom、Script、Style
JS 入口类型,提供基础 Dom 容器
负责注册平台侧提供的应用列表
负责加载和解析子应用入口资源
预加载能力
解析子应用导出内容
沙箱隔离(Sandbox)
提供代码执行能力,收集执行代码时存在的副作用
提供销毁收集副作用的能力
支持沙箱多实例,收集不同实例的副作用
路由托管(Router)
解决不同应用间的路由不同步问题
提供路由劫持能力,在主应用上管控子应用路由
提供路由驱动能力来拼装完整的平台的能力
子应用通信(Store)
建立通信桥梁
提供共享机制
当然Web Components方案不是十全十美的,也会带来一定程度的问题,比如组件样式越过shadow root边界尝试访问外部的dom节点这种情况,一个典型场景就是几乎所有组件库的modal组件默认都会挂载到document.body上,从而导致使用组件默认行为会导致modal组件无法渲染。
转载本站文章《微前端学习笔记(6):为什么不用iframe?Web Components最佳?》,
请注明出处:https://www.zhoulujun.cn/html/webfront/engineer/Architecture/9022.html