取消异步下载?

6

我有一个问题。如何取消下载?

 client.CancelAsync();

由于如果我取消下载并开始新的下载,代码仍然尝试访问旧的下载文件,所以对我没有用。 你需要知道,在我的代码中,当下载完成时,它应该解压已下载的文件。例如:Example.zip。 因此,当我取消下载并开始新的下载时,脚本会尝试解压缩旧的Example.zip文件,但它应该跳过这个文件。
为了解压缩,我正在使用Iconic.Zip.dll(http://dotnetzip.codeplex.com/)。
如何使其工作?

更新:

这是我的下载表格

     private void button3_Click_1(object sender, EventArgs e)
    {

        DialogResult dialogResult = MessageBox.Show("This will cancel your current download ! Continue ?", "Warning !", MessageBoxButtons.YesNo);
        if (dialogResult == DialogResult.Yes)
        {

            cancelDownload = true;
            URageMainWindow.isDownloading = false;
            this.Close();

        }
        else if (dialogResult == DialogResult.No)
        {

        } 
    }

这是我的主表单,当您开始下载某些内容时,会出现此表单。
 private void checkInstall(object sender, WebBrowserDocumentCompletedEventArgs e)
    {

            string input = storeBrowser.Url.ToString();

            // Test these endings
            string[] arr = new string[]
           {"_install.html"};

            // Loop through and test each string
            foreach (string s in arr)
            {
                if (input.EndsWith(s) && isDownloading == false)
                {


                   // MessageBox.Show("U.Rage is downloading your game");
                    Assembly asm = Assembly.GetCallingAssembly();
                    installID = storeBrowser.Document.GetElementById("installid").GetAttribute("value");
                   // MessageBox.Show("Name: " + installname + " ID " + installID);
                    installname = storeBrowser.Document.GetElementById("name").GetAttribute("value");
                    installurl = storeBrowser.Document.GetElementById("link").GetAttribute("value");

                    isDownloading = true;
                    string install_ID = installID;
                    string Install_Name = installname;

                    // MessageBox.Show("New Update available ! " + " - Latest version: " + updateversion + "  - Your version: " + gameVersion);
                    string url = installurl;
                    WebClient client = new WebClient();
                    client.DownloadProgressChanged += new DownloadProgressChangedEventHandler(client_InstallProgressChanged);
                    client.DownloadFileCompleted += new AsyncCompletedEventHandler(client_InstallFileCompleted);
                    client.DownloadFileAsync(new Uri(url), @"C:\U.Rage\Downloads\" + installID + "Install.zip");
                    if (Downloader.cancelDownload == true)
                    {
                        //MessageBox.Show("Downloader has been cancelled");
                        client.CancelAsync();
                        Downloader.cancelDownload = false;
                    }
                    notifyIcon1.Visible = true;
                    notifyIcon1.ShowBalloonTip(2, "Downloading !", "U.Rage is downloading " + installname, ToolTipIcon.Info);
                    System.Media.SoundPlayer player = new System.Media.SoundPlayer(@"c:/U.Rage/Sounds/notify.wav");
                    player.Play();

                    storeBrowser.GoBack();
                    igm = new Downloader();
                    igm.labelDWGame.Text = installname;
                    // this.Hide();
                    igm.Show();
                    return;
                }

                  if (input.EndsWith(s) && isDownloading == true)
                {
                  System.Media.SoundPlayer player = new System.Media.SoundPlayer(@"c:/U.Rage/Sounds/notify.wav");
                  player.Play();
                  MessageBox.Show("Please wait until your download has been finished", "Warning");
                  storeBrowser.GoBack();
                }
            }
        }

当下载完成时会发生这种情况。

     void client_InstallFileCompleted(object sender, AsyncCompletedEventArgs e)
    {
        if(Downloader.cancelDownload == false)
        {
            using (ZipFile zip = ZipFile.Read(@"C:\U.Rage\Downloads\" + installID + "Install.zip"))
            {
                //zip.Password = "iliketrains123";
                zip.ExtractAll("C:/U.Rage/Games/", ExtractExistingFileAction.OverwriteSilently);
            }
            System.IO.File.Delete(@"C:/U.Rage/Downloads/" + installID + "Install.zip");
            notifyIcon1.Visible = true;
            notifyIcon1.ShowBalloonTip(2, "Download Completed !", "Installing was succesful !", ToolTipIcon.Info);
            System.Media.SoundPlayer player = new System.Media.SoundPlayer(@"c:/U.Rage/Sounds/notify.wav");
            player.Play();
            this.Show();
            igm.Close();
            isDownloading = false;
            listView.Items.Clear();
            var files = Directory.GetFiles(@"C:\U.Rage\Games\", "*.ugi").Select(f => new ListViewItem(f)).ToArray();
            foreach (ListViewItem f in files)
            {
                this.LoadDataFromXml(f);
            }

      }
    }
3个回答

12

这是支持取消功能的异步数据下载方法:

private static async Task<byte[]> downloadDataAsync(Uri uri, CancellationToken cancellationToken)
{
    if (String.IsNullOrWhiteSpace(uri.ToString()))
        throw new ArgumentNullException(nameof(uri), "Uri can not be null or empty.");

    if (!Uri.IsWellFormedUriString(uri.ToString(), UriKind.Absolute))
        return null;

    byte[] dataArr = null;
    try
    {
        using (var webClient = new WebClient())
        using (var registration = cancellationToken.Register(() => webClient.CancelAsync()))
        {
            dataArr = await webClient.DownloadDataTaskAsync(uri);
        }
    }
    catch (WebException ex) when (ex.Status == WebExceptionStatus.RequestCanceled)
    {
        // ignore this exception
    }

    return dataArr;
}

9
当您调用CancelAsync时,传递给完成回调的AsyncCompletedEventArgs对象将具有Cancelled属性设置为true。所以您可以这样写:
void client_InstallFileCompleted(object sender, AsyncCompletedEventArgs e)
{
    if(e.Cancelled)
    {
        // delete the partially-downloaded file
        return;
    }
    // unzip and do whatever...
    using (ZipFile zip = ZipFile.Read(@"C:\U.Rage\Downloads\" + installID + "Install.zip"))

请查看文档以获取更多信息。


好的。取消操作已经生效,但是他仍在下载旧版本:P 如何中断流或用新的下载链接替换它? - user2287884
他取消了旧的下载并创建了一个新的下载文件,但仍然向旧文件添加字节。 - user2287884
谢谢,我已经解决了。我忘记将我的WebClient设置为public :) - user2287884
给出负评的理由是惯例。 - Jim Mischel
谢谢,我之前不知道有“Cancelled”属性。 - Keemo Kimo

5
选定的答案对我来说不起作用。这是我所做的事情:
当他们点击取消按钮时,我调用了
Client.CancelAsync();

然后在Web.Client DownloadFileCompleted事件中:

Client.DownloadFileCompleted += (s, e) =>
{
      if (e.Cancelled)
      {
          //cleanup delete partial file
          Client.Dispose();                    
          return;
      }
 }

当您尝试重新下载时,只需实例化一个新的客户端:

Client = WebClient();

这样旧的异步参数就不会被保留。


当您删除客户端时,它是否真正删除了部分下载的文件? - Emil

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接