Polymorphic Request-Response in EasyNetQ

1.2k views Asked by At

I was wondering whether I could do polymorphic request-response in EasyNetQ, in a way similar to polymorphic publish-subscribe

Here is an example that uses Mike Hadlow's example with Cats and Dogs (check the link above) but with Animal being a class instead of an interface. I am trying to do something like:

Animal d = new Dog();
bus.Request<Animal, string>(d);

If on the receiving end I have the following,

bus.Respond<Dog, string>(...);

the request is never captured by the responder as it is sent as Animal instead of Dog.

The point here is that the request doesn't really care what it's sending (apart from the fact that it's sending an Animal) and the input comes from different parts of the system so I can't know the exact type in advance. There will be different listeners to respond to different subclasses (one listener for Dog and another one for Cat), so I can't just listen on Animal requests. TResponse is going to be the same regardless of TRequest.

Is there a way to do something equivalent to the polymorphic publish-subscribe? For example, something like:

bus.Request<string>(d.getType(), d);

Thanks a lot in advance!

EDIT: More info:

currently in my codebase I use the (extension) method bus.Publish(msg.GetType(), msg); in order to properly route the message to the correct listener based on the instance type of msg which I only know at runtime. This allows me to avoid code duplication like bus.Publish<Dog>(msg), bus.Publish<Cat>(msg); by providing the same function call (no code flow branches) as a way to publish different types of messages. I wanted to use a non-generic bus.Request() method too, and use it like bus.Request(msg.GetType(), string.GetType(), msg), to avoid calling this method multiple times like in bus.Request<Dog, string>(msg), bus.Request<Cat, string>(msg);. Hopefully I could avoid doing this: calling generic method at runtime.

2

There are 2 answers

0
Mike Hadlow On

The routing is by the combination of TRequest, TResponse, so you have to make sure they are the same on both the requester and the responder. Any subtype combination of TRequest, TResponse should serialise correctly.

0
altyne On

Tried using the dynamic keyword; before publishing the command.

  public void MethodName(IAnimal animal)
    {
        dynamic actualObject = animal;
        bus.Publish(actualObject);
    }