web-dev-qa-db-ja.com

Java NIO-メッセージの蓄積

私はJava NIOソケットを使用するアプリケーションを作成しています。これは3つのサーバーとクライアントのセットで構成されています。クライアントはサーバーと通信でき、サーバーはクライアントとクライアントと通信できます。他のサーバー。

サーバーからサーバー、およびクライアントからサーバーは、byte[]配列にシリアル化されるMessagesを送信します。各Messageの最初のバイトにはメッセージのサイズが含まれ、当然、各メッセージに含まれるバイト数が127 (2^8 -1)を超えないことが保証されています。サーバーとクライアントのメッセージの送信は、ループで動作していると考えることができます。

Message msg = new Message()
while (true) {
    sendMessage(msg, server or client)
    receiveMessage()
}

次に、実装はByteBufferを利用します。当然、他のJava NIO実装と同様に、各サーバーはselector.select()を実行し、次にSelectionKeysを取得してreading(handleRead()メソッド)、writeing(handleWrite()を呼び出す)、またはaccepting(handleAccept()を呼び出す)を処理する必要があります。すべてのhandleXXメソッドは有限数のステップを実行し、他のものを待つことをブロックしません。

特定のkeyのデータ(handleRead())を取得するとき、特定のマップにデータを格納するだけですMap<SelectionKey, List<byte[]>> readDataForKey;次に、リストを走査して、受信したすべてのメッセージを抽出します。

ただし、一部のhandleReadkeyを入力すると、処理待ちのメッセージが何千もあることに気づきました。なぜこれが当てはまるのか理解できませんか?私はhandleReadにいくつかのメッセージが表示されることを期待し、それだけです。

数千のメッセージが処理される前に蓄積されるという事実。どういう意味ですか?私のhandleReadまたはhandleWriteまたはNIO実装の他の一部に時間がかかりすぎて、基盤となるバッファがいっぱいになることを意味しますか?それは時々私が(〜10msの間)GCを取得し、その間にバッファがいっぱいになることを意味しますか?おそらくhandleReadで遅いコードがあり、そのためメッセージが蓄積されるということですか?

非常に多くのメッセージが蓄積するのは正常ですか?

4
insumity

コメントできないので、ここにコメントを追加します...

問題が発生しますか
1。単一のクライアントと単一のサーバー? 2サーバーのみ(つまり、クライアントなし)?

  1. 複数のクライアントを持つ単一サーバー?

  2. について:

それは私のhandleReadまたはhandleWriteまたはNIO実装の他の一部に時間がかかりすぎることを意味しますか

ログを追加して、そこに費やした時間を測定できます(または、さらに進めたい場合は、MATまたはVisualVMを使用できます。これは、GCが原因で遅れている場合にもヒントになる可能性があります)

0
user514949