BattlefieldDuck

How to properly handle exception in Task.Run

The Problem

A try catch block has already used outside the ExtractZip function, exception still throw, the program stopped.

Possible Solutions

Basic Solution

Catch and return the exception inside Task.Run, throw the exception outside.

public static async Task ExtractZip(string sourceArchiveFileName, string destinationDirectoryName)
{
    Exception? exception = await Task.Run(() =>
    {
        try
        {
            ZipFile.ExtractToDirectory(sourceArchiveFileName, destinationDirectoryName);
            return null;
        }
        catch (Exception e)
        {
            return e;
        }
    });

    if (exception != null)
    {
        throw exception;
    }
}

Better Solution

Create TaskEx.cs and replace Task.Run to TaskEx.Run 👏

public static Task ExtractZip(string sourceArchiveFileName, string destinationDirectoryName)
{
    return TaskEx.Run(() => ZipFile.ExtractToDirectory(sourceArchiveFileName, destinationDirectoryName));
}

⚠️ There is a special case where TaskEx.Run cannot be used. If the Task/Action inside TaskEx.Run returns Exception, the exception will throw and you cannot get the Exception.

TaskEx.cs

本作品采用 知识共享署名-非商业性使用-禁止演绎 4.0 国际许可协议 进行许可。