2017年值得关注的JavaScript框架与主题

CharleneMcK 7年前
   <p><a href="/misc/goto?guid=4959729721129726402" rel="nofollow,noindex">2017年值得关注的JavaScript框架与主题</a> 翻译自 <a href="/misc/goto?guid=4959729721245671840" rel="nofollow,noindex">Top JavaScript Frameworks & Topics to Learn in 2017</a> ,从属于笔者的 <a href="/misc/goto?guid=4959729721338977129" rel="nofollow,noindex">Web 前端入门与最佳实践</a> 。其他有关于2016年前端开发的总结包括 <a href="/misc/goto?guid=4959729721429868698" rel="nofollow,noindex">2016 年前端工具使用度调研报告</a> 、 <a href="/misc/goto?guid=4959729721522977929" rel="nofollow,noindex">2016年里做前端是怎样一种体验</a> 、2016前端学习路线图。另外推荐 <a href="/misc/goto?guid=4959729721625781042" rel="nofollow,noindex">The State of UX in 2017</a> ,作为开发者了解下设计的想法也是必需的。</p>    <p><img src="https://simg.open-open.com/show/dafed9beb64ed8125d63f73b377501b1.jpg"></p>    <p>JavaScript的繁荣促生了很多优秀的技术、框架与工具库,这空前的繁荣也给很多人造成了困惑,无所适从。到底何者是值得投入,代表了未来的方向,而何者又是真正适合于当前项目,当前团队的?而本文即时作者基于自身实践的一些思考,与诸君共享。</p>    <h2>JavaScript & DOM Fundamentals</h2>    <p>工欲善其事,必先知其器。在我们准备了解使用其他JavaScript框架的时候,我们首先需要去了解JavaScript的语法要点与一些工程实践:</p>    <ul>     <li> <p>内建方法:我们需要了解标准数据类型 (特别是 <a href="/misc/goto?guid=4959638272176803780" rel="nofollow,noindex">arrays</a> , <a href="/misc/goto?guid=4959638272798223322" rel="nofollow,noindex">objects</a> , <a href="/misc/goto?guid=4959638272980314563" rel="nofollow,noindex">strings</a> , 以及 <a href="/misc/goto?guid=4959638272714727073" rel="nofollow,noindex">numbers</a> ).</p> </li>     <li> <p>函数 & <a href="/misc/goto?guid=4959729721849033066" rel="nofollow,noindex"> <strong>纯函数</strong> </a> <strong>:</strong> 或许你觉得自己已经很了解函数了,但是总有些小技巧是你没有接触过的。另外不仅仅是对于基本的函数的用法,我们还要对函数式编程的思想,譬如纯函数高阶函数等有所掌握。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729721941278352" rel="nofollow,noindex"><strong>Closures</strong> </a> <strong>:</strong> 在学习闭包的过程中了解JavaScript传统的函数作用域。</p> </li>     <li> <p>Callbacks:回调是JavaScript异步编程的基本概念,某个回调函数会在某个异步操作结束后被调用,就好比领导对你说:好好干你的工作,做好了跟我汇报下。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729722021326133" rel="nofollow,noindex"><strong>Promises</strong> </a> <strong>:</strong> Promise是处理将来值的方法之一,当某个函数返回的是Promise对象时,你可以调用该对象的 then 函数来获取异步传入的值。而调用者是通过传入的 resolve 回调来传值,譬如 doSomething().then(value => console.log(value));</p> </li>     <li> <p><a href="/misc/goto?guid=4959007486484251452" rel="nofollow,noindex"><strong>Ajax & 服务端API调用</strong> </a> <strong>:</strong> 绝大部分有趣的应用都需要与服务端通过网络进行交互,你应该了解基本的HTTP Client知识。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729722203690244" rel="nofollow,noindex"><strong>ES6</strong> </a> <strong>:</strong> 最新的JavaScript版本为ES7,或者叫ES2016,不过很多人ES6还没用熟练,正在过渡期吧。</p> </li>     <li> <p><a href="/misc/goto?guid=4958967308506101269" rel="nofollow,noindex"><strong>Classes</strong> </a> (note: <a href="/misc/goto?guid=4959652741009243293" rel="nofollow,noindex"> <strong>避免类继承</strong> </a> . 参考 <a href="/misc/goto?guid=4959729722398405172" rel="nofollow,noindex">How to Use Classes and Sleep at Night</a> .)</p> </li>     <li> <p><a href="/misc/goto?guid=4959729722515270250" rel="nofollow,noindex"><strong>函数式编程基础</strong> </a> <strong>:</strong> 函数式编程基于数据函数的组合来构建业务逻辑,避免了共享状态与可变数据,这一点会避免很多的问题。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729722611315465" rel="nofollow,noindex"><strong>Generators</strong> </a> <strong>&</strong> <a href="/misc/goto?guid=4959729722714961931" rel="nofollow,noindex"> <strong>async/await</strong> </a> <strong>:</strong> 个人观点,最好的异步代码的写法就是用写同步代码的方式去写异步代码。不可否认这些都存在学习曲线,不过磨刀不误砍柴工。</p> </li>     <li> <p>Performance: <a href="/misc/goto?guid=4959729722818575587" rel="nofollow,noindex"> <strong>RAIL</strong> </a> <strong>—</strong> 参考 <a href="/misc/goto?guid=4958854485248259878" rel="nofollow,noindex">“PageSpeed Insights”</a> & <a href="/misc/goto?guid=4959729722969861872" rel="nofollow,noindex">“WebPageTest.org”</a></p> </li>     <li> <p>Progressive Web Applications (PWAs):参考 <a href="/misc/goto?guid=4959729723072280484" rel="nofollow,noindex">“Native Apps are Doomed”</a> & <a href="/misc/goto?guid=4959729723170590957" rel="nofollow,noindex">“Why Native Apps Really Are Doomed”</a></p> </li>     <li> <p><a href="/misc/goto?guid=4959729723286882828" rel="nofollow,noindex"><strong>Node & Express</strong> </a> <strong>:</strong> Node允许你在服务端运行JavaScript程序,而Express则是目前最为流行的基于NodeJS的Web框架。</p> </li>     <li> <p><a href="/misc/goto?guid=4958871496205746239" rel="nofollow,noindex"><strong>Lodash</strong> </a> <strong>:</strong> 一个非常好用的、模块清晰的JavaScript辅助工具,其也遵循了很多函数式编程的理念,你可以通过 lodash/fp 导入。</p> </li>    </ul>    <h2>Tooling</h2>    <ul>     <li> <p><a href="/misc/goto?guid=4959637675583151052" rel="nofollow,noindex"><strong>Chrome Dev Tools</strong> </a> <strong>:</strong> <a href="/misc/goto?guid=4959729723477965398" rel="nofollow,noindex">DOM inspect</a> & <a href="/misc/goto?guid=4959729723595603168" rel="nofollow,noindex">JS debugger</a> : Chrome Dev Tools算是最为优秀的调试工具了,Firefox也有很多不错的扩展。</p> </li>     <li> <p><a href="/misc/goto?guid=4958867133348946608" rel="nofollow,noindex"><strong>npm</strong> </a> <strong>:</strong> 官方开源的JavaScript包管理工具。</p> </li>     <li> <p><a href="/misc/goto?guid=4959623112065163570" rel="nofollow,noindex"><strong>git</strong> </a> <strong>&</strong> <a href="/misc/goto?guid=4958183584851817768" rel="nofollow,noindex"> <strong>GitHub</strong> </a> <strong>:</strong> 分布式版本管理系统,很适合团队协作。</p> </li>     <li> <p><a href="/misc/goto?guid=4958877845976897237" rel="nofollow,noindex"><strong>Babel</strong> </a> <strong>:</strong> 能够将ES6代码编译到ES5使之能够兼容老版本浏览器。</p> </li>     <li> <p><a href="/misc/goto?guid=4958977348404680831" rel="nofollow,noindex"><strong>Webpack</strong> </a> <strong>:</strong> 最著名的模块打包工具之一,有不少优秀的模板配置奥,譬如 <a href="/misc/goto?guid=4959729723912937936" rel="nofollow,noindex">Webpack2-React-Redux-Boilerplate</a> 。</p> </li>     <li> <p><a href="/misc/goto?guid=4958832861167207492" rel="nofollow,noindex"><strong>Atom</strong> </a> <strong>,</strong> <a href="https://code.visualstudio.com/d?utm_expid=101350005-35.Eg8306GUR6SersZwpBjURQ.3&utm_referrer=https%3A%2F%2Fwww.google.com%2F" rel="nofollow,noindex"> <strong>VSCode</strong> </a> <strong>, or</strong> <a href="/misc/goto?guid=4958865832660050715" rel="nofollow,noindex"> <strong>WebStorm</strong> </a> <strong>+</strong> <a href="/misc/goto?guid=4959729724257233531" rel="nofollow,noindex"> <strong>vim</strong> </a> <strong>:</strong> 你需要为自己选择合适的编辑器来辅助你快速开发。Atom与VSCode都是非常优秀的JavaScript编辑器,WebStorm也不错但是它是收费版本。如果你打算直接在服务端开发的话,Vim是个不错的选择。</p> </li>     <li> <p><a href="/misc/goto?guid=4958870940891400873" rel="nofollow,noindex"><strong>ESLint:</strong> </a> ESLint能够帮助开发者更快地发现语法错误与样式问题,在Code Review与TDD之后这是个不错的减少Bug的方法。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729724426909941" rel="nofollow,noindex"><strong>Tern.js:</strong> </a> 基于编辑器插件的标准JavaScript类型推导工具,不需要任何编译步骤或者注解支持。</p> </li>     <li> <p><a href="/misc/goto?guid=4958999003582682021" rel="nofollow,noindex"><strong>Yarn</strong> </a> <strong>*:</strong> 类似于NPM的工具,不过安装起来更为可靠快速。</p> </li>     <li> <p><a href="/misc/goto?guid=4958989889583944253" rel="nofollow,noindex"><strong>TypeScript*:</strong> </a> JavaScript的静态类型支持,不过需要特别注意的是,除非你在学习Angular 2,不然我觉得你如果要选用Angular 2的话还是要慎重考虑。我个人很喜欢TypeScript,也很钦佩他们团队的优秀工作,不过任然有很多的权衡,可以参阅 <a href="/misc/goto?guid=4959729724633383708" rel="nofollow,noindex">“The Shocking Secret About Static Types”</a> & <a href="/misc/goto?guid=4959729724752612579" rel="nofollow,noindex">“You Might Not Need TypeScript”</a> .</p> </li>     <li> <p><a href="/misc/goto?guid=4959714402765517148" rel="nofollow,noindex"><strong>Flow*:</strong> </a> JavaScript静态类型检测工具,可以阅读 <a href="/misc/goto?guid=4959729724915263588" rel="nofollow,noindex">“TypeScript vs Flow”</a> 来对于这二者有个大概的了解,如果你打算Flow的话也是推荐我的编辑器 <a href="/misc/goto?guid=4959729725042942288" rel="nofollow,noindex">Nuclide</a> 。</p> </li>    </ul>    <h2>React</h2>    <p><a href="/misc/goto?guid=4958968605084997344" rel="nofollow,noindex"><strong>React</strong> </a> 是个专注于构建用户视图层的JavaScript库,其基于单向数据流的设计思想,也就意味着:</p>    <ul>     <li> <p>React 以Props的形式将参数传入Components,并且在数据发生变化的时候选择性重渲染部分DOM。在重渲染阶段发生的数据变化并不会立刻触发重渲染,而是在下一个绘制阶段的时候才会进行重渲染。</p> </li>     <li> <p>渲染完毕之后,就进入了事件处理,React使用特殊的合成事件帮助开发者监听与响应事件,将所有的节点上的事件交托单一事件监听器处理以获得更好的性能体验。你可以在这些事件的监听函数中通过外部传入的回调重新设置Props或者直接修改内部State。</p> </li>     <li> <p>对于数据的任何变化都会重复步骤1。</p> </li>    </ul>    <p>这种单向数据流与当时以Angular 1 / Knockout为代表的双向数据绑定形成对比,双向数据绑定中如果发现绑定的数据发生变化则会立刻触发重渲染,而无论当前是否处于渲染流程中,这一点也就导致了Reflows与Repaints的性能表现非常差。React并没有预置专门的数据管理系统,不过官方推荐基于Flux的解决方案。React 的单向数据流的概念借鉴了很多函数式编程的设计思想,并且对于不可变数据结构的应用也在很大程度上改变了我们对前端框架的认识。如果你希望了解更多关于React与Flux架构的知识,推荐阅读 <a href="/misc/goto?guid=4959729725207039411" rel="nofollow,noindex">“The Best Way to Learn to Code is to Code: Learn App Architecture by Building Apps”</a> 。</p>    <ul>     <li> <p><a href="/misc/goto?guid=4958996917562467082" rel="nofollow,noindex"><strong>create-react-app*:</strong> </a> 官方出品的快速脚手架搭建工具。</p> </li>     <li> <p><a href="/misc/goto?guid=4959729725361071324" rel="nofollow,noindex"><strong>react-router*:</strong> </a> 方便的React路由解决方案。</p> </li>     <li> <p><a href="/misc/goto?guid=4958999007763604188" rel="nofollow,noindex"><strong>Next.js*:</strong> </a> 非常简单的通用React应用开发框架。</p> </li>     <li> <p><a href="/misc/goto?guid=4959652752832580129" rel="nofollow,noindex"><strong>velocity-react*:</strong> </a> 非常不错的React动画辅助库。</p> </li>    </ul>    <h2>Redux</h2>    <p><a href="/misc/goto?guid=4959672803167376147" rel="nofollow,noindex"><strong>Redux</strong> </a> 为应用提供了事务式的,确定性的状态管理支持。在Redux中,我们仅可以通过Action来修改当前的应用状态。如果你希望深入了解为啥这么做,可以参阅 <a href="/misc/goto?guid=4959729725607925240" rel="nofollow,noindex">“10 Tips for Better Redux Architecture.”</a> 或者跟着 <a href="/misc/goto?guid=4959729725720706193" rel="nofollow,noindex">Dan Abramov</a> 的官方课程:</p>    <ul>     <li> <p><a href="/misc/goto?guid=4959007488744343835" rel="nofollow,noindex"><strong>“Getting Started with Redux”</strong> </a></p> </li>     <li> <p><a href="/misc/goto?guid=4959716569182169503" rel="nofollow,noindex"><strong>“Building React Applications with Idiomatic Redux”</strong> </a></p> </li>    </ul>    <p>实际上即使你不使用Redux,也很推荐学习Redux的设计思想,它可以给你很多关于状态管理的最佳实践,告诉你纯函数的价值所在,以及告诉你何谓Reducers,何谓General-Purpose函数。在Redux的工程实践中,对于异步Action的处理也是值得讨论的:</p>    <ul>     <li> <p><a href="/misc/goto?guid=4959729725915493563" rel="nofollow,noindex"><strong>redux-saga*:</strong> </a> A synchronous-style side-effect library for Redux. Use this to manage I/O (such as handling network requests).</p> </li>    </ul>    <h2>Angular 2*</h2>    <p><a href="/misc/goto?guid=4958866372165218034" rel="nofollow,noindex"><strong>Angular 2</strong> </a> 脱胎于风靡一时的Angular 1,鉴于当年疯狂的流行度,学会这个会是你简历上浓墨重彩的一笔,不过我还是推荐先学习React。我个人也认为React是优于Angular 2的, <a href="/misc/goto?guid=4959729726065001355" rel="nofollow,noindex">React over Angular 2</a> because:</p>    <ol>     <li> <p>它更简单</p> </li>     <li> <p>社区很强大</p> </li>    </ol>    <h2>RxJS</h2>    <p><a href="/misc/goto?guid=4958978078564672477" rel="nofollow,noindex"><strong>RxJS</strong> </a> 是JavaScript中一系列响应式编程工具的集合,就好比流处理领域的Lodash,它把响应式编程带入到了JavaScript的领域。ECMAScript Observables是stage-1阶段的草稿,RxJS 5+则是当前的标准实现。虽然我个人非常喜欢RxJS,但是如果你想在工程中使用RxJS的话还是需要考虑下,因为其内置了很多的Operators,其会增加你的包体尺寸。不过我们可以通过仅引入部分所需要的库来解决这个问题,最后大概只会使得包体增加200KB左右吧。</p>    <h2>为什么没有提到其他框架?</h2>    <p>有不少人问我为啥没有把他们喜欢的框架也列举进来,对于我而言我会先考虑:这个在真实的工作中会所有帮助吗?当然,这一点见仁见智,我也是打算从一些所谓的人气投票中一窥变化。首先,我会去Google Trends中查看各个框架关联关键词的被搜索情况:</p>    <p style="text-align:center"><img src="https://simg.open-open.com/show/ce81f858acb6f94feab4af2efc34f7e2.png"></p>    <p>另一个很有帮助的网站就是Indeed.com,会聚合不同站点上对于不同职位的开发者的需求信息,可以看出目前招聘上对于前端开发者技能需求的情况为:</p>    <p style="text-align:center"><img src="https://simg.open-open.com/show/c7270077539f181b999a922a4283ab73.png"></p>    <p>在上图中,Angular(Angular 1+Angular 2)还是高于React的,不过我个人还是会推荐React,有如下几个原因吧:</p>    <ul>     <li> <p><a href="/misc/goto?guid=4959729726223265765" rel="nofollow,noindex">More people are interested in learning React than Angular</a></p> </li>     <li> <p><a href="/misc/goto?guid=4959729726223265765" rel="nofollow,noindex">React significantly leads Angular in user satisfaction</a></p> </li>    </ul>    <p> </p>    <p>来自:https://segmentfault.com/a/1190000007805673</p>    <p> </p>