2013-02-25 80 views
2

我正在製作一個.NET應用程序,它應該通過套接字與Java應用程序進行通信。 這裏是.NET代碼:C#<-> Java套接字通信

string str = " MSG1234"; 
TcpClient client = new TcpClient(); 
client.Connect("127.0.0.1", 8080); 
byte[] msg = Encoding.UTF8.GetBytes(str); 
client.Client.Send(msg); 
StreamWriter sw = new StreamWriter(client.GetStream()); 
StreamReader sr = new StreamReader(client.GetStream()); 
while (true) 
{ 
    Console.WriteLine(sr.Read()); 
} 

的問題是,Java應用程序將不會發送答案。該應用程序是一個第三方的軟件,我不能改變它,但是我已經下載了一個反編譯器,發現在Java類相關的代碼:

try { 
    while (this.is.available() <= 0); 
    body = new byte[this.is.available()]; 
    this.is.readFully(body); 
    System.out.println("Message received"); 
} catch (Exception e) { 
    System.out.println("Error: " + body); 
} 

「是」,在這種情況下是DataInputStream類。這是發生了什麼: 1.我創建一個套接字和發送郵件 2.我等待迴應,什麼都不會發生 3.我手動關閉應用程序 - 它會導致插座到期 4.突然出現在整個郵件Java應用程序的日誌。這意味着發生了異常,並且實際上有一些東西在體內。

你能指出我錯誤的地方嗎?我相信this.is.readFully(身體)線不應該在那裏,但我不確定。也許我應該手動從C#代碼發送一個EOF,但我無法知道如何。

另外,與代碼小問題是,該消息的前兩個字符被剝奪,這就是爲什麼我已經包括在實際消息的前面的兩個空間。

預先感謝您。

編輯

所以我試圖填補一些隨機數據插口和我終於得到了答案:

for (int i = 0; i < 600; i++) 
{ 
    sw.Write("some long random string"); 
    sw.Flush(); 
} 

這不是一個很好的解決方案,但因爲消息我發送必須是確切的。 然後我試圖通過soc.Disconnect(false);發送相關數據後關閉套接字,這會導致Java應用程序的日誌填充正確的調試信息。 有什麼方法可以將EOL發送到套接字,這樣Java應用程序就會停止監聽並開始發送數據? 謝謝。

EDIT 2 我試圖創建一個Java客戶端連接到服務器,同樣的事情發生了。

然後我創建了一個虛擬服務器監聽同一端口的Java應用程序,我也連接上,它也表現方式與Java應用程序應該和它的工作。

現在我覺得我唯一的機會是發送EOT或EOF命令到流中,但我不知道如何在.NET上執行它,我也無法在Internet上找到答案。

+0

我認爲這個問題可能是假設在一面上寫入的一個字節會瞬間出現在另一面。強烈建議:閱讀[Beej的套接字編程指南](http://beejjus.com/guide/bgnet/output/html/multipage/) – paulsm4 2013-02-25 23:22:40

+1

您是否嘗試過在發送後調用Flush方法?如果您發送的數據塊很小,我認爲您可能會與Nagle的算法發生衝突。 – 2013-02-25 23:25:33

+0

如果其他應用程序不回答您的問題,那麼您可能會做錯某些事情。應用程序使用什麼協議,您是否發送了有效的消息?你是如何決定發送什麼的,你如何表示你已經發送了? – CodeCaster 2013-02-25 23:40:50

回答

1

如果Java應用程序是由第三方,有機會,你正在做的事情是錯誤的。 DataInputStream.readFully(byte[])函數會阻塞應用程序,直到它讀取了字節數組可以容納的字節數爲止,因此您擁有的代碼片段來自讀取操作。

我也看到您使用Socket.Send(byte[])功能與Java應用程序通信,我建議你使用的東西更高的水平一樣的StreamWriter或的BinaryWriter,更多像這樣少:

StreamWriter = new BinaryWriter(client.GetStream()); 
StreamWriter.Write(msg); 
StreamWriter.Flush(); 
+0

我試過StreamWriter WriteLine或寫入和沖洗後,它也沒有幫助。我試過的是這樣的: for(int i = 0; i <600; i ++) sw.Write(「some long random string」); sw.Flush(); } 它引發服務器的響應。我必須填寫整個緩衝區或其他東西。這真的很奇怪。 – user2109153 2013-02-26 06:05:02

0

你可以嘗試刷新StreamWriter(所以它寫入其緩衝區的流對象)和實際NetworkStream你從client.GetStream()(所以它發送一個數據包,儘管數據包還沒有「全」呢)?

NetworkStream ns = client.GetStream(); 
StreamWriter sw = new StreamWriter(ns); 
StreamReader sr = new StreamReader(ns); 
// ... 
sw.Flush(); 
ns.Flush(); 

最有可能的是,你沒有沖洗你需要衝洗的所有東西。您是否嘗試過使用例如wireshark - 數據實際上是out?如果沒有,問題出在你的.NET代碼中。

+0

我已經嘗試了rawcap,因爲它發生在回送上,並且是的,數據實際上正在正確傳輸。我也嘗試了NetworkStream刷新,並沒有幫助。 – user2109153 2013-02-26 10:58:46

+0

然後嘗試接下來編寫自定義Java偵聽器,並查看是否有效。 – 2013-02-26 13:57:56

+0

我已經完成了。首先,我爲服務器創建了一個Java客戶端,它顯示了同樣的問題。然後,我創建了一個Java服務器,並使用相同的.NET代碼進行連接,並且它正在工作。 – user2109153 2013-02-26 16:49:16