2011-02-02 10 views
1

私はXMPPサーバーに接続するコメットサーバーを設定しています。ここではそれがダウンした方法は次のとおりです。ストリームの早すぎる終了を与えるJavaソケット

クライアントは、彗星サーバーに接続し、他のものの間で、ソケット接続がオープンさ:ソケットからのデータを待機するスレッドが開始され

try { 
     radio = new Socket("server", 5222); 
     out = new PrintWriter(radio.getOutputStream(), true); 
     in = new BufferedReader(new InputStreamReader(radio.getInputStream())); 
    } catch (UnknownHostException e) { 
     System.out.println("Unknown host: "+e); 
     error = e.toString(); 
    } catch(IOException e) { 
     System.out.println("IO error: "+e); 
     error = e.toString(); 
    } 

次に、 :

public void run() { 
     System.out.println("Thread started."); 
     String data; 
     String error; 
     Client remote; 
     Client client; 
     while(!done) { 
      data = this.output(); 
      remote = bayeux.getClient(remoteId); 
      client = bayeux.getClient(clientId); 
      if(data!=null) { 
       Map<String, Object> packet = new HashMap<String, Object>(); 
       packet.put("xml", data); 
       remote.deliver(client, "/radio/from", packet, null); 
      } 
      error = this.error(); 
      if(error!=null) { 
       Map<String, Object> packet = new HashMap<String, Object>(); 
       packet.put("details", error); 
       remote.deliver(client, "/radio/error", packet, null); 
      } 
      /* try { 
       Thread.sleep(500); 
      } 
      catch (InterruptedException e) { 
       System.out.println("Interrupted!"); } */ 
     } 

     try { 
      in.close(); 
      out.close(); 
      radio.close(); 
     } catch(IOException e) { 
      System.out.println("Error disconnecting: "+e); 
      error = e.toString(); 
     } 
     System.out.println("Thread stopped."); 
    } 

    public String output() { 
     try { 
      String data = in.readLine(); 
      System.out.println("From: "+data); 
      if(data==null) { 
       System.out.println("End of stream!"); 
       try { 
        Thread.currentThread().sleep(1000); 
       } catch (InterruptedException e) { 
        e.printStackTrace(); 
       } 
       //error = "End of stream."; 
       //this.disconnect(); 
      } 
      return data; 
     } catch (IOException e) { 
      error = e.toString(); 
      System.out.println("IO error! "+e); 
     } 
     return null; 
    } 

クライアントから受信した任意の入力は、XMPPサーバーに転送されます。

public void input(String xml) { 
     System.out.println("To: "+xml); 
     out.println(xml); 
    } 

問題がどこに来るのですか。クライアントは接続を開き、適切なXMLをXMPPサーバーに送信してストリームを開始します。 in.readLine();は、サーバーからの応答が受信されるまでハングします。それが受信されるとすぐに、in.readLine();は何度も何度もnullを返すようになります。これは起こらないはずです。データを受信するまでハングするはずです。サーバーが閉鎖された可能性は低いですが、</stream:stream>にXMPPストリームの終わりを知らせるために送信していません。何が問題になる可能性があるかについての任意のアイデア?

ありがとうございました!

+0

サーバが接続を閉じている可能性は低いと思いますが、安全であることを確認するために、readLine()がnullを返した後にradio.isConnected()が返すものを実際に確認しましたか? –

+0

BOSH(http://xmpp.org/extensions/xep-0206.html)を使用しただけでなく、クライアント、サーバー、またはその両方のために既製のものを使用している可能性があります。 。 –

答えて

0

XMPP接続では、不完全なスタンザ、または複数のスタンザを1回の読み取りで提供できることに注意してください。あなたのCOMET接続が、あなたが渡しているものが正しい形式のXMLであることを期待しているなら、問題があるでしょう。また、XMPPは改行文字で終了していないので、なぜreadLine()がひどく役に立つと思うのか分かりません。

次に、同じスレッド上の2つの異なるソケットで同期I/Oを実行していますか?デッドロックのレシピのように聞こえる。この道を踏み出すことを頼んだら(ちょうどBOSHを使用するのではなく)、私はあなたの睡眠ハックの代わりにNIOを使うことを強く勧めます。

+0

現代のLinuxシステム(私はPOSIXが言及されたと思う)のどこかで、スレッドソケットは実際にはNIOより効率的であるとはいえ、私はNIOに打ち明けます。しかし、私はいくつかのコードを書くことは良いと思うでしょう。コードはちょっとしたコードを吸っています –

+0

そして、readLineの呼び出しがXMLで役に立たないというのは、愚かなことでした。 –