微前端架构初探以及我的前端技术盘点

徐小夕 等级 666 0 0

前言

最近几年微前端一直是前端界的热门议题, 它类似于微服务架构, 主要面向于浏览器端,能将一个复杂而庞大的单体应用拆分为多个功能模块清晰且独立的子应用,且共同服于务同一个主应用。各个子应用可以独立运行、独立开发和独立部署。

微前端架构概念的诞生及应用对于提供复杂应用服务的企业来说显然是一种机遇, 同样也是一种挑战.本文主要就微前端架构的概念和实现方案做一个总结和复盘,并且通过一个实际案例来实践微前端架构,希望能对同样有此需求的朋友们提供一些帮助和思路.

你将收获

  • 什么是微服务以及微服务能给企业带来什么
  • 微前端架构概念及方案
  • umi下的微前端架构方案实战
  • 一个程序员的技术复盘与展望

正文

在总结微前端架构之前,让我们来先看看微服务是什么.

1.什么是微服务以及微服务能给企业带来什么

微服务是一种用于构建应用的架构方案。微服务架构有别于更为传统的单体式方案,可将应用拆分成多个核心功能。每个功能都被称为一项服务,可以单独构建和部署,这意味着各项服务在工作(和出现故障)时不会相互影响。

传统的web软件开发架构往往如下图所示: 微前端架构初探以及我的前端技术盘点 虽然我们在传统应用中可以采用模块化来拆分业务逻辑和开发方式,但最终它们会打包并部署为单体式应用。这种架构往往更适合中小型项目, 开发简单直接,更适合集中化管理应用.但往往也会存在很多缺点,比如可扩展性不足,相同或者相似业务复用困难,部署时间长, 业务复杂之后很难维护等问题.

对于复杂系统和业务来说,我们一般会采用微服务架构。其思路是将一个完整的应用分解为小的、互相连接的微服务,每个服务完成特定的功能, 并且某些特定的服务还能为其他服务提供API接口. 微前端架构初探以及我的前端技术盘点 由上图可以发现微服务给我们带来的好处:

  • 将一个庞大的单体拆解成多个子服务,大大降低了开发复杂度
  • 任务边界划分明确, 每个子服务之间单独开发, 不同服务之间可并行由不同的开发人员开发,提高开发效率
  • 更细粒度的加强了模块化进程, 可维护性和可读性更高
  • 团队之间只要制定好API约定, 那么不同成员或者团队可以采用不同的技术开发服务
  • 可用共享服务, 使得不同子服务可组合实现更复杂的功能
  • 每个微服务可独立部署发布,使得自动化CI(持续集成)/CD(持续交付)成为可能

但微服务并不是任何场景下都是合适的, 微服务的目标是充分分解应用程序,以促进敏捷开发和持续集成部署。在部署微服务时我们需要做好适当的边界划分,并处理不同微服务之间的并发问题,这些都是对整个项目带来的挑战,需要更加专业的技术成员来把控.目前市面上也有很多开源的微服务框架比如Dubbo, Spring Cloud等,笔者之前公司采用的Spring Cloud就是一个很好的微服务架构方案.

2.微前端架构概念及方案

2.1 理解微前端架构

上面简单介绍了一下微服务架构,接下来我们进入主题,来聊聊微前端. 微前端微服务实现的目的类似,都是将应用由单一的单体应用转变为多个小型子应用,差别就在于:

  1. 微前端应用于浏览器端,主要是对web应用进行拆解,最后将不同子系统(模块)聚合成一个完整的应用.
  2. 微前端主要目的是聚合,即将不同子系统聚合成一个大系统,而微服务架构目前更多是解耦,即解耦不同服务间的依赖.

我们先来看看微前端的一些思考者. 微前端架构初探以及我的前端技术盘点 Michael Geers 大佬发表了一些对微前端的一些思考,内容大致总结一下就是:

“ 微前端 ”是将微服务的概念扩展到前端领域。为了构建一个功能强大的浏览器应用程序(也称为单页应用程序),当前普遍的趋势是将其建立在微服务架构之上。但是随着时间的流逝,通常由独立团队开发的前端层会不断增长,并且变得更加难以维护。Micro Frontends背后的想法是将Web应用程序视为由独立团队拥有的功能的组合。每个团队都有自己关心和专长的不同业务或任务领域。每个团队可以跨职能,并且从数据库到用户界面,端到端地开发其功能。

正如下面的例子所示: 微前端架构初探以及我的前端技术盘点 当我们的系统中有多个不同的子模块,并且子模块之间有相对独立且完整的功能体系时, 一旦子模块变得越来越多, 那么整个应用将变得非常庞大且臃肿,开发和维护成本大大提高.如果在这种场景下我们采用SPA模式开发,那么项目后期将变得不可想象,页面首次加载将变得非常慢(笔者曾经就经历过,开发一个复杂系统页面首次加载花了20多秒,所以不得不采用MPA来处理); 但是我们采用MPA(多页应用)模式,虽然解决了应用臃肿的问题, 但仍然存在很多有待处理问题,比如模块切换需要重新刷新页面, 公共组件无法共享,子模块直接,父子模块之间的通信问题,开发部署繁琐等.这写都是传统开发模式会遇到的问题.

试想一下,如果面对以上问题, 如果有一种架构模式, 可以让我们在主应用中共享公共组件和状态(但是要保证子应用运行时内部的状态隔离), 并且不同子模块之间可以单独开发部署, 模块间切换不刷新页面, 并且模块之间,父子应用之间可以通过某种简单的方式实现通信,这样是不是就完美了?不错, 这也许就是微前端要解决的问题. 微前端架构初探以及我的前端技术盘点 往往企业的中后台系统更加适合使用微前端架构,因为B端大部分都是业务驱动,而往往这些业务之间会非常复杂, 比如Saas, Paas等系统.像类似于云平台,CRM,ERP系统往往是微前端架构的拯救对象.

笔者曾经接手的ERP系统,由于开发时间比较早,往往有很多遗留的历史包袱,比如新老技术栈的糅合, 前端业务代码庞大而毫无违和感,为了对其继续迭代开发, 重构是必经之路,微前端另一个重要的作用笔者认为就是解放.解放不可挽回的痛😭.

笔者之前在写从0到1教你搭建前端团队的组件系统(高级进阶必备)这篇文章时简单提了一下微前端的一些知识,这里先回放一张笔者之前做的简陋的图,方便大家理解微前端架构. 微前端架构初探以及我的前端技术盘点 但我们所看到的不是事实的全部,在文章后面笔者会总结一张更全面的图,来整理微前端的一些实践应用.

2.2 微前端架构实现的方案

上面内容我们大致了解了一下微前端的概念和作用,接下来笔者总结一下曾经经历过的微前端实现方案.

1. 基于MPA + iframe + requirejs实现的微前端架构 这是笔者接手最早的一个项目,主要是服务于企业内部的ERP系统,当时采用的技术栈主要是jquery+layui+requirejs,记得还是笔者刚毕业时参与的项目.主要是利用AMD模块化机制来复用代码,当时项目代码及其庞大复杂,大致架构如下: 微前端架构初探以及我的前端技术盘点 传统实现方式一般是通多多页面的方式来对应用解耦,并采用模块化加载机制来导入可复用组件.系统间通型采用storage+window.opener+iframe.比如我们一个大系统的首页可能会有来自不同子系统的页面,已iframe的方式嵌入.不同子系统间由不同的人维护,虽然做到了微前端的模式,但是还是有很多缺点. 微前端架构初探以及我的前端技术盘点 微前端架构初探以及我的前端技术盘点 改架构的一般分工是架构组主要负责制定架构标准和规范,维护公共模块(类似于现在的组件,当时由于采用jquery生态,可以简单的说成公共UI插件的维护);业务组主要负责编写业务代码,实现某个系统的具体交互和功能。

2. 基于MPA + iframe + Webpack实现的微前端架构 基于MPA + iframe + Webpack实现的微前端架构实现和上面介绍的传统架构实现类似,只不过采用了更新的技术栈,以及真正的模块化,组件化技术。笔者之前做的Saas系统就是一个很典型的该方案的例子: 微前端架构初探以及我的前端技术盘点 上图可知不同子系统之间可以各自维护,单独打包部署,最后通过node或者nginx做路由分发。我们采用公共的ui组件库和js类库来抽离公共组件,但是前提是不同组件库和技术栈强相关,如果没有历史遗留的新项目,建议采用一致的技术栈。

以上两个方案的缺点就是组件库只能复用而无法真正共享,并且切换路由会导致页面重新渲染刷新。父子系统通信困难,仍然需要iframe最为容器来通信。(有关iframe父子页面通信的各种方式笔者在记一次老项目中的跨页面通信问题和前端实现文件下载功能

3. 基umi + qiankun实现的微前端架构 目前市面上也有非常成熟的微前端架构方案,比如single-spa,之前的美团外卖微前端架构和蚂蚁金服基于single-spa开发的微前端架构qiankun(乾坤),都是非常不错的方案。

qiankun主要采用HTML Entry模式,直接将子应用打出来 HTML作为入口,主框架可以通过 fetch html 的方式获取子应用的静态资源,同时将 HTML document 作为子节点塞到主框架的容器中。这样不仅可以极大的减少主应用的接入成本,子应用的开发方式及打包方式基本上也不需要调整,而且可以天然的解决子应用之间样式隔离的问题。 微前端架构初探以及我的前端技术盘点 其方案具有如下特点:

  • 支持子应用并行
  • 支持js沙箱环境(js隔离)
  • css隔离
  • HTML Entry,简化开发者使用
  • 按需加载
  • 公共依赖加载
  • 父子应用通信机制
  • 子应用嵌套

因为我们的前端项目基于umi生态开发构建(之前采用webpack搭建,后面发现umi使用也很爽,就直接基于umi二次开发了),所以很自然的选择了乾坤作为微前端架构。具体架构如下: 微前端架构初探以及我的前端技术盘点

3.umi下的微前端架构方案实战

接下来我具体介绍如何使用乾坤来搭建我们的微前端架构,由于我们内部采用umi,所以这里我们直接使用其提供的@umijs/plugin-qiankun插件来实现。(好处就是改动成本几乎为零) 首先我们来实现这样一个场景:我们有一个主应用作为基座工程,然后有3个子系统,他们是独立创建维护的,可以采用不同的git仓库来管理。当我们在主应用中切换路由时会切换到对应的子系统,且不刷新页面,完全的SPA体验,接下来我们来具体实现一下吧。

这里我们采用umi2.0来开发,关于如何安装与使用umi,这里就不做详细介绍了。

  1. 创建工程
    mkdir mainSystem subSystemA subSystemB subSystemC
    // 分别进入各系统目录下,执行以下命令创建我们的项目
    yarn create umi
  2. 在各个系统下安装@umijs/plugin-qiankun插件
    yarn add @umijs/plugin-qiankun
  3. 主应用下的配置
    // .umirc.js
    export default {
    plugins: [
     [
       '@umijs/plugin-qiankun',
       {
         master: {
           // 注册子应用信息
           jsSandbox: true, // 是否启用 js 沙箱,默认为 false
           prefetch: true, // 是否启用 prefetch 特性,默认为 true
         },
       },
     ],
    ],
    };
    // app.js
    const isDev = process.env.NODE_ENV === 'development'
    export const qiankun = {
    apps: [
     {
       mountElementId: 'root-subapp-container',  // 洗子应用挂载的节点
       name: 'subSystemA', // 唯一 id,和package对应的name字段最好保持一致
       entry: isDev ? '//localhost:8001' : '/subSystemA/index.html', // html entry
       base: '/subSystemA',  的路由前缀,通过这个前缀判断是否要启动该应用,通常跟子应用的 base 保持一致
       history: 'browser', // 子应用的 history 配置,默认为当前主应用 history 配置
     },
     {
       mountElementId: 'root-subapp-container',
       name: 'subSystemB',
       entry: isDev ? '//localhost:8002' : '/subSystemB/index.html',
       base: '/subSystemB',
     },
     {
       mountElementId: 'root-subapp-container',
       name: 'subSystemC',
       entry: isDev ? '//localhost:8003' : '/subSystemB/index.html',
       base: '/subSystemC',
     }
    ],
    fetch: url => {
     return fetch(url)
    }
    };
    以上是基本的配置,当然我们还可以在app.js里面加入lifeCycles等钩子来控制不同生命周期下的行为。

在子应用中我们同样需要引入@umijs/plugin-qiankun这个插件,具体配置如下:

export default {
  base: `/${appName}`, // 子应用的 base,默认为 package.json 中的 name 字段
  plugins: ['@umijs/plugin-qiankun', { slave: true }],
};

基本准备工作已经完成,剩下就是编写业务代码了,我们要想让整个应用一起跑起来,需要先启动基座工程,然后再启动对应的子工程(当然他们可以单独运行)。

但是值得注意的是我们在开发环境中采用devServer提供的带来才能跨域抓取资源,如果应用发布到线上,如果不同子应用采用不同域名,我们还需要解决跨域问题(跨域解决的方案及安全机制也有很多,已经不再是个问题)。实际开发环境我们需要考虑的问题还有很多,这里只做简单介绍,不过根据官方提供的api基本上可以满足大部分的需求场景,所以还是非常值得一试的。笔者后期也会写一个微前端的实际案例发布到github上,可以一起交流学习。

4.一个程序员的技术复盘与展望

由于今年受疫情影响,工作任务比较紧张,复盘的时间也比较少,但是笔者还是会坚持每周更新1-2篇文章,来总结和复盘工作中或学到的新技术。自己写的零零散散的文章是时候做一个分类和梳理,以便更加清晰未来的方向和不足的补救。

1.node相关

2.工程化相关

3. 设计模式

4.react相关

6.css相关

7.算法相关

8. H5游戏

10.工作问题汇总

最后

如果想学习更多H5游戏, webpacknodegulpcss3javascriptnodeJScanvas数据可视化等前端知识和实战,欢迎在公号《趣谈前端》加入我们的技术群一起学习讨论,共同探索前端的边界。 微前端架构初探以及我的前端技术盘点

收藏
评论区

相关推荐

教你用200行代码写一个爱豆拼拼乐H5小游戏(附源码)
前言 本文将带大家一步步实现一个H5拼图小游戏,考虑到H5游戏的轻量级和代码体积,我没有使用react或vue这些框架,而采用我自己写的dom库和原生javascript来实现业务功能,具体库代码可见我的文章如何用不到200行代码写一款属于自己的js类库(https://juejin.im/post/6844903880707293198),构建工具我采
昨天写了这些骚代码,今天上班差点被同事揍了
昨天写了这些骚代码,今天上班差点被同事揍了 前端开发 微信号 qianduan1024 功能介绍 专注于Web前端技术文章分享,包含JavaScript、HTML5、CSS3等前端基础知识,以及Vue.js,React,Augular等前端框架 收录于话题 来自:掘金,作者:布拉德特皮 链接:h
微前端架构初探以及我的前端技术盘点
前言 最近几年微前端一直是前端界的热门议题, 它类似于微服务架构, 主要面向于浏览器端,能将一个复杂而庞大的单体应用拆分为多个功能模块清晰且独立的子应用,且共同服于务同一个主应用。各个子应用可以独立运行、独立开发和独立部署。 微前端架构概念的诞生及应用对于提供复杂应用服务的企业来说显然是一种机遇, 同样也是一种挑战.本文主要就微前端架构的概念和实现方案做一
Taro 入门教程
简介 Taro 是一个遵循 React 语法规范的开放式跨端跨框架解决方案,支持使用 React/Vue/Nerv 等框架来开发微信/京东/百度/
喜大普奔,微信终于支持外网打开小程序啦!
前言 千呼万唤始出来,微信小程序终于支持以URL Scheme的形式从外部唤起了。 long long ago 我们只能在微信内的网页中使用微信开发标签小程序跳转按钮
Spring Cloud OAuth2 微服务认证授权
OAuth 2.0 是用于授权的行业标准协议,它致力于简化客户端开发人员的工作,同时为 Web 应用、桌面应用、移动应用等各种客户端应用提供了特定的授权流程。本文讲解如何使用 OAuth2 协议来授权客户端应用访问 Spring Cloud 微服务。 微服务认证授权概述 单点登录 相比于单体应用,微服务应用需要在多个服务之间共享
Spring Cloud 微服务开发指南
如同 Spring Boot 在 Java Web 开发领域中的统治地位,Spring Cloud 在 Java 微服务应用开发领域中同样处于垄断地位。软件系统从单体升级到微服务架构,随之会出现各种分布式系统所特有的问题,包括服务注册发现、认证授权、限流熔断、调用追踪等。Spring Cloud 提供了各种组件来解决这些问题,本文将通过升级改造一个单体 AP
微信小程序 - 引入字体图标
网站图标要想做到清晰无锯齿,使用普通图片或者雪碧图都很难达到这个目的,一般我们都会引入字体图标(svg转font,使用图标像使用字体一样,详见《web页面使用字体图标》,那么如何在微信小程序中使用自定义图标呢?请看详细步骤:1、从上选择喜欢的图标加入购物车,在购物车弹窗中点击“下载代码”后,解压阿里图库 加入购物车购物车 下载代码图标文件内容2.、进入导入第
uni-app开发 常见异常和解决办法
前言uniapp 是一个基于 Vue.js 开发所有前端应用的框架,开发者编写一套代码,可发布到iOS、Android、Web(响应式)、以及各种小程序(微信/支付宝/百度/头条/QQ/钉钉/淘宝)、快应用等多个平台。在开发过程中可能会遇到一些异常,这些异常及其解决办法总结如下。 1.调用微信开发者工具报错IDE service port dis
手写一个仿微信登录的nodejs程序
前言首先,我们看一下微信开放文档中的一张图:上面的一幅图中清楚地介绍了微信登录整个过程,下面对图上所示进行总结:一、二维码的获得1. 用户打开登录网页后,登录网页后台根据微信OAuth2.0协议向微信开发平台请求授权登录,并传递事先在微信开发平台中审核通过的AppID和AppSecrect等参数; 2. 微信开发平台对AppID等参数进行验证,并向
如何在React Native和Expo中掩盖Text和TextInput组件
在本文中,我将向您展示如何在React Native和Expo中使用自定义蒙版,可用于iOS,Android和Web!我们将使用一个名为库,这是一个没有本机代码的完整javascript库,然后您可以在React Native环境的所有CLI中使用。](https://res.cloudinary.com/practicaldev/image/fetch/s
微信小程序体验composition-api(类似vue3)
微信小程序compositionapi用该是什么样子? 使用使用起来应该像是这个样子wxue(options) setup配置应该是包含一个setup选项是一个函数,返回的函数可以this.xxx调用,返回的数据可以this.data.xxx用到,如下import wxue, reactive from 'wxue'wxue( setup(option
想搞定大厂面试官?被逼无奈开始狂啃底层技术
Part 1微服务架构设计概述1.1 传统应用架构的问题1.2 微服务架构是什么1.3 微服务架构有哪些特点和挑战1.4 如何搭建微服务架构 Part 2微服务开发框架2.1 Spring Boot 是什么2.2 如何使用Spring Boot框架2.3 Spring Boot生产级特性 Part 3微服务网关3.1 Node.js 是什么3.2 如何使用
美团java研发岗二面:覆盖所有面试知识点
面试真题以及解析 Web,RESTful API 在微服务中的作用是什么?微服务架构基于一个概念,其中所有服务应该能够彼此交互以构建业务功能。因此,要实现这一点,每个微服务必须具有接口。这使得 Web API 成为微服务的一个非常重要的推动者。RESTful API 基于 Web 的开放网络原则,为构建微服务架构的各个组件之间的接口提供了最合理的模型。
微信拟推出个人微信云存储付费服务,你的微信聊天记录值多少钱?
消息称微信拟推出个人微信云存储付费服务有知情人士表示,腾讯拟推出个人微信云存储付费服务,据悉,该业务可能采用按年付费的模式,苹果用户或在180元/年左右,安卓用户或在130元/年左右。但该费用具体可以存储多大容量的数据尚未得到确定。知情人士表示,当前该项目仍在最后推动中,具体细节未最终敲定。(中国日报网)其实,一直以来,保存和迁移微信聊天记录既是用户的痛点,