Die Ausnahme (n) einer Aufgabe wurden nicht beobachtet, wenn Sie auf die Aufgabe warten oder auf ihre Ausnahmeeigenschaft zugreifen. Infolgedessen war die unbeobachtete Ausnahme

Was bedeutet das und wie triggers man es?

Ich verwende TPL-Aufgaben.

Der ganze Fehler

Die Ausnahme (n) einer Aufgabe wurden nicht beobachtet, wenn Sie auf die Aufgabe warten oder auf ihre Ausnahmeeigenschaft zugreifen. Als Ergebnis wurde die unbeobachtete Ausnahme durch den Finalizer-Thread erneut ausgetriggers.

bei System.Threading.Tasks.TaskExceptionHolder.Finalize ()

mscorlib

Wenn Sie eine Aufgabe erstellen und task.Wait() nicht aufrufen oder versuchen, das Ergebnis einer Task abzurufen, wird die Anwendung beim Abschluss der Aufgabe durch den Garbage Collector erfasst. Weitere Informationen finden Sie auf der MSDN-Seite zur Ausnahmebehandlung in der TPL .

Die beste Option ist hier, die Ausnahme zu behandeln. Dies kann über eine Fortsetzung geschehen – Sie können eine Fortführung an die Aufgabe anhängen und / log / swallow / etc die auftretende Ausnahme protokollieren. Dies bietet eine saubere Möglichkeit, Task-Ausnahmen zu protokollieren, und kann als einfache Erweiterungsmethode geschrieben werden, dh:

 public static void LogExceptions(this Task task) { task.ContinueWith( t => { var aggException = t.Exception.Flatten(); foreach(var exception in aggException.InnerExceptions) LogException(exception); }, TaskContinuationOptions.OnlyOnFaulted); } 

Mit dem oben genannten können Sie verhindern, dass eine Aufgabe die App abruft und protokolliert, über:

 Task.Factory.StartNew( () => { // Do your work... }).LogExceptions(); 

Alternativ können Sie die TaskScheduler.UnobservedTaskException abonnieren und dort behandeln.

Sicher; es bedeutet, dass eine Task abgeschlossen wurde, nachdem sie der Garbage Collection überlassen wurde, aber die Task selbst ist fehlgeschlagen. Es gibt zwei Fixes:

  • Behandeln Sie die Aufgaben nicht direkt (verwenden Sie ContinueWith(...) zum Abonnieren und überprüfen Sie .IsFaulted und .Exception für die Task im Parameter)
  • TaskScheduler.UnobservedTaskException das TaskScheduler.UnobservedTaskException Ereignis, und markieren Sie es beobachtet (rufen Sie e.SetObserved() nach dem Protokollieren des Fehlers auf)

Probier diese:

 public static void ThrowFirstExceptionIfHappens(this Task task) { task.ContinueWith(t => { var aggException = t.Exception.Flatten(); foreach (var exception in aggException.InnerExceptions) { throw exception; // throw only first, search for solution } }, TaskContinuationOptions.OnlyOnFaulted); // not valid for multi task continuations } public static Task CreateHandledTask(Action action) { Task tsk = Task.Factory.StartNew(action); tsk.ThrowFirstExceptionIfHappens(); return tsk; }