文章摘要
scriptc 是一种零运行时TypeScript工具,能将普通TypeScript代码编译成小型、快速的原生可执行文件,无需Node或JavaScript引擎。它保持代码不变,通过真实TypeScript编译器进行类型检查,并支持静态编译和动态运行两种模式。
文章总结
好的,这是根据您的要求,对原文内容进行的中文重述,保留了核心细节,并删减了与主题无关的重复或冗余信息。
scriptc:零运行时 TypeScript 编译器
scriptc 是一个将普通 TypeScript 代码编译成小型、快速的原生可执行文件的工具。编译后的二进制文件不包含 Node.js、V8 或任何 JavaScript 引擎。
核心特性:
- 无需修改代码:你无需添加注解或使用特定方言,直接使用在 Node.js 上运行的 TypeScript 代码即可。scriptc 会使用真正的 TypeScript 编译器进行类型检查,然后编译为原生代码,其行为与 Node.js 逐字节一致。
安装与平台:
- 通过
npm install -g scriptc安装。 - 需要
clang(Xcode 命令行工具自带)。主要支持 macOS arm64 平台,Linux 和 Windows 通过交叉编译支持。
工作原理:静态性优先
scriptc 会分析代码,判断哪些部分可以静态编译为原生代码,并给出明确的报告。
- 静态编译:默认模式,将代码编译为原生机器码,无需任何引擎。
- 动态运行:通过
--dynamic标志,使用一个嵌入的 JavaScript 引擎(quickjs-ng,约 620KB)来执行无法静态编译的部分(如 npm 依赖的 JS 代码)。静态与动态代码之间的值传递会在运行时进行验证。 - 拒绝编译:无法编译的代码会给出明确的错误码和修改建议,绝不会静默地错误编译。
可编译的内容:
- 语言特性:支持单继承类、闭包、泛型、受歧视联合类型、async/await、异常处理、解构、迭代器、模板字符串、正则表达式等。
- 标准库:支持字符串、数组、Map、Set、JSON、Math、类型化数组、Buffer、Error 等,语义与 JavaScript 完全一致。
- Node.js API:支持
fs、path、process、child_process、os、crypto、url、zlib、timers、net、http、https、tls、dgram、dns等,以及fetch和 WHATWG Web 子集。 - npm 依赖:通过
--dynamic模式,可以嵌入 npm 包。这些包在构建时被嵌入二进制文件,运行时无需读取node_modules。
正确性保障:
- 差异测试:所有测试程序都会在 Node.js 和原生二进制文件上运行,确保标准输出、错误输出和退出码完全一致。
- 内存安全:整个测试套件会在 AddressSanitizer 下运行,内存泄漏和释放后使用都会导致构建失败。
- 明确差异:与 Node.js 的少数刻意差异(如时间内部实现、错误对象属性)都有文档记录和编号,不会静默地产生不同行为。
性能表现:
- 启动时间:约 2.4ms,与 Zig 相当,优于 Go 和 Rust,远快于 Node.js 的约 47ms。
- 二进制体积:静态编译为 170-200KB,使用
--dynamic模式约为 3MB。 - 内存占用:典型 RSS 为 1-4MB,远低于 Node.js 的 67-116MB。
扩展机制:
- 编译时计算:
comptime(() => ...)允许在构建时运行 TypeScript 代码,并将结果嵌入二进制文件。 - 原生 FFI:通过
--ffi标志,可以直接调用 C ABI 函数。 - 动态模式:
--dynamic用于嵌入 npm 依赖和无法静态编译的代码。 - 检查类型转换:
JSON.parse(...) as Config会在运行时验证类型,不匹配时会抛出可捕获的错误。
架构:
- 编译器:使用 TypeScript 编译器 API 进行解析和类型检查,生成类型化中间表示(IR),然后通过 LLVM 或 C 后端生成原生代码。
- 运行时:用 C 语言编写,包含引用计数、循环收集器、事件循环、服务器栈等。功能模块按需链接,二进制文件只包含实际使用的代码。
- CLI:提供
scriptc build、run、coverage等命令。
评论总结
根据评论内容,主要观点和论据总结如下:
正面观点(认可度较高): - 项目理念有吸引力,能将TypeScript编译为原生代码,无需JS运行时。关键引用:"It's a compelling value proposition, TypeScript is already well typed and barring a few cases it can be turned into machine code without a JS runtime."(satvikpendem) - 对后端开发有实际价值,可替代将TypeScript子集转换为Rust的方案。关键引用:"We are increasingly using a subset of typescript in our backend... This project will enable an alternative of that vision earlier."(elendilm) - 确认了小型、快速原生可执行文件的需求。关键引用:"It's nice they acknowledge and confirm the need for small, fast native executables."(weinzierl)
负面观点(认可度较高): - 对Vercel的动机和项目可持续性表示怀疑,认为这是AI驱动的炒作。关键引用:"another vercel labs thing that's been slopped together, hyped up on twitter and then left to be forgotten about in a few months time."(pdantix) - 质疑项目进展速度,认为可能不切实际。关键引用:"I'm more than a little suspicious of how Vercel has made so much progress so fast."(acmnrs) - 指出与npm生态系统的兼容性问题,认为仍需JS引擎。关键引用:"Most packages only ship untyped JavaScript with type declarations... so realistically you'd still need a JavaScript engine if you use any packages."(sheept)
中立/技术性观点: - 存在类似项目(如Porffor、QuickJS、GraalVM),但各有局限。关键引用:"Hasn't quickjs and GraalVM been able to do this for a while now?"(MrDrMcCoy) - 对实用性持怀疑态度,类比Java原生编译的漫长历程。关键引用:"After many small steps between GraalVM Native finally tackled the problem more holistically... still it's a major pain."(weinzierl) - 关注跨平台编译限制。关键引用:"does 'Linux and Windows binaries build by cross-compilation' mean that you can't run it on non-MacOS?"(MrDrMcCoy)
总体评价: 评论呈现两极分化,正面观点认可技术价值,负面观点质疑Vercel的动机和项目可持续性,中立观点则关注实际可行性和生态系统兼容性。