CubemonkeyNYC
CubemonkeyNYC

Reputation: 283

Zipping asynchronously using Task.Run() is blocking UI. What am I missing?

Part of my process sometimes zips files, and I'm trying to make that process asynchronous. I'm rather new at this.

I've used "await Task.Run(() => DoSomething())" before and did not encounter any issues. For some reason, when my program reaches that awaited Task.Run(), it hangs indefinitely.

Would anyone let me know what I'm missing? Thanks in advance.

public static async Task<BackupResultHelper> BackupAndZip(List<MyBackupItem> itemList, FileInfo targetFi) {
        DirectoryInfo zipSourceDi = new DirectoryInfo(targetFi.Directory + "\\Temp");

        if (targetFi.Exists)
            targetFi.Delete();

        if (!Directory.Exists(zipSourceDi.FullName))
            Directory.CreateDirectory(zipSourceDi.FullName);

        foreach (MyBackupItem item in itemList) {
            DirectoryInfo dir = new DirectoryInfo(zipSourceDi.FullName + "\\" + item.Name);
            if (!BackupItem(item, dir.FullName)) return ErrorResultHelper;
        }

        await Task.Run(() => ZipFile.CreateFromDirectory(zipSourceDi.FullName, targetFi.FullName, CompressionLevel.Optimal, false));

        Directory.Delete(zipSourceDi.FullName, true);
        string time = DateTime.Now.ToLongTimeString();
        return new BackupResultHelper(){Success = true, Message = "Backup complete!", BackupDateTime = time};
    }

Upvotes: 1

Views: 2012

Answers (1)

Stephen Cleary
Stephen Cleary

Reputation: 456577

I suspect that you have code further up your call stack that is calling Task.Wait or Task<T>.Result, and that is where the problem is.

If you are using a UI or ASP.NET request thread to do the processing, and then block on an asynchronous task, you run the risk of a deadlock that I describe on my blog. By default, await will capture the current "context" (e.g., a UI context) and resume the async method in that context (e.g., on the UI thread). If you block that context (e.g., by calling Task.Wait or Task<T>.Result on the UI thread), then the async method cannot resume execution and is prevented from completing that task.

Upvotes: 1

Related Questions