我有一个控制器方法,如下所示:
[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;
}
调用以下方法:
private void ExecuteCommand<T>(T command) where T : Command
{
var task = _commandBus.ExecuteAsync(command);
task.Wait(TimeSpan.FromSeconds(10));
}
原因是_commandBus
只有一个我需要调用的泛型方法。
然而问题是ExecuteCommand
似乎在某些时候陷入僵局。我无法弄清楚为什么。 ICommandBus.ExecuteAsync
方法将使用async / await调用其他任务,因此它可能是某种死锁,因为WebApi使用同步上下文? (await vs Task.Wait - Deadlock?)
因此,如果我理解正确,可能有两种解决方案:
MethodInfo
?两种解决方案都让我迷失了方向。有人可以帮忙吗?
答案 0 :(得分:4)
更改ExecuteCommand<T>
,使其看起来像这样(我假设你的实际代码会在超时时做某事):
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);
}
并进行任何调用async Task
。然后,当您调用该方法时,您可以执行以下操作:
var task = method.Invoke(this, new object[] { request }) as Task;
await task;