Javaでクライアントを作成しましたが、C#のサーバーにデータを送信したいだけです。
問題は、たとえばhelloなどのクライアントに書き込むと、最初の文字しか表示されないことです。バイト配列には要素が1つだけあります。
私のサーバーではJAVAのサーバーがすべて正常に動作するため、JAVAのクライアントは正常に動作するため、サーバー側に問題があると思います。
誰か問題がありますか?
前もって感謝します。
あなたはTCPについて間違った方法で考えています、あなたは単に一度「受信」して1つの「送信」の結果を得るのではありません。
TCPは「ストリーミング」プロトコルであり、自動的に「パケット」に分離されることはありません。1回の受信で2回の送信のデータを取得することもできます。
一般的なパターンは、1つのメッセージの前にその長さを付けることです。これにより、要求されたバイト数を取得するまで、receiveを呼び出すことができます。バッファにデータがない場合にReceiveをすぐに返すには、ソケットを非ブロッキングに設定します。
これで、ローカルネットワークに遅延がほとんどないため、提供されたコードはどちらの方法でも機能するはずです。Javaパーツが蒸気をバッファリングするかどうかを確認しましたか/手動でフラッシュできますか?
Damon Gantが言ったように、TCPはストリーミングプロトコルです。独自のプロトコルを作成することをお勧めします。文字列は送信しません。些細なことをしているのなら、これが本当に最善の方法です。
通常、プロトコルヘッダーには、マジックナンバー、チェックサム、パケット本体の長さ(バイト単位)、およびプロトコルバージョンを含めます。マジックナンバーを使用すると、ストリーム内のパケットの描写が簡単になります(カスタムプロトコルストリームのデバッグに非常に役立ちます)。チェックサムがあると、正しく解析していることを確認できます。TCPプロトコルにはすでにチェックサムがあるため、チェックサムはTCPを介した整合性にはあまり役立ちません。パケット本体の長さは、パケットのすべてのバイトがあることを検出するのに役立ちます。プロトコルバージョンは、パケット本文のバイトを解釈する方法を知るのに役立ちます。
データを受信したら、すべてのバイトを別のバッファーに配置し、プロトコルヘッダーをスキャンします。ヘッダーを解析できる場合は、パケットのバイトがすべて存在することを確認してください。その場合は、パケットを解析します。不完全なパケットが見つかるか、バッファが空になるまで、このプロセスを繰り返します。
送信するパケットごとに、クラスを作成します。パケットを送信する場合は、適切なクラスを作成してシリアル化し、そのクラスのバイトの前にプロトコルヘッダーを追加します。
Javaのシリアライザーを使用することもできますが、単一のサーバーに多数のクライアントが接続している場合は、サーバーにJavaを使用したくない可能性があります。これにより、Javaシリアライザーを別の言語で実装する必要があるため、事態が困難になります。このため、通常は、パケットを手動でバイトに変換するか(面倒ですが単純です)、リフレクションを使用して独自のシリアライザーを作成する方が適切です。より大きなプロジェクトには後者をお勧めします。
リスナーが正常に動作するため、問題はおそらくJava側にあります。テストアプリケーションにリスナーコードをコピーして貼り付けました。別のテストアプリケーションを作成してハローワードを送信し、それを完全に聞いたよりも。
public static void sender()
{
TcpClient client = new TcpClient();
IPEndPoint serverEndPoint = new IPEndPoint(IPAddress.Parse("192.168.2.236"), 30000);
client.Connect(serverEndPoint);
NetworkStream clientStream = client.GetStream();
ASCIIEncoding encoder = new ASCIIEncoding();
byte[] buffer = encoder.GetBytes("Hello Server!");
clientStream.Write(buffer, 0, buffer.Length);
clientStream.Flush();
}
Connection accepted from 192.168.2.236:22811
Recieved...
Hello Server!
ところで、これはより良いリスナーかもしれません。
public void listener()
{
TcpListener tcpListener = new TcpListener(IPAddress.Any, 30000);
tcpListener.Start();
TcpClient tcpClient = tcpListener.AcceptTcpClient();
NetworkStream clientStream = tcpClient.GetStream();
byte[] message = new byte[4096];
int bytesRead;
while (true)
{
bytesRead = 0;
try
{
//blocks until a client sends a message
bytesRead = clientStream.Read(message, 0, 4096);
}
catch
{
//a socket error has occured
break;
}
if (bytesRead == 0)
{
//the client has disconnected from the server
break;
}
//message has successfully been received
ASCIIEncoding encoder = new ASCIIEncoding();
Console.Write(encoder.GetString(message, 0, bytesRead));
}
tcpClient.Close();
}