进程#

源代码: lib/process.js

process 对象提供有关当前 Node.js 进程的信息,并对其进行控制。

import process from 'node:process';const process = require('node:process');

进程事件#

process 对象是 EventEmitter 的实例。

事件:'beforeExit'#

当 Node.js 清空其事件循环且没有其他工作安排时,将发出 'beforeExit' 事件。通常,Node.js 进程将在没有安排工作时退出,但注册在 'beforeExit' 事件上的监听器可以进行异步调用,从而导致 Node.js 进程继续运行。

监听器回调函数将使用 process.exitCode 的值作为唯一参数调用。

'beforeExit' 事件不会为导致显式终止的条件发出,例如调用 process.exit() 或未捕获的异常。

除非目的是安排额外的工作,否则不应'beforeExit' 用作 'exit' 事件的替代方案。

import process from 'node:process';

process.on('beforeExit', (code) => {
  console.log('Process beforeExit event with code: ', code);
});

process.on('exit', (code) => {
  console.log('Process exit event with code: ', code);
});

console.log('This message is displayed first.');

// Prints:
// This message is displayed first.
// Process beforeExit event with code: 0
// Process exit event with code: 0const process = require('node:process');

process.on('beforeExit', (code) => {
  console.log('Process beforeExit event with code: ', code);
});

process.on('exit', (code) => {
  console.log('Process exit event with code: ', code);
});

console.log('This message is displayed first.');

// Prints:
// This message is displayed first.
// Process beforeExit event with code: 0
// Process exit event with code: 0

事件:'disconnect'#

如果 Node.js 进程使用 IPC 通道生成(请参阅 子进程集群 文档),则当 IPC 通道关闭时,将发出 'disconnect' 事件。

事件:'exit'#

当 Node.js 进程即将退出时,将发出 'exit' 事件,原因可能是

  • 显式调用 process.exit() 方法;
  • Node.js 事件循环不再有任何其他工作要执行。

此时无法阻止事件循环退出,并且一旦所有 'exit' 监听器完成运行,Node.js 进程将终止。

监听器回调函数将使用 process.exitCode 属性或传递给 process.exit() 方法的 exitCode 参数调用。

import process from 'node:process';

process.on('exit', (code) => {
  console.log(`About to exit with code: ${code}`);
});const process = require('node:process');

process.on('exit', (code) => {
  console.log(`About to exit with code: ${code}`);
});

监听器函数**必须**只执行**同步**操作。Node.js 进程将在调用'exit' 事件监听器后立即退出,导致事件循环中排队的任何额外工作都被放弃。例如,在以下示例中,超时永远不会发生

import process from 'node:process';

process.on('exit', (code) => {
  setTimeout(() => {
    console.log('This will not run');
  }, 0);
});const process = require('node:process');

process.on('exit', (code) => {
  setTimeout(() => {
    console.log('This will not run');
  }, 0);
});

事件:'message'#

如果 Node.js 进程使用 IPC 通道生成(参见 子进程集群 文档),则每当父进程使用 childprocess.send() 发送的消息被子进程接收时,就会发出'message' 事件。

消息会经过序列化和解析。最终的消息可能与最初发送的消息不同。

如果在生成进程时将serialization 选项设置为advanced,则message 参数可以包含 JSON 无法表示的数据。有关更多详细信息,请参见 child_process 的高级序列化

事件:'multipleResolves'#

稳定性:0 - 已弃用

  • type <string> 解析类型。'resolve''reject' 之一。
  • promise <Promise> 多次解析或拒绝的 Promise。
  • value <any> Promise 在原始解析后解析或拒绝的值。

每当Promise 已经

  • 已解析多次。
  • 已拒绝多次。
  • 解析后被拒绝。
  • 拒绝后被解析。

这对于使用Promise构造函数跟踪应用程序中的潜在错误很有用,因为多个解析会被静默地吞并。但是,此事件的发生并不一定表示错误。例如,Promise.race() 可以触发 'multipleResolves' 事件。

由于像上面Promise.race()示例这样的情况中事件的不可靠性,它已被弃用。

import process from 'node:process';

process.on('multipleResolves', (type, promise, reason) => {
  console.error(type, promise, reason);
  setImmediate(() => process.exit(1));
});

async function main() {
  try {
    return await new Promise((resolve, reject) => {
      resolve('First call');
      resolve('Swallowed resolve');
      reject(new Error('Swallowed reject'));
    });
  } catch {
    throw new Error('Failed');
  }
}

main().then(console.log);
// resolve: Promise { 'First call' } 'Swallowed resolve'
// reject: Promise { 'First call' } Error: Swallowed reject
//     at Promise (*)
//     at new Promise (<anonymous>)
//     at main (*)
// First callconst process = require('node:process');

process.on('multipleResolves', (type, promise, reason) => {
  console.error(type, promise, reason);
  setImmediate(() => process.exit(1));
});

async function main() {
  try {
    return await new Promise((resolve, reject) => {
      resolve('First call');
      resolve('Swallowed resolve');
      reject(new Error('Swallowed reject'));
    });
  } catch {
    throw new Error('Failed');
  }
}

main().then(console.log);
// resolve: Promise { 'First call' } 'Swallowed resolve'
// reject: Promise { 'First call' } Error: Swallowed reject
//     at Promise (*)
//     at new Promise (<anonymous>)
//     at main (*)
// First call

事件:'rejectionHandled'#

当一个Promise被拒绝并且错误处理程序比 Node.js 事件循环的一次轮转更晚地附加到它(例如,使用 promise.catch())时,会发出 'rejectionHandled' 事件。

Promise 对象之前可能已在 'unhandledRejection' 事件中发出,但在处理过程中获得了拒绝处理程序。

对于Promise链,没有一个可以始终处理拒绝的顶层概念。由于其本质上是异步的,Promise拒绝可以在将来的某个时间点被处理,可能比发出 'unhandledRejection' 事件的事件循环轮转要晚得多。

另一种说法是,与同步代码中始终存在一个不断增长的未处理异常列表不同,对于 Promise,可能存在一个不断增长和缩小的未处理拒绝列表。

在同步代码中,当未处理异常列表增长时,会发出 'uncaughtException' 事件。

在异步代码中,当未处理拒绝列表增长时,会发出 'unhandledRejection' 事件,而当未处理拒绝列表缩小时,会发出 'rejectionHandled' 事件。

import process from 'node:process';

const unhandledRejections = new Map();
process.on('unhandledRejection', (reason, promise) => {
  unhandledRejections.set(promise, reason);
});
process.on('rejectionHandled', (promise) => {
  unhandledRejections.delete(promise);
});const process = require('node:process');

const unhandledRejections = new Map();
process.on('unhandledRejection', (reason, promise) => {
  unhandledRejections.set(promise, reason);
});
process.on('rejectionHandled', (promise) => {
  unhandledRejections.delete(promise);
});

在这个例子中,unhandledRejections Map 会随着时间的推移而增长和缩小,反映了最初未处理的拒绝,然后被处理。可以在错误日志中记录此类错误,可以定期记录(对于长时间运行的应用程序来说可能是最好的方法),也可以在进程退出时记录(对于脚本来说可能是最方便的方法)。

事件: 'uncaughtException'#

  • err <Error> 未捕获的异常。
  • origin <string> 指示异常是来自未处理的拒绝还是同步错误。可以是 'uncaughtException''unhandledRejection'。后者用于在基于 Promise 的异步上下文中发生异常(或 Promise 被拒绝)时,并且 --unhandled-rejections 标志设置为 strictthrow(默认值)并且拒绝未被处理,或者当在命令行入口点的 ES 模块静态加载阶段发生拒绝时。

当未捕获的 JavaScript 异常一直冒泡回事件循环时,会发出 'uncaughtException' 事件。默认情况下,Node.js 通过将堆栈跟踪打印到 stderr 并以代码 1 退出来处理此类异常,从而覆盖任何先前设置的 process.exitCode。为 'uncaughtException' 事件添加处理程序将覆盖此默认行为。或者,在 'uncaughtException' 处理程序中更改 process.exitCode 将导致进程以提供的退出代码退出。否则,在存在此类处理程序的情况下,进程将以 0 退出。

import process from 'node:process';
import fs from 'node:fs';

process.on('uncaughtException', (err, origin) => {
  fs.writeSync(
    process.stderr.fd,
    `Caught exception: ${err}\n` +
    `Exception origin: ${origin}\n`,
  );
});

setTimeout(() => {
  console.log('This will still run.');
}, 500);

// Intentionally cause an exception, but don't catch it.
nonexistentFunc();
console.log('This will not run.');const process = require('node:process');
const fs = require('node:fs');

process.on('uncaughtException', (err, origin) => {
  fs.writeSync(
    process.stderr.fd,
    `Caught exception: ${err}\n` +
    `Exception origin: ${origin}\n`,
  );
});

setTimeout(() => {
  console.log('This will still run.');
}, 500);

// Intentionally cause an exception, but don't catch it.
nonexistentFunc();
console.log('This will not run.');

可以通过安装 'uncaughtExceptionMonitor' 监听器来监视 'uncaughtException' 事件,而不会覆盖退出进程的默认行为。

警告: 正确使用 'uncaughtException'#

'uncaughtException' 是一种用于异常处理的粗略机制,仅应作为最后的手段使用。该事件不应用作 On Error Resume Next 的等效项。未处理的异常本质上意味着应用程序处于未定义状态。尝试在没有从异常中正确恢复的情况下恢复应用程序代码会导致其他不可预见和不可预测的问题。

从事件处理程序中抛出的异常将不会被捕获。相反,进程将以非零退出代码退出,并且将打印堆栈跟踪。这是为了避免无限递归。

尝试在未捕获异常后正常恢复,就像在升级计算机时拔掉电源线一样。十次中有九次,什么也不会发生。但第十次,系统会损坏。

'uncaughtException' 的正确用法是在关闭进程之前执行已分配资源(例如文件描述符、句柄等)的同步清理。'uncaughtException' 之后恢复正常操作是不安全的。

为了以更可靠的方式重启崩溃的应用程序,无论是否发出 'uncaughtException',都应在单独的进程中使用外部监视器来检测应用程序故障并根据需要恢复或重启。

事件:'uncaughtExceptionMonitor'#

  • err <Error> 未捕获的异常。
  • origin <string> 指示异常是否源于未处理的拒绝或同步错误。可以是 'uncaughtException''unhandledRejection'。后者用于在基于 Promise 的异步上下文中发生异常(或如果 Promise 被拒绝)时,并且 --unhandled-rejections 标志设置为 strictthrow(这是默认值)并且拒绝未被处理,或者在命令行入口点的 ES 模块静态加载阶段发生拒绝时。

'uncaughtExceptionMonitor' 事件在发出 'uncaughtException' 事件或通过 process.setUncaughtExceptionCaptureCallback() 安装的钩子被调用之前发出。

安装 'uncaughtExceptionMonitor' 监听器不会改变发出 'uncaughtException' 事件后的行为。如果未安装 'uncaughtException' 监听器,进程仍然会崩溃。

import process from 'node:process';

process.on('uncaughtExceptionMonitor', (err, origin) => {
  MyMonitoringTool.logSync(err, origin);
});

// Intentionally cause an exception, but don't catch it.
nonexistentFunc();
// Still crashes Node.jsconst process = require('node:process');

process.on('uncaughtExceptionMonitor', (err, origin) => {
  MyMonitoringTool.logSync(err, origin);
});

// Intentionally cause an exception, but don't catch it.
nonexistentFunc();
// Still crashes Node.js

事件:'unhandledRejection'#

只要 Promise 被拒绝且在事件循环的一次循环中没有错误处理程序附加到 promise,就会发出 'unhandledRejection' 事件。在使用 Promise 进行编程时,异常被封装为“拒绝的 promise”。可以使用 promise.catch() 捕获和处理拒绝,并通过 Promise 链传播。'unhandledRejection' 事件对于检测和跟踪尚未处理的被拒绝的 promise 很有用。

import process from 'node:process';

process.on('unhandledRejection', (reason, promise) => {
  console.log('Unhandled Rejection at:', promise, 'reason:', reason);
  // Application specific logging, throwing an error, or other logic here
});

somePromise.then((res) => {
  return reportToUser(JSON.pasre(res)); // Note the typo (`pasre`)
}); // No `.catch()` or `.then()`const process = require('node:process');

process.on('unhandledRejection', (reason, promise) => {
  console.log('Unhandled Rejection at:', promise, 'reason:', reason);
  // Application specific logging, throwing an error, or other logic here
});

somePromise.then((res) => {
  return reportToUser(JSON.pasre(res)); // Note the typo (`pasre`)
}); // No `.catch()` or `.then()`

以下情况也会触发 'unhandledRejection' 事件的发出

import process from 'node:process';

function SomeResource() {
  // Initially set the loaded status to a rejected promise
  this.loaded = Promise.reject(new Error('Resource not yet loaded!'));
}

const resource = new SomeResource();
// no .catch or .then on resource.loaded for at least a turnconst process = require('node:process');

function SomeResource() {
  // Initially set the loaded status to a rejected promise
  this.loaded = Promise.reject(new Error('Resource not yet loaded!'));
}

const resource = new SomeResource();
// no .catch or .then on resource.loaded for at least a turn

在这个示例中,可以将拒绝跟踪为开发人员错误,就像其他 'unhandledRejection' 事件通常那样。为了解决此类故障,可以将非操作 .catch(() => { }) 处理程序附加到 resource.loaded,这将阻止 'unhandledRejection' 事件的发出。

事件:'warning'#

  • warning <Error> 警告的关键属性是
    • name <string> 警告的名称。默认值: 'Warning'
    • message <string> 系统提供的警告描述。
    • stack <string> 到发出警告的代码位置的堆栈跟踪。

只要 Node.js 发出进程警告,就会发出 'warning' 事件。

进程警告类似于错误,因为它描述了正在提请用户注意的异常情况。但是,警告不是 Node.js 和 JavaScript 错误处理流程的正常部分。Node.js 可以在检测到可能导致应用程序性能下降、错误或安全漏洞的错误编码实践时发出警告。

import process from 'node:process';

process.on('warning', (warning) => {
  console.warn(warning.name);    // Print the warning name
  console.warn(warning.message); // Print the warning message
  console.warn(warning.stack);   // Print the stack trace
});const process = require('node:process');

process.on('warning', (warning) => {
  console.warn(warning.name);    // Print the warning name
  console.warn(warning.message); // Print the warning message
  console.warn(warning.stack);   // Print the stack trace
});

默认情况下,Node.js 会将进程警告打印到stderr--no-warnings 命令行选项可用于抑制默认的控制台输出,但'warning' 事件仍将由process 对象发出。目前,除了弃用警告之外,无法抑制特定警告类型。要抑制弃用警告,请查看--no-deprecation 标志。

以下示例说明了当向事件添加过多侦听器时打印到stderr 的警告

$ node
> events.defaultMaxListeners = 1;
> process.on('foo', () => {});
> process.on('foo', () => {});
> (node:38638) MaxListenersExceededWarning: Possible EventEmitter memory leak
detected. 2 foo listeners added. Use emitter.setMaxListeners() to increase limit 

相反,以下示例关闭默认警告输出并向'warning' 事件添加自定义处理程序

$ node --no-warnings
> const p = process.on('warning', (warning) => console.warn('Do not do that!'));
> events.defaultMaxListeners = 1;
> process.on('foo', () => {});
> process.on('foo', () => {});
> Do not do that! 

--trace-warnings 命令行选项可用于使警告的默认控制台输出包含警告的完整堆栈跟踪。

使用--throw-deprecation 命令行标志启动 Node.js 将导致自定义弃用警告作为异常抛出。

使用--trace-deprecation 命令行标志将导致自定义弃用与堆栈跟踪一起打印到stderr

使用--no-deprecation 命令行标志将抑制所有自定义弃用的报告。

*-deprecation 命令行标志仅影响使用名称'DeprecationWarning' 的警告。

发出自定义警告#

有关发出自定义或应用程序特定警告,请参阅process.emitWarning() 方法。

Node.js 警告名称#

对于 Node.js 发出的警告类型(由name 属性标识)没有严格的指南。可以随时添加新的警告类型。一些最常见的警告类型包括

  • 'DeprecationWarning' - 指示使用已弃用的 Node.js API 或功能。此类警告必须包含一个'code' 属性,用于标识弃用代码
  • 'ExperimentalWarning' - 表示使用了实验性的 Node.js API 或功能。此类功能必须谨慎使用,因为它们随时可能更改,并且不受与支持功能相同的严格语义版本控制和长期支持策略的约束。
  • 'MaxListenersExceededWarning' - 表示在 EventEmitterEventTarget 上注册了太多给定事件的侦听器。这通常表明存在内存泄漏。
  • 'TimeoutOverflowWarning' - 表示向 setTimeout()setInterval() 函数提供了无法容纳在 32 位有符号整数中的数值。
  • 'UnsupportedWarning' - 表示使用了不受支持的选项或功能,这些选项或功能将被忽略,而不是被视为错误。一个例子是在使用 HTTP/2 兼容性 API 时使用 HTTP 响应状态消息。

事件:'worker'#

创建新的 <Worker> 线程后,将发出 'worker' 事件。

信号事件#

当 Node.js 进程接收到信号时,将发出信号事件。有关标准 POSIX 信号名称(如 'SIGINT''SIGHUP' 等)的列表,请参阅 signal(7)

信号在 Worker 线程上不可用。

信号处理程序将接收信号的名称('SIGINT''SIGTERM' 等)作为第一个参数。

每个事件的名称将是信号的通用大写名称(例如,SIGINT 信号的 'SIGINT')。

import process from 'node:process';

// Begin reading from stdin so the process does not exit.
process.stdin.resume();

process.on('SIGINT', () => {
  console.log('Received SIGINT. Press Control-D to exit.');
});

// Using a single function to handle multiple signals
function handle(signal) {
  console.log(`Received ${signal}`);
}

process.on('SIGINT', handle);
process.on('SIGTERM', handle);const process = require('node:process');

// Begin reading from stdin so the process does not exit.
process.stdin.resume();

process.on('SIGINT', () => {
  console.log('Received SIGINT. Press Control-D to exit.');
});

// Using a single function to handle multiple signals
function handle(signal) {
  console.log(`Received ${signal}`);
}

process.on('SIGINT', handle);
process.on('SIGTERM', handle);
  • 'SIGUSR1' 由 Node.js 保留,用于启动 调试器。可以安装侦听器,但这样做可能会干扰调试器。
  • 'SIGTERM''SIGINT' 在非 Windows 平台上具有默认处理程序,这些处理程序在以代码 128 + 信号编号 退出之前重置终端模式。如果其中一个信号安装了侦听器,则其默认行为将被删除(Node.js 将不再退出)。
  • 'SIGPIPE' 默认情况下被忽略。它可以安装侦听器。
  • 'SIGHUP' 在 Windows 上关闭控制台窗口时生成,在其他平台上则在各种类似条件下生成。请参阅 signal(7)。它可以安装侦听器,但是 Node.js 大约 10 秒后将被 Windows 无条件终止。在非 Windows 平台上,SIGHUP 的默认行为是终止 Node.js,但是一旦安装了侦听器,其默认行为将被删除。
  • 'SIGTERM' 在 Windows 上不受支持,可以对其进行侦听。
  • 'SIGINT' 来自终端的信号在所有平台上都受支持,通常可以通过 Ctrl+C 生成(尽管这可能是可配置的)。当 终端原始模式 启用且使用 Ctrl+C 时,不会生成此信号。
  • 'SIGBREAK' 在 Windows 上按下 Ctrl+Break 时传递。在非 Windows 平台上,可以监听它,但没有办法发送或生成它。
  • 'SIGWINCH' 在控制台大小调整时传递。在 Windows 上,这只会发生在写入控制台时,当光标正在移动时,或者在原始模式下使用可读的 tty 时。
  • 'SIGKILL' 无法安装监听器,它将在所有平台上无条件地终止 Node.js。
  • 'SIGSTOP' 无法安装监听器。
  • 'SIGBUS''SIGFPE''SIGSEGV''SIGILL',当不使用 kill(2) 人工引发时,本质上会将进程置于无法安全调用 JS 监听器的状态。这样做可能会导致进程停止响应。
  • 0 可以发送以测试进程是否存在,如果进程存在,它不会有任何影响,但如果进程不存在,则会抛出错误。

Windows 不支持信号,因此没有等效于通过信号终止的机制,但 Node.js 通过 process.kill()subprocess.kill() 提供了一些模拟。

  • 发送 SIGINTSIGTERMSIGKILL 将导致目标进程无条件终止,之后,子进程将报告进程已通过信号终止。
  • 发送信号 0 可以用作测试进程是否存在的一种平台无关的方式。

process.abort()#

process.abort() 方法会导致 Node.js 进程立即退出并生成核心文件。

此功能在 Worker 线程中不可用。

process.allowedNodeEnvironmentFlags#

process.allowedNodeEnvironmentFlags 属性是一个特殊的只读 Set,它包含在 NODE_OPTIONS 环境变量中允许使用的标志。

process.allowedNodeEnvironmentFlags 扩展了 Set,但覆盖了 Set.prototype.has 以识别几种不同的标志表示形式。process.allowedNodeEnvironmentFlags.has() 在以下情况下将返回 true

  • 标志可以省略前导单 (-) 或双 (--) 破折号;例如,inspect-brk 代表 --inspect-brk,或 r 代表 -r
  • 传递给 V8 的标志(如 --v8-options 中列出的)可以将一个或多个非前导破折号替换为下划线,反之亦然;例如,--perf_basic_prof--perf-basic-prof--perf_basic-prof 等。
  • 标志可以包含一个或多个等号 (=) 字符;第一个等号之后和包括第一个等号在内的所有字符将被忽略;例如,--stack-trace-limit=100
  • 标志必须NODE_OPTIONS 中允许。

当迭代 process.allowedNodeEnvironmentFlags 时,标志将只出现一次;每个标志都将以一个或多个破折号开头。传递给 V8 的标志将包含下划线而不是非前导破折号

import { allowedNodeEnvironmentFlags } from 'node:process';

allowedNodeEnvironmentFlags.forEach((flag) => {
  // -r
  // --inspect-brk
  // --abort_on_uncaught_exception
  // ...
});const { allowedNodeEnvironmentFlags } = require('node:process');

allowedNodeEnvironmentFlags.forEach((flag) => {
  // -r
  // --inspect-brk
  // --abort_on_uncaught_exception
  // ...
});

process.allowedNodeEnvironmentFlagsadd()clear()delete() 方法什么也不做,并且将静默失败。

如果 Node.js 是没有 NODE_OPTIONS 支持的情况下编译的(如 process.config 中所示),process.allowedNodeEnvironmentFlags 将包含本来允许的内容。

process.arch#

编译 Node.js 二进制文件的操作系统 CPU 架构。可能的值为:'arm''arm64''ia32''loong64''mips''mipsel''ppc''ppc64''riscv64''s390''s390x''x64'

import { arch } from 'node:process';

console.log(`This processor architecture is ${arch}`);const { arch } = require('node:process');

console.log(`This processor architecture is ${arch}`);

process.argv#

process.argv 属性返回一个数组,其中包含启动 Node.js 进程时传递的命令行参数。第一个元素将是 process.execPath。如果需要访问 argv[0] 的原始值,请参见 process.argv0。第二个元素将是正在执行的 JavaScript 文件的路径。其余元素将是任何其他命令行参数。

例如,假设以下脚本用于 process-args.js

import { argv } from 'node:process';

// print process.argv
argv.forEach((val, index) => {
  console.log(`${index}: ${val}`);
});const { argv } = require('node:process');

// print process.argv
argv.forEach((val, index) => {
  console.log(`${index}: ${val}`);
});

将 Node.js 进程启动为

node process-args.js one two=three four 

将生成以下输出

0: /usr/local/bin/node
1: /Users/mjr/work/node/process-args.js
2: one
3: two=three
4: four 

process.argv0#

process.argv0 属性存储了 Node.js 启动时传递的 argv[0] 的原始值的只读副本。

$ bash -c 'exec -a customArgv0 ./node'
> process.argv[0]
'/Volumes/code/external/node/out/Release/node'
> process.argv0
'customArgv0' 

process.channel#

如果 Node.js 进程是用 IPC 通道生成的(参见 子进程 文档),则 process.channel 属性是对 IPC 通道的引用。如果不存在 IPC 通道,则此属性为 undefined

process.channel.ref()#

如果之前调用过 .unref(),此方法将使 IPC 通道保持进程的事件循环运行。

通常,这是通过 process 对象上的 'disconnect''message' 监听器的数量来管理的。但是,此方法可用于明确请求特定行为。

process.channel.unref()#

此方法使 IPC 通道不保持进程的事件循环运行,并允许它在通道打开时完成。

通常,这是通过 process 对象上的 'disconnect''message' 监听器的数量来管理的。但是,此方法可用于明确请求特定行为。

process.chdir(directory)#

process.chdir() 方法更改 Node.js 进程的当前工作目录,或者如果这样做失败(例如,如果指定的 directory 不存在)则抛出异常。

import { chdir, cwd } from 'node:process';

console.log(`Starting directory: ${cwd()}`);
try {
  chdir('/tmp');
  console.log(`New directory: ${cwd()}`);
} catch (err) {
  console.error(`chdir: ${err}`);
}const { chdir, cwd } = require('node:process');

console.log(`Starting directory: ${cwd()}`);
try {
  chdir('/tmp');
  console.log(`New directory: ${cwd()}`);
} catch (err) {
  console.error(`chdir: ${err}`);
}

此功能在 Worker 线程中不可用。

process.config#

process.config 属性返回一个冻结的 Object,其中包含用于编译当前 Node.js 可执行文件的配置选项的 JavaScript 表示。这与运行 ./configure 脚本时生成的 config.gypi 文件相同。

可能的输出示例如下

{
  target_defaults:
   { cflags: [],
     default_configuration: 'Release',
     defines: [],
     include_dirs: [],
     libraries: [] },
  variables:
   {
     host_arch: 'x64',
     napi_build_version: 5,
     node_install_npm: 'true',
     node_prefix: '',
     node_shared_cares: 'false',
     node_shared_http_parser: 'false',
     node_shared_libuv: 'false',
     node_shared_zlib: 'false',
     node_use_openssl: 'true',
     node_shared_openssl: 'false',
     strict_aliasing: 'true',
     target_arch: 'x64',
     v8_use_snapshot: 1
   }
} 

process.connected#

如果 Node.js 进程使用 IPC 通道生成(参见 子进程集群 文档),只要 IPC 通道连接,process.connected 属性将返回 true,并在调用 process.disconnect() 后返回 false

一旦 process.connectedfalse,就无法再使用 process.send() 通过 IPC 通道发送消息。

process.constrainedMemory()#

稳定性:1 - 实验性

获取基于操作系统限制的进程可用内存量(以字节为单位)。如果没有此类限制,或限制未知,则返回 undefined

有关更多信息,请参见 uv_get_constrained_memory

process.cpuUsage([previousValue])#

process.cpuUsage() 方法返回当前进程的用户和系统 CPU 时间使用情况,以包含 usersystem 属性的对象形式返回,其值以微秒(百万分之一秒)表示。这些值分别测量在用户代码和系统代码中花费的时间,如果多个 CPU 内核正在为该进程执行工作,则最终可能大于实际经过的时间。

可以将先前对 process.cpuUsage() 的调用的结果作为参数传递给该函数,以获取差异读数。

import { cpuUsage } from 'node:process';

const startUsage = cpuUsage();
// { user: 38579, system: 6986 }

// spin the CPU for 500 milliseconds
const now = Date.now();
while (Date.now() - now < 500);

console.log(cpuUsage(startUsage));
// { user: 514883, system: 11226 }const { cpuUsage } = require('node:process');

const startUsage = cpuUsage();
// { user: 38579, system: 6986 }

// spin the CPU for 500 milliseconds
const now = Date.now();
while (Date.now() - now < 500);

console.log(cpuUsage(startUsage));
// { user: 514883, system: 11226 }

process.cwd()#

process.cwd() 方法返回 Node.js 进程的当前工作目录。

import { cwd } from 'node:process';

console.log(`Current directory: ${cwd()}`);const { cwd } = require('node:process');

console.log(`Current directory: ${cwd()}`);

process.debugPort#

启用时 Node.js 调试器使用的端口。

import process from 'node:process';

process.debugPort = 5858;const process = require('node:process');

process.debugPort = 5858;

process.disconnect()#

如果 Node.js 进程是用 IPC 通道生成的(请参阅 子进程集群 文档),则 process.disconnect() 方法将关闭与父进程的 IPC 通道,允许子进程在没有其他连接保持其活动状态的情况下优雅地退出。

调用 process.disconnect() 的效果与从父进程调用 ChildProcess.disconnect() 相同。

如果 Node.js 进程不是用 IPC 通道生成的,则 process.disconnect() 将为 undefined

process.dlopen(module, filename[, flags])#

process.dlopen() 方法允许动态加载共享对象。它主要由 require() 用于加载 C++ 插件,不应直接使用,除非在特殊情况下。换句话说,除非有特殊原因,例如自定义 dlopen 标志或从 ES 模块加载,否则应优先使用 require() 而不是 process.dlopen()

flags 参数是一个整数,允许指定 dlopen 行为。有关详细信息,请参阅 os.constants.dlopen 文档。

调用 process.dlopen() 时,一个重要要求是必须传递 module 实例。然后可以通过 module.exports 访问 C++ 插件导出的函数。

以下示例展示了如何加载一个名为 local.node 的 C++ 插件,该插件导出一个 foo 函数。通过传递 RTLD_NOW 常量,所有符号将在调用返回之前加载。在此示例中,假设该常量可用。

import { dlopen } from 'node:process';
import { constants } from 'node:os';
import { fileURLToPath } from 'node:url';

const module = { exports: {} };
dlopen(module, fileURLToPath(new URL('local.node', import.meta.url)),
       constants.dlopen.RTLD_NOW);
module.exports.foo();const { dlopen } = require('node:process');
const { constants } = require('node:os');
const { join } = require('node:path');

const module = { exports: {} };
dlopen(module, join(__dirname, 'local.node'), constants.dlopen.RTLD_NOW);
module.exports.foo();

process.emitWarning(warning[, options])#

  • warning <string> | <Error> 要发出的警告。
  • options <Object>
    • type <string>warningString 时,type 是用于要发出的警告类型的名称。默认值: 'Warning'
    • code <string> 要发出的警告实例的唯一标识符。
    • ctor <Function>warningString 时,ctor 是一个可选函数,用于限制生成的堆栈跟踪。默认值: process.emitWarning
    • detail <string> 要包含在错误中的附加文本。

process.emitWarning() 方法可用于发出自定义或应用程序特定的进程警告。可以通过向 'warning' 事件添加处理程序来监听这些警告。

import { emitWarning } from 'node:process';

// Emit a warning with a code and additional detail.
emitWarning('Something happened!', {
  code: 'MY_WARNING',
  detail: 'This is some additional information',
});
// Emits:
// (node:56338) [MY_WARNING] Warning: Something happened!
// This is some additional informationconst { emitWarning } = require('node:process');

// Emit a warning with a code and additional detail.
emitWarning('Something happened!', {
  code: 'MY_WARNING',
  detail: 'This is some additional information',
});
// Emits:
// (node:56338) [MY_WARNING] Warning: Something happened!
// This is some additional information

在此示例中,process.emitWarning() 在内部生成一个 Error 对象,并将其传递给 'warning' 处理程序。

import process from 'node:process';

process.on('warning', (warning) => {
  console.warn(warning.name);    // 'Warning'
  console.warn(warning.message); // 'Something happened!'
  console.warn(warning.code);    // 'MY_WARNING'
  console.warn(warning.stack);   // Stack trace
  console.warn(warning.detail);  // 'This is some additional information'
});const process = require('node:process');

process.on('warning', (warning) => {
  console.warn(warning.name);    // 'Warning'
  console.warn(warning.message); // 'Something happened!'
  console.warn(warning.code);    // 'MY_WARNING'
  console.warn(warning.stack);   // Stack trace
  console.warn(warning.detail);  // 'This is some additional information'
});

如果 warning 作为 Error 对象传递,则 options 参数将被忽略。

process.emitWarning(warning[, type[, code]][, ctor])#

  • warning <string> | <Error> 要发出的警告。
  • type <string>warningString 时,type 是用于要发出的警告类型的名称。默认值: 'Warning'
  • code <string> 要发出的警告实例的唯一标识符。
  • ctor <Function>warningString 时,ctor 是一个可选函数,用于限制生成的堆栈跟踪。默认值: process.emitWarning

process.emitWarning() 方法可用于发出自定义或应用程序特定的进程警告。可以通过向 'warning' 事件添加处理程序来监听这些警告。

import { emitWarning } from 'node:process';

// Emit a warning using a string.
emitWarning('Something happened!');
// Emits: (node: 56338) Warning: Something happened!const { emitWarning } = require('node:process');

// Emit a warning using a string.
emitWarning('Something happened!');
// Emits: (node: 56338) Warning: Something happened!
import { emitWarning } from 'node:process';

// Emit a warning using a string and a type.
emitWarning('Something Happened!', 'CustomWarning');
// Emits: (node:56338) CustomWarning: Something Happened!const { emitWarning } = require('node:process');

// Emit a warning using a string and a type.
emitWarning('Something Happened!', 'CustomWarning');
// Emits: (node:56338) CustomWarning: Something Happened!
import { emitWarning } from 'node:process';

emitWarning('Something happened!', 'CustomWarning', 'WARN001');
// Emits: (node:56338) [WARN001] CustomWarning: Something happened!const { emitWarning } = require('node:process');

process.emitWarning('Something happened!', 'CustomWarning', 'WARN001');
// Emits: (node:56338) [WARN001] CustomWarning: Something happened!

在以上每个示例中,process.emitWarning() 在内部生成一个 Error 对象,并将其传递给 'warning' 处理程序。

import process from 'node:process';

process.on('warning', (warning) => {
  console.warn(warning.name);
  console.warn(warning.message);
  console.warn(warning.code);
  console.warn(warning.stack);
});const process = require('node:process');

process.on('warning', (warning) => {
  console.warn(warning.name);
  console.warn(warning.message);
  console.warn(warning.code);
  console.warn(warning.stack);
});

如果 warning 被传递为一个 Error 对象,它将被直接传递给 'warning' 事件处理程序(可选的 typecodector 参数将被忽略)。

import { emitWarning } from 'node:process';

// Emit a warning using an Error object.
const myWarning = new Error('Something happened!');
// Use the Error name property to specify the type name
myWarning.name = 'CustomWarning';
myWarning.code = 'WARN001';

emitWarning(myWarning);
// Emits: (node:56338) [WARN001] CustomWarning: Something happened!const { emitWarning } = require('node:process');

// Emit a warning using an Error object.
const myWarning = new Error('Something happened!');
// Use the Error name property to specify the type name
myWarning.name = 'CustomWarning';
myWarning.code = 'WARN001';

emitWarning(myWarning);
// Emits: (node:56338) [WARN001] CustomWarning: Something happened!

如果 warning 不是字符串或 Error 对象,则会抛出 TypeError

虽然进程警告使用 Error 对象,但进程警告机制不是正常错误处理机制的替代品。

如果警告 type'DeprecationWarning',则会实现以下额外处理。

  • 如果使用 --throw-deprecation 命令行标志,则弃用警告将作为异常抛出,而不是作为事件发出。
  • 如果使用 --no-deprecation 命令行标志,则弃用警告将被抑制。
  • 如果使用 --trace-deprecation 命令行标志,则弃用警告将与完整堆栈跟踪一起打印到 stderr

避免重复警告#

作为最佳实践,警告应该在每个进程中只发出一次。为此,将 emitWarning() 放置在一个布尔值后面。

import { emitWarning } from 'node:process';

function emitMyWarning() {
  if (!emitMyWarning.warned) {
    emitMyWarning.warned = true;
    emitWarning('Only warn once!');
  }
}
emitMyWarning();
// Emits: (node: 56339) Warning: Only warn once!
emitMyWarning();
// Emits nothingconst { emitWarning } = require('node:process');

function emitMyWarning() {
  if (!emitMyWarning.warned) {
    emitMyWarning.warned = true;
    emitWarning('Only warn once!');
  }
}
emitMyWarning();
// Emits: (node: 56339) Warning: Only warn once!
emitMyWarning();
// Emits nothing

process.env#

process.env 属性返回一个包含用户环境的对象。参见 environ(7)

此对象的示例如下所示

{
  TERM: 'xterm-256color',
  SHELL: '/usr/local/bin/bash',
  USER: 'maciej',
  PATH: '~/.bin/:/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin',
  PWD: '/Users/maciej',
  EDITOR: 'vim',
  SHLVL: '1',
  HOME: '/Users/maciej',
  LOGNAME: 'maciej',
  _: '/usr/local/bin/node'
} 

可以修改此对象,但此类修改不会反映在 Node.js 进程之外,或者(除非明确要求)反映到其他 Worker 线程。换句话说,以下示例将不起作用

node -e 'process.env.foo = "bar"' && echo $foo 

而以下示例将起作用

import { env } from 'node:process';

env.foo = 'bar';
console.log(env.foo);const { env } = require('node:process');

env.foo = 'bar';
console.log(env.foo);

process.env 上分配属性将隐式地将值转换为字符串。此行为已弃用。 Node.js 的未来版本在值不是字符串、数字或布尔值时可能会抛出错误。

import { env } from 'node:process';

env.test = null;
console.log(env.test);
// => 'null'
env.test = undefined;
console.log(env.test);
// => 'undefined'const { env } = require('node:process');

env.test = null;
console.log(env.test);
// => 'null'
env.test = undefined;
console.log(env.test);
// => 'undefined'

使用 deleteprocess.env 中删除属性。

import { env } from 'node:process';

env.TEST = 1;
delete env.TEST;
console.log(env.TEST);
// => undefinedconst { env } = require('node:process');

env.TEST = 1;
delete env.TEST;
console.log(env.TEST);
// => undefined

在 Windows 操作系统上,环境变量不区分大小写。

import { env } from 'node:process';

env.TEST = 1;
console.log(env.test);
// => 1const { env } = require('node:process');

env.TEST = 1;
console.log(env.test);
// => 1

除非在创建 Worker 实例时明确指定,否则每个 Worker 线程都有自己的 process.env 副本,该副本基于其父线程的 process.env,或者作为 Worker 构造函数的 env 选项指定的任何内容。对 process.env 的更改不会在 Worker 线程之间可见,只有主线程可以进行对操作系统或本机插件可见的更改。在 Windows 上,Worker 实例上的 process.env 副本以区分大小写的方式运行,这与主线程不同。

process.execArgv#

process.execArgv 属性返回启动 Node.js 进程时传递的特定于 Node.js 的命令行选项集。这些选项不会出现在 process.argv 属性返回的数组中,也不包括 Node.js 可执行文件、脚本名称或脚本名称后的任何选项。这些选项对于使用与父进程相同的执行环境生成子进程很有用。

node --harmony script.js --version 

process.execArgv 中的结果

['--harmony'] 

以及 process.argv

['/usr/local/bin/node', 'script.js', '--version'] 

有关使用此属性的 worker 线程的详细行为,请参阅 Worker 构造函数

process.execPath#

process.execPath 属性返回启动 Node.js 进程的可执行文件的绝对路径名。如果存在符号链接,则会解析它们。

'/usr/local/bin/node' 

process.exit([code])#

process.exit() 方法指示 Node.js 以 code 的退出状态同步终止进程。如果省略 code,则退出使用“成功”代码 0process.exitCode 的值(如果已设置)。在所有 'exit' 事件监听器被调用之前,Node.js 不会终止。

要以“失败”代码退出

import { exit } from 'node:process';

exit(1);const { exit } = require('node:process');

exit(1);

执行 Node.js 的 shell 应该将退出代码视为 1

调用 process.exit() 将强制进程尽快退出,即使仍有异步操作挂起,尚未完全完成,包括对 process.stdoutprocess.stderr 的 I/O 操作。

在大多数情况下,实际上没有必要显式调用process.exit()。如果事件循环中没有待处理的额外工作,Node.js 进程会自行退出。process.exitCode属性可以设置为告诉进程在进程正常退出时使用哪个退出代码。

例如,以下示例说明了process.exit()方法的误用,这可能导致打印到 stdout 的数据被截断并丢失。

import { exit } from 'node:process';

// This is an example of what *not* to do:
if (someConditionNotMet()) {
  printUsageToStdout();
  exit(1);
}const { exit } = require('node:process');

// This is an example of what *not* to do:
if (someConditionNotMet()) {
  printUsageToStdout();
  exit(1);
}

造成此问题的原因是,Node.js 中对process.stdout的写入有时是异步的,并且可能在 Node.js 事件循环的多个滴答中发生。但是,调用process.exit()会强制进程执行这些对stdout的额外写入之前退出。

代码应该设置process.exitCode,并通过避免为事件循环安排任何额外工作来允许进程自然退出,而不是直接调用process.exit()

import process from 'node:process';

// How to properly set the exit code while letting
// the process exit gracefully.
if (someConditionNotMet()) {
  printUsageToStdout();
  process.exitCode = 1;
}const process = require('node:process');

// How to properly set the exit code while letting
// the process exit gracefully.
if (someConditionNotMet()) {
  printUsageToStdout();
  process.exitCode = 1;
}

如果需要由于错误条件而终止 Node.js 进程,则抛出未捕获的错误并允许进程相应地终止比调用process.exit()更安全。

Worker线程中,此函数会停止当前线程而不是当前进程。

process.exitCode#

当进程正常退出或通过process.exit()退出而没有指定代码时,该数字将是进程退出代码。

process.exit(code)指定代码将覆盖之前对process.exitCode的任何设置。

process.getActiveResourcesInfo()#

稳定性:1 - 实验性

process.getActiveResourcesInfo() 方法返回一个字符串数组,其中包含当前使事件循环保持活动状态的活动资源的类型。

import { getActiveResourcesInfo } from 'node:process';
import { setTimeout } from 'node:timers';

console.log('Before:', getActiveResourcesInfo());
setTimeout(() => {}, 1000);
console.log('After:', getActiveResourcesInfo());
// Prints:
//   Before: [ 'CloseReq', 'TTYWrap', 'TTYWrap', 'TTYWrap' ]
//   After: [ 'CloseReq', 'TTYWrap', 'TTYWrap', 'TTYWrap', 'Timeout' ]const { getActiveResourcesInfo } = require('node:process');
const { setTimeout } = require('node:timers');

console.log('Before:', getActiveResourcesInfo());
setTimeout(() => {}, 1000);
console.log('After:', getActiveResourcesInfo());
// Prints:
//   Before: [ 'TTYWrap', 'TTYWrap', 'TTYWrap' ]
//   After: [ 'TTYWrap', 'TTYWrap', 'TTYWrap', 'Timeout' ]

process.getegid()#

process.getegid() 方法返回 Node.js 进程的数值有效组标识。(参见 getegid(2)。)

import process from 'node:process';

if (process.getegid) {
  console.log(`Current gid: ${process.getegid()}`);
}const process = require('node:process');

if (process.getegid) {
  console.log(`Current gid: ${process.getegid()}`);
}

此函数仅在 POSIX 平台上可用(即,不包括 Windows 或 Android)。

process.geteuid()#

process.geteuid() 方法返回进程的数值有效用户标识。(参见 geteuid(2)。)

import process from 'node:process';

if (process.geteuid) {
  console.log(`Current uid: ${process.geteuid()}`);
}const process = require('node:process');

if (process.geteuid) {
  console.log(`Current uid: ${process.geteuid()}`);
}

此函数仅在 POSIX 平台上可用(即,不包括 Windows 或 Android)。

process.getgid()#

process.getgid() 方法返回进程的数值组标识。(参见 getgid(2)。)

import process from 'node:process';

if (process.getgid) {
  console.log(`Current gid: ${process.getgid()}`);
}const process = require('node:process');

if (process.getgid) {
  console.log(`Current gid: ${process.getgid()}`);
}

此函数仅在 POSIX 平台上可用(即,不包括 Windows 或 Android)。

process.getgroups()#

process.getgroups() 方法返回一个包含辅助组 ID 的数组。POSIX 没有明确规定是否包含有效组 ID,但 Node.js 确保始终包含。

import process from 'node:process';

if (process.getgroups) {
  console.log(process.getgroups()); // [ 16, 21, 297 ]
}const process = require('node:process');

if (process.getgroups) {
  console.log(process.getgroups()); // [ 16, 21, 297 ]
}

此函数仅在 POSIX 平台上可用(即,不包括 Windows 或 Android)。

process.getuid()#

process.getuid() 方法返回进程的数值用户标识。(参见 getuid(2)。)

import process from 'node:process';

if (process.getuid) {
  console.log(`Current uid: ${process.getuid()}`);
}const process = require('node:process');

if (process.getuid) {
  console.log(`Current uid: ${process.getuid()}`);
}

此函数仅在 POSIX 平台上可用(即,不包括 Windows 或 Android)。

process.hasUncaughtExceptionCaptureCallback()#

指示是否已使用 process.setUncaughtExceptionCaptureCallback() 设置回调。

process.hrtime([time])#

稳定性: 3 - 遗留。请使用 process.hrtime.bigint() 代替。

这是在 JavaScript 中引入 bigint 之前 process.hrtime.bigint() 的遗留版本。

process.hrtime() 方法返回一个 [seconds, nanoseconds] 元组 Array,表示当前高分辨率实时时间,其中 nanoseconds 是无法用秒精度表示的实时时间的剩余部分。

time 是一个可选参数,必须是先前 process.hrtime() 调用的结果,用于与当前时间进行比较。如果传入的参数不是元组 Array,则会抛出 TypeError。传入用户定义的数组而不是先前调用 process.hrtime() 的结果会导致未定义的行为。

这些时间相对于过去某个任意时间,与一天中的时间无关,因此不受时钟漂移的影响。主要用途是在间隔之间测量性能。

import { hrtime } from 'node:process';

const NS_PER_SEC = 1e9;
const time = hrtime();
// [ 1800216, 25 ]

setTimeout(() => {
  const diff = hrtime(time);
  // [ 1, 552 ]

  console.log(`Benchmark took ${diff[0] * NS_PER_SEC + diff[1]} nanoseconds`);
  // Benchmark took 1000000552 nanoseconds
}, 1000);const { hrtime } = require('node:process');

const NS_PER_SEC = 1e9;
const time = hrtime();
// [ 1800216, 25 ]

setTimeout(() => {
  const diff = hrtime(time);
  // [ 1, 552 ]

  console.log(`Benchmark took ${diff[0] * NS_PER_SEC + diff[1]} nanoseconds`);
  // Benchmark took 1000000552 nanoseconds
}, 1000);

process.hrtime.bigint()#

process.hrtime.bigint() 方法的 bigint 版本,返回以纳秒为单位的当前高分辨率实时时间,以 bigint 表示。

process.hrtime() 不同,它不支持额外的 time 参数,因为可以通过直接减去两个 bigint 来计算差值。

import { hrtime } from 'node:process';

const start = hrtime.bigint();
// 191051479007711n

setTimeout(() => {
  const end = hrtime.bigint();
  // 191052633396993n

  console.log(`Benchmark took ${end - start} nanoseconds`);
  // Benchmark took 1154389282 nanoseconds
}, 1000);const { hrtime } = require('node:process');

const start = hrtime.bigint();
// 191051479007711n

setTimeout(() => {
  const end = hrtime.bigint();
  // 191052633396993n

  console.log(`Benchmark took ${end - start} nanoseconds`);
  // Benchmark took 1154389282 nanoseconds
}, 1000);

process.initgroups(user, extraGroup)#

process.initgroups() 方法读取 /etc/group 文件并初始化组访问列表,使用用户所属的所有组。这是一个特权操作,需要 Node.js 进程拥有 root 权限或 CAP_SETGID 能力。

在降低权限时请谨慎操作。

import { getgroups, initgroups, setgid } from 'node:process';

console.log(getgroups());         // [ 0 ]
initgroups('nodeuser', 1000);     // switch user
console.log(getgroups());         // [ 27, 30, 46, 1000, 0 ]
setgid(1000);                     // drop root gid
console.log(getgroups());         // [ 27, 30, 46, 1000 ]const { getgroups, initgroups, setgid } = require('node:process');

console.log(getgroups());         // [ 0 ]
initgroups('nodeuser', 1000);     // switch user
console.log(getgroups());         // [ 27, 30, 46, 1000, 0 ]
setgid(1000);                     // drop root gid
console.log(getgroups());         // [ 27, 30, 46, 1000 ]

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.kill(pid[, signal])#

  • pid <number> 进程 ID
  • signal <string> | <number> 要发送的信号,可以是字符串或数字。默认值: 'SIGTERM'

process.kill() 方法将 signal 发送到由 pid 标识的进程。

信号名称是字符串,例如 'SIGINT''SIGHUP'。有关更多信息,请参阅 信号事件kill(2)

如果目标 pid 不存在,此方法将抛出错误。作为特殊情况,可以使用 0 信号来测试进程是否存在。Windows 平台将在使用 pid 杀死进程组时抛出错误。

尽管此函数的名称是 process.kill(),但它实际上只是一个信号发送器,类似于 kill 系统调用。发送的信号可能执行的操作并非杀死目标进程。

import process, { kill } from 'node:process';

process.on('SIGHUP', () => {
  console.log('Got SIGHUP signal.');
});

setTimeout(() => {
  console.log('Exiting.');
  process.exit(0);
}, 100);

kill(process.pid, 'SIGHUP');const process = require('node:process');

process.on('SIGHUP', () => {
  console.log('Got SIGHUP signal.');
});

setTimeout(() => {
  console.log('Exiting.');
  process.exit(0);
}, 100);

process.kill(process.pid, 'SIGHUP');

当 Node.js 进程接收到 SIGUSR1 时,Node.js 将启动调试器。请参阅 信号事件

process.loadEnvFile(path)#

稳定性:1.1 - 积极开发

.env 文件加载到 process.env 中。在 .env 文件中使用 NODE_OPTIONS 不会对 Node.js 产生任何影响。

const { loadEnvFile } = require('node:process');
loadEnvFile();import { loadEnvFile } from 'node:process';
loadEnvFile();

process.mainModule#

稳定性: 0 - 已弃用: 请使用 require.main 代替。

process.mainModule 属性提供了一种检索 require.main 的替代方法。区别在于,如果主模块在运行时发生变化,require.main 可能会继续引用在更改发生之前已加载的模块中的原始主模块。通常情况下,可以安全地假设两者引用的是同一个模块。

require.main 一样,如果不存在入口脚本,process.mainModule 将为 undefined

process.memoryUsage()#

返回一个对象,描述 Node.js 进程的内存使用情况,以字节为单位。

import { memoryUsage } from 'node:process';

console.log(memoryUsage());
// Prints:
// {
//  rss: 4935680,
//  heapTotal: 1826816,
//  heapUsed: 650472,
//  external: 49879,
//  arrayBuffers: 9386
// }const { memoryUsage } = require('node:process');

console.log(memoryUsage());
// Prints:
// {
//  rss: 4935680,
//  heapTotal: 1826816,
//  heapUsed: 650472,
//  external: 49879,
//  arrayBuffers: 9386
// }
  • heapTotalheapUsed 指的是 V8 的内存使用情况。
  • external 指的是与 V8 管理的 JavaScript 对象绑定的 C++ 对象的内存使用情况。
  • rss,驻留集大小,是指进程在主内存设备中占用的空间量(即总分配内存的一个子集),包括所有 C++ 和 JavaScript 对象以及代码。
  • arrayBuffers 指的是为 ArrayBufferSharedArrayBuffer 分配的内存,包括所有 Node.js Buffer。这也包含在 external 值中。当 Node.js 用作嵌入式库时,此值可能为 0,因为在这种情况下可能不会跟踪为 ArrayBuffer 分配的内存。

当使用 Worker 线程时,rss 将是一个对整个进程有效的数值,而其他字段将只引用当前线程。

process.memoryUsage() 方法会遍历每个页面以收集有关内存使用情况的信息,这可能会很慢,具体取决于程序的内存分配。

process.memoryUsage.rss()#

process.memoryUsage.rss() 方法返回一个整数,表示以字节为单位的常驻集大小 (RSS)。

常驻集大小是指进程在主内存设备中占用的空间量(它是分配内存的子集),包括所有 C++ 和 JavaScript 对象和代码。

这与 process.memoryUsage() 提供的 rss 属性相同,但 process.memoryUsage.rss() 速度更快。

import { memoryUsage } from 'node:process';

console.log(memoryUsage.rss());
// 35655680const { memoryUsage } = require('node:process');

console.log(memoryUsage.rss());
// 35655680

process.nextTick(callback[, ...args])#

  • callback <Function>
  • ...args <any> 在调用 callback 时要传递的附加参数

process.nextTick()callback 添加到“下一个刻度队列”。在当前 JavaScript 堆栈上的操作运行完成并且事件循环允许继续之前,此队列将被完全清空。如果递归调用 process.nextTick(),则有可能创建无限循环。有关更多背景信息,请参阅 事件循环 指南。

import { nextTick } from 'node:process';

console.log('start');
nextTick(() => {
  console.log('nextTick callback');
});
console.log('scheduled');
// Output:
// start
// scheduled
// nextTick callbackconst { nextTick } = require('node:process');

console.log('start');
nextTick(() => {
  console.log('nextTick callback');
});
console.log('scheduled');
// Output:
// start
// scheduled
// nextTick callback

这在开发 API 时很重要,以便让用户有机会在对象构造后但任何 I/O 发生之前分配事件处理程序。

import { nextTick } from 'node:process';

function MyThing(options) {
  this.setupOptions(options);

  nextTick(() => {
    this.startDoingStuff();
  });
}

const thing = new MyThing();
thing.getReadyForStuff();

// thing.startDoingStuff() gets called now, not before.const { nextTick } = require('node:process');

function MyThing(options) {
  this.setupOptions(options);

  nextTick(() => {
    this.startDoingStuff();
  });
}

const thing = new MyThing();
thing.getReadyForStuff();

// thing.startDoingStuff() gets called now, not before.

对于 API 来说,100% 同步或 100% 异步非常重要。考虑以下示例

// WARNING!  DO NOT USE!  BAD UNSAFE HAZARD!
function maybeSync(arg, cb) {
  if (arg) {
    cb();
    return;
  }

  fs.stat('file', cb);
} 

此 API 很危险,因为在以下情况下

const maybeTrue = Math.random() > 0.5;

maybeSync(maybeTrue, () => {
  foo();
});

bar(); 

不清楚 foo()bar() 将先被调用。

以下方法要好得多

import { nextTick } from 'node:process';

function definitelyAsync(arg, cb) {
  if (arg) {
    nextTick(cb);
    return;
  }

  fs.stat('file', cb);
}const { nextTick } = require('node:process');

function definitelyAsync(arg, cb) {
  if (arg) {
    nextTick(cb);
    return;
  }

  fs.stat('file', cb);
}

何时使用 queueMicrotask()process.nextTick()#

queueMicrotask() API 是 process.nextTick() 的替代方案,它也使用与执行已解析承诺的 then、catch 和 finally 处理程序相同的微任务队列来推迟函数的执行。在 Node.js 中,每次“下一个刻度队列”被清空时,微任务队列都会在之后立即被清空。

import { nextTick } from 'node:process';

Promise.resolve().then(() => console.log(2));
queueMicrotask(() => console.log(3));
nextTick(() => console.log(1));
// Output:
// 1
// 2
// 3const { nextTick } = require('node:process');

Promise.resolve().then(() => console.log(2));
queueMicrotask(() => console.log(3));
nextTick(() => console.log(1));
// Output:
// 1
// 2
// 3

对于大多数用户级用例,queueMicrotask() API 提供了一种可移植且可靠的推迟执行机制,该机制适用于多个 JavaScript 平台环境,并且应该优先于 process.nextTick()。在简单的情况下,queueMicrotask() 可以作为 process.nextTick() 的直接替代品。

console.log('start');
queueMicrotask(() => {
  console.log('microtask callback');
});
console.log('scheduled');
// Output:
// start
// scheduled
// microtask callback 

这两个 API 之间的一个值得注意的差异是 process.nextTick() 允许指定附加值,这些值将在延迟函数被调用时作为参数传递给它。要使用 queueMicrotask() 达到相同的结果,需要使用闭包或绑定函数。

function deferred(a, b) {
  console.log('microtask', a + b);
}

console.log('start');
queueMicrotask(deferred.bind(undefined, 1, 2));
console.log('scheduled');
// Output:
// start
// scheduled
// microtask 3 

从下一个刻度队列和微任务队列中引发的错误的处理方式存在细微差异。在排队的微任务回调中抛出的错误应尽可能在排队的回调中处理。如果它们没有被处理,则 process.on('uncaughtException') 事件处理程序可用于捕获和处理错误。

如有疑问,除非需要 process.nextTick() 的特定功能,否则请使用 queueMicrotask()

process.noDeprecation#

process.noDeprecation 属性指示当前 Node.js 进程是否设置了 --no-deprecation 标志。有关此标志行为的更多信息,请参阅 'warning' 事件emitWarning() 方法 的文档。

process.permission#

此 API 可通过 --experimental-permission 标志使用。

process.permission 是一个对象,其方法用于管理当前进程的权限。有关更多文档,请参阅 权限模型

process.permission.has(scope[, reference])#

验证进程是否能够访问给定的范围和引用。如果没有提供引用,则假定为全局范围,例如,process.permission.has('fs.read') 将检查进程是否具有所有文件系统读取权限。

引用根据提供的范围具有不同的含义。例如,当范围是文件系统时,引用表示文件和文件夹。

可用的范围是

  • fs - 所有文件系统
  • fs.read - 文件系统读取操作
  • fs.write - 文件系统写入操作
  • child - 子进程生成操作
  • worker - 工作线程生成操作
// Check if the process has permission to read the README file
process.permission.has('fs.read', './README.md');
// Check if the process has read permission operations
process.permission.has('fs.read'); 

process.pid#

process.pid 属性返回进程的 PID。

import { pid } from 'node:process';

console.log(`This process is pid ${pid}`);const { pid } = require('node:process');

console.log(`This process is pid ${pid}`);

process.platform#

process.platform 属性返回一个字符串,标识为其编译 Node.js 二进制文件的操作系统平台。

当前可能的值是

  • 'aix'
  • 'darwin'
  • 'freebsd'
  • 'linux'
  • 'openbsd'
  • 'sunos'
  • 'win32'
import { platform } from 'node:process';

console.log(`This platform is ${platform}`);const { platform } = require('node:process');

console.log(`This platform is ${platform}`);

如果 Node.js 是在 Android 操作系统上构建的,则也可能返回值 'android'。但是,Node.js 中的 Android 支持 是实验性的

process.ppid#

process.ppid 属性返回当前进程父进程的 PID。

import { ppid } from 'node:process';

console.log(`The parent process is pid ${ppid}`);const { ppid } = require('node:process');

console.log(`The parent process is pid ${ppid}`);

process.release#

process.release 属性返回一个 Object,其中包含与当前版本相关的元数据,包括源代码包和仅包含头文件的代码包的 URL。

process.release 包含以下属性

  • name <string> 一个始终为 'node' 的值。
  • sourceUrl <string> 指向包含当前版本源代码的 .tar.gz 文件的绝对 URL。
  • headersUrl<string> 指向仅包含当前版本源代码头文件的 .tar.gz 文件的绝对 URL。此文件比完整源文件小得多,可用于编译 Node.js 本地插件。
  • libUrl <string> | <undefined> 指向与当前版本架构和版本匹配的 node.lib 文件的绝对 URL。此文件用于编译 Node.js 本地插件。此属性仅存在于 Windows 版本的 Node.js 中,在所有其他平台上都将缺失。
  • lts <string> | <undefined> 一个字符串标签,标识此版本的 LTS 标签。此属性仅存在于 LTS 版本中,对于所有其他版本类型(包括当前版本)都是 undefined。有效值包括 LTS 版本代码名称(包括不再受支持的名称)。
    • 'Fermium' 用于从 14.15.0 开始的 14.x LTS 版本。
    • 'Gallium' 用于从 16.13.0 开始的 16.x LTS 版本。
    • 'Hydrogen' 用于从 18.12.0 开始的 18.x LTS 版本。有关其他 LTS 版本代码名称,请参见 Node.js 变更日志存档
{
  name: 'node',
  lts: 'Hydrogen',
  sourceUrl: 'https://node.org.cn/download/release/v18.12.0/node-v18.12.0.tar.gz',
  headersUrl: 'https://node.org.cn/download/release/v18.12.0/node-v18.12.0-headers.tar.gz',
  libUrl: 'https://node.org.cn/download/release/v18.12.0/win-x64/node.lib'
} 

在来自非发布版本源代码树的自定义构建中,可能只存在 name 属性。不应依赖其他属性的存在。

process.report#

process.report 是一个对象,其方法用于生成当前进程的诊断报告。更多文档请参见 报告文档

process.report.compact#

以紧凑格式写入报告,单行 JSON,比默认的多行格式更容易被日志处理系统使用,默认的多行格式设计用于人类阅读。

import { report } from 'node:process';

console.log(`Reports are compact? ${report.compact}`);const { report } = require('node:process');

console.log(`Reports are compact? ${report.compact}`);

process.report.directory#

写入报告的目录。默认值为空字符串,表示报告将写入 Node.js 进程的当前工作目录。

import { report } from 'node:process';

console.log(`Report directory is ${report.directory}`);const { report } = require('node:process');

console.log(`Report directory is ${report.directory}`);

process.report.filename#

写入报告的文件名。如果设置为空字符串,输出文件名将包含时间戳、PID 和序列号。默认值为空字符串。

如果 process.report.filename 的值设置为 'stdout''stderr',则报告将分别写入进程的 stdout 或 stderr。

import { report } from 'node:process';

console.log(`Report filename is ${report.filename}`);const { report } = require('node:process');

console.log(`Report filename is ${report.filename}`);

process.report.getReport([err])#

  • err <Error> 用于报告 JavaScript 堆栈的自定义错误。
  • 返回值:<Object>

返回运行进程的诊断报告的 JavaScript 对象表示形式。报告的 JavaScript 堆栈跟踪来自 err(如果存在)。

import { report } from 'node:process';
import util from 'node:util';

const data = report.getReport();
console.log(data.header.nodejsVersion);

// Similar to process.report.writeReport()
import fs from 'node:fs';
fs.writeFileSync('my-report.log', util.inspect(data), 'utf8');const { report } = require('node:process');
const util = require('node:util');

const data = report.getReport();
console.log(data.header.nodejsVersion);

// Similar to process.report.writeReport()
const fs = require('node:fs');
fs.writeFileSync('my-report.log', util.inspect(data), 'utf8');

更多文档请参见 报告文档

process.report.reportOnFatalError#

如果为true,则在致命错误(例如内存不足错误或 C++ 断言失败)时生成诊断报告。

import { report } from 'node:process';

console.log(`Report on fatal error: ${report.reportOnFatalError}`);const { report } = require('node:process');

console.log(`Report on fatal error: ${report.reportOnFatalError}`);

process.report.reportOnSignal#

如果为true,则当进程接收到由process.report.signal指定的信号时生成诊断报告。

import { report } from 'node:process';

console.log(`Report on signal: ${report.reportOnSignal}`);const { report } = require('node:process');

console.log(`Report on signal: ${report.reportOnSignal}`);

process.report.reportOnUncaughtException#

如果为true,则在未捕获的异常时生成诊断报告。

import { report } from 'node:process';

console.log(`Report on exception: ${report.reportOnUncaughtException}`);const { report } = require('node:process');

console.log(`Report on exception: ${report.reportOnUncaughtException}`);

process.report.signal#

用于触发创建诊断报告的信号。默认为'SIGUSR2'

import { report } from 'node:process';

console.log(`Report signal: ${report.signal}`);const { report } = require('node:process');

console.log(`Report signal: ${report.signal}`);

process.report.writeReport([filename][, err])#

  • filename <string> 报告写入的文件名。这应该是一个相对路径,它将附加到process.report.directory中指定的目录,或者如果未指定,则附加到 Node.js 进程的当前工作目录。

  • err <Error> 用于报告 JavaScript 堆栈的自定义错误。

  • 返回值:<string> 返回生成的报告的文件名。

将诊断报告写入文件。如果未提供filename,则默认文件名包含日期、时间、PID 和序列号。报告的 JavaScript 堆栈跟踪来自err(如果存在)。

如果filename的值设置为'stdout''stderr',则报告将分别写入进程的 stdout 或 stderr。

import { report } from 'node:process';

report.writeReport();const { report } = require('node:process');

report.writeReport();

更多文档请参见 报告文档

process.resourceUsage()#

  • 返回值:<Object> 当前进程的资源使用情况。所有这些值都来自uv_getrusage调用,该调用返回一个uv_rusage_t 结构
    • userCPUTime <integer> 映射到以微秒计算的 ru_utime。它与 process.cpuUsage().user 的值相同。
    • systemCPUTime <integer> 映射到以微秒计算的 ru_stime。它与 process.cpuUsage().system 的值相同。
    • maxRSS <integer> 映射到 ru_maxrss,它是以千字节为单位的最大驻留集大小。
    • sharedMemorySize <integer> 映射到 ru_ixrss,但不受任何平台支持。
    • unsharedDataSize <integer> 映射到 ru_idrss,但不受任何平台支持。
    • unsharedStackSize <integer> 映射到 ru_isrss,但不受任何平台支持。
    • minorPageFault <integer> 映射到 ru_minflt,它是进程的次要页面错误次数,有关更多详细信息,请参阅 这篇文章
    • majorPageFault <integer> 映射到 ru_majflt,它是进程的主要页面错误次数,有关更多详细信息,请参阅 这篇文章。此字段在 Windows 上不受支持。
    • swappedOut <integer> 映射到 ru_nswap,但不受任何平台支持。
    • fsRead <integer> 映射到 ru_inblock,它是文件系统必须执行输入的次数。
    • fsWrite <integer> 映射到 ru_oublock,它是文件系统必须执行输出的次数。
    • ipcSent <integer> 映射到 ru_msgsnd,但不受任何平台支持。
    • ipcReceived <integer> 映射到 ru_msgrcv,但不受任何平台支持。
    • signalsCount <integer> 映射到 ru_nsignals,但不受任何平台支持。
    • voluntaryContextSwitches <integer> 映射到 ru_nvcsw,它是由于进程在时间片完成之前自愿放弃处理器(通常是为了等待资源可用)而导致 CPU 上下文切换的次数。此字段在 Windows 上不受支持。
    • involuntaryContextSwitches <integer> 映射到 ru_nivcsw,它是由于更高优先级的进程变得可运行或当前进程超过其时间片而导致 CPU 上下文切换的次数。此字段在 Windows 上不受支持。
import { resourceUsage } from 'node:process';

console.log(resourceUsage());
/*
  Will output:
  {
    userCPUTime: 82872,
    systemCPUTime: 4143,
    maxRSS: 33164,
    sharedMemorySize: 0,
    unsharedDataSize: 0,
    unsharedStackSize: 0,
    minorPageFault: 2469,
    majorPageFault: 0,
    swappedOut: 0,
    fsRead: 0,
    fsWrite: 8,
    ipcSent: 0,
    ipcReceived: 0,
    signalsCount: 0,
    voluntaryContextSwitches: 79,
    involuntaryContextSwitches: 1
  }
*/const { resourceUsage } = require('node:process');

console.log(resourceUsage());
/*
  Will output:
  {
    userCPUTime: 82872,
    systemCPUTime: 4143,
    maxRSS: 33164,
    sharedMemorySize: 0,
    unsharedDataSize: 0,
    unsharedStackSize: 0,
    minorPageFault: 2469,
    majorPageFault: 0,
    swappedOut: 0,
    fsRead: 0,
    fsWrite: 8,
    ipcSent: 0,
    ipcReceived: 0,
    signalsCount: 0,
    voluntaryContextSwitches: 79,
    involuntaryContextSwitches: 1
  }
*/

process.send(message[, sendHandle[, options]][, callback])#

  • message <Object>
  • sendHandle <net.Server> | <net.Socket>
  • options <Object> 用于参数化某些类型句柄的发送。options 支持以下属性
    • keepOpen <boolean> 在传递 net.Socket 实例时可以使用的一个值。当为 true 时,套接字在发送过程中保持打开状态。默认值: false
  • callback <Function>
  • 返回值:<boolean>

如果 Node.js 是使用 IPC 通道生成的,则可以使用 process.send() 方法向父进程发送消息。消息将作为父进程的 ChildProcess 对象上的 'message' 事件接收。

如果 Node.js 不是使用 IPC 通道生成的,则 process.send 将为 undefined

消息会经过序列化和解析。最终的消息可能与最初发送的消息不同。

process.setegid(id)#

process.setegid() 方法设置进程的有效组标识。(参见 setegid(2)。)id 可以作为数字 ID 或组名字符串传递。如果指定了组名,则此方法在解析关联的数字 ID 时会阻塞。

import process from 'node:process';

if (process.getegid && process.setegid) {
  console.log(`Current gid: ${process.getegid()}`);
  try {
    process.setegid(501);
    console.log(`New gid: ${process.getegid()}`);
  } catch (err) {
    console.error(`Failed to set gid: ${err}`);
  }
}const process = require('node:process');

if (process.getegid && process.setegid) {
  console.log(`Current gid: ${process.getegid()}`);
  try {
    process.setegid(501);
    console.log(`New gid: ${process.getegid()}`);
  } catch (err) {
    console.error(`Failed to set gid: ${err}`);
  }
}

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.seteuid(id)#

process.seteuid() 方法设置进程的有效用户标识。(参见 seteuid(2)。)id 可以作为数字 ID 或用户名字符串传递。如果指定了用户名,则此方法在解析关联的数字 ID 时会阻塞。

import process from 'node:process';

if (process.geteuid && process.seteuid) {
  console.log(`Current uid: ${process.geteuid()}`);
  try {
    process.seteuid(501);
    console.log(`New uid: ${process.geteuid()}`);
  } catch (err) {
    console.error(`Failed to set uid: ${err}`);
  }
}const process = require('node:process');

if (process.geteuid && process.seteuid) {
  console.log(`Current uid: ${process.geteuid()}`);
  try {
    process.seteuid(501);
    console.log(`New uid: ${process.geteuid()}`);
  } catch (err) {
    console.error(`Failed to set uid: ${err}`);
  }
}

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.setgid(id)#

process.setgid() 方法设置进程的组标识。(参见 setgid(2)。)id 可以作为数字 ID 或组名字符串传递。如果指定了组名,则此方法在解析关联的数字 ID 时会阻塞。

import process from 'node:process';

if (process.getgid && process.setgid) {
  console.log(`Current gid: ${process.getgid()}`);
  try {
    process.setgid(501);
    console.log(`New gid: ${process.getgid()}`);
  } catch (err) {
    console.error(`Failed to set gid: ${err}`);
  }
}const process = require('node:process');

if (process.getgid && process.setgid) {
  console.log(`Current gid: ${process.getgid()}`);
  try {
    process.setgid(501);
    console.log(`New gid: ${process.getgid()}`);
  } catch (err) {
    console.error(`Failed to set gid: ${err}`);
  }
}

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.setgroups(groups)#

process.setgroups() 方法设置 Node.js 进程的补充组 ID。这是一个特权操作,需要 Node.js 进程具有 rootCAP_SETGID 能力。

groups 数组可以包含数字组 ID、组名或两者。

import process from 'node:process';

if (process.getgroups && process.setgroups) {
  try {
    process.setgroups([501]);
    console.log(process.getgroups()); // new groups
  } catch (err) {
    console.error(`Failed to set groups: ${err}`);
  }
}const process = require('node:process');

if (process.getgroups && process.setgroups) {
  try {
    process.setgroups([501]);
    console.log(process.getgroups()); // new groups
  } catch (err) {
    console.error(`Failed to set groups: ${err}`);
  }
}

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.setuid(id)#

process.setuid(id) 方法设置进程的用户标识。(参见 setuid(2)。)id 可以作为数字 ID 或用户名字符串传递。如果指定了用户名,则此方法在解析关联的数字 ID 时会阻塞。

import process from 'node:process';

if (process.getuid && process.setuid) {
  console.log(`Current uid: ${process.getuid()}`);
  try {
    process.setuid(501);
    console.log(`New uid: ${process.getuid()}`);
  } catch (err) {
    console.error(`Failed to set uid: ${err}`);
  }
}const process = require('node:process');

if (process.getuid && process.setuid) {
  console.log(`Current uid: ${process.getuid()}`);
  try {
    process.setuid(501);
    console.log(`New uid: ${process.getuid()}`);
  } catch (err) {
    console.error(`Failed to set uid: ${err}`);
  }
}

此函数仅在 POSIX 平台(即非 Windows 或 Android)上可用。此功能在 Worker 线程中不可用。

process.setSourceMapsEnabled(val)#

稳定性:1 - 实验性

此函数启用或禁用 Source Map v3 对堆栈跟踪的支持。

它提供与使用命令行选项 --enable-source-maps 启动 Node.js 进程相同的功能。

只有在启用源映射后加载的 JavaScript 文件中的源映射才会被解析和加载。

process.setUncaughtExceptionCaptureCallback(fn)#

process.setUncaughtExceptionCaptureCallback() 函数设置一个函数,该函数将在发生未捕获异常时被调用,并将接收异常值本身作为其第一个参数。

如果设置了这样的函数,则不会发出 'uncaughtException' 事件。如果从命令行传递了 --abort-on-uncaught-exception 或通过 v8.setFlagsFromString() 设置,则进程不会中止。配置为在异常发生时执行的操作(例如报告生成)也会受到影响。

要取消设置捕获函数,可以使用 process.setUncaughtExceptionCaptureCallback(null)。如果在设置了另一个捕获函数的情况下使用非 null 参数调用此方法,则会抛出错误。

使用此函数与使用已弃用的 domain 内置模块是互斥的。

process.sourceMapsEnabled#

稳定性:1 - 实验性

process.sourceMapsEnabled 属性返回堆栈跟踪的 Source Map v3 支持是否已启用。

process.stderr#

process.stderr 属性返回一个连接到 stderr(fd 2)的流。它是一个 net.Socket(它是一个 Duplex 流),除非 fd 2 指向文件,在这种情况下它是一个 Writable 流。

process.stderr 在重要方面与其他 Node.js 流不同。有关更多信息,请参见 关于进程 I/O 的说明

process.stderr.fd#

此属性引用 process.stderr 的底层文件描述符的值。该值固定为 2。在 Worker 线程中,此字段不存在。

process.stdin#

process.stdin 属性返回一个连接到 stdin (fd 0) 的流。它是一个 net.Socket (它是一个 双工 流),除非 fd 0 指向一个文件,在这种情况下它是一个 可读 流。

有关如何从 stdin 读取的详细信息,请参阅 readable.read()

作为 双工 流,process.stdin 也可以在与 Node.js v0.10 之前版本编写的脚本兼容的“旧”模式下使用。有关更多信息,请参阅 流兼容性

在“旧”流模式下,stdin 流默认情况下处于暂停状态,因此必须调用 process.stdin.resume() 才能从中读取。还要注意,调用 process.stdin.resume() 本身会将流切换到“旧”模式。

process.stdin.fd#

此属性引用 process.stdin 的底层文件描述符的值。该值固定为 0。在 Worker 线程中,此字段不存在。

process.stdout#

process.stdout 属性返回一个连接到 stdout (fd 1) 的流。它是一个 net.Socket (它是一个 双工 流),除非 fd 1 指向一个文件,在这种情况下它是一个 可写 流。

例如,要将 process.stdin 复制到 process.stdout

import { stdin, stdout } from 'node:process';

stdin.pipe(stdout);const { stdin, stdout } = require('node:process');

stdin.pipe(stdout);

process.stdout 在重要方面与其他 Node.js 流不同。有关更多信息,请参阅 关于进程 I/O 的说明

process.stdout.fd#

此属性引用 process.stdout 的底层文件描述符的值。该值固定为 1。在 Worker 线程中,此字段不存在。

关于进程 I/O 的说明#

process.stdoutprocess.stderr 在重要的方面与其他 Node.js 流不同

  1. 它们分别由 console.log()console.error() 在内部使用。
  2. 写入可能是同步的,具体取决于流连接到的内容以及系统是 Windows 还是 POSIX
    • 文件:Windows 和 POSIX 上同步
    • TTY(终端):Windows 上异步,POSIX 上同步
    • 管道(和套接字):Windows 上同步,POSIX 上异步

这些行为部分是出于历史原因,因为更改它们会导致向后不兼容,但它们也是一些用户所期望的。

同步写入避免了诸如使用 console.log()console.error() 写入的输出意外交错,或者如果在异步写入完成之前调用 process.exit() 则根本没有写入的问题。有关更多信息,请参阅 process.exit()

警告:同步写入会阻塞事件循环,直到写入完成。在向文件输出的情况下,这可能几乎是瞬时的,但在系统负载高、未在接收端读取的管道或终端或文件系统速度慢的情况下,事件循环可能会被阻塞足够频繁和足够长的时间,从而对性能产生严重的负面影响。在写入交互式终端会话时,这可能不是问题,但在将生产日志记录到进程输出流时,请特别注意这一点。

要检查流是否连接到 TTY 上下文,请检查 isTTY 属性。

例如

$ node -p "Boolean(process.stdin.isTTY)"
true
$ echo "foo" | node -p "Boolean(process.stdin.isTTY)"
false
$ node -p "Boolean(process.stdout.isTTY)"
true
$ node -p "Boolean(process.stdout.isTTY)" | cat
false 

有关更多信息,请参阅 TTY 文档。

process.throwDeprecation#

process.throwDeprecation 的初始值指示当前 Node.js 进程中是否设置了 --throw-deprecation 标志。process.throwDeprecation 是可变的,因此弃用警告是否会导致错误可以在运行时更改。有关更多信息,请参阅 'warning' 事件emitWarning() 方法 的文档。

$ node --throw-deprecation -p "process.throwDeprecation"
true
$ node -p "process.throwDeprecation"
undefined
$ node
> process.emitWarning('test', 'DeprecationWarning');
undefined
> (node:26598) DeprecationWarning: test
> process.throwDeprecation = true;
true
> process.emitWarning('test', 'DeprecationWarning');
Thrown:
[DeprecationWarning: test] { name: 'DeprecationWarning' } 

process.title#

process.title 属性返回当前进程标题(即返回 ps 的当前值)。将新值分配给 process.title 会修改 ps 的当前值。

分配新值时,不同的平台会对标题施加不同的最大长度限制。通常,此类限制非常有限。例如,在 Linux 和 macOS 上,process.title 限制为二进制名称的大小加上命令行参数的长度,因为设置 process.title 会覆盖进程的 argv 内存。Node.js v0.8 允许更长的进程标题字符串,方法是还覆盖 environ 内存,但这在某些(相当模糊的)情况下可能是不安全的,并且令人困惑。

将值分配给process.title可能不会在 macOS 活动监视器或 Windows 服务管理器等进程管理器应用程序中产生准确的标签。

process.traceDeprecation#

process.traceDeprecation属性指示当前 Node.js 进程是否设置了--trace-deprecation标志。有关此标志行为的更多信息,请参阅'warning'事件emitWarning()方法的文档。

process.umask()#

稳定性:0 - 已弃用。调用不带参数的process.umask()会导致进程范围的 umask 被写入两次。这在线程之间引入了竞争条件,并且是一个潜在的安全漏洞。没有安全的、跨平台的替代 API。

process.umask()返回 Node.js 进程的文件模式创建掩码。子进程从父进程继承掩码。

process.umask(mask)#

process.umask(mask)设置 Node.js 进程的文件模式创建掩码。子进程从父进程继承掩码。返回之前的掩码。

import { umask } from 'node:process';

const newmask = 0o022;
const oldmask = umask(newmask);
console.log(
  `Changed umask from ${oldmask.toString(8)} to ${newmask.toString(8)}`,
);const { umask } = require('node:process');

const newmask = 0o022;
const oldmask = umask(newmask);
console.log(
  `Changed umask from ${oldmask.toString(8)} to ${newmask.toString(8)}`,
);

Worker线程中,process.umask(mask)将抛出异常。

process.uptime()#

process.uptime()方法返回当前 Node.js 进程运行的秒数。

返回值包括秒的几分之一。使用Math.floor()获取完整的秒数。

process.version#

process.version 属性包含 Node.js 版本字符串。

import { version } from 'node:process';

console.log(`Version: ${version}`);
// Version: v14.8.0const { version } = require('node:process');

console.log(`Version: ${version}`);
// Version: v14.8.0

要获取不带前缀 v 的版本字符串,请使用 process.versions.node

process.versions#

process.versions 属性返回一个对象,其中列出了 Node.js 及其依赖项的版本字符串。process.versions.modules 指示当前 ABI 版本,每当 C++ API 发生更改时,该版本都会增加。Node.js 将拒绝加载针对不同模块 ABI 版本编译的模块。

import { versions } from 'node:process';

console.log(versions);const { versions } = require('node:process');

console.log(versions);

将生成类似于以下内容的对象

{ node: '20.2.0',
  acorn: '8.8.2',
  ada: '2.4.0',
  ares: '1.19.0',
  base64: '0.5.0',
  brotli: '1.0.9',
  cjs_module_lexer: '1.2.2',
  cldr: '43.0',
  icu: '73.1',
  llhttp: '8.1.0',
  modules: '115',
  napi: '8',
  nghttp2: '1.52.0',
  nghttp3: '0.7.0',
  ngtcp2: '0.8.1',
  openssl: '3.0.8+quic',
  simdutf: '3.2.9',
  tz: '2023c',
  undici: '5.22.0',
  unicode: '15.0',
  uv: '1.44.2',
  uvwasi: '0.0.16',
  v8: '11.3.244.8-node.9',
  zlib: '1.2.13' } 

退出代码#

Node.js 通常在没有更多异步操作挂起时以 0 状态代码退出。以下状态代码用于其他情况

  • 1 未捕获的致命异常:存在未捕获的异常,并且未由域或 'uncaughtException' 事件处理程序处理。
  • 2:未使用(由 Bash 为内置错误使用保留)
  • 3 内部 JavaScript 解析错误:Node.js 引导过程中内部的 JavaScript 源代码导致解析错误。这种情况极其罕见,通常只会在 Node.js 自身开发过程中发生。
  • 4 内部 JavaScript 评估失败:Node.js 引导过程中内部的 JavaScript 源代码在评估时未能返回函数值。这种情况极其罕见,通常只会在 Node.js 自身开发过程中发生。
  • 5 致命错误:V8 中存在致命的不可恢复错误。通常会在 stderr 中打印一条以 FATAL ERROR 为前缀的消息。
  • 6 非函数内部异常处理程序:存在未捕获的异常,但内部致命异常处理程序函数不知何故被设置为非函数,无法调用。
  • 7 内部异常处理程序运行时失败:存在未捕获的异常,并且内部致命异常处理程序函数本身在尝试处理它时抛出了错误。例如,如果 'uncaughtException'domain.on('error') 处理程序抛出错误,就会发生这种情况。
  • 8: 未使用。在之前的 Node.js 版本中,退出代码 8 有时表示未捕获的异常。
  • 9 无效参数: 指定了未知选项,或提供了需要值的选项但未提供值。
  • 10 内部 JavaScript 运行时错误: Node.js 引导过程中内部的 JavaScript 源代码在调用引导函数时抛出错误。这种情况非常罕见,通常只会在 Node.js 自身开发过程中发生。
  • 12 无效调试参数: 设置了 --inspect 和/或 --inspect-brk 选项,但选择的端口号无效或不可用。
  • 13 未完成的顶层 Await: await 在顶层代码中函数外部使用,但传递的 Promise 未解决。
  • 14 快照失败: Node.js 启动以构建 V8 启动快照,但由于应用程序状态的某些要求未满足而失败。
  • >128 信号退出: 如果 Node.js 收到致命信号,例如 SIGKILLSIGHUP,则其退出代码将为 128 加上信号代码的值。这是标准的 POSIX 实践,因为退出代码被定义为 7 位整数,而信号退出设置高位,然后包含信号代码的值。例如,信号 SIGABRT 的值为 6,因此预期的退出代码将为 128 + 6,即 134