切换语言为:繁体

前段进阶必须掌握的模块化与组件化

  • 爱糖宝
  • 2024-07-30
  • 2069
  • 0
  • 0

如果把编程比作一门武学,除了掌握扎实的基本功外。想要进阶为大宗师,我们还得内外兼修,掌握像vue,react等高级招式。更重要的是需要精进面向对象的高级内功心法。

什么是模块化

在前端发展历程中,起初并没有模块化的概念,从原生js开发到jQuery一把梭,一个html中穿插着各式各样的js文件,相互之前不好隔离,变量与方法都是提升到全局。随着项目复杂度的提升,变得不利于维护管理。并且没办法很好的满足“高内聚,低耦合” 的思想。逐渐的,模块化开发在社区里面流行了起来。

前端模块化可以将一个大型的前端项目拆分成多个小模块,方便管理和维护。常见的前端模块化规范有 CommonJS、AMD、CMD 和 ES6 Module。

这些模块化方案都各具特色,这里优先建议使用ES6 Module

什么是组件化

其实web从一开始变有了组件化的思想,只是直到react,vue等流行起来之后,组件化的思想才开始深入人心,伴随着我们的日常开发。

在组件化的思想里面,我们认为一个网页的呈现可以由若干个UI组件组成,一个组件只是网页组成部分的一个单位而已。而组件化又十分灵活,我们可以组件嵌套,组合,打散等等,将各类复杂应用合理的拆分成一个个便于维护的组件单位。然后形成一棵枝繁叶茂的组件树

原生组件化(Shadow DOM)

html中有各式各样的标签,这些标签就是一个个的组件。例如:video,input,button...等等,都html内置好的web component。

除此之外,我们也可以通过 shadow DOM 的方式去自定义实现一个原生的web组件。

框架组件化(react,vue,angular,svelte...)

这些主流的前端框架更加丰富了组件的定义,生命周期,组件通信,信息隔离等等功能,利用现在主流的前端框架,我们可以轻松的实现组件化开发,极大提高了开发效率与质量。

组件化开发的设计思路

当我们对一个项目或者网页进行组件化设计的时候,应该权衡利弊,找到一个合理的平衡点。因为过渡的拆分组件会使得代码过于分散,复杂度高。如果组件抽象程度不够,代码又过于冗余,复用性不高。如何通过合理的设计组件,来对代码进行解耦与分类,是一个值得思考的问题。

在各类场景下应该如何封装组件?

对于何时应该封装一个组件,每个人的见解都不一样。有人认为多处地方使用了相同的逻辑,就应该抽离一个组件,有人认为组件拆分之后代码变多了,组件之前通信变复杂了,还不如不封装组件。那么在面对复杂多变的需求业务场景下,我们应该如何去合理拆分组件呢?

一、  分析网页的UI组成

当我们在UI设计师哪里拿到一张精美的设计稿的时候,我们首先是需要看着设计稿开始分析网页的组成部分是什么?例如一个后台管理系统,最经典的就是圣杯布局,整个网页可以分为“头部导航栏”,“左侧菜单”,“右侧内容”,“底部描述”。基于基本布局,我们至少便需要封装四个基本组件,再根据组件复杂度进一步拆分

二、  组件颗粒度定义

● 原子级组件:最小单位的组件,这类组件通常只包含一个单一功能,不参杂多余的业务代码。例如网页中的按钮,图标,输入框,下拉框等。原子级的组件应该具备最大通用性与复用性。市面上大多数UI组件库提供了许多原子级组件,极大提高了开发效率。

● 分子级组件:由多个不同的原子级组件组成,通常实现了一些基础常见的功能模块。例如:级联选择器,穿梭框,标签页等。

● 复合型组件:由多个不同的原子级和分子级组件组成,通常实现了一些较为复杂的业务功能。例如:表格,表单,日历,tree树等。

● 页面级组件:集大成者,由多个不同的原子,分子,复合组件组成,通常实现了一些具有独立业务需求的功能模块。例如:购物车列表,收货地址设置,导航菜单等。

三、  什么情况下应该抽离组件?

讲了这么多,那么在面对日益复杂的业务需求时。怎样合理的抽象组件,达到一个合理的平衡点呢?在什么情况下,我们需要抽离组件出来呢?

● 页面UI层次分明,复杂度高

○ 当页面UI层次分明且复杂度高的时候,我们第一时间应该是考虑“拆”,根据页面特性,ui展示,业务需求不同维度去拆成一个个组件

● 多出地方使用,出场率高

○ 当一个ui组件会以相同的形式出现在不同地方,只需要通过参数控制即可满足不同场景时。便可以考虑将这些逻辑封装成一个组件多处使用了

● 具备完整的功能闭环

○ 某些业务场景功能比较纯粹,功能单一且能完整闭环,例如某个纯展示的卡片信息面板,步骤条显示,一些特定业务逻辑处理的包装组件等。这个时候变可以考虑将其封装成一个组件。

● 业务极其复杂且耦合度高

○ 在面对业务复杂且耦合度高的需求开发时,就可以利用组件拆分来对代码进行解耦以达到逻辑分解,关注点分离,提高代码质量的目的

● 无需关注内部实现,只关心结果呈现

○ 日常开发中经常会遇到一些“黑匣子”开发,在此类场景上我们往往不需要关注组件内部实现,只需要该组件能在网页上正常运行预期结果即可。例如:一个圆形的饼状统计图,一个播放器的二次包装,一个canvas画板容器等

如何设计一个优秀的组件

说一千道一万,我们应该如何才能设计好一个优秀的组件,一个优秀的组件应该具备什么品质呢?

● 从需求角度出发

○ 当接到一个需求之后,应该第一时间去理解需求。考虑需求的本质与后续迭代可能会产生的变化。从而再去设计组件,以便应对需求的持续更新

● 从UI设计稿角度出发

○ 在通过代码还原设计稿之外,还需要考虑好组件样式的兼容性,不同屏幕尺寸的适配性,文案长短,异常数据显示,缺省页展示等等

● 从使用者角度出发

○ 开发完一个组件,往往是需要提供给团队的其它成员或者是自己使用的。这里用上很喜欢的一句话「代码只是能友好的运行在机器上,但最终是写给人看的」

○ 要以人为本,多为组件的使用者着想。想想别人在使用该组件的时候,心里会不会骂娘,一段时间后自己在回过头来看这个组件的代码,是否能看得懂

● 从组件自身角度出发

○ 组件本身要经过足够多的测试,以确保组件能够在不同场景下稳定运行

○ 对外暴露的api配置要尽量精炼且满足功能

○ 对外暴露的api以及组件关键代码处需留下注释或者api文档

○ 具备一定的拓展性和维护性,以确保使用者能在不修改源代码的情况下实现一些定制化需求

○ 具备极强的易用性,简单性。别让组件的使用成本过高心智负担过重

○ 对入参有一定的包容性,对出参有一定的健壮性。对一些参数类型,参数值做兜底与兼容处理,对出参同样要保持稳定,必要时给出相应的异常描述以便排查问题

○ 组件需要具备一定的灵活性,做到像接口一样即插即用

○ 无副作用,无不良依赖。尽量避免与其他业务耦合,职责单一

○ 具备极强「普适性」要能最大程度的与其他组件组合使用,且不造成污染

结束语

不难看出,不论是模块化还是组件化,其本质都是基于面向对象思想开发。在代码中多使用面向对象的思想,能使得我们的代码结构,组织逻辑,优雅程度更上一层楼。许多的设计模式看似高深,在理解了面向对象之后,再看这些设计模式就会有一种原来如此,恍然大悟的感觉。行走于江湖,修得此心法,必将突破天元境!

0条评论

您的电子邮件等信息不会被公开,以下所有项均必填

OK! You can skip this field.