当前位置: 首页 > Web前端 > vue.js

微模块-前端业务模块化探索,拆解巨石应用的又一利器

时间:2023-03-31 19:28:24 vue.js

微模块——前端业务模块化探索,拆解巨石应用的又一利器同构方案》,欢迎理解……文前声明,以下推论和结论纯属个人探索,鉴于本人能力有限知识层面,谬误在所难免,求各位赐教……什么是前端“微模块”?Elux中的“微模块”是指前端web项目中根据不同的业务功能对代码和相关资源进行分类和模块化。按照业务功能进行模块化一直是后端的普遍做法,而web前端通常是按照UI界面的view块View进行模块化。这样的模块实际上只是Component组件,不具备独立自主的能力。.原因我想是因为在Web1.0早期,前端的作用只是作为后端API数据的渲染器,所以前后端的愿景和布局——端是有区别的,很多人说前端根本就没有架构。说。但是,在网络生态发展的今天,浏览器的功能越来越强大,甚至可以说是一个小型操作系统。这时候,Web前端不再是简单的数据渲染器。数据持久化、文件缓存、通信协议……随着PWA、小程序、快应用的推广,WebAPP不再是一个瘦客户端,而是逐渐成长为一个大胖子。这时候我们就应该跳出“渲染器”的井口,从一个完整的软件项目来思考我们的前端架构。Web前端不仅仅是一层View和GUI。我们需要回到与后端A驱动的模块化视角一致的业务领域。为什么前端需要“微模块”?从开发的角度来看:我们需要一个高内聚低耦合的松散结构,而不是牵一发而动全身的单体应用。这对于后期的开发、维护和逐步重构至关重要。Front-endLeader:经过一年多的迭代和人员变动,我们的代码已经变得混乱,开发难度越来越大。必须要重构,不然我们就玩不下去了!产品经理:嗯,我理解很多是因为我们的需求变化频繁导致的。我支持你的重构!Front-endLeader:谢谢理解,新的需求先停止,我们重构后再迭代?产品经理:重构需要多长时间?Front-endLeader:产品这么复杂,估计至少3个月吧。产品经理吓出一身冷汗:老大,3天后你还能考虑。停3个月,公司可能倒闭……前端负责人:但是产品这么复杂,重构需要几天时间。谭。产品经理想了想:这样我每次迭代少安排几个需求,这样你每个月可以节省几天重构的时间。Front-endLeader:这不是1+1=2的问题,而是0和1的问题,大佬你不懂!产品经理:谁说我看不懂,就不能增量重构?Front-endLeader:……这时候如果我们的前端项目是基于“微模块”,一来我们很容易找到“局部重构”的边界,二来我们也可以无限替换通过维护“微模块”的外部接口。从产品的角度来看:软件架构总是服务于业务需求。我们希望我们的产品可以像搭积木一样按需组合,快速包装出各种灵活多样的包装,以满足客户日益精细化的定制需求。一个大型应用程序包含A、B、C、D、E、F、G等几个功能,一直都是作为一个整体打包销售……随着用户需求的多样化,一些用户只需要一些功能,好聪明前端架构师“小李”利用时下流行的微前端技术,将应用拆分成3个子应用:-【基础应用】包含功能:A-【子应用A]包含功能:B、C、D-【子应用B】包含功能:E、F、G,即有3种套餐供客户选择:-套餐A:基础应用+子应用A-套餐B:基础应用+子应用B-套餐C:基础应用+子应用A+子应用B但是现在用户的需求越来越细化,有的需要ABCD,有的需要ACEG,有的需要ABDF……而且同一个功能可能会有不同的需求版本,这让“小李”无所适从,现在我们用“微模块”来帮助小李解决e问题:将各个独立的业务功能打包成不同的微模块:A,B,C,D,E,F,G根据需求迭代各个微模块的版本,发布为一个npm包。客户需要A、C1(某版本的C功能)、E2(某版本的E功能)、G功能。我们为客户创建一个聚合工程分支,安装对应版本的微模块:npminstallAC@1E@2G我们知道世界上有神器wordpress。它曾声称世界上50%的网站都是由它创建的。我认为它成功的秘诀在于社区模板机制和功能插件。想要什么功能,总能找到“前端+后端”打包安装的插件,这也类似于“微模块”的概念。从工程的角度来看:“微模块”是跨项目、跨项目共享通用业务代码的理想解决方案,尤其适用于跨终端、跨平台的业务逻辑复用。前端“微模块”的划分原则和边界具有高内聚低耦合的工程结构。拥有独立自主的子域逻辑。从图中可以看出,每个微模块负责定义和维护自己域内的事务,麻雀虽小,五脏俱全,具有独立的路由分析、状态管理、数据模型、控制器、view、component、resource、Businessentities、APImanagement等等……简而言之,所有与自己领域相关的资源都被聚合在一起。以下是某巨石应用的src目录,其特点是“文件功能”为一级分类,“功能模块”为二级分类:├─src│├─api#API接口管理│├─assets#静态资源文件│├─components#全局组件│├─config#全局配置项│├─enums#项目枚举│├─hooks#常用Hook│├─language#语言国际化│├─layout#框架布局│├─routers#路由管理│├─store#store│├─styles#全局样式│├─typings#全局ts语句│├─utils#工具库│├─views#项目所有页面│├─App.vue#入口页面│└─main.ts#入口文件下面是Elux中基于微模块的src目录。改进是将“功能模块”作为一级分类,将“文件功能”作为二级分类:src├──modules│├──ModuleA││├──entities││├──assets││├──api││├──utils││├──语言││├──组件││├──views││├──model.ts││└──index.ts│││├──ModuleB│├──ModuleC微模块前后端开发终于呈现UI界面,但这只是表象,支持UI世界表面渲染和交互是状态、模型、控制器等一系列幕后功臣。它们根据各自的不同领域被封装在各种微模块中。由于UI与它们密切相关,因此它也必须遵循它们。View和ComponentView本质上是一个Component,只是我们从架构的角度来区分它们:View:业务视图,用于表达业务规则和逻辑,通常可以相对独立、完整地解决某个领域的问题。Component:UI组件,用于表达渲染规则和交互逻辑,通常与具体业务没有直接关系,可以在各种业务场景中复用。因此,在“微模块”架构中,丰富多彩的UI界面由职责单一的View聚合而成。每个View也根据自己解决的领域问题分散在各个微模块中。有几个注意点:域:View分配到不同的微模块的原则是它解决的问题域,而不是视觉几何空间。视图可以可视化的拆解、聚合、嵌套,不影响其所属的微模块。Integrity:一个View通常可以解决一个相对独立完整的问题。View与View之间的关系比较松散。如果两个视图密切相关,则不应拆分它们。不使用视觉延伸和几何空间作为View的微模块归属原则:如下图,假设有一个View显示用户信息,我们将其放在微模块UserModule中,并称之为UserModule.DetailView,但你发现它包含用户发表的文章列表。当然,你也可以将这个列表单独抽取出来,作为一个新的View。从视觉上看,好像是和userprofile连在一起的,好像可以和UserModule.DetailView放在同一个微模块中;但是从它解决的问题来看,属于文章领域,和用户领域关系不大,所以我们最好把它放在ArticleModule里面,叫它ArticleModule.ListView的前端“微-module”实现方案定义和创建微模块,可以使用Eluxjs框架,当然也可以找其他框架。要管理微模块,您可以使用NPM存储库。使用微模块可以使用打包工具:静态编译:微模块以npm包的形式安装到项目中,可以通过打包工具(如webpack)正常编译打包。这种方式的好处是代码产品经过打包工具去重和优化;缺点是当一个模块更新时,需要整体重新打包。动态注入:使用ModuleFederation将微模块独立部署为子应用,类似于流行的微前端。这种方式的好处是,当子应用中的一个微模块更新时,其他依赖该微模块的应用不需要重新编译,刷新浏览器即可动态获取最新的模块;缺点是没有打包工具的整体编译和优化,代码和Resources容易出现重复加载或冲突。微模块vs微前端从本质上讲,微模块只是一种工程结构和模块化的解决方案,微前端只是其应用场景之一。微模块架构不仅可以构建复杂的单体应用,还可以结合ModuleFederation,实现多个子应用独立部署的“微前端”。如果将微模块+ModuleFederation方式实现的微前端与qiankun、icestark等传统微前端方案进行对比的话,微模块的方式粒度更优、更灵活、更轻量,而传统方式在隔离方面更好性更好。想一个很形象的比喻:IFramevsmicro-frontendvsmicro-module可以类比processvsthreadvscoroutine从左到右:越来越轻量,隔离性逐渐弱化,灵活性逐渐增强。因此,你不能两者兼得,哪种方案最合适取决于不同的产品需求。微模块之间的通信微模块按照一定的规则和约定共享同一个Runtime,强制隔离性弱,因此它们之间的通信是轻量级的,可以相互引用和调用。推荐使用观察者模式,或者使用事件总线模式维护微模块之间的松散关系,这个是另外一回事,参考Eluxjs中的ActionBus。微模块高内聚低耦合的划分原则也意味着微模块之间不会有特别复杂的交互和通信(交互紧密的微模块应该合并)。落地实战只练不谈笨招,只谈不练假招。到这里,先把思路和概念说完,接下来开始举例。先喝口水,请听下一章分解……