I have a controller method which looks something like this:
[HttpPut, Route("cqs/command")]
public HttpResponseMessage Command([ValueProvider(typeof(HeaderValueProviderFactory))] string typeName)
{
object reply = null;
var code = HttpStatusCode.OK;
try
{
var cmdObject = DeserializeRequest(typeName);
var method = _commandMethod.MakeGenericMethod(type);
method.Invoke(this, new object[] { request });
}
catch (Exception exception)
{
code = HttpStatusCode.InternalServerError;
reply = exception;
}
var responseMsg = new HttpResponseMessage(code);
if (reply != null)
{
responseMsg.Headers.Add("X-TypeName", reply.GetType().AssemblyQualifiedName);
var replyJson = JsonConvert.SerializeObject(reply);
responseMsg.Content = new StringContent(replyJson, Encoding.UTF8, "application/json");
}
return responseMsg;
}
Which invokes the following method:
private void ExecuteCommand<T>(T command) where T : Command
{
var task = _commandBus.ExecuteAsync(command);
task.Wait(TimeSpan.FromSeconds(10));
}
The reason to that is that the _commandBus
only have a generic method which I need to invoke.
The problem is however that the ExecuteCommand
seems to deadlock at some times. I can't figure out why. The ICommandBus.ExecuteAsync
method will invoke other tasks using async/await, so it might be some kind of dead lock since WebApi uses a synchronization context? ( await vs Task.Wait - Deadlock? )
So if I understand it all correctly, there might be two solutions:
MethodInfo
? I'm lost when it comes to both solutions. Can anyone help?
Change ExecuteCommand<T>
so that it looks like this (I'm assuming your actual code will do something on a timeout):
private async Task ExecuteCommandAsync<T>(T command) where T : Command
{
var timeout = Task.Delay(TimeSpan.FromSeconds(10));
var task = _commandBus.ExecuteAsync(command);
await Task.WhenAny(task, timeout);
}
And make whatever calls it async Task
as well. Then, when you invoke the method, you can do this:
var task = method.Invoke(this, new object[] { request }) as Task;
await task;
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.