Reputation: 59
I'm trying to deserialize objects using generics but consumers can't pick them up even though they look completely fine.
private readonly IContainer _container = Ioc.GetContainer();
public async Task Test()
{
var command = new TestCommand();
var serializeObject = JsonConvert.SerializeObject(command);
var message = JsonConvert.DeserializeObject(serializeObject, command.GetType());
await Process(message);
await Process(command);
}
private async Task Process<TMessage>(TMessage message)
{
await _container.Resolve<IMessageDispatcher>().Dispatch(message);
}
public async Task Dispatch<TMessage>(TMessage message)
{
using (var scope = _lifetimeScope.BeginLifetimeScope())
{
var consumers = scope.Resolve<IEnumerable<IMessageConsumer<TMessage>>>().ToList();
if(consumers.Any() == false) throw new Exception($"No consumer for message {message.GetType().Name}");
foreach (var consumer in consumers)
{
await consumer.Consume(message, CancellationToken.None);
}
}
}
public interface IMessageConsumer<TMessage>
{
Task Consume(TMessage message, CancellationToken cancellationToken);
}
My message fails to find a consumer but the command variable does? Even though these objects look identical?
Upvotes: 0
Views: 469
Reputation: 9839
The variable
message below will be of compile time type object
and runtime type TMessage
. For generics type binding to work, the type needs to be possible to evaluate at compile time.
var message = JsonConvert.DeserializeObject(serializeObject, command.GetType());
You will either need to Deserialize to a more specific generic type:
var message = JsonConvert.DeserializeObject<TestCommand>(serializeObject);
or check the type at runtime in some way, for example:
if(message is TestCommand)
...
Upvotes: 1