来自 Web前端 2019-10-05 02:15 的文章
当前位置: 澳门三合彩票 > Web前端 > 正文

有的是的前端开拓框架、技能体系争妍斗艳,R

我的前端之路:工具化与工程化

2017/01/07 · 基础技术 · 工具化, 工程化

原文出处: 王下邀月熊_Chevalier   

澳门三合彩票 1

前言

近年来,随着浏览器性能的提升与移动互联网浪潮的汹涌而来,Web前端开发进入了高歌猛进,日新月异的时代。这是最好的时代,我们永远在前行,这也是最坏的时代,无数的前端开发框架、技术体系争妍斗艳,让开发者们陷入困惑,乃至于无所适从。

Web前端开发可以追溯于1991年蒂姆·伯纳斯-李公开提及HTML描述,而后1999年W3C发布HTML4标准,这个阶段主要是BS架构,没有所谓的前端开发概念,网页只不过是后端工程师的顺手之作,服务端渲染是主要的数据传递方式。接下来的几年间随着互联网的发展与REST等架构标准的提出,前后端分离与富客户端的概念日渐为人认同,我们需要在语言与基础的API上进行扩充,这个阶段出现了以jQuery为代表的一系列前端辅助工具。2009年以来,智能手机开发普及,移动端大浪潮势不可挡,SPA单页应用的设计理念也大行其道,相关联的前端模块化、组件化、响应式开发、混合式开发等等技术需求甚为迫切。这个阶段催生了Angular 1、Ionic等一系列优秀的框架以及AMD、CMD、UMD与RequireJS、SeaJS等模块标准与加载工具,前端工程师也成为了专门的开发领域,拥有独立于后端的技术体系与架构模式。

而近两年间随着Web应用复杂度的提升、团队人员的扩充、用户对于页面交互友好与性能优化的需求,我们需要更加优秀灵活的开发框架来协助我们更好的完成前端开发。这个阶段涌现出了很多关注点相对集中、设计理念更为优秀的框架,譬如 ReactVueJSAngular2 等组件框架允许我们以声明式编程来替代以DOM操作为核心的命令式编程,加快了组件的开发速度,并且增强了组件的可复用性与可组合性。而遵循函数式编程的 Redux 与借鉴了响应式编程理念的 MobX 都是非常不错的状态管理辅助框架,辅助开发者将业务逻辑与视图渲染剥离,更为合理地划分项目结构,更好地贯彻单一职责原则与提升代码的可维护性。在项目构建工具上,以 GruntGulp 为代表的任务运行管理与以 WebpackRollupJSPM 为代表的项目打包工具各领风骚,帮助开发者更好的搭建前端构建流程,自动化地进行预处理、异步加载、Polyfill、压缩等操作。而以NPM/Yarn为代表的依赖管理工具一直以来保证了代码发布与共享的便捷,为前端社区的繁荣奠定了重要基石。

前端迷思与React.js

前言

纷扰

分久必合,合久必分啊,无论是前端开发中各个模块的分割还是所谓的前后端分离,都不能形式化的单纯按照语言或者模块来划分,还是需要兼顾功能,合理划分。

任何一个编程生态都会经历三个阶段:

  • 第一个是原始时期,由于需要在语言与基础的API上进行扩充,这个阶段会催生大量的Tools。
  • 第二个阶段,随着做的东西的复杂化,需要更多的组织,会引入大量的设计模式啊,架构模式的概念,这个阶段会催生大量的Frameworks。
  • 第三个阶段,随着需求的进一步复杂与团队的扩充,就进入了工程化的阶段,各类分层MVC,MVP,MVVM之类,可视化开发,自动化测试,团队协同系统。这个阶段会出现大量的小而美的Library。

本文的主旨希望能够尽可能地脱离工具的束缚,回归到前端工程化的本身,回归到语言的本身,无论React、AngularJS、VueJS,它们更多的意义是辅助开发,为不同的项目选择合适的工具,而不是执念于工具本身。总结而言,目前前端工具化已经进入到了非常繁荣的时代,随之而来很多前端开发者也甚为苦恼,疲于学习。工具的变革会非常迅速,很多优秀的工具可能都只是历史长河中的一朵浪花,而蕴藏其中的工程化思维则会恒久长存。无论你现在使用的是React还是Vue还是Angular 2或者其他优秀的框架,都不应该妨碍我们去了解尝试其他。

    前端技术这几年蓬勃发展, 这是当时某几个项目需要做前端技术选型时, 相关资料整理, 部分评论引用自社区。

二十载光辉岁月

澳门三合彩票 2

近年来,随着浏览器性能的提升与移动互联网浪潮的汹涌而来,Web前端开发进入了高歌猛进,日新月异的时代。这是最好的时代,我们永远在前行,这也是最坏的时代,无数的前端开发框架、技术体系争妍斗艳,让开发者们陷入困惑,乃至于无所适从。Web前端开发可以追溯于1991年蒂姆·伯纳斯-李公开提及HTML描述,而后1999年W3C发布HTML4标准,这个阶段主要是BS架构,没有所谓的前端开发概念,网页只不过是后端工程师的顺手之作,服务端渲染是主要的数据传递方式。接下来的几年间随着互联网的发展与REST等架构标准的提出,前后端分离与富客户端的概念日渐为人认同,我们需要在语言与基础的API上进行扩充,这个阶段出现了以jQuery为代表的一系列前端辅助工具。2009年以来,智能手机开发普及,移动端大浪潮势不可挡,SPA单页应用的设计理念也大行其道,相关联的前端模块化、组件化、响应式开发、混合式开发等等技术需求甚为迫切。这个阶段催生了Angular 1、Ionic等一系列优秀的框架以及AMD、CMD、UMD与RequireJS、SeaJS等模块标准与加载工具,前端工程师也成为了专门的开发领域,拥有独立于后端的技术体系与架构模式。而近两年间随着Web应用复杂度的提升、团队人员的扩充、用户对于页面交互友好与性能优化的需求,我们需要更加优秀灵活的开发框架来协助我们更好的完成前端开发。这个阶段涌现出了很多关注点相对集中、设计理念更为优秀的框架,譬如React、VueJS、Angular 2等组件框架允许我们以声明式编程来替代以DOM操作为核心的命令式编程,加快了组件的开发速度,并且增强了组件的可复用性与可组合性。而遵循函数式编程的Redux与借鉴了响应式编程理念的MobX都是非常不错的状态管理辅助框架,辅助开发者将业务逻辑与视图渲染剥离,更为合理地划分项目结构,更好地贯彻单一职责原则与提升代码的可维护性。在项目构建工具上,以Grunt、Gulp为代表的任务运行管理与以Webpack、Rollup、JSPM为代表的项目打包工具各领风骚,帮助开发者更好的搭建前端构建流程,自动化地进行预处理、异步加载、Polyfill、压缩等操作。而以NPM/Yarn为代表的依赖管理工具一直以来保证了代码发布与共享的便捷,为前端社区的繁荣奠定了重要基石。

工具化

我们学习的速度已经跟不上新框架新概念涌现的速度,用于学习上的成本远大于实际开发项目的成本。我们不一定要去用最新最优秀的工具,但是我们有了更多的选择余地,相信这一点对于大部分非处女座人士而言都是喜讯。

工具化是有意义的。工具的存在是为了帮助我们应对复杂度,在技术选型的时候我们面临的抽象问题就是应用的复杂度与所使用的工具复杂度的对比。工具的复杂度是可以理解为是我们为了处理问题内在复杂度所做的投资。为什么叫投资?那是因为如果投的太少,就起不到规模的效应,不会有合理的回报。这就像创业公司拿风投,投多少是很重要的问题。如果要解决的问题本身是非常复杂的,那么你用一个过于简陋的工具应付它,就会遇到工具太弱而使得生产力受影响的问题。反之,是如果所要解决的问题并不复杂,但你却用了很复杂的框架,那么就相当于杀鸡用牛刀,会遇到工具复杂度所带来的副作用,不仅会失去工具本身所带来优势,还会增加各种问题,例如培训成本、上手成本,以及实际开发效率等。

所谓GUI应用程序架构,就是对于富客户端的代码组织/职责划分。纵览这十年内的架构模式变迁,大概可以分为MV与Unidirectional两大类,而Clean Architecture则是以严格的层次划分独辟蹊径。从MVC到MVP的变迁完成了对于View与Model的解耦合,改进了职责分配与可测试性。而从MVP到MVVM,添加了View与ViewModel之间的数据绑定,使得View完全的无状态化。最后,整个从MV到Unidirectional的变迁即是采用了消息队列式的数据流驱动的架构,并且以Redux为代表的方案将原本MV*中碎片化的状态管理变为了统一的状态管理,保证了状态的有序性与可回溯性。 具体到前端的衍化中,在Angular 1兴起的时代实际上就已经开始了从直接操作Dom节点转向以状态/数据流为中心的变化,jQuery 代表着传统的以 DOM 为中心的开发模式,但现在复杂页面开发流行的是以 React 为代表的以数据/状态为中心的开发模式。应用复杂后,直接操作 DOM 意味着手动维护状态,当状态复杂后,变得不可控。React 以状态为中心,自动帮我们渲染出 DOM,同时通过高效的 DOM Diff 算法,也能保证性能。

澳门三合彩票 3
开始吧:

纷扰之虹

笔者在前两天看到了Thomas Fuchs的一则Twitter,也在Reddit等社区引发了热烈的讨论:我们用了15年的时间来分割HTML、JS与CSS,然而一夕之间事务仿佛回到了原点。
澳门三合彩票 4分久必合,合久必分啊,无论是前端开发中各个模块的分割还是所谓的前后端分离,都不能形式化的单纯按照语言或者模块来划分,还是需要兼顾功能,合理划分。笔者在2015-我的前端之路:数据流驱动的界面中对自己2015的前端感受总结中提到过,任何一个编程生态都会经历三个阶段,第一个是原始时期,由于需要在语言与基础的API上进行扩充,这个阶段会催生大量的Tools。第二个阶段,随着做的东西的复杂化,需要更多的组织,会引入大量的设计模式啊,架构模式的概念,这个阶段会催生大量的Frameworks。第三个阶段,随着需求的进一步复杂与团队的扩充,就进入了工程化的阶段,各类分层MVC,MVP,MVVM之类,可视化开发,自动化测试,团队协同系统。这个阶段会出现大量的小而美的Library。在2016的上半年中,笔者在以React的技术栈中挣扎,也试用过VueJS与Angular等其他优秀的前端框架。在这一场从直接操作DOM节点的命令式开发模式到以状态/数据流为中心的开发模式的工具化变革中,笔者甚感疲惫。在2016的下半年中,笔者不断反思是否有必要使用React/Redux/Webpack/VueJS/Angular,是否有必要去不断追逐各种刷新Benchmark 记录的新框架?本文定名为工具化与工程化,即是代表了本文的主旨,希望能够尽可能地脱离工具的束缚,回归到前端工程化的本身,回归到语言的本身,无论React、AngularJS、VueJS,它们更多的意义是辅助开发,为不同的项目选择合适的工具,而不是执念于工具本身。

总结而言,目前前端工具化已经进入到了非常繁荣的时代,随之而来很多前端开发者也甚为苦恼,疲于学习。工具的变革会非常迅速,很多优秀的工具可能都只是历史长河中的一朵浪花,而蕴藏其中的工程化思维则会恒久长存。无论你现在使用的是React还是Vue还是Angular 2或者其他优秀的框架,都不应该妨碍我们去了解尝试其他,笔者在学习Vue的过程中感觉反而加深了自己对于React的理解,加深了对现代Web框架设计思想的理解,也为自己在未来的工作中更自由灵活因地制宜的选择脚手架开阔了视野。

引言的最后,我还想提及一个词,算是今年我在前端领域看到的出镜率最高的一个单词:Tradeoff(妥协)。

工具化的不足:抽象漏洞定理

抽象漏洞定理是Joel在2002年提出的,所有不证自明的抽象都是有漏洞的。抽象泄漏是指任何试图减少或隐藏复杂性的抽象,其实并不能完全屏蔽细节,试图被隐藏的复杂细节总是可能会泄漏出来。抽象漏洞法则说明:任何时候一个可以提高效率的抽象工具,虽然节约了我们工作的时间,但是,节约不了我们的学习时间。我们在上一章节讨论过工具化的引入实际上以承受工具复杂度为代价消弭内在复杂度,而工具化滥用的结局即是工具复杂度与内在复杂度的失衡。

谈到这里我们就会明白,不同的项目具备不同的内在复杂度,一刀切的方式评论工具的好坏与适用简直耍流氓,而且我们不能忽略项目开发人员的素质、客户或者产品经理的素质对于项目内在复杂度的影响。对于典型的小型活动页,譬如某个微信H5宣传页,往往注重于交互动画与加载速度,逻辑复杂度相对较低,此时Vue这样渐进式的复杂度较低的库就大显身手。而对于复杂的Web应用,特别是需要考虑多端适配的Web应用,尽量使用React这样相对规范严格的库。

  • 目前, Web 开发技术框架选型为两种的占 80% 。这种戏剧性的变化持续了近 6 年。
  • 自 2013 年 5 月推出以来,ReactJS 在过去三年中已成为了 Web 开发领域的中坚力量。

工具化

澳门三合彩票 5

月盈而亏,过犹不及。相信很多人都看过了2016年里做前端是怎样一种体验这篇文章,2016年的前端真是让人感觉从入门到放弃,我们学习的速度已经跟不上新框架新概念涌现的速度,用于学习上的成本远大于实际开发项目的成本。不过笔者对于工具化的浪潮还是非常欢迎的,我们不一定要去用最新最优秀的工具,但是我们有了更多的选择余地,相信这一点对于大部分非处女座人士而言都是喜讯。年末还有一篇曹刘阳:2016年前端技术观察也引发了大家的热议,老实说笔者个人对文中观点认同度一半对一半,不想吹也不想黑。不过笔者看到这篇文章的第一感觉当属作者肯定是大公司出来的。文中提及的很多因为技术负债引发的技术选型的考虑、能够拥有相对充分完备的人力去进行某个项目,这些特征往往是中小创公司所不会具备的。

React?Vue?Angular 2?

React,Vue,Angular 2都是非常优秀的库与框架,它们在不同的应用场景下各自具有其优势。Vue最大的优势在于其渐进式的思想与更为友好的学习曲线,Angular 2最大的优势其兼容并包形成了完整的开箱即用的All-in-one框架,而这两点优势在某些情况下反而也是其劣势,也是部分人选用React的理由。很多对于技术选型的争论乃至于谩骂,不一定是工具的问题,而是工具的使用者并不能正确认识自己或者换位思考他人所处的应用场景,最终吵的驴唇不对马嘴。

任何组件与框架都有它的适用场景, 我们应该冷静分析与权衡, 先来看React.js

工具化的意义

工具化是有意义的。笔者在这里非常赞同尤雨溪:Vue 2.0,渐进式前端解决方案的思想,工具的存在是为了帮助我们应对复杂度,在技术选型的时候我们面临的抽象问题就是应用的复杂度与所使用的工具复杂度的对比。工具的复杂度是可以理解为是我们为了处理问题内在复杂度所做的投资。为什么叫投资?那是因为如果投的太少,就起不到规模的效应,不会有合理的回报。这就像创业公司拿风投,投多少是很重要的问题。如果要解决的问题本身是非常复杂的,那么你用一个过于简陋的工具应付它,就会遇到工具太弱而使得生产力受影响的问题。反之,是如果所要解决的问题并不复杂,但你却用了很复杂的框架,那么就相当于杀鸡用牛刀,会遇到工具复杂度所带来的副作用,不仅会失去工具本身所带来优势,还会增加各种问题,例如培训成本、上手成本,以及实际开发效率等。

澳门三合彩票 6

笔者在GUI应用程序架构的十年变迁:MVC,MVP,MVVM,Unidirectional,Clean一文中谈到,所谓GUI应用程序架构,就是对于富客户端的代码组织/职责划分。纵览这十年内的架构模式变迁,大概可以分为MV*与Unidirectional两大类,而Clean Architecture则是以严格的层次划分独辟蹊径。从笔者的认知来看,从MVC到MVP的变迁完成了对于View与Model的解耦合,改进了职责分配与可测试性。而从MVP到MVVM,添加了View与ViewModel之间的数据绑定,使得View完全的无状态化。最后,整个从MV*到Unidirectional的变迁即是采用了消息队列式的数据流驱动的架构,并且以Redux为代表的方案将原本MV*中碎片化的状态管理变为了统一的状态管理,保证了状态的有序性与可回溯性。 具体到前端的衍化中,在Angular 1兴起的时代实际上就已经开始了从直接操作Dom节点转向以状态/数据流为中心的变化,jQuery 代表着传统的以 DOM 为中心的开发模式,但现在复杂页面开发流行的是以 React 为代表的以数据/状态为中心的开发模式。应用复杂后,直接操作 DOM 意味着手动维护状态,当状态复杂后,变得不可控。React 以状态为中心,自动帮我们渲染出 DOM,同时通过高效的 DOM Diff 算法,也能保证性能。

小而美的视图层

React 与 VueJS 都是所谓小而美的视图层Library,而不是Angular 2这样兼容并包的Frameworks。任何一个编程生态都会经历三个阶段,第一个是原始时期,由于需要在语言与基础的API上进行扩充,这个阶段会催生大量的Tools。第二个阶段,随着做的东西的复杂化,需要更多的组织,会引入大量的设计模式啊,架构模式的概念,这个阶段会催生大量的Frameworks。第三个阶段,随着需求的进一步复杂与团队的扩充,就进入了工程化的阶段,各类分层MVC,MVP,MVVM之类,可视化开发,自动化测试,团队协同系统。这个阶段会出现大量的小而美的Library。
React 并没有提供很多复杂的概念与繁琐的API,而是以最少化为目标,专注于提供清晰简洁而抽象的视图层解决方案,同时对于复杂的应用场景提供了灵活的扩展方案,典型的譬如根据不同的应用需求引入MobX/Redux这样的状态管理工具。React在保证较好的扩展性、对于进阶研究学习所需要的基础知识完备度以及整个应用分层可测试性方面更胜一筹。不过很多人对React的意见在于其陡峭的学习曲线与较高的上手门槛,特别是JSX以及大量的ES6语法的引入使得很多的传统的习惯了jQuery语法的前端开发者感觉学习成本可能会大于开发成本。与之相比Vue则是典型的所谓渐进式库,即可以按需渐进地引入各种依赖,学习相关地语法知识。比较直观的感受是我们可以在项目初期直接从CDN中下载Vue库,使用熟悉的脚本方式插入到HTML中,然后直接在script标签中使用Vue来渲染数据。随着时间的推移与项目复杂度的增加,我们可以逐步引入路由、状态管理、HTTP请求抽象以及可以在最后引入整体打包工具。这种渐进式的特点允许我们可以根据项目的复杂度而自由搭配不同的解决方案,譬如在典型的活动页中,使用Vue能够兼具开发速度与高性能的优势。不过这种自由也是有利有弊,所谓磨刀不误砍材工,React相对较严格的规范对团队内部的代码样式风格的统一、代码质量保障等会有很好的加成。
一言蔽之,Vue会更容易被纯粹的前端开发者的接受,毕竟从直接以HTML布局与jQuery进行数据操作切换到指令式的支持双向数据绑定的Vue代价会更小一点,特别是对现有代码库的改造需求更少,重构代价更低。而React及其相对严格的规范可能会更容易被后端转来的开发者接受,可能在初学的时候会被一大堆概念弄混,但是熟练之后这种严谨的组件类与成员变量/方法的操作会更顺手一点。便如Dan Abramov所述,Facebook推出React的初衷是为了能够在他们数以百计的跨平台子产品持续的迭代中保证组件的一致性与可复用性。

1 从功能开发角度说,React的思路很好。
2 从页面设计角度说,传统的HTML+CSS以及同样思路的模板更好。

工具化的不足:抽象漏洞定理

抽象漏洞定理是Joel在2002年提出的,所有不证自明的抽象都是有漏洞的。抽象泄漏是指任何试图减少或隐藏复杂性的抽象,其实并不能完全屏蔽细节,试图被隐藏的复杂细节总是可能会泄漏出来。抽象漏洞法则说明:任何时候一个可以提高效率的抽象工具,虽然节约了我们工作的时间,但是,节约不了我们的学习时间。我们在上一章节讨论过工具化的引入实际上以承受工具复杂度为代价消弭内在复杂度,而工具化滥用的结局即是工具复杂度与内在复杂度的失衡

谈到这里我们就会明白,不同的项目具备不同的内在复杂度,一刀切的方式评论工具的好坏与适用简直耍流氓,而且我们不能忽略项目开发人员的素质、客户或者产品经理的素质对于项目内在复杂度的影响。对于典型的小型活动页,譬如某个微信H5宣传页,往往注重于交互动画与加载速度,逻辑复杂度相对较低,此时Vue这样渐进式的复杂度较低的库就大显身手。而对于复杂的Web应用,特别是需要考虑多端适配的Web应用,笔者会倾向于使用React这样相对规范严格的库。

函数式思维:抽象与直观

近年来随着应用业务逻辑的日益复杂与并发编程的大规模应用,函数式编程在前后端都大放异彩。软件开发领域有一句名言:可变的状态是万恶之源,函数式编程即是避免使用共享状态而避免了面向对象编程中的一些常见痛处。函数式编程不可避免地会使得业务逻辑支离破碎,反而会降低整个代码的可维护性与开发效率。与React相比,Vue则是非常直观的代码架构,每个Vue组件都包含一个script标签,这里我们可以显式地声明依赖,声明操作数据的方法以及定义从其他组件继承而来的属性。而每个组件还包含了一个template标签,等价于React中的render函数,可以直接以属性方式绑定数据。最后,每个组件还包含了style标签而保证了可以直接隔离组件样式。我们可以先来看一个典型的Vue组件,非常直观易懂,而两相比较之下也有助于理解React的设计思想。

在现代浏览器中,对于JavaScript的计算速度远快于对DOM进行操作,特别是在涉及到重绘与重渲染的情况下。并且以JavaScript对象代替与平台强相关的DOM,也保证了多平台的支持,譬如在ReactNative的协助下我们很方便地可以将一套代码运行于iOS、Android等多平台。总结而言,JSX本质上还是JavaScript,因此我们在保留了JavaScript函数本身在组合、语法检查、调试方面优势的同时又能得到类似于HTML这样声明式用法的便利与较好的可读性。

     大家开发前端的思路早已不是当年的 Web page,而是Application。大多数公司不是Facebook,没有那么多全栈高手。团队中擅长写业务的,未必擅长页面布局;擅长页面布局的,未必擅长写业务。这样在团队中必定会有分工,其中会有些人着重实现炫酷的页面效果,而React显然对这种分工不友好。

React?Vue?Angular 2?

澳门三合彩票 7

笔者最近翻译过几篇盘点文,发现很有趣的一点,若文中不提或没夸Vue,则一溜的评论:垃圾文章,若文中不提或没夸Angular 2,则一溜的评论:垃圾文章。估计若是笔者连React也没提,估计也是一溜的评论:垃圾文章。好吧,虽然可能是笔者翻译的确实不好,玷污了原文,但是这种戾气笔者反而觉得是对于技术的不尊重。React,Vue,Angular 2都是非常优秀的库与框架,它们在不同的应用场景下各自具有其优势,本章节即是对笔者的观点稍加阐述。Vue最大的优势在于其渐进式的思想与更为友好的学习曲线,Angular 2最大的优势其兼容并包形成了完整的开箱即用的All-in-one框架,而这两点优势在某些情况下反而也是其劣势,也是部分人选用React的理由。笔者觉得很多对于技术选型的争论乃至于谩骂,不一定是工具的问题,而是工具的使用者并不能正确认识自己或者换位思考他人所处的应用场景,最终吵的驴唇不对马嘴。

前后端分离与全栈:技术与人

前后端分离与全栈并不是什么新鲜的名词,都曾引领一时风骚。Web前后端分离优势显著,对于整个产品的开发速度与可信赖性有着很大的作用。全栈工程师对于程序员自身的提升有很大意义,对于项目的初期速度有一定增速。如果划分合理的话能够促进整个项目的全局开发速度与可信赖性,但是如果划分不合理的话只会导致项目接口混乱,一团乱麻。

我们常说的前后端分离会包含以下两个层面:

  • 将原本由服务端负责的数据渲染工作交由前端进行,并且规定前端与服务端之间只能通过标准化协议进行通信。
  • 组织架构上的分离,由早期的服务端开发人员顺手去写个界面转变为完整的前端团队构建工程化的前端架构。

前后端分离本质上是前端与后端适用不同的技术选型与项目架构,不过二者很多思想上也是可以融会贯通,譬如无论是响应式编程还是函数式编程等等思想在前后端皆有体现。而全栈则无论从技术还是组织架构的划分上似乎又回到了按照需求分割的状态。不过呢,我们必须要面对现实,很大程度的工程师并没有能力做到全栈,这一点不在于具体的代码技术,而是对于前后端各自的理解,对于系统业务逻辑的理解。如果我们分配给一个完整的业务块,同时,那么最终得到的是无数个碎片化相互独立的系统。

为什么需要 React,Why?

    我们需要技术栈提供好用的模块化方式,可以是Web Component,可以是非Web Component的某种机制,不管什么库或者框架,我们需要技术赋予我们完成一个抽象,一次构建,多处复用的能力,并且这个过程不能太麻烦,不能做个很日常的抽象翻半天文档。
    我们需要数据绑定,在各种粒度上真正实现事件驱动,因为这样我们就不用自己重复手写本质上并不依赖场景的从视图到数据从数据到视图的自动更新,否则我们就得自己操作DOM,优化DOM操作,还要自己维护状态,一自己维护状态,就要陷入状态同步的漩涡,浪费大量时间和精力。
    我们需要技术栈隐藏掉平台的微妙差异,写一段代码可以真正实现跨平台,而不用我们自己纠结于那些本不该应用开发纠结的事,我们需要持续稳定的跨平台支持,最好的移植就是不用移植,这在商业上有很大的价值。
我们需要库或者框架好学,好用,从第一天起就能快速开发,而不是不得不经历几个月的学习曲线那种,因为大多数团队的程序员水平都存在梯度,我们不希望因为一个技术栈把初学水平的人挡在门外很久,理想的状态是技术本身能对招聘工作完全透明,同样的工期,同样的项目,随时找人都可以,招人的时候不用写得过于具体,只要会JavaScript就能快速上手,我们需要概念负担尽量少的技术栈,真正理解了Simplicity的技术。
    我们希望技术栈有非常好的性能,性能的水平和垂直扩展性都很好,这样我们就不用项目写到一半回头去纠结应用开发团队很难解决的性能问题,我们需要在快速开发和基础性能之间平衡得很好的工具,而不是因为要强调某一方面而对另一方面关注太少的那些工具。
    我们需要使用的工具有专业的团队或者社区持续地跟进,最好这些团队和社区自己就把自己的东西投入生产使用的技术,这样至少对我们来说风险就有起码的控制。我们不需要那些心血来潮,永远不成熟因为永远没有专门投入的技术。
    我们需要那些普通人喜欢用,也用得好的技术。
    React满足上面的一些方面,不满足另一些方面,和其他工具一样。你需要React,是因为两点
    第一,你充分评估了你的项目,理解你要解决的问题是什么,是快速开发,性能,团队的人类工程学,多数情况下要解决的问题是多个要素的平衡
    第二,你充分评估了React这个栈,理解它是解决你的具体问题的最佳工具,你真的理解了自己的场景中非用React不可的那些事情

    如果你觉得React快所以需要,事实是React并没有那么快,尤其是大型应用,小型应用里快是不重要的,所有的框架都足够快。
    如果你觉得React开发快所以需要,事实是React并一定是最好用的,尤其是当你考虑了团队的构成。

    如果你觉得React是Facebook开发的所以需要,我的揣测是经历过一个社区adoption的高峰以后,Facebook未必能解决剩下的那1%的问题。
    如果你觉得React Native很火所以需要,这或许是一个理由,但RN也不是唯一选择,从各方面评估,NativeScript这样的栈并不比RN坏多少,也许还稍微好一点。如果是大预算的商业开发,RN甚至不应该成为首选。

    大部分人在用 React 的时候,用到的是两个特性:

    1. 虚拟 DOM

    2. 组件化

   至于其他的伪特性,我认为是有些同学「一瓶子不满,半瓶子咣当」,意淫出来的。这些伪特性包括:

    1. 跨平台。虽然 ReactNative 可以在多个平台上使用,但是 ReactNative 并没有封装不同系统的 API。从这方面来说,这货甚至连 weex 都不如。
    2. 更易于组织逻辑。这明显是 flux/redux 做的事情。而且 redux 已经明确说明了,不仅仅适用于 React,其他框架也可以用 redux。

小而美的视图层

React 与 VueJS 都是所谓小而美的视图层Library,而不是Angular 2这样兼容并包的Frameworks。任何一个编程生态都会经历三个阶段,第一个是原始时期,由于需要在语言与基础的API上进行扩充,这个阶段会催生大量的Tools。第二个阶段,随着做的东西的复杂化,需要更多的组织,会引入大量的设计模式啊,架构模式的概念,这个阶段会催生大量的Frameworks。第三个阶段,随着需求的进一步复杂与团队的扩充,就进入了工程化的阶段,各类分层MVC,MVP,MVVM之类,可视化开发,自动化测试,团队协同系统。这个阶段会出现大量的小而美的Library。
React 并没有提供很多复杂的概念与繁琐的API,而是以最少化为目标,专注于提供清晰简洁而抽象的视图层解决方案,同时对于复杂的应用场景提供了灵活的扩展方案,典型的譬如根据不同的应用需求引入MobX/Redux这样的状态管理工具。React在保证较好的扩展性、对于进阶研究学习所需要的基础知识完备度以及整个应用分层可测试性方面更胜一筹。不过很多人对React的意见在于其陡峭的学习曲线与较高的上手门槛,特别是JSX以及大量的ES6语法的引入使得很多的传统的习惯了jQuery语法的前端开发者感觉学习成本可能会大于开发成本。与之相比Vue则是典型的所谓渐进式库,即可以按需渐进地引入各种依赖,学习相关地语法知识。比较直观的感受是我们可以在项目初期直接从CDN中下载Vue库,使用熟悉的脚本方式插入到HTML中,然后直接在script标签中使用Vue来渲染数据。随着时间的推移与项目复杂度的增加,我们可以逐步引入路由、状态管理、HTTP请求抽象以及可以在最后引入整体打包工具。这种渐进式的特点允许我们可以根据项目的复杂度而自由搭配不同的解决方案,譬如在典型的活动页中,使用Vue能够兼具开发速度与高性能的优势。不过这种自由也是有利有弊,所谓磨刀不误砍材工,React相对较严格的规范对团队内部的代码样式风格的统一、代码质量保障等会有很好的加成。
一言蔽之,笔者个人觉得Vue会更容易被纯粹的前端开发者的接受,毕竟从直接以HTML布局与jQuery进行数据操作切换到指令式的支持双向数据绑定的Vue代价会更小一点,特别是对现有代码库的改造需求更少,重构代价更低。而React及其相对严格的规范可能会更容易被后端转来的开发者接受,可能在初学的时候会被一大堆概念弄混,但是熟练之后这种严谨的组件类与成员变量/方法的操作会更顺手一点。便如Dan Abramov所述,Facebook推出React的初衷是为了能够在他们数以百计的跨平台子产品持续的迭代中保证组件的一致性与可复用性。

相辅相成的客户端渲染与服务端渲染

最初的网页是数据、模板与样式的混合,即以经典的APS.NET、PHP与JSP为例,是由服务端的模板提供一系列的标签完成从业务逻辑代码到页面的流动。所以,前端只是用来展示数据,所谓附庸之徒。而随着Ajax技术的流行,将WebAPP也视作CS架构,抽象来说,会认为CS是客户端与服务器之间的双向通信,而BS是客户端与服务端之间的单向通信。换言之,网页端本身也变成了有状态。从初始打开这个网页到最终关闭,网页本身也有了一套自己的状态,而拥有这种变化的状态的基础就是AJAX,即从单向通信变成了双向通信。

而近两年来随着React的流行服务端渲染的概念重回人们的视线。需要强调的是,我们现在称之为服务端渲染的技术并非传统的以JSP、PHP为代表的服务端模板数据填充,更准确的服务端渲染作用的描述是对于客户端应用的预启动与预加载。我们千方百计将客户端代码拉回到服务端运行并不是为了替换现有的API服务器,并且在服务端运行过的代码同样需要在客户端重新运行。

引入服务端渲染带来的优势主要在于以下三个方面:

  • 对浏览器兼容性的提升,目前React、Angular、Vue等现代Web框架纷纷放弃了对于旧版本浏览器的支持,引入服务端渲染之后至少对于使用旧版本浏览器的用户能够提供更加友好的首屏展示,虽然后续功能依然不能使用。

  • 对搜索引擎更加友好,客户端渲染意味着整体的渲染用脚本完成,这一点对于爬虫并不友好。虽然现代爬虫往往也会通过内置自动化浏览器等方式支持脚本执行,但是这样无形会加重很多爬虫服务器的负载,因此Google这样的大型搜索引擎在进行网页索引的时候还是依赖于文档本身。如果你希望提升在搜索引擎上的排行,让你的网站更方便地被搜索到,那么支持服务端渲染是个不错的选择。

  • 整体加载速度与用户体验优化,在首屏渲染的时候,服务端渲染的性能是远快于客户端渲染的。不过在后续的页面响应更新与子视图渲染时,受限于网络带宽与重渲染的范畴,服务端渲染是会弱于客户端渲染。另外在服务端渲染的同时,我们也会在服务端抓取部分应用数据附加到文档中,在目前HTTP/1.1仍为主流的情况下可以减少客户端的请求连接数与时延,让用户更快地接触到所需要的应用数据。

总结而言,服务端渲染与客户端渲染是相辅相成的,在React等框架的协助下我们也可以很方便地为开发阶段的纯客户端渲染应用添加服务端渲染支持。

我们真的需要上述的两个特性吗?

函数式思维:抽象与直观

近年来随着应用业务逻辑的日益复杂与并发编程的大规模应用,函数式编程在前后端都大放异彩。软件开发领域有一句名言:可变的状态是万恶之源,函数式编程即是避免使用共享状态而避免了面向对象编程中的一些常见痛处。不过老实说笔者并不想一味的推崇函数式编程,在下文关于Redux与MobX的讨论中,笔者也会提及函数式编程不可避免地会使得业务逻辑支离破碎,反而会降低整个代码的可维护性与开发效率。与React相比,Vue则是非常直观的代码架构,每个Vue组件都包含一个script标签,这里我们可以显式地声明依赖,声明操作数据的方法以及定义从其他组件继承而来的属性。而每个组件还包含了一个template标签,等价于React中的render函数,可以直接以属性方式绑定数据。最后,每个组件还包含了style标签而保证了可以直接隔离组件样式。我们可以先来看一个典型的Vue组件,非常直观易懂,而两相比较之下也有助于理解React的设计思想。

XHTML

<script> export default { components: {}, data() { return { notes: []澳门三合彩票,, }; }, created() { this.fetchNotes(); }, methods: { addNote(title, body, createdAt, flagged) { return database('notes').insert({ title, body, created_at: createdAt, flagged }); }, }; </script> <template> <div class="app"> <header-menu :addNote='addNote' > </div> </template> <style scoped> .app { width: 100%; height: 100%; postion: relative; } </style>

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
<script>
export default {
  components: {},
  data() {
    return {
      notes: [],
    };
  },
  created() {
    this.fetchNotes();
  },
  methods: {
    addNote(title, body, createdAt, flagged) {
     return database('notes').insert({ title, body, created_at: createdAt, flagged });
  },
};
</script>
<template>
  <div class="app">
    <header-menu
      :addNote='addNote'
      >
  </div>
</template>
<style scoped>
  .app {
    width: 100%;
    height: 100%;
    postion: relative;
  }
</style>

当我们将视角转回到React中,作为单向数据绑定的组件可以抽象为如下渲染函数:

JavaScript

View = f(Data)

1
View = f(Data)

这种对用户界面的抽象方式确实令笔者耳目一新,这样我们对于界面的组合搭配就可以抽象为对于函数的组合,某个复杂的界面可以解构为数个不同的函数调用的组合变换。0.14版本时,React放弃了MixIn功能,而推荐使用高阶函数模式进行组件组合。这里很大一个考虑便是Mixin属于面向对象编程,是多重继承的一种实现,而函数式编程里面的Composition(合成)可以起到同样的作用,并且能够保证组件的纯洁性而没有副作用。

很多人第一次学习React的时候都会觉得JSX语法看上去非常怪异,这种背离传统的HTML模板开发方式真的靠谱吗?(在2.0版本中Vue也引入了JSX语法支持)。我们并不能单纯地将JSX与传统的HTML模板相提并论,JSX本质上是对于React.createElement函数的抽象,而该函数主要的作用是将朴素的JavaScript中的对象映射为某个DOM表示。其大概思想图示如下:
澳门三合彩票 8

在现代浏览器中,对于JavaScript的计算速度远快于对DOM进行操作,特别是在涉及到重绘与重渲染的情况下。并且以JavaScript对象代替与平台强相关的DOM,也保证了多平台的支持,譬如在ReactNative的协助下我们很方便地可以将一套代码运行于iOS、Android等多平台。总结而言,JSX本质上还是JavaScript,因此我们在保留了JavaScript函数本身在组合、语法检查、调试方面优势的同时又能得到类似于HTML这样声明式用法的便利与较好的可读性。

项目中的全栈工程师:技术全栈,需求隔离,合理分配

全栈工程师对于个人发展有很大的意义,对于实际的项目开发,特别是中小创公司中以进度为第一指挥棒的项目而言更具有非常积极的意义。但是全栈往往意味着一定的Tradeoff,步子太大,容易扯着蛋。任何技术架构和流程的调整,最好都不要去违背康威定律,即设计系统的组织,其产生的设计等同于组织之内、组织之间的沟通结构。有些全栈的结果就是强行按照功能来分配任务,即最简单的来说可能把登录注册这一块从数据库设计、服务端接口到前端界面全部分配给一个人或者一个小组完成。然后这个具体的执行者,因为其总体负责从上到下的全部逻辑,在很多应该规范化的地方,特别是接口定义上就会为了求取速度而忽略了必要的规范。最终导致整个系统支离破碎成一个又一个的孤岛,不同功能块之间表述相同意义的变量命名都能发生冲突,各种奇形怪状的id、uuid、{resource}_id令人眼花缭乱。

现代经济发展的一个重要特征就是社会分工日益精细明确,想要成为无所不知的通才不过南柯一梦。在自己的小团队中应该提倡职位轮替,一般某个项目周期完成后会调换部分前后端工程师的位置,一方面是为了避免繁杂的事务性开发让大家过于疲惫。另一方面也是希望每个人都了解对方的工作,这样以后出Bug的时候就能换位思考,毕竟团队内部矛盾,特别是各个小组之间的矛盾一直是项目管理中头疼的问题。

虚拟 DOM

虚拟 DOM 解决了频繁操作 DOM
产生的性能问题。那么下面几项事实必定会导致这一特性「没有前途」:

  1. 设备的硬件性能会越来越好,性能在将来不再是问题。
  2. 假如说我们要解决性能问题,相比虚拟 DOM,
    下面几个解决方案会更好:
  3. 浏览器实现虚拟 DOM。而且这也是虚拟 DOM 被应用的正确场景和姿势。
  4. 再操作数据的地方做 diff,而不是在虚拟 DOM 的基础上做 diff。这是才是 cache/diff 的正确用法。

本文由澳门三合彩票发布于Web前端,转载请注明出处:有的是的前端开拓框架、技能体系争妍斗艳,R

关键词: