Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to receive GenericMessage with Object payload instead of string from MessageCollector

I try to test message sending and receiving via spring-cloud-stream using MessageCollector.

When i am using native java serialization for stream cloud all works fine, but when i change serialization to json, MessageCollector returns me GenericMessage with string payload instead of SomeObject payload.

Configuration is

  cloud.stream.default.contentType=application/json 

Test case:

    Message outMsg = new GenericMessage<SomeObject>(new SomeObject(1));
    someChannel.send(outMsg);
    GenericMessage<SomeObject> inMsg = (GenericMessage<SomeObject>) messageCollector.forChannel(someChannel).poll();

    Assert.assertTrue(inMsg.getPayload() instanceof SomeObject);

As a result Assertions is false. inMsg contains string payload (the string contains valid json representation of SomeObject).

And my question is: How can i receive GenericMessage with SomeObject payload from MessageCollector?

production environment works fine without explicitly mapping to SomeObject.

like image 912
Bukharov Sergey Avatar asked Sep 27 '17 17:09

Bukharov Sergey


People also ask

What is the payload of a message object?

Message is an object and the payload property contains the message data which is binary data. To access the message from you main script requires a little more work as the on_message callback is asynchronous and also usually run in a separate thread.

How do I work with the message payload in EJB?

You can work with the message payload in a pre-existing mediation handler, and transcode the message payload from one message format to another. Create or open a mediation handler in an EJB project. For more information, see Writing a mediation handler .

Why do service bus messages have an empty payload?

Occasionally, that metadata alone is sufficient to carry the information that the sender wants to communicate to receivers, and the payload remains empty. The object model of the official Service Bus clients for .NET and Java reflect the abstract Service Bus message structure, which is mapped to and from the wire protocols Service Bus supports.

How do I work with the contents of a message?

To work with the contents of a message, use the SIMessage and SIMessageContext APIs. Additionally, use SIMediationSession to provide your mediation with access to the service integration bus, to send and receive messages. For more information, see: To work with specific fields within a message, use Service Data Objects (SDO) Version 1 data graphs.


1 Answers

But that's correct. The channel is for output to the messaging broker. So, we have just serialized your payload into the JSON and it is ready to be delivered. That's why you use everything OK in production because you have a messaging broker in between and the proper deserializer for the input on another side. This messageCollector approach is exactly for assertion what we are going to send to the broker, so adding some additional deserialization functionality is out of scope this utility.

Only what I may suggest you is to use Jackson ObjectMapper directly on the payload after receiving inMsg from the collector:

Message outMsg = new GenericMessage<SomeObject>(new SomeObject(1));
someChannel.send(outMsg);
GenericMessage<String> inMsg = (GenericMessage<String>) messageCollector.forChannel(someChannel).poll();
SomeObject someObject = new ObjectMapper().readValue(inMsg.getPayload(), SomeObject.class);

Assert.assertTrue(someObject instanceof SomeObject);
like image 77
Artem Bilan Avatar answered Oct 06 '22 00:10

Artem Bilan