Nodejs系列:什么是集群?如何开启多核处理器?

279 阅读3分钟

开启多核处理器的两种方式:

1. 使用cluster模块(进程集群方式)

基本原理:

Node.js 的cluster模块允许轻松创建共享服务器端口的子进程。它利用了多核处理器的优势,每个子进程可以在不同的核心上运行,从而提高应用程序的性能和吞吐量。

const cluster = require('cluster');
const http = require('http');
const numCPUs = require('os').cpus().length;

if (cluster.isMaster) {
    // 主进程分支
    console.log(`主进程 ${process.pid} 正在运行`);
    // 衍生工作进程
    for (let i = 0; i < numCPUs; i++) {
        cluster.fork();
    }
    cluster.on('exit', (worker, code, signal) => {
        console.log(`工作进程 ${worker.process.pid} 已退出,代码: ${code}, 信号: ${signal}`);
        // 当工作进程退出时,可以选择重新启动它
        cluster.fork();
    });
} else {
    // 工作进程分支
    http.createServer((req, res) => {
        res.writeHead(200);
        res.end('你好,世界!');
    }).listen(3000);
    console.log(`工作进程 ${process.pid} 已启动,正在监听端口3000`);
}
  • 代码解释

    • 主进程会根据 CPU 核心数创建子进程(工作进程)
      • 每个子进程通过cluster.fork()方法创建。
    • 通过cluster.on('exit')监听工作进程的退出事件
      • 当工作进程退出时,可以在事件回调中重新启动一个工作进程。
    • 工作进程会创建一个 HTTP 服务器,监听 3000 端口,并在有请求时返回简单的响应。
      • 每个工作进程都独立运行这个服务器,从而可以同时处理多个请求,充分利用多核处理器。

2. 使用worker_threads模块(线程方式)

基本原理:

worker_threads模块允许在 Node.js 中使用多线程。虽然 Node.js 主要是单线程的,但通过这个模块可以创建多个线程来并行执行任务,适用于 CPU 密集型任务,提高多核处理器的利用率。

const { Worker, isMainThread, parentPort } = require('worker_threads');
if (isMainThread) {
    const worker = new Worker(__filename);
    worker.on('message', (result) => {
        console.log(`从线程接收到结果: ${result}`);
    });
    worker.postMessage(40);
} else {
    parentPort.on('message', (num) => {
        const result = num * 2;
        parentPort.postMessage(result);
    });
}
  • 代码解释

    • 如果是主线程:主线程创建一个新的工作线程,
      • 然后通过worker.on('message')监听工作线程发送的消息。
      • 使用worker.postMessage向工作线程发送一个数字 40。
    • 如果不是主进程:说明这是工作线程。
      • 工作线程通过parentPort.on('message')监听主线程发送的消息
      • 再通过parentPort.postMessage发送回主线程。

使用worker_threads模块需要注意线程间通信和共享资源可能带来的复杂性。

Node.js集群: 一种用于提升性能的架构模式

  • Node.js 集群是一种通过创建多个子进程来充分利用多核 CPU 资源的机制。它使得 Node.js 应用能够同时处理多个任务,提升应用的性能和处理能力。

运行机制:

  • 主从结构: 有一个主进程(master process)和多个工作进程(worker processes)。
    • 主进程主要负责调度和管理工作进程,比如创建工作进程和监控它们的状态。
    • 工作进程负责实际的任务处理,像处理网络请求或者执行其他计算任务。
  • 共享端口:工作进程能够共享服务器端口来接收请求。
    • 这使得多个工作进程可以同时监听同一个端口,对外就好像是一个应用在处理所有请求。
      • 例如,在处理 HTTP 请求时,多个工作进程可以一起接收和处理来自客户端的请求。
  • 负载均衡: 当请求到达时,会按照一定的策略(如轮询)分配给不同的工作进程。
    • 这确保了每个工作进程都能参与处理请求,避免某个工作进程过载,而其他工作进程闲置的情况,从而高效地利用系统资源。
  • 进程间通信(IPC)
    • 主进程和工作进程之间,以及工作进程相互之间需要进行信息交流。它们通过 IPC 机制来实现通信,例如传递任务、共享状态信息等。这有助于协调各个进程的工作,确保集群的高效运行。

应用优势:

  • 性能提升

    • 对于高并发的场景,如 Web 服务器,集群能够充分利用多核 CPU。因为多个工作进程可以同时运行在不同的 CPU 核心上,相比单个进程能处理更多的请求,大大缩短了响应时间。
  • 高可用性

    • 如果一个工作进程出现故障(例如因为程序错误或者系统资源耗尽),主进程可以检测到并启动新的工作进程来替代它,使得服务不会中断,增强了整个应用的可靠性。