查看原文
其他

【第2633期】JavaScript运行时环境和标准

whilefor 前端早读课 2022-06-07

前言

今日前端早读课文章由UCloud云计算前端工程师@whilefor投稿分享。

@whilefor,UCloud云计算。专栏:https://www.zhihu.com/column/feworld

正文从这开始~~

JavaScript 主要运行在浏览器端,随着技术不断发展出现很多服务端 JavaScript 运行时,甚至可以做硬件相关的嵌入式开发。

开发 Web 站点时,使用 SSG (Static Site Generation) 或 SSR (Server Side Render)等相关技术时 ,前后端开发可以使用同一种编程语言,对开发者的体验是相当友好。

但不同端的 JavaScript 运行时环境,会有一些差异。

Web 标准规范组织

JavaScript 标准规范是由 ECMA International 组织制定,但很多 Web APIs 不属于 ECMAScript 规范标准。

这些 Web APIs 规范标准是由 WHATWG 和 W3C 来制定,包括 HTML、DOM、调试用的 Console API、编码相关的 Encoding、请求相关的 Fetch API、存储相关的 Storage 等等,都有相关的规范标准。

浏览器端几乎所有的 Web APIs 都有规范标准,服务器端则会选择性的遵循部分 Web APIs 标准规范,而一些则是服务端特有的,比如 Node.js 的 Common JS 模块规范等。

JavaScript 运行时环境

JavaScript 的运行时环境就是各家的 JS 引擎,包括 Chrome 的 V8、Firefox 的 SpiderMonkey、Safari 的 JavaScriptCore,另外还有轻量化的 QuickJS、Hermes 等。

尽管都使用 JavaScript 语言,但到了服务端,JavaScript 就是一门后端语言,它没有 DOM、Window、Canvas、Cookies 等一些浏览器相关的 Web APIs,进而会有文件系统、网络相关 API、与底层操作系统交互的各种 API 等等。

Full JavaScript Runtime

现有服务端 JavaScript 运行时环境著名的有 Node.js、Deno,都基于 V8 引擎,Deno 则使用 Rust 来原生支持了 TypeScript 。

做为后端语言,优势为异步非阻塞、事件驱动机制。同时支撑着庞大的前端工程化相关体系,包括很多的脚手架、打包工具、一些前端相关的编译器等等。

Edge JavaScript Runtime

CDN 作为内容存储分发,用户可以就近取得所需内容;边缘计算则提供计算能力,让服务端的能力在靠近用户的边缘节点上就可以提供。

依托覆盖全球的边缘节点,在提供存储的基础上提供一定的计算能力,边缘计算可以更好的提高应用性能和延迟。

现有主流边缘计算相关的产品有:

  • AWS Lambda@Edge

  • Cloudflare Workers

  • Vercel Edge Functions

  • Netlify Edge Functions

他们都提供支持使用 JavaScript 来编写在边缘节点运行的后端代码(无需自己的服务器),Lambda@Edge、Cloudflare Workers、Vercel Edge Functions 采用 Node.js 来作为他们的 JavaScript 运行时,Netlify Edge Functions 则选择使用 Deno。

因为是边缘节点的 JavaScript 运行时,所以在使用一些 API 上会有所限制,比如不能使用本地文件系统、对代码大小的限制、执行时间限制等,并且会提供一些扩展的 APIs 来满足自己的相关业务需求。

普通的 CDN 中,你只能存取静态文件内容,没有命中则会从源站中取得然后缓存在节点中。边缘计算则可以将本来放在单个地区的服务器的一些业务逻辑放到靠近用户的边缘节点中,比如一些 A/B 测试、权限授权验证、缓存 API 内容、API 请求限制等等。

IoT JavaScript Runtime

在嵌入式设备上运行 JavaScript,需要在内存和计算资源都及其有限的情况下运行,并针对硬件有相关的优化。

大多会选择性的遵循 ECMAScript 部分标准和一些 Web APIs 规范标准,一切为了在嵌入式设备上可以流畅运行。

相关的 JavaScript 运行时:

  • jerryscript - https://github.com/jerryscript-project/jerryscript

  • duktape - https://github.com/svaarala/duktape

  • Espruino - https://github.com/espruino/Espruino

  • tiny-js - https://github.com/gfwilliams/tiny-js

Application JavaScript Runtime

许多应用也会利用 JavaScript 运行时来实现自己的需求。比如因为 Node.js 的特性,很多 NoSQL 都使用 Node.js 来查询数据和管理应用。

Nginx 则通过自研 JavaScript 的运行时 njs 来扩展 Nginx 功能,参考 【第2353期】Nginx 中运行 JavaScript 详细介绍。

前端跨平台方案,小程序、React Native、Weex 等,都会使用 JS 引擎,iOS 上一般会是 JavaScriptCore、Android 上则是 V8。因为使用在移动端,需要兼顾引擎的大小、性能、内存使用等,React Native 团队则自己研发了 JS 引擎 Hermes 。

WinterCG

WinterCG 社区(Web-interoperable Runtimes Community Group),是由 Cloudflare 、Node.js、Deno 合作最近正式成立的一个社区组。

致力于促进 Web APIs 标准的发展。让开发者可以在不同的 JavaScript 运行时中编写可移植的代码,包括浏览器端、服务端、嵌入式应用、边缘计算等,即 Write once, run everywhere.

我把 Web APIs 分为三种:

  • 只适用于浏览器端,比如像 HTML、CSS、Canvas 的规范标准,可访问性相关的标准等。

  • 只适用于非浏览器端,比如像本地文件系统、和操作系统交互的 API 等。

  • 多端通用,比如 Encoding、Fetch、URL、Stream 等。

WinterCG 的定位是,与现有的 Web APIs 标准规范组织(如 WHATWG 、 W3C)合作,充分考虑浏览器端和非浏览器端 JavaScript 运行时所需要的异同 ,让标准可以通用化。

如果一些标准在浏览器端和非浏览器端需要有必要的差异,则提供描述这些差异的清晰文档。

不排除如果一些功能只适合于非浏览器端,并且不于现在的 Web API 标准相冲突,则可能会发布自己的规范进行推进。比如只存在于服务端的文件系统等、未来发展的边缘计算 JavaScript 运行时中,必定会有只适合在该运行时的标准规范需要创建推进。

总结

WHATWG 和 W3C 在浏览器端的 Web APIs 标准规范已经很全。但随着不同类型的 JavaScript 运行时的发展,每种运行时的使用场景和解决的问题可能都会有所差异。

如果所有的 JavaScript 运行时都可以使用同一套标准规范,这必定有利于各 JavaScript 运行时的发展,各运行时可以直接使用已有的标椎规范来实现,而非自己实现临时的方案。

开发者可以以最小的代价移植应用程序到不同平台,比如可以无缝的在不同提供边缘计算服务的厂商中迁移,Node.js 和 Deno 的代码可以完全复用。

参考链接

  • WinterCG 社区正式成立,前端代码终于可以运行在后端了

  • Netlify Edge Functions: A new serverless runtime powered by Deno

  • Differences between Node.js and the Browser

  • Web-interoperable Runtimes Community Group

关于本文
作者:@whilefor
原文:https://zhuanlan.zhihu.com/p/521432526

运行相关阅读。欢迎自荐投稿,前端早读课等你来。

您可能也对以下帖子感兴趣

文章有问题?点此查看未经处理的缓存