nodejs を使用する友人は皆、node がシングルスレッドであることを知っています。つまり、ノードは 8 コア CPU 上で実行され、1 つのコアの計算能力しか使用できません。
シングル スレッドは常にノードに対する批判でしたが、バージョン 0.6 でのクラスターの導入により、開発者はクラスターを利用してノード サーバーをマルチスレッド サーバーに簡単に拡張できるようになりました。
クラスターとは
クラスターはノードによって提供されるマルチスレッド ライブラリであり、ユーザーはこれを使用して複数のスレッドを作成できます。このポートに外部リクエストがあると、クラスターはそのリクエストをランダムなスレッドに転送します。 。各ノードのスレッドは数十メガバイトのメモリを占有するため、PHP のようにリクエストごとにスレッドを作成することはできません。一般的に、作成されるスレッドの数は最大でも CPU のコア数を超えません。
if (cluster.isMaster) {
// フォークワーカー。
for (var i = 0; i
cluster.fork();
}
cluster.on('exit', function(worker, code, signal) {
console.log('ワーカー ' worker.process.pid ' が死亡しました');
});
} else {
// ワーカーは任意の TCP 接続を共有できます
// この場合は HTTP サーバーです
http.createServer(function(req, res) {
res.writeHead(200);
res.end("hello worldn");
}).listen(8000);
}
上記のコードに示すように、プログラムの実行中に、cluster.isMaster は true に設定されます。cluster.fork() を呼び出した後、プログラムはスレッドを作成し、この時点で再度実行されます。 false に設定されます。この変数は主に、現在のスレッドが子スレッドであるかどうかを判断するために使用します。
各子スレッドが作成された後、競合を引き起こすことなくポート 8000 をリッスンすることもわかります。これがクラスター共有ポートの機能です。
スレッド間の通信
スレッドが作成されるとき、スレッドは相互にメモリやデータを共有しません。すべてのデータ交換は、worker.send および worker.on('message', handler) を介してメイン スレッドでのみ処理できます。これはブロードキャスト システムの例です。
if (cluster.isMaster) {
var ワーカー=[];
// 新しいワーカーを作成します
関数 newWorker(){
var worker=cluster.fork();
//情報を聞き、その種類がブロードキャストであればブロードキャストと判断します
worker.on('メッセージ', function(msg) {
If(msg.type=='ブロードキャスト'){
varevent=msg.event;
//このブロードキャストをすべてのワーカーに送信します
works.forEach(function(worker){
ワーカー.send(イベント);
})
}
});
従業員を復帰させます;
}
for (var i = 0; i
Workers.push(newWorker());
}
cluster.on('online',function(worker){
console.log('ワーカー %d はオンラインです',worker.id);
})
} else {
var worker=cluster.worker;
//ブロードキャストはブロードキャストタイプのメッセージを送信するもので、イベントはブロードキャストの内容です
worker.broadcast=関数(イベント){
worker.send({
タイプ: 'ブロードキャスト'、
イベント:イベント
});
}
//ここではworker.onを使用して返された情報を監視することはできないようです
process.on('メッセージ',function(イベント){
console.log('worker: 'worker.id ' が 'event.workerId からイベントを受け取りました);
})
//ブロードキャストを送信
worker.broadcast({
メッセージ:'オンライン'、
ワーカーID:ワーカー.id
})
}
注意が必要な問題
前述したように、スレッド間でデータを共有することはできず、すべてのデータ交換はスレッド間の通信を通じてのみ行われます。また、交換されるデータはすべてシリアル化可能であるため、関数、ファイル記述子、HttpResponse などを渡すことはできません。
クラスターを使用する場合、プログラム設計時にデータ交換の問題を考慮する必要があります。私自身のアプローチは、セッションなどのデータを Redis に保存することであり、各スレッドはデータへのアクセスを適切に実行します。ノードメモリ内。
最後のポイント、クラスターは現在、ノードによって正式に実験的としてマークされており、API は将来変更される可能性があります。