У меня есть метод, который регистрирует фоновую задачу, которая выглядит так:
//snippet from task builder method
try
{
cancellationTokenSource.CancelAfter(10000);
btr = Task.Run(() => registerTask(builder, btr,cancellationTokenSource.Token), cancellationTokenSource.Token).Result;
}
catch (OperationCanceledException) // something went wrong
{
return null;
}
private BackgroundTaskRegistration registerTask(BackgroundTaskBuilder builder, BackgroundTaskRegistration btr, CancellationToken token)
{
CancellationTokenSource newToken = new CancellationTokenSource();
Task cancelledCheck = Task.Run(() =>
{
while (true)
{
if (token.IsCancellationRequested)
{
newToken.Cancel();
token.ThrowIfCancellationRequested();
}
}
}, newToken.Token);
btr = Task.Run(()=> builder.Register(),token).Result;
return btr;
}
Моя проблема в том, что иногда метод builder.Register() ничего не возвращает. Вероятно, это какая-то ошибка Windows; метод Register() никогда не завершается внутри. Действительно, через 10 секунд вызывается метод token.ThrowIfCancellationRequested(), но он не вызывает исключение в операторе try-catch, где он вызывается. Первоначально я вызывал builder.Register() напрямую без Task.Run(), но это не сработало, и это тоже.
Однако, если я заменю btr = Task.Run(() =>...
на Task.Delay(ms)
вместо ms > 10000
, произойдет ожидаемый эффект.
Я делаю что-то неправильно? Или есть лучший способ сделать это? По сути, мне просто нужен код, который заставит метод registerTask() возвращать значение null, если builder.Register() не завершится через несколько секунд.
.Result
проблематично, так как это заблокирует поток; можно ли вместо этого использовать асинхронные функции иawait
? - person Jacob   schedule 07.07.2016