2012-03-31 8 views
-3

すべて 私はチャットルームで使用するnettyをサーバー用に作成します。クライアント用にフラッシュします。プロトコルでは、 "\ r \ n"の末尾にjson文字列を使用します.3つのハンドラ "MessageDecoder"、 "MessageHandler"、 "MessageEncoder"を記述します。フラッシュクライアントを使用してメッセージを送信します。しかし、私は次のエラーを取得します。チャットルームにnettyを使用する方法。フラッシュクライアント

java.lang.IllegalStateException: decode() method must read at least one byte if it returned a frame (caused by: class com.mbaobao.chatroom.socket.handlers.MessageDecoder) 
at org.jboss.netty.handler.codec.frame.FrameDecoder.callDecode(FrameDecoder.java:294) 
at org.jboss.netty.handler.codec.frame.FrameDecoder.messageReceived(FrameDecoder.java:216) 
at org.jboss.netty.channel.Channels.fireMessageReceived(Channels.java:274) 
at org.jboss.netty.channel.Channels.fireMessageReceived(Channels.java:261) 
at org.jboss.netty.channel.socket.nio.NioWorker.read(NioWorker.java:351) 
at org.jboss.netty.channel.socket.nio.NioWorker.processSelectedKeys(NioWorker.java:282) 
at org.jboss.netty.channel.socket.nio.NioWorker.run(NioWorker.java:202) 
at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(ThreadPoolExecutor.java:886) 
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:908) 
at java.lang.Thread.run(Thread.java:619) 

私はソケットプログラムを書くことはありません

protected Object decode(ChannelHandlerContext ctx, Channel channel, ChannelBuffer buffer) 
                          throws Exception { 
    logger.debug("message decode"); 
    if (buffer.readableBytes() < 4) { 
     return null; 
    } 

    StringBuffer stringBuffer = new StringBuffer(); 
    String json = null; 
    for (int i = 0; i < buffer.capacity(); i++) { 
     char c = (char) buffer.getByte(i); 
     logger.info(c); 
     stringBuffer.append(c); 
     if (c == 13 || c == 10) { 
      json = stringBuffer.toString(); 
      break; 
     } 
    } 
    ChatData chatData = JSON.parseObject(json, ChatData.class); 

    return chatData; 

} 

MessageDecoder。 mutilスレッド管理ソケットを使用してください。しかし、私はそれがひどいと思う。だから私はネットを使用します。私はchatroomのためにそれを使用する方法を知らない。

誰でも私にお勧めしますか?

+0

MessageDecoderクラスの完全なソースを提供してください。 – Vincent

答えて

1

受信したChannelBufferのリーダーインデックスを、読み込んだメッセージが終了する位置に配置してください。 @see ChannelBuffer.readerIndex(int)これは、ChannelBuffer.getByte(int)/ .getBytes()がリーダーのインデックスを変更しないためです。

あなたがそうしないと、Nettyはあなたがバッファから何バイトも読まなかったとみなします(もしあれば、パイプラインの次のハンドラにそれを渡します)。ちょうど遭遇したexcetionを投げます。

0

Netty API内の の文字列を処理するための組み込み機能を使用することをお勧めします。

  • DelimiterBasedFrameDecoder
  • StringDecoder
  • StringEncoder

私は、適切なドキュメントのページへのリンクを作成しようとしたが、stackoverflowのは、以上の2つのリンクを掲示から 私を防ぎます。

Netty SecureChat Exampleは、 チャンネルパイプラインでこれらのハンドラを使用する方法を明確に説明しています。

+0

個。それは最善の方法です。 – fred

1

これを修正するには、buffer.getByte(..)をbuffer.readByte()に置き換えてください。

関連する問題