Google protocol Buffer Codec

"Trustin Lee (이희승)" trustin at gmail.com
Fri Jan 8 17:30:17 EST 2010


Hi Tom,

ritom wrote:
> Jannick,
> Thanks for taking time to write the sample for me. 
> 
> Trustin,
> You always amaze me I only started using netty because you were on the team.
> I could now see Mina on the small corner of the world down the road. I only
> wish we could have some one take initiative to upgrade quickfix/j to the
> netty implementation with Java 1.5.

Hey, thank you!  Please keep sending your feed back - it will make Netty
even better. :)

Out of curiosity, does QuickFIX/J team want to migrate to Netty?  If so,
I would be more than happy to assist the effort.

Cheers,
Trustin

> I took Jannick's advice and wrote a RequestProtocol and ResponseProtocol
> request is for sending messages to server which consist of multiple objects
> and Response to get the response back from server and it works like charm.
> 
> Thanks a lot.
> 
> 
> Thingfish wrote:
>> Hi again :)
>>
>> Made a quick example of doing the same thing Trustin just demonstrated, by
>> using the protobuf union type/wrapper trick. Should note that protobuf
>> does
>> not (and can not be made to) generate any code to provide easy handling
>> for
>> this approach, so its a bit cumbersome. Okay, to the example, lets say you
>> want to send the messages Foo and Bar. The trick is to define a "union
>> type"
>> or a sort of a container that you put your actual message inside:
>>
>> message Foo{
>> optional string some_field = 1;
>> }
>>
>> message Bar{
>> optional string some_other_field = 1;
>> }
>>
>>
>> message MessageWrapper{
>> enum Type {FOO = 1; BAR = 2; }
>> required Type type = 1;
>>
>> optional Foo foo = 2;
>> optional Bar bar = 3;
>> }
>>
>>
>> So when you want to send a Foo message, you construct the Foo message as
>> usual, and then wrap it inside a MessageWrapper mesage. You then have to
>> adhere to the convention, that always
>>  1) Set just one of the optional fields
>>  2) Set the Type field to the enum representing that field.
>>
>> For example to send Foo:
>>
>> Foo fooMsg =
>> Foo.newBuilder().
>> setSomeField("SomeValue").
>> build();
>>  MessageWrapper wrapperMsg =
>> MessageWrapper.newBuilder().
>> setType(Type.FOO).
>> setFoo(fooMsg).
>> build();
>>
>> someChannel.write(wrapperMsg);
>>
>> Note: It's important that you always remember to wrap the messages you
>> send,
>> otherwise you get a very strange behavior.
>>
>> You then setup your pipeline with a handler to receive this wrapper
>> message:
>> p.addLast("protobufDecoder", new
>> ProtobufDecoder(MessageWrapper.getDefaultInstance()));
>>
>> and in your application specific handler do something like:
>>
>> public void messageReceived(ChannelHandlerContext ctx, MessageEvent e) {
>> MessageWrapper wrapperMsg = (MessageWrapper)e.getMessage();
>>  switch (wrapperMsg.getType()){
>>  case FOO:
>> Foo fooMsg = wrapperMsg.getFoo();
>> //Handle a Foo message
>> break;
>>  case BAR:
>> Bar barMsg = wrapperMsg.getBar();
>> //Handle a Bar message
>> break;
>>  default:
>> throw new IllegalArgumentException("..... Type: " + wrapperMsg.getType());
>>  }
>>  }
>>
>>
>> Hope this helps. Will see if I can find time to put a complete sample
>> together.
>>
>> Regards
>> Jannick
>>
>>
>> 2010/1/7 "Trustin Lee (이희승)" <trustin at gmail.com>
>>
>>> Tom,
>>>
>>> I would write a custom decoder instead of using ProtobufDecoder in such
>>> a case; something like the following, which prepends the message type
>>> and the message length field:
>>>
>>> public class MyProtobufDecoder extends FrameDecoder {
>>>
>>>  boolean waitingForHeader;
>>>  int msgType;
>>>  int msgLength;
>>>
>>>  Message prototypeA =
>>>      MessageA.getDefaultInstance().getDefaultInstanceForType();
>>>  Message prototypeB =
>>>      MessageB.getDefaultInstance().getDefaultInstanceForType();
>>>  Message prototypeC =
>>>      MessageC.getDefaultInstance().getDefaultInstanceForType();
>>>
>>>  @Override
>>>  protected Object decode(ctx, msg) {
>>>    ChannelBuffer buf = (ChannelBuffer) msg;
>>>    if (waitingForHeader) {
>>>      // Wait until at least 5 bytes are received in the buffer
>>>      if (buf.readableBytes() < 5) {
>>>        return null;
>>>      }
>>>      msgType = buf.readByte();
>>>      msgLength = buf.readInt();
>>>      waitingForHeader = false;
>>>    }
>>>
>>>    if (!waitingForHeader) {
>>>      ChannelBuffer pbmsg = buf.readBytes(msgLength);
>>>      Message prototype;
>>>      switch (msgType) {
>>>      case 0: prototype = prototypeA; break;
>>>      case 1: prototype = prototypeB; break;
>>>      case 2: prototype = prototypeC; break;
>>>
>>>      // This is a user defined exception.
>>>      // Handle this exception in exceptionCaught()
>>>      // in your terminal handler
>>>      default: throw new ProtocolViolationException();
>>>      }
>>>
>>>      try {
>>>        return prototype.newBuilderForType().mergeFrom(
>>>                    new ChannelBufferInputStream(pbmsg)).build();
>>>      } finally {
>>>        waitingForHeader = true;
>>>      }
>>>    }
>>>  }
>>> }
>>>
>>> You will have to learn how to write a decoder eventually to customize
>>> the protocol to meet your need.  The user guide and the factorial
>>> example is a good starting point.
>>>
>>> However, I would still recommend the solution Jannick provided.
>>>
>>> HTH,
>>> Trustin
>>>
>>> ritom wrote:
>>>> Thanks for very much for the insight. If you do have multiple messages
>>> how to
>>>> you handle them in the decoder. In the example looks like everything is
>>>> based on one object what if you have two message type Foo and Bar
>>> instead
>>> of
>>>> LocalTimeProtocol alone. Can you please give a example. Thanks a lot in
>>>> advance.
>>>>
>>>>   p.addLast("protobufDecoder", new
>>>> ProtobufDecoder(LocalTimeProtocol.Locations.getDefaultInstance()));
>>>>
>>>>
>>>> Thingfish wrote:
>>>>> Hi
>>>>>
>>>>> The easiest solution is to wrap all your messages in a 'union type' as
>>>>> described in this protobuf tutorial:
>>>>>
>>> http://code.google.com/intl/da-DK/apis/protocolbuffers/docs/techniques.html#union
>>>>> Alternatively you will have to manually prepend some kind of command
>>> id
>>> to
>>>>> identity the kind of protobuf message being sent, but unlikely to be
>>> worth
>>>>> the trouble.
>>>>>
>>>>>
>>>>> Regards
>>>>> Jannick
>>>>> <
>>> http://code.google.com/intl/da-DK/apis/protocolbuffers/docs/techniques.html#union
>>>>> 2010/1/2 ritom <ritom at hotmail.com>
>>>>>
>>>>>> Can somebody please help me understand the google protobuf support
>>> within
>>>>>> Netty.
>>>>>> In the LocalTimeServerPipelineFactory example we have
>>>>>>
>>>>>> p.addLast("protobufDecoder", new
>>>>>> ProtobufDecoder(LocalTimeProtocol.Locations.getDefaultInstance()));
>>>>>>
>>>>>> That would mean we can now receive the Locations message in
>>>>>> TimeServerHandler.
>>>>>>
>>>>>>  public void messageReceived(ChannelHandlerContext ctx, MessageEvent
>>> e)
>>> {
>>>>>>        Locations locations = (Locations) e.getMessage();
>>>>>>
>>>>>> How would I implement support for multiple incoming message types
>>> where
>>>>>> you
>>>>>> might be receiving different types of request from the client. Lets
>>> say
>>>>>> you
>>>>>> are receiving Logon first then BalanceRequest, TransferRequest and so
>>> on.
>>>>>> Also server will reply with multiple Message Types depending on the
>>>>>> request.
>>>>>> Can somebody please please help.
>>>>>>
>>>>>> Tom
>>>>>> --
>>>>>> View this message in context:
>>>>>>
>>> http://n2.nabble.com/Google-protocol-Buffer-Codec-tp4241485p4241485.html
>>>>>> Sent from the Netty User Group mailing list archive at Nabble.com.
>>>>>> _______________________________________________
>>>>>> netty-users mailing list
>>>>>> netty-users at lists.jboss.org
>>>>>> https://lists.jboss.org/mailman/listinfo/netty-users
>>>>>>
>>>>> _______________________________________________
>>>>> netty-users mailing list
>>>>> netty-users at lists.jboss.org
>>>>> https://lists.jboss.org/mailman/listinfo/netty-users
>>>>>
>>>>>
>>> --
>>> what we call human nature in actuality is human habit
>>> http://gleamynode.net/
>>>
>>>
>>>
>>> _______________________________________________
>>> netty-users mailing list
>>> netty-users at lists.jboss.org
>>> https://lists.jboss.org/mailman/listinfo/netty-users
>>>
>>>
>> _______________________________________________
>> netty-users mailing list
>> netty-users at lists.jboss.org
>> https://lists.jboss.org/mailman/listinfo/netty-users
>>
>>
> 

-- 
what we call human nature in actuality is human habit
http://gleamynode.net/


-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 260 bytes
Desc: OpenPGP digital signature
Url : http://lists.jboss.org/pipermail/netty-users/attachments/20100109/aa93eee4/attachment.bin 


More information about the netty-users mailing list