React框架刚刚发布的时候,JSX颠覆了不少人的想法。习惯了HTML标签与JavaScript代码分离的前端工程师们,看到JSX大概都会不由吐槽:“这些奇怪的标签出如今JavaScript里是要干啥?!”咱们一贯贯彻的关注点分离原则呢?Facebook的工程师难道一点都不了解这些社区中已经默认的规范?前端
像不少人同样,我一开始对JSX这种语法是持怀疑态度的。甚至当我爱上JSX后,每次我向别的开发者推荐这种语法,我都会以为我是在向别人展现我丑陋的孩子。react
从一开始的怀疑到爱上JSX,我渐渐意识到JSX其实并无那么激进。它不过是硬币的另外一面。JSX实际上是前端开发中天然进化的一个过渡。为何这么说呢,咱们有必要回顾一下前端这几年的发展历程了。数组
还记得那个jQuery盛行的时代么?非侵入式的JavaScript被各类提倡。咱们的HTML是纯HTML,咱们的JavaScript是纯JavaScript。咱们开发时是严格贯彻所谓的关注点分离的。前端工程师
咱们像下面这样写HTML:框架
<a class="hide">Click to hide me</a>
而咱们的JavaScript会这样写:ide
$(".hide").click(function() { $(this).hide(); })
按照以前的理解,这样作是真的作到了关注点分离对吧?然而我以为并非这样。函数
这样写看起来像是一个好主意。咱们的HTML是绝对纯净的,彻底不参合任何逻辑代码。可是咱们会慢慢发现一个问题:我怎么知道哪行JavaScript代码在控制个人HTML呢?答案是:除非我阅读了整个JavaScript文件,我才能明白,哪段JavaScript代码在控制哪段HTML。(译者注:这样的状况很常见,尤为是在大型项目中,咱们有无数的还有可能重复的DOM节点,HTML和JavaScript文件不在一块儿,要修改起来简直太复杂了)。在这种模式中,你不能仅仅简单的修改一个标签而不去检查对应的JavaScript代码以确保你的修改没有破换选择器执行。你看,这里实际上并无实现关注点分离,咱们仍是要不断的关注HTML和JavaScript之间的联系。咱们作到的仅仅是把JS和HTML分离到了两个不一样的文件中。在本质上这两种技术是密不可分的,他们必须保持步调一致,不然就会致使咱们的应用崩溃。oop
直接分割HTML和JS致使咱们的应用更加难以维护和调试。每次你想修改一个标签,老是会担忧破坏一个jQuery选择器。若是咱们对关注点的分离不那么严格,也许能够减轻一些痛苦。因而,咱们迎来了第二阶段...学习
在Knockout和Angular中出现的双向绑定,让全部前端开发者眼前一亮。许多开发者开始抛弃以前信奉的关注点分离,并全力拥抱这种在HTML标签中声明式绑定的力量。当数据发生改变,UI也自动发生变更。当UI发生变更,数据也随之变更。如此清晰,如此简单。(译者注:我认为这是另外一种意义上的关注点分离,咱们再也不须要关注HTML与JavaScript之间的联系,咱们须要作的就是维护好数据。)ui
这些框架的实现的确大不相同,但他们都在试图作相同的事情。试想使用这几个流行框架实现迭代数组这个例子:
//Angular <div ng-repeat=”user in users”> //Ember {{#each user in users}} //Knockout data-bind=”foreach: users”
可是这里出现了一些有意思的事情————不多有人意识到一个很是显著的问题:咱们实际上在把JavaScript放到HTML中。这并非咱们所理解的那种关注点分离。咱们能够发现这些框架都在处理同一件事:经过为HTML添加额外的特殊标记使其更强大。这些标记能够被解析为JavaScript。所以,既然咱们可以接受JavaScript与HTML经过这种方式混合在一起,那么是时候让React介入并向咱们展现硬币的另外一面了...
React的JSX并非一个激进的改变,是由于咱们这个行业从一开始就注定HTML和JavaScript应该是在一块儿的。
只有当你体验过React和JSX以后,才能体会到这样作有多少好处。React的JSX彻底优于全部的“第二阶段”风格的框架的缘由有如下几点:
当你的HTML中出现输入错误时,你很难知道本身是哪里写错了。在不少状况下这是一种无声的运行时错误。好比,若是你在写Angular应用时输入n-repeat而不是ng-repeat,什么都不会发生。当你在写Knockout应用时把data-bind写成data-bnd,也一样什么都不会发生。在出现这些错误时,你的应用会悄无声息的运行时失败。这太使人沮丧了。
相比之下,当你在JSX中发生相似的输入错误时,它是不会被编译的。忘记闭合<li>
标签了?难道你不想在你输入错误的HTML时获得丰富的反馈么?
ReactifyError: /components/header.js: Parse Error: Line 23: Expected corresponding JSX closing tag for li while parsing file: /components/header.js
有了JSX,这样丰富的错误反馈终于成为现实!靠这一点JSX绝对完胜。如此快速而又丰富的反馈极大的提升了生产效率。正如我在个人Clean Code课程中讨论的那样————良好的工程解决方案遵循速错原则。(译者注:原文是:well- engineered solutions fail fast,关于fail fast能够查看http://geeklu.com/2010/07/fai... 进行了解)
使用JavaScript编写你的标记,意味着这些标记能够借助JavaScript的所有能力,而不是像Angular或者Knockout这种以HTML为中心的框架只能提供有限的特殊标记。(译者注:我认为这里做者的表述并不许确,Angular也一样能够自由扩展HTML,只不过没有React那么灵巧方便)。
Client-side frameworks shouldn’t require you to learn a proprietary syntax for declaring loops and conditionals.
客户端框架不该当要求使用者学习特殊的语法来声明循环或者条件语句。
React减小了使用者学习另外一种特殊的声明循环和基本条件语句的成本。你能够看看第二阶段中提到的几个框架,他们实现双向绑定的方式都是依靠一些属于他们本身的特殊语法。相反,JSX看上去和HTML几乎同样,像循环和条件语句,彻底依赖原生的JavaScript。与众多的JavaScript框架相比,不须要去学习相似于数据绑定等特殊语法,这一点又让React和JSX脱颖而出。
而且,因为你将这些标记与相关联的JavaScript数据写在一个文件中,当你引用函数时,许多IDE可以提供一些智能提示。想一想当你使用那些以HTML为中心的框架时,调用一个function却老是输入错误时的苦恼吧!
JSX并不一个疯狂的主意,它就是一段很正常的程序,所以不要再反感它了。
JSX isn’t revolutionary. It’s evolutionary.
JSX不是革命,它只是进化发展的结果。
像不少进化、演变同样,它给咱们带来的是一种改善。