JavaScript 恩仇录
共 9312字,需浏览 19分钟
·
2020-11-20 00:19
前段时间看了一本书讲 ?JS 发展史的书(感谢 @doodlewind 翻译这本书)。看完和朋友聊了会儿,他说你别和我唠什么规范、语言设计,我就想听八卦,你和我唠八卦,我就不困了。所以就有了这篇尽量减少技术细节的八卦文,文章略长,各位看官慢慢品。
JavaScript(下文简称 JS )是 目前最为流行的编程语言之一,在计算机的世界里它也是一个软件。如今,我们使用它编写页面和数据交互逻辑、搭建组件库、实现可视化效果和各种算法等等。StackOverflow 联合创始人 Jeff Atwood 曾说: “所有能用 JS 实现的,最终都将使用 JS 实现”[1],目前来看似乎已经得到了部分的证实。
同其他同类一样,作为一门编程语言性质的软件,JS 有 bug、也会倒排赶工期、经历迭代,还有来自“老板”的需求,甚至还有多部门共建时搞出了一堆问题的情况。今天,和大家一起扒一扒这段曲折精彩的历史。
互联网的新纪元
1991 年 8 月 2 日,一位来自欧洲核子研究组织的工程师 Time Berners Lee 在邮件组里群发说他做了一个项目,叫万维网(World Wide Web),这个项目里大致做了这样几个东西: 一个用于网络传输的协议 (HTTP)、一个超文本标记语言(HTML)、一个命令行的浏览器、一个在 NeXT 电脑上 运行的 HTML 编辑器、一个服务端可以生成文件的软件。目的是给物理学家们交流新闻、信息、文档,项目比较初级,希望感兴趣的人联系他一起交流[2]。从互联网诞生之日起,Web 的初心就相当纯粹:“希望提供人人可以访问的、用来交流分享信息的场所”。
很快,这个项目就从高能物理学圈这个使用范围逐渐扩大到其他使用计算机的用户上,1992 年,世界上有了 26 个网站,这个年底,在美国国家超级电脑应用中心工作的两名小伙 Andreessen 和 Bina,在同行产品的启发下搞了另外一个新的浏览器取名 Mosaic,相比于命令行的浏览器,Mosaic 具有更美观的图形化界面、更加好用一些。一下让本来还不算火爆的互联网火爆了起来,到 1995 年,世界上存在的网站数量已经超过了 1 万个[3]。
诞生之日
在这一发不可收拾的浪潮中,1994 年 Andreessen 和 Bina 和硅谷图形公司的 Jim Clark,成立了一家新的叫做 Netscape(网景) 的公司,希望做出更好的浏览器替代 Mosaic,在 1994 年 10 月,公司发行了一款新的浏览器 Netscape Navigator,这款浏览器很快就火了,逐步替代掉了 Mosaic。
在当时,微软 Office 套件中提供了可以自定义的 VB 来编写一些特殊功能, 苹果也提供了 AppleScript 来解决用户想要自己编写特殊脚本的需求。业界也涌现了是不是要有一门语言能让开发者操作 HTML 的想法。1995 年 网景 招聘了一名之前从事 Unix 网络、内核这些底层开发的程序员 Brendan Eich,希望他来解决浏览器里操作 HTML 的语言的问题。
当时商业环境复杂,1995 年,Sun 公司开始为即将发布的 Java 做各种营销,找到了网景,希望做一些合作。网景表达了合作意向,希望在 Netscape Navigator 2 中集成 Java,这个合作意向让 Brendan Eich 的工作彻底难办起来,不仅技术选型更困难了,距离发布会的时间也相当的短。短时间实现 Java 和 HTML 的整合是不可能的,且 Java 还没正式发布, 第一版也不好用,包括 老板 Andreessen 本人对 Java 也有一定的怀疑。这次运营活动,让开发很为难,最后 Andreessen 拍板临时实现一门语言,最后这门语言最后应该会叫做 “JavaScript”。
Brendan Eich 本来是想集中精力搞一个运行在浏览器的 Scheme 语言,但是这次时间显然非常仓促,公司还要求在外表上尽量接近 Java 并且学习使用门槛要低。他花了 10 天完成了语言的原型,后面稍微做了一些补充性的改动,在 1995 年 9 月正式发版[4]。在这一段时间里,Eich 除了要实现老板提到的这些需求,也掺杂了大量的过往经验。JS 的背后有很多设计参考了 C、Self、HyperTalk、Awk、Logo、Lisp 这些语言。当时有人提出需要实现和 Java 一样的面向对象功能,但是时间显然不够,Eich 参考了 Self 实现了原型模式[5]。
就这样,经历了倒排、来自老板的需求、面向发布会编程,JS 开启了它的历史使命。
浏览器之争
早在 1994 年,微软向网景表达了低价收购意向,被网景拒绝了。微软也在盖茨的领导下开始将战略调整到 Web 方向上[6],开始重点投入 IE 浏览器。微软和网景也从此进入了对峙阶段。
在 JS 正式发布后,微软立刻宣布,接下来会致力于将 VB 推广为 Web 的主要语言。但直到第二年 5 月底,微软才宣布自己做了个和语言无关的标准,支持包括 JS、VBScript 在内的多种脚本语言。
而这一年对微软来说也是难过的一年,Robert Welland 于 95 年 10 月加入微软,主要工作就是研究 VB、JS 在 Web 上的支持。首先,VB 团队评估要支持 Web 工时大概是两年,希望 VB 直接支持的浏览器的希望破灭了。同时,JS 在当时没有规范可言,为了支持这门语言,Welland 等微软工程师需要逆向的去猜测网景实现的那版 JS 的底层实现,逆向的结果让他们十分震惊和迷惑,骂声不断。网景的同行也在这段时间遭受了大量来自微软的批评。最后,他们基于 VB 的一些特性,实现了一个脚本的子集,叫 VBScript,另外基于对 JS 的逆向,称之为 JScript[7],最后这些被打包为 ActiveScript,在 96 年 5 月发布。
因为在 JS 上遭受了不少的同行批评,网景的老板 Andreessen 希望 Eich 投入到 语言规范的投入上。而 Eich 这段时间只想把 JS 前一版本中遗留的一些问题给解决掉,并且优化对应的性能,和老板的安排发生了一些冲突,所以 有个性的 Eich 回家办公了两周,集中时间开发了一个新的版本的引擎,代号为 Spider Monkey[8],这次改造后性能有了较大提升。
Web 从诞生之日便决定了它开放的性质,任何想要垄断和封闭的行为都会失去市场。在开放的环境中竞争,微软和网景的竞争暴露了 JS 在标准实现上的不足,因为一开始没有标准可言,让互联网的开发者们遭受了更多的痛苦,不得不说,商业和技术两全其美的愿望是艰难的。
事实标准
在商业视野上来说,Andreessen 的判断并没有错,他的期待是能将 JS 这门语言推广为 Web 脚本的事实标准。商场如战场,一旦微软主导了开发语言,比如使用 VB 开发 Web,浏览器乃至整个互联网都会有走向封闭的趋势。
包含着商业利益的目的,网景和 Sun 在 1996 年春天非常积极的在寻找一个标准化组织制定 JS 的标准化。同时希望做到微软可以参与,但是不能成为标准化的主导者。他们找了 W3C 和 IETF 两个组织,W3C 元老级人物 Time Berners Lee 等人反对由 W3C 来制定 JS 标准,IETF 更多是关注各类 Web 标准协议的事情,觉得 JS 标准不适合他们来制定。此时,网景的标准化专家恰好认识 ECMA 组织的秘书长,另外 Sun 也是 ECMA 的会员,利用人脉关系,可以做到又快速的产出标准,又能将微软的参与度控制在合适的范围内。为了讨论这个标准,他们成立了第 39 号技术小组(简称 TC39)来讨论。
TC39 小组有一些公约,比如将 HTML 标准交给 W3C 去制定自己不参与、同时不讨论这门语言在特定平台和环境下的功能。在他们的第一次讨论会上,主要有网景和微软提供的两份标准化文件,其中微软的两名贡献者语言背景更为专业和深厚一些,他们对标准的讲解的内容受到了更多人的喜欢。经过很多次会议讨论,求同存异,ECMA 组织制定出了第一版 JS 标准。
因为 「JavaScript」 的商标是由 Sun 注册的,Sun 明确表示不会将这个商标转移给 ECMA 标准组织,最后经过各种抉择,选择使用 ECMAScript 来作为发布标准的语言名称,文档编号 262,所以 JS 的标准文档都叫 Standard ECMA-262。
到此 ECMAScript 第一版发布完毕,但是国际化标准组织(ISO)经过审核发现了很多问题,希望 ECMA 进行一部分修改,所以 这中间又发了一版,称为 ES2,因为改动很小,所以这个版本很少被提及。有趣的是,TC39 在并不知道 ISO 这边非得发一个新的版本才能通过审核之前就开始了下一阶段的讨论,所以他们开启了 V2 版本的讨论实际上对应发版的是 ECMAScript 3。
伴随着标准化的进程,开发者们也逐渐意识到所谓的「JavaScript」本质上只是一个噱头,跟 Java 没有半毛钱关系。此时也诞生了一位著名的 JS 布道师,就是写了那本 《JavaScript 语言精粹》的 Crockford[9],他做了 JS 的初版压缩工具 JSMIN、第一个 JS 的 Lint 工具、还定义了 JSON 这种数据格式。这位大佬不多说,后面我们还会提到他。
革新年代
1997 年,微软发布了电子邮件客户端的 Web 版本[10], 后续他们更新了一个新的版本使用了动态 HTML,还使用了一个新的浏览器 API,叫 XMLHttp,这个 API 可以做到不刷新页面也能更新局部的 UI,这个在如今看来不起眼的小功能在当时可是了不得的一项突破。虽然微软技术超群,但是这种技术广为人知的版本却是:“2000 年左右,Gmail 使用这项技术实现他们的 Web 版本,从此世界上的 Web 技术发生了革新,正式进入 互联网 2.0 时代”。
伴随着技术的革新,网页的复杂度也在倍数增长,浏览器兼容性又十分恼人。为了开发者良好的体验,这个阶段成长起来相当多的 JS 工具,比如 Dojo、Prototype、MooTools、jQuery 这些在一定程度上给开发者屏蔽了处理浏览器的细节。针对这种现象,甚至出现了一个新的词来定义。在暂时不支持某项功能浏览器上支持新特性的补丁脚本 --- Polyfill[11] [12]。
也正是在这个发展过程中,网景遭受来自微软的恶意竞争,一方面大公司碾压级别斗小公司,外加微软的操作系统浏览器捆绑,网景逐渐式微,1998 年网景最终选择开放浏览器源代码(后发展为 Firefox),公司主体也被美国在线收购。而微软成为了这次竞争的赢家,后续也在不思进取逐步又丢失了自己创造的大好局面。
网景的这帮人,虽然在商业上的竞争上失败,但从失败后选择开源继续做浏览器这件事上看,真的是令人佩服,为纯粹和理想主义点赞。
宏图愿景
1998 年,JS 标准 ES3 基本完成了标准和浏览器对语言实现的接轨。TC39 也开始筹划新版本的 JS 标准 ES4, 对于 ES4 语言专家们初期的想法都是希望能成为新的里程碑,改掉老设计中错误的地方。在这之前,大家构想了特别多的想法,比如支持 class 和 模块 还有 package 等概念,这些提案没有纳入 ES3 标准,所以希望在 ES4 中能添加。
在 ES4 的讨论会上,来自惠普赞助的 W3C 研究员提出一个叫做 Spice 的提案[13],用于将 HTML/CSS/JS 结合的更紧密,这个提案整体反馈比较负面。但是部分内容值得考虑。讨论了几轮没啥结果,为了确保 99 年 1 月能提交一份合理的提案给 TC39, 他们单独成立了一个小组叫 TC39-Spice,讨论了一些高级一点的概念,比如类型注解、类、接口、流式执行模型等特性,里面有大量的内容都和 ES3 不兼容。当时 ES3 还没正式发版,讨论中其实遇到很多没解决的问题,但是大家精力还是集中在 ES3 的发版上。
2000 年,微软觉得目前关于 ES4 的提案太大了,砍掉了一些,希望 12 月能发布,当时微软的兴趣就在于「类型注解」。到当年的 6 月,微软发布了 .NET Framework, 在这之前他们因为项目的保密性没法和 TC39 讨论 .NET,但是发布之后他们就可以好好聊一聊了,于是他们找了 TC39 里的核心成员讨论了一些 ES4 标准上的分歧,也没得到个所以然。更让人头大的事情是 微软希望 ECMA 能承担 .NET 的标准化工作,于是又让 TC39 去搞 .NET 的标准化,本来讨论 JS 的小组,被降级为 TC39-TG1,后面参与的人越来越少,这个小组最终降级成为了一个讨论 ECMAScript 对 XML 的支持小组,最终搞了一个标准叫 E4X,这标准搞出来就是个失败的产品,最后只有 Firefox 实现了这个标准,现在已经没人知道他是干嘛的了。
从 98 年到 2000 年,两年时间大家兴致冲冲的设定了下一代编程语言的宏图愿景,最终却因为浏览器斗争、没有核心领袖牵头人导致发展十分混乱, 最后黯然收场。
不死心与理想派
2000 年,一家叫 Macromedia(宏媒体)的公司,发明了一个新的软件叫 Flash,并且配套了一门编程语言 ActionScript,当年 Flash 大红大紫,从 03 年左右开始,Flash 在 web 开发中得到了比较多的应用。因为 ActionScript 是基于 ECMAScript 来实现的,随着发展,AS 遇到了较大的发展瓶颈时,想改语言本身,恰好又有来自 TC39 的大佬,所以想着是不是能把 AS 的一些改造推到标准里面一起建设,其实这里本质上和微软的思路一样,希望以自己家的东西成为事实标准。
2004 年,ES4 还没有讨论个所以然出来,作为元老,Breadan Eich 在投入 Firefox 开发的间隙中抽时间站出来说你们这样搞不行,Web 本身就是开放的,你这一会儿 .NET, 一会儿 ActionScript, 搞这些封闭的东西,莫不是想毁掉老夫的心血?
差不多到 2005 年,工作小组终于可以抽时间搞语言本身的事情,差不多花了两年时间,Eich 带着小组搞了差不多五十多个提案,像解构、let、const 、iterator、generator 这些东西都是在这段时间内完成设计的。但是这门语言是不兼容之前版本的,几家欢喜几家愁。
这两年微软全程没有参与规范的制定。这里一位大佬横空出场,Allen Wirfs-Brock,作为微软的专家,出于对微软战略层面上的考虑,觉得 ES4 这个改动可能会让 ActionScript 变成和 Java、C# 一样的企业级开发语言,会威胁到微软,所以微软你要安排点资源到 JavaScript 标准上来。等他参与进来安排同事发了封邮件声明了微软对 ES4 的反对[14], 这邮件把 Eich 给气坏了,直接回了一句 「Profiled specs are evil(Profile 提案真的邪恶)」。
与此同时,前文提到的 Douglas Crokford 也是 ES4 的反对者,他觉得安全的兼容比任何优异的特性更为重要,于是微软、雅虎的两名核心人物成了 ES4 的反对者。另外 ES4 也很艰难,还有很多问题没解决,规范也没有产出,现在又有了两大反对者,确实很难办。
后续差不多分裂出来两派人物,一派继续支持 ES4 的开发,一派继续保持兼容开发 ES 3.1。
2008 年 6 月,Adobe 放弃了支持 ES4 开发,也标志着 ES4 规范设计的失败,从 1998 到 2008,ES4 背负了太多历史使命,花了十年最终还是难产了。
ES4 失败了,但我突然喜欢上了 Breadan Eich 这个技术人,很纯粹,讨厌封闭的行为,希望 Web 始终保持开放,虽然失败,但还是得给他点赞。
偏见
说到这,大家肯定觉得,Allen Wirfs-Brock 这个人不是好人啊,这两年内微软也没参与 ES4 的建设,你跑过来就是一顿指指点点,说三道四,最后 ES4 凉了,你们微软高兴了吧。
但作为一个技术人,还是不要轻易评判。一方面 Allen Wirfs-Brock 肯定发现了 ES4 的问题,另外一方面肯定也有一定的私心,为自己的雇主微软工作。后面他做的这些事情,或许你也会改变对他的看法。
他率先整理了所有 JScript 和 JS 之间的差异,主动努力去解决兼容性的问题,不再讨论 .Net 这些东西在 Web 上的支持,而是就以 JS 的发展为主要目标,稳步的迭代出 3.1 版本,为了测试最后浏览器的兼容问题,主动公开了 IE 的 JScript 实现原型,Mozilla 本身就是开源,Chrome 也在类似的时间宣布了谷歌浏览器的测试套件。
可以说,ES3.1 几乎让受尽折磨的开发者们看到了一丝曙光,未来还是值得期待的,总有一天,能和兼容性说再见 ?。ES3.1 最终在提交之后发布成为 ES5。
代号「和谐」
在完成 ES5 之后,大家似乎都认识到彼此的初心,都不是为了竞争,单纯出于厂商斗争的目的变小了。TC39 成员开始着手下个迭代的开发。
这中间其实经历了非常多的发展,比如 Coffescript 让大家意识到可以通过一门语言编译到 JS 来曲线救治 JS 这门语言,Google 也开始开发 性能超群的 V8 引擎,CommonJS 模块规范、服务端的 Node 也横空出世了。没必要蹑手蹑脚的保持原有的 JS 标准小步子迭代了。
新版本的 ES 在社区也被成为 ES Harmony,TC39 设立了新的提案机制[15]、倡导者机制,让大家可以通过规范化的流程来实现语言标准。
曲线登顶的微软
作为一个卑微的前端开发,刚开始工作那会儿,我一直有个萌新的认知: “我写的 JS 和微软没有什么关系,但是我写的兼容代码,一定和微软有关系”。
最近几年,事情似乎悄悄发生变化,我的编辑器变成了 微软开发的 VSCode,我常逛的开源社区 Github 被微软收购了,我用的包管理 npm 也被微软收购了,我用的 TypeScript 也是微软开发的。
今天我还知道了,Ajax 也是微软最早在弄的,JavaScript 的标准规范甚至也一直被微软主导着,微软就像那只看不见的手,主导着万千开发者。
也许是花了几十年才让这家公司明白,封闭是无法获得投票的,拥抱开放才是当今时代的精神,这几年的微软,确实牛逼。
题外话
我现在工作和区块链相关,有很多人问我,你一个前端和搞区块链有毛关系啊?
你们知道么?Brendan Eich 现在离开了 Firefox,开了一家公司叫「Brave」,还是做浏览器,不过是基于区块链技术的。你说祖师爷都搞区块链了,我能不跟着走么?
如果你正在寻找一份祖师爷也在做的工作,「蚂蚁链招前端」
欢迎联系我,发送邮件至「wynterding@gmail.com」。
参考资料
[1] Jeff Atwood: https://en.wikipedia.org/wiki/Jeff_Atwood
[2] The Birth of The Web: https://home.cern/science/computing/birth-web/short-history-web
[3] NCSA Mosaic: https://en.wikipedia.org/wiki/Mosaic_(web_browser)
[4] Brendan Eich 谈 JavaScript 的诞生: https://web.archive.org/web/20150817165652/http://devchat.tv/js-jabber/124-jsj-the-origin-of-javascript-with-brendan-eich
[5] Prototype Based Programming: https://en.wikipedia.org/wiki/Prototype-based_programming
[6] The Internet Tidal Wave: https://web.archive.org/web/20110724184430/http://www.lettersofnote.com/2011/07/internet-tidal-wave.html
[7] JScript: https://en.wikipedia.org/wiki/JScript
[8] Spider Monkey: https://developer.mozilla.org/zh-CN/docs/Mozilla/Projects/SpiderMonkey
[9] Douglas Crockford https://en.wikipedia.org/wiki/Douglas_Crockford
[10] MicroSoft Outlook on the Web: https://en.wikipedia.org/wiki/Outlook_on_the_web
[11] What is Polyfill https://remysharp.com/2010/10/08/what-is-a-polyfill/
[12] Polyfill 方案的过去、现在和未来 https://github.com/sorrycc/blog/issues/80
[13] Spice 提案: https://www.ecma-international.org/archive/ecmascript/1998/TC39WG/980928-spice-docs/index.html
[14] 简化 ES4 版本讨论: https://web.archive.org/web/20071103151603/http://wiki.ecmascript.org:80/doku.php?id=discussion:browser_profile
[15] TC39 Process https://tc39.es/process-document/