On Wed, Oct 27, 2010 at 11:50 AM, Jun8 <[email protected]> wrote:
> I've Google for a day now and could not find full information on the
> following problem.
>
> I want to serialize protobuf messages in C++, send them to a JMS
> (using activemq-cpp API) and parse in my Java server. Based on what I
> found in my searches, here's my C++ function that serializes the
> message:
>
> /*
> * Serialize given protobuf message and send to Active MQ JMS using
> the producer.
> */
> void MessageProducer::send( const diva::messaging::Message&
> proto_mesg )
> {
> using namespace google::protobuf::io;
>
> long bufLength = proto_mesg.ByteSize() +
> CodedOutputStream::VarintSize32( proto_mesg.ByteSize() );
> unsigned char buf[bufLength];
>
> ZeroCopyOutputStream* raw_output = new ArrayOutputStream( buf,
> bufLength );
> CodedOutputStream* coded_output = new CodedOutputStream(raw_output);
>
> // Prepend the message size to wire message.
> coded_output->WriteVarint32( proto_mesg.ByteSize() );
>
You're writing the message size as a prefix to the message data here...
>
> proto_mesg.SerializeToCodedStream(coded_output);
>
> // Create an ACtive JMS message and insert task & module information
> in header.
> cms::BytesMessage* message = m_session->createBytesMessage();
>
> // Write serialized protobuf message to the JMS message and send.
> message->writeBytes( buf, 0, bufLength );
> m_producer->send( message );
>
> delete message;
> delete coded_output;
> delete raw_output;
> }
>
> And here's the part in Java that parses teh received messages from
> JMS:
>
> // Create a byte array for received message.
> BytesMessage receivedMessage =
> (BytesMessage)received_message;
> logger.info("received message in NAC");
> byte[] mesg_bytes = new
> byte[(int)receivedMessage.getBodyLength()];
> int num_read =
> receivedMessage.readBytes(mesg_bytes);
>
Presumably these bytes contain all the data that you wrote out, including
the size prefix...
> if ( num_read != receivedMessage.getBodyLength() ) {
> throw new Exception("Error reading message
> into byte array");
> }
>
> // Create registry for all possible DIVA messages.
> ExtensionRegistry er =
> ExtensionRegistry.newInstance();
> DivaBase.registerAllExtensions(er);
>
> // Parse the received message.
> diva.messaging.DivaBase.Message m =
> diva.messaging.DivaBase.Message.parseFrom( mesg_bytes, er );
>
...but parseFrom expects only the message data, not a message length prefix.
I'd just remove the WriteVarint32(proto_mesg.ByteSize()) call, since you are
using a transport mechanism that has its own means for delimiting messages.
> Currently, I get
>
> Problem parsing message received in NAC:
> com.google.protobuf.InvalidProtocolBufferException: Protocol message
> end-group tag did not match expected tag.
> Problem parsing message received in NAC: java.lang.ClassCastException:
> org.apache.activemq.command.ActiveMQTextMessage cannot be cast to
> javax.jms.BytesMessage
>
> errors for each message and cannot see what I'm doing wrong.
>
> Thanks for any comments on the code and/or pointers you might provide.
>
> --
> You received this message because you are subscribed to the Google Groups
> "Protocol Buffers" group.
> To post to this group, send email to [email protected].
> To unsubscribe from this group, send email to
> [email protected]<protobuf%[email protected]>
> .
> For more options, visit this group at
> http://groups.google.com/group/protobuf?hl=en.
>
>
--
You received this message because you are subscribed to the Google Groups
"Protocol Buffers" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/protobuf?hl=en.