[英]Where could an UnobservedTaskException be occurring?
I have a WPF client that accesses a WCF service. 我有一个访问WCF服务的WPF客户端。 The service runs along very nicely using a timer to execute some processing every n minutes. 该服务使用计时器很好地运行,每n分钟执行一次处理。 The client UI has a ProcessNow
command, which overrides the service's timer, and performs the processing immediately. 客户端UI具有ProcessNow
命令,该命令将覆盖服务的计时器,并立即执行处理。 I am trying to sort out a usability problem where clicking the Process Now
button more than once, while processing is still busy, results in a "connection closed" exception, from the WCF comms channel I assume, followed by a UnobservedTaskException
. 我正在尝试解决一个可用性问题,其中在处理仍很忙的情况下多次单击“ Process Now
按钮时,会从我假设的WCF通讯通道中导致“连接已关闭”异常,然后出现UnobservedTaskException
。
The exception message explains that its cause is either not waiting on the task, or not accessing its Exception
property. 异常消息说明其原因不是等待任务,就是未访问其Exception
属性。 I only have two apparent uses of a Task
anywhere in my solution, and one is in my view model: 我在解决方案中的任何地方都只有两种明显的Task
用途,一种是在视图模型中:
async void ExecuteProcessNowCommand()
{
await _proxy.ProcessAsync(true);
}
The other is in a small utility method in the same viewmodel: 另一个在同一viewmodel中的小型实用程序方法中:
private void ExecuteWithTimeout(Action task, int? timeout = null)
{
timeout = timeout ?? HostServiceConstants.ServiceControlTimeout;
var source = new CancellationTokenSource();
var timedTask = new Task(task, source.Token);
timedTask.Start();
bool done = timedTask.Wait(timeout.Value);
if (!done)
{
source.Cancel();
var frame = new StackFrame(1);
var methodName = frame.GetMethod().Name;
_logger.Warn("'{0}' timed out after {1} milliseconds.", methodName, timeout);
}
}
In the first code excerpt, I do seem to be waiting on the task, but I am more suspicious of the second, based on an example I found somewhere online. 在第一个代码摘录中,我似乎确实在等待任务,但是根据我在网上某个地方找到的示例,我对第二个更怀疑。 I use that to try and perform non-blocking checks like: 我用它来尝试执行非阻塞检查,例如:
bool CanExecuteProcessNowCommand()
{
bool result = false;
ExecuteWithTimeout(() =>
{
try
{
result = _proxy.CanUserForceProcessing();
}
catch (EndpointNotFoundException)
{
result = false;
}
});
return result;
}
The last piece of code is called in my WCF client when I try and keep my command button updated with: 当我尝试通过以下命令更新命令按钮时,将在WCF客户端中调用最后一段代码:
ProcessNow.RaiseCanExecuteChanged();
I am very new to both async and WCF, so please excuse any obvious blunders here. 我对异步和WCF都是新手,所以请在这里找任何明显的错误。
ExecuteProcessNowCommand
will not cause this. ExecuteProcessNowCommand
不会导致此情况。 If an unhandled exception is thrown in async void method, process is taken down. 如果在异步void方法中引发了未处理的异常,则将删除进程。 So that's not the case. 事实并非如此。
Only thing left is ExecuteWithTimeout
. 剩下的只有ExecuteWithTimeout
。 Yes it can cause result in UnObservedTaskException
if unhandled exception is thrown in the timedTask
. 是的,它可以导致结果UnObservedTaskException
如果未处理的异常被抛出timedTask
。
You're waiting on it, waiting should observe the exception, but you're waiting with a Timeout. 您正在等待它,正在等待应观察到异常,但是您正在等待超时。 If the exception is thrown after the Timeout has been passed, you'll see this behavior. 如果通过超时后引发异常,您将看到此行为。
You need to attach continuation to the timedTask
and observe the exception. 您需要将延续附加到timedTask
并观察异常。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.