ホームページ  >  記事  >  ウェブフロントエンド  >  Nodejsアドバンスコアモジュールネット入門学習と事例解説

Nodejsアドバンスコアモジュールネット入門学習と事例解説

高洛峰
高洛峰オリジナル
2016-12-06 11:49:331087ブラウズ

モジュール概要

netモジュールは、nodejsのコアモジュールでもあります。 http モジュールの概要で述べたように、http.Server は net.Server を継承します。また、http クライアントと http サーバー間の通信はソケット (net.Socket) に依存します。つまり、ノードサーバープログラミングを行う場合、基本的にnetは避けて通れないモジュールとなります。

構成の観点から見ると、net モジュールは主に 2 つの部分で構成されます。ソケット プログラミングを知っている学生はよく知っているはずです:

net.Server: ソケットを介して内部でクライアントと通信する TCP サーバー。

net.Socket: 全二重ストリームインターフェースを実装する、tcp/ローカルソケットのノードバージョン実装。

この記事は、読者に概要を提供するために、単純な TCP サーバー/クライアントの例から始まります。次に、net.Server と net.Socket のより重要な API、プロパティ、イベントをそれぞれ紹介します。

初心者の場合は、理解を深めるために記事内の例をローカルで実行することをお勧めします。

単純なサーバー + クライアントの例

tcp サーバー プログラムは次のとおりです:

var net = require('net');
 
var PORT = 3000;
var HOST = '127.0.0.1';
 
// tcp服务端
var server = net.createServer(function(socket){
  console.log('服务端:收到来自客户端的请求');
 
  socket.on('data', function(data){
    console.log('服务端:收到客户端数据,内容为{'+ data +'}');
 
    // 给客户端返回数据
    socket.write('你好,我是服务端');
  });
 
  socket.on('close', function(){
     console.log('服务端:客户端连接断开');
  });
});
server.listen(PORT, HOST, function(){
  console.log('服务端:开始监听来自客户端的请求');
});

tcp クライアントは次のとおりです:

var net = require('net');
 
var PORT = 3000;
var HOST = '127.0.0.1';
 
// tcp客户端
var client = net.createConnection(PORT, HOST);
 
client.on('connect', function(){
  console.log('客户端:已经与服务端建立连接');
});
 
client.on('data', function(data){
  console.log('客户端:收到服务端数据,内容为{'+ data +'}');
});
 
client.on('close', function(data){
  console.log('客户端:连接断开');
});
 
client.end('你好,我是客户端');

サーバーとクライアントのコードを実行すると、コンソールの出力は次のようになります:

サーバー:

サーバー: クライアントからのリクエストのリッスンを開始します
サーバー: クライアントからリクエストを受信します
サーバー: {こんにちは、私はクライアントです} という内容のクライアント データを受信します
サーバー: クライアント接続が切断されました

クライアント:

クライアント: サーバーとの接続が確立されました
クライアント: サーバー データを受信しました。内容は {こんにちは、サーバーです}
クライアント: 接続が切断されました

サーバー net.Server

server.address()
Returnsバインドされた IP アドレス、ポートなどのサーバーのアドレス情報。

console.log( server.address() );
// 输出如下 { port: 3000, family: 'IPv4', address: '127.0.0.1' }

server.close(callback])

サーバーを閉じて、新しいクライアントリクエストの受信を停止します。注意すべき点がいくつかあります:

処理中のクライアントリクエストの場合、サーバーは正式にシャットダウンする前に、リクエストが処理されるまで待機します (またはタイムアウトします)。

通常のシャットダウン中に、コールバックが実行され、close イベントがトリガーされます。

例外が閉じられると、コールバックも実行され、対応するエラーがパラメータとして渡されます。 (例:server.listen(port)が呼び出される前にserver.close()が呼び出されます)

以下は2つの具体的な例を通して比較され、結論が最初にリストされます

server.listen()が呼び出されています: 正常なシャットダウン、close イベントがトリガーされてからコールバックが実行され、エラー パラメーターが未定義

server.listen() が呼び出されない: 異常なシャットダウン、close イベントがトリガーされてからコールバックが実行され、エラーが発生特定のエラーメッセージ。 (エラーイベントがトリガーされないことに注意してください)

例 1: サーバーは正常にシャットダウンされます

var net = require('net');
var PORT = 3000;
var HOST = '127.0.0.1';
var noop = function(){};
 
// tcp服务端
var server = net.createServer(noop);
 
server.listen(PORT, HOST, function(){
 
  server.close(function(error){
    if(error){
      console.log( 'close回调:服务端异常:' + error.message );
    }else{
      console.log( 'close回调:服务端正常关闭' );
    }      
  }); 
});
 
server.on('close', function(){
  console.log( 'close事件:服务端关闭' );
});
 
server.on('error', function(error){
  console.log( 'error事件:服务端异常:' + error.message );
});

出力は次のとおりです:

close イベント: サーバーがシャットダウンされます
close コールバック: サーバーが正常にシャットダウンされます

例 2: サーバーが異常終了しました

コードは次のとおりです

var net = require('net');
var PORT = 3000;
var HOST = '127.0.0.1';
var noop = function(){};
 
// tcp服务端
var server = net.createServer(noop);
 
// 没有正式启动请求监听
// server.listen(PORT, HOST);
 
server.on('close', function(){
  console.log( 'close事件:服务端关闭' );
});
 
server.on('error', function(error){
  console.log( 'error事件:服务端异常:' + error.message );
});
 
server.close(function(error){
  if(error){
    console.log( 'close回调:服务端异常:' + error.message );
  }else{
    console.log( 'close回调:服务端正常关闭' );
  }      
});

出力は次のとおりです:

close イベント: サーバーが閉じています
close コールバック: サーバー例外: 実行されていません

server.ref() /server.unref()

ノード イベント ループを理解する 学生は、主にイベント ループからサーバーを追加または削除するために使用される API についてよく知っている必要があります。プロセス。

ネットを勉強している学生は特に注意する必要はありません、興味があれば自分で実験してみてください。

イベント listen/connection/close/error

listening: listen リクエストが正式に開始されたときにトリガーされる、server.listen() を呼び出します。

connection: 新しいリクエストが到着するとトリガーされ、パラメータはリクエストに関連するソケットです。

close: サーバーが閉じられるとトリガーされます。

error: すでに占有されているポートの監視など、サービス エラーが発生したときにトリガーされます。

いくつかのイベントは比較的単純です。ここでは接続の例を示します。

テスト結果から、新しいクライアント接続が生成されると net.createServer(callback) のコールバックが呼び出され、接続イベントに登録されたコールバック関数も呼び出されることがわかります。

実際、 net.createServer(callback) のコールバックは、ノードの内部実装の接続イベントのリスニング関数としても追加されています。興味があれば、ノードのソースコードを見てください。

var net = require('net');
var PORT = 3000;
var HOST = '127.0.0.1';
var noop = function(){};
 
// tcp服务端
var server = net.createServer(function(socket){
  socket.write('1. connection 触发\n');
});
 
server.on('connection', function(socket){
  socket.end('2. connection 触发\n');
});
 
server.listen(PORT, HOST);

次のコマンドで効果をテストします

curl http://127.0.0.1:3000

出力:

1. 接続トリガー
2. client net.Socket

この記事のクライアントの例はすでに示したので、ここに別の例を投稿します。 (注意: 厳密に言えば、net.Socket はクライアントと呼ばれるべきではありません。ここで説明するのに便利なだけです。)

公式ノードのドキュメントを見るだけでは、net.Socket は net.Server よりもはるかに複雑であるように感じますが、さらに多くのイベントとプロパティがあります。しかし実際には、net.Socket に関連する API、イベント、プロパティを分類してみると、それほど複雑ではないことがわかります。

詳しくは次のセクションをご覧ください。

var net = require('net');
 
var PORT = 3000;
var HOST = '127.0.0.1';
 
// tcp客户端
var client = net.createConnection(PORT, HOST);
 
client.on('connect', function(){
  console.log('客户端:已经与服务端建立连接');
});
 
client.on('data', function(data){
  console.log('客户端:收到服务端数据,内容为{'+ data +'}');
});
 
client.on('close', function(data){
  console.log('客户端:连接断开');
});
 
client.end('你好,我是客户端');

API と属性の分類

net.Socket の以下の API と属性を、読者が理解しやすいように用途に応じて大まかに分類します。ほとんどの API とプロパティは比較的単純なので、ドキュメントを読めばその機能がわかるため、ここでは詳しく説明しません。

接続関連

socket.connect(): さまざまなシナリオで使用される 3 つの異なるパラメーターがあります。

socket.setTimeout(): 接続タイムアウトの設定に使用されます。

socket.setKeepAlive(): 長い接続を設定するために使用されます。

socket.destroy()、socket.destroyed: エラーが発生したときにソケットを破棄し、このソケットで他の IO 操作が行われないようにするために使用されます。

データの読み書き関連

socket.write()、socket.end()、socket.pause()、socket.resume()、socket.setEncoding()、socket.setNoDelay()

データ属性関連

socket.bufferSize、socket.bytesRead、socket.bytesWritten

イベントループ関連

socket.ref()、socket.unref()

アドレス関連

socket.address()

socket.remoteAddress、 socket.remoteFamily、socket.remotePort

socket.localAddress/socket.localPort

イベント紹介

data: 相手側からのデータを受信したときにトリガーされます。

connect: 接続が確立されるとトリガーされます。

close: 接続が切断されたときにトリガーされます。通信エラーにより接続が切断された場合、パラメータはerrorとなります。

end: 接続の相手側が FIN パケットを送信するとトリガーされます (読者は HTTP がどのように切断されるかを確認できます)。デフォルト (allowHalfOpen == false) では、ソケットは自己破壊操作を完了します。ただし、allowHalfOpen を true に設定して、ソケットへのデータの書き込みを続行できるようにすることもできます。もちろん、最終的には手動でsocket.end()

errorを呼び出す必要があります。エラーが発生し、パラメータがerrorの場合にトリガーされます。 (公式ドキュメントでは基本的に一文で言及されていますが、間違いが多すぎる可能性を考慮すると、それは理解できます)

timeout: ソケットがタイムアウトしたため、接続を手動で閉じる必要があることをユーザーにプロンプ​​トします。

drain: 書き込みキャッシュが空のときにトリガーされます。 (説明するのは簡単ではありません。詳細については、以下の概要を参照してください)

lookup: ドメイン名解決が完了するとトリガーされます。


声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。