- assert 断言
- async_hooks 异步钩子
- async_hooks/context 异步上下文
- buffer 缓冲区
- C++插件
- C/C++插件(使用 Node-API)
- C++嵌入器
- child_process 子进程
- cluster 集群
- CLI 命令行
- console 控制台
- Corepack 核心包
- crypto 加密
- crypto/webcrypto 网络加密
- debugger 调试器
- deprecation 弃用
- dgram 数据报
- diagnostics_channel 诊断通道
- dns 域名服务器
- domain 域
- Error 错误
- events 事件触发器
- fs 文件系统
- global 全局变量
- http 超文本传输协议
- http2 超文本传输协议 2.0
- https 安全超文本传输协议
- inspector 检查器
- Intl 国际化
- module 模块
- module/cjs CommonJS 模块
- module/esm ECMAScript 模块
- module/package 包模块
- net 网络
- os 操作系统
- path 路径
- perf_hooks 性能钩子
- permission 权限
- process 进程
- punycode 域名代码
- querystring 查询字符串
- readline 逐行读取
- repl 交互式解释器
- report 诊断报告
- sea 单个可执行应用程序
- stream 流
- stream/web 网络流
- string_decoder 字符串解码器
- test 测试
- timers 定时器
- tls 安全传输层
- trace_events 跟踪事件
- tty 终端
- url 网址
- util 实用工具
- v8 引擎
- vm 虚拟机
- wasi 网络汇编系统接口
- worker_threads 工作线程
- zlib 压缩
Node.js v20.20.0 文档
- Node.js v20.20.0
- 目录
-
导航
- assert 断言
- async_hooks 异步钩子
- async_hooks/context 异步上下文
- buffer 缓冲区
- C++插件
- C/C++插件(使用 Node-API)
- C++嵌入器
- child_process 子进程
- cluster 集群
- CLI 命令行
- console 控制台
- Corepack 核心包
- crypto 加密
- crypto/webcrypto 网络加密
- debugger 调试器
- deprecation 弃用
- dgram 数据报
- diagnostics_channel 诊断通道
- dns 域名服务器
- domain 域
- Error 错误
- events 事件触发器
- fs 文件系统
- global 全局变量
- http 超文本传输协议
- http2 超文本传输协议 2.0
- https 安全超文本传输协议
- inspector 检查器
- Intl 国际化
- module 模块
- module/cjs CommonJS 模块
- module/esm ECMAScript 模块
- module/package 包模块
- net 网络
- os 操作系统
- path 路径
- perf_hooks 性能钩子
- permission 权限
- process 进程
- punycode 域名代码
- querystring 查询字符串
- readline 逐行读取
- repl 交互式解释器
- report 诊断报告
- sea 单个可执行应用程序
- stream 流
- stream/web 网络流
- string_decoder 字符串解码器
- test 测试
- timers 定时器
- tls 安全传输层
- trace_events 跟踪事件
- tty 终端
- url 网址
- util 实用工具
- v8 引擎
- vm 虚拟机
- wasi 网络汇编系统接口
- worker_threads 工作线程
- zlib 压缩
- 其他版本
WebAssembly 系统接口 (WASI)#>
🌐 WebAssembly System Interface (WASI)
node:wasi 模块目前尚未提供某些 WASI 运行时所具备的全面文件系统安全属性。未来可能会实现对安全文件系统沙箱的完全支持,也可能不会。在此期间,不要依赖它来运行不受信任的代码。
源代码: lib/wasi.js
WASI API 提供了 WebAssembly 系统接口 规范的实现。WASI 通过一系列类似 POSIX 的函数,使 WebAssembly 应用能够访问底层操作系统。
🌐 The WASI API provides an implementation of the WebAssembly System Interface specification. WASI gives WebAssembly applications access to the underlying operating system via a collection of POSIX-like functions.
import { readFile } from 'node:fs/promises';
import { WASI } from 'node:wasi';
import { argv, env } from 'node:process';
const wasi = new WASI({
version: 'preview1',
args: argv,
env,
preopens: {
'/local': '/some/real/path/that/wasm/can/access',
},
});
const wasm = await WebAssembly.compile(
await readFile(new URL('./demo.wasm', import.meta.url)),
);
const instance = await WebAssembly.instantiate(wasm, wasi.getImportObject());
wasi.start(instance);'use strict';
const { readFile } = require('node:fs/promises');
const { WASI } = require('node:wasi');
const { argv, env } = require('node:process');
const { join } = require('node:path');
const wasi = new WASI({
version: 'preview1',
args: argv,
env,
preopens: {
'/local': '/some/real/path/that/wasm/can/access',
},
});
(async () => {
const wasm = await WebAssembly.compile(
await readFile(join(__dirname, 'demo.wasm')),
);
const instance = await WebAssembly.instantiate(wasm, wasi.getImportObject());
wasi.start(instance);
})();
要运行上述示例,请创建一个名为 demo.wat 的新 WebAssembly 文本格式文件:
🌐 To run the above example, create a new WebAssembly text format file named
demo.wat:
(module
;; Import the required fd_write WASI function which will write the given io vectors to stdout
;; The function signature for fd_write is:
;; (File Descriptor, *iovs, iovs_len, nwritten) -> Returns number of bytes written
(import "wasi_snapshot_preview1" "fd_write" (func $fd_write (param i32 i32 i32 i32) (result i32)))
(memory 1)
(export "memory" (memory 0))
;; Write 'hello world\n' to memory at an offset of 8 bytes
;; Note the trailing newline which is required for the text to appear
(data (i32.const 8) "hello world\n")
(func $main (export "_start")
;; Creating a new io vector within linear memory
(i32.store (i32.const 0) (i32.const 8)) ;; iov.iov_base - This is a pointer to the start of the 'hello world\n' string
(i32.store (i32.const 4) (i32.const 12)) ;; iov.iov_len - The length of the 'hello world\n' string
(call $fd_write
(i32.const 1) ;; file_descriptor - 1 for stdout
(i32.const 0) ;; *iovs - The pointer to the iov array, which is stored at memory location 0
(i32.const 1) ;; iovs_len - We're printing 1 string stored in an iov - so one.
(i32.const 20) ;; nwritten - A place in memory to store the number of bytes written
)
drop ;; Discard the number of bytes written from the top of the stack
)
)
使用 wabt 将 .wat 编译为 .wasm
🌐 Use wabt to compile .wat to .wasm
wat2wasm demo.wat
安全#>
🌐 Security
WASI 提供了一种基于能力的模型,通过该模型,应用可以获得自己的自定义 env、preopens、stdin、stdout、stderr 和 exit 能力。
🌐 WASI provides a capabilities-based model through which applications are provided
their own custom env, preopens, stdin, stdout, stderr, and exit
capabilities.
当前的 Node.js 威胁模型并未提供像某些 WASI 运行时中那样的安全沙箱环境。
虽然能力特性受到支持,但它们并未在 Node.js 中形成安全模型。例如,文件系统沙箱可以通过各种技术被绕过。该项目正在探索未来是否可以添加这些安全保证。
🌐 While the capability features are supported, they do not form a security model in Node.js. For example, the file system sandboxing can be escaped with various techniques. The project is exploring whether these security guarantees could be added in future.
类:WASI#>
🌐 Class: WASI
WASI 类提供了 WASI 系统调用 API 以及用于处理基于 WASI 的应用的额外便捷方法。每个 WASI 实例代表一个独立的环境。
🌐 The WASI class provides the WASI system call API and additional convenience
methods for working with WASI-based applications. Each WASI instance
represents a distinct environment.
new WASI([options])#>
options<Object>args<Array> 一个字符串数组,WebAssembly 应用将把它们视为命令行参数。第一个参数是 WASI 命令本身的虚拟路径。默认值:[]。env<Object> 一个类似于process.env的对象,WebAssembly 应用将其视作环境变量。默认值:{}。preopens<Object> 该对象表示 WebAssembly 应用的本地目录结构。preopens的字符串键被视为文件系统中的目录。preopens中对应的值是这些目录在主机上的真实路径。returnOnExit<boolean> 默认情况下,当 WASI 应用调用__wasi_proc_exit()时,wasi.start()会返回指定的退出代码,而不是终止进程。将此选项设置为false将导致 Node.js 进程以指定的退出代码退出。默认值:true。stdin<integer> 在 WebAssembly 应用中用作标准输入的文件描述符。默认值:0。stdout<integer> 在 WebAssembly 应用中用作标准输出的文件描述符。默认值:1。stderr<integer> 在 WebAssembly 应用中用作标准错误的文件描述符。默认值:2。version<string> 请求的 WASI 版本。目前唯一支持的版本是unstable和preview1。此选项为必填项。
wasi.getImportObject()#>
返回一个可以传递给 WebAssembly.instantiate() 的导入对象,如果除了 WASI 提供的之外不需要其他 WASM 导入。
🌐 Return an import object that can be passed to WebAssembly.instantiate() if
no other WASM imports are needed beyond those provided by WASI.
如果在构造函数中传入版本 unstable,它将返回:
🌐 If version unstable was passed into the constructor it will return:
{ wasi_unstable: wasi.wasiImport }
如果在构造函数中传入了版本 preview1 或未指定版本,它将返回:
🌐 If version preview1 was passed into the constructor or no version was
specified it will return:
{ wasi_snapshot_preview1: wasi.wasiImport }
wasi.start(instance)#>
instance<WebAssembly.Instance>
尝试通过调用其 _start() 导出将 instance 作为 WASI 命令开始执行。如果 instance 不包含 _start() 导出,或者 instance 包含 _initialize() 导出,则会抛出异常。
🌐 Attempt to begin execution of instance as a WASI command by invoking its
_start() export. If instance does not contain a _start() export, or if
instance contains an _initialize() export, then an exception is thrown.
start() 要求 instance 导出一个名为 memory 的 WebAssembly.Memory。如果 instance 没有 memory 导出,将抛出异常。
如果多次调用 start(),将抛出异常。
🌐 If start() is called more than once, an exception is thrown.
wasi.initialize(instance)#>
instance<WebAssembly.Instance>
尝试通过调用其 _initialize() 导出将 instance 初始化为 WASI 反应器(如果存在)。如果 instance 包含 _start() 导出,则会抛出异常。
🌐 Attempt to initialize instance as a WASI reactor by invoking its
_initialize() export, if it is present. If instance contains a _start()
export, then an exception is thrown.
initialize() 要求 instance 导出一个名为 memory 的 WebAssembly.Memory。如果 instance 没有 memory 导出,将抛出异常。
如果多次调用 initialize(),将抛出异常。
🌐 If initialize() is called more than once, an exception is thrown.
wasi.wasiImport#>
wasiImport 是一个实现了 WASI 系统调用 API 的对象。这个对象应在实例化 WebAssembly.Instance 时作为 wasi_snapshot_preview1 导入传入。