示例#1
0
        private static async void DownloadUnKownSizeFile(DownloadInfo info, IDownloadManagerListener managerListener)
        {
            try
            {
                using (var httpClient = CreateHttpClient())
                {
                    var response =
                        await
                        httpClient.GetAsync(info.Url, HttpCompletionOption.ResponseHeadersRead,
                                            info.CancellationTokenSource.Token);

                    using (var stream = await response.Content.ReadAsStreamAsync())
                    {
                        var bytes = new byte[_bytesLength];
                        using (
                            var fileStream = new FileStream(Path.Combine(info.Url, info.Name), FileMode.Append,
                                                            FileAccess.Write))
                        {
                            int writeLength;
                            stream.Position = fileStream.Length;
                            while ((writeLength = (stream.Read(bytes, 0, _bytesLength))) > 0)
                            {
                                if (info.CancellationTokenSource.Token.IsCancellationRequested)
                                {
                                    info.DownloadStatus = DownloadStatus.UnDownload;
                                    info.Listener.OnDownloadCancled(info);
                                    break;
                                }

                                fileStream.Write(bytes, 0, writeLength);
                                info.DownloadSize += writeLength;
                                info.Listener.OnDownloadProgress(info);
                            }
                            fileStream.Flush();
                            fileStream.Close();
                            stream.Flush();
                            stream.Close();
                        }
                        if (info.DownloadStatus == DownloadStatus.Downloading)
                        {
                            info.DownloadStatus = DownloadStatus.Downloaded;
                            info.Listener.OnDownloadCompleted(info);
                            managerListener.OnDownloadCompleted(info);
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                Logger.LogHelper.Error("下载文件出错", ex);
                info.Exception      = ex;
                info.Message        = ex.Message;
                info.DownloadStatus = DownloadStatus.DownloadFailed;
                info.Listener.OnDownloadFailed(info);
            }
        }
示例#2
0
 public static bool CanDownload(DownloadInfo downloadInfo, out string msg)
 {
     msg = "";
     if (string.IsNullOrEmpty(downloadInfo.Url))
     {
         msg = "下载地址不能为空";
         return(false);
     }
     if (_downloadInfos.Values.Count(o => o.Url == downloadInfo.Url && downloadInfo.DownloadStatus != DownloadStatus.DownloadPause) > 0)
     {
         Logger.LogHelper.Info($"当前文件{downloadInfo.Name}({downloadInfo.Name})正在下载");
         msg = "文件已经在下载中,请不要重复下载";
         return(false);
     }
     return(true);
 }
示例#3
0
        private static async Task <Tuple <string, long> > GetFileSize(DownloadInfo info)
        {
            using (var httpClient = CreateHttpClient())
            {
                httpClient.Timeout = _timeOut;
                var response =
                    await
                    httpClient.GetAsync(info.Url, HttpCompletionOption.ResponseHeadersRead,
                                        info.CancellationTokenSource.Token);

                var contentLength = response.Content.Headers.ContentLength;
                if (contentLength == null)
                {
                    Logger.LogHelper.Info($"下载文件:{info.Name}({info.Url});无法获取文件长度");
                    return(new Tuple <string, long>(response.Content.Headers.ContentDisposition?.FileName, 0));
                }
                return(new Tuple <string, long>(response.Content.Headers.ContentDisposition?.FileName, contentLength.Value));;
            }
        }
示例#4
0
        private static void MergeFile(DownloadInfo info)
        {
            var path = Path.Combine(info.SavePath, info.Name.Replace(".", ""));

            //这里排序一定要正确,转成数字后排序(字符串会按1 10 11排序,默认10比2小)
            foreach (var filePath in Directory.GetFiles(path).OrderBy(Path.GetFileNameWithoutExtension))
            {
                var file = Directory.GetParent(path).FullName + @"\" + info.Name;

                using (var fs = File.Open(file, FileMode.Append, FileAccess.Write, FileShare.ReadWrite))
                {
                    //int count = 0;
                    //while (count < 20 && Win32.IsOpen(filePath))
                    //{
                    //    await Task.Delay(200);
                    //    count++;
                    //}
                    var bytes = File.ReadAllBytes(filePath); //读取文件到字节数组
                    fs.Write(bytes, 0, bytes.Length);        //写入文件
                    fs.Flush();
                    fs.Close();
                }
                //int sequence = 0;
                //while (sequence < 20 && Win32.IsOpen(filePath))
                //{
                //    await Task.Delay(200);
                //    sequence++;
                //}
                if (!Win32.IsOpen(filePath))
                {
                    File.Delete(filePath);
                }
            }
            if (!Directory.GetFiles(path).Any())
            {
                Directory.Delete(path);
            }
        }
示例#5
0
        /// <summary>
        /// 单线程下载
        /// </summary>
        /// <param name="info"></param>
        /// <param name="managerListener"></param>
        public static async void DownloadWithSingleThreed(DownloadInfo info, IDownloadManagerListener managerListener)
        {
            try
            {
                var contentLength = info.FileSize;
                if (info.FileSize <= 0 || string.IsNullOrEmpty(info.Name))
                {
                    var file = await GetFileSize(info);

                    if (string.IsNullOrEmpty(info.Name))
                    {
                        info.Name = file.Item1;
                    }
                    if (file.Item2 <= 0)
                    {
                        DownloadUnKownSizeFile(info, managerListener);
                        return;
                    }
                }
                if (string.IsNullOrEmpty(info.Name))
                {
                    info.Name = Guid.NewGuid().ToString();
                }
                info.Listener.OnDownloadStart(info);
                using (var httpClient = CreateHttpClient())
                {
                    if (!Directory.Exists(info.SavePath))
                    {
                        Directory.CreateDirectory(info.SavePath);
                    }
                    using (var fileStream = new FileStream(Path.Combine(info.SavePath, info.Name), FileMode.Append, FileAccess.Write))
                    {
                        var bytes       = new byte[_bytesLength];
                        var beginSecond = DateTime.Now.Second;
                        if (fileStream.Length >= contentLength)
                        {
                            info.Listener.OnDownloadCompleted(info);
                            managerListener.OnDownloadCompleted(info);
                            return;
                        }
                        httpClient.DefaultRequestHeaders.Add("Range", "bytes = " + fileStream.Length + " - " + (contentLength - 1));
                        contentLength -= fileStream.Length;
                        var response = await httpClient.GetAsync(info.Url, info.CancellationTokenSource.Token);

                        using (var stream = await response.Content.ReadAsStreamAsync())
                        {
                            int writeLength;
                            var readLength = _bytesLength;
                            if (readLength != -1 && contentLength < readLength)
                            {
                                readLength = (int)contentLength;
                            }
                            while ((writeLength = (stream.Read(bytes, 0, readLength))) > 0)
                            {
                                if (info.CancellationTokenSource.Token.IsCancellationRequested)
                                {
                                    info.Listener.OnDownloadCancled(info);
                                }

                                fileStream.Write(bytes, 0, writeLength);

                                info.DownloadSize += writeLength;
                                info.Progress      = info.DownloadSize / contentLength;

                                if (beginSecond != DateTime.Now.Second)
                                {
                                    info.Speed = writeLength / (DateTime.Now.Second - beginSecond) / 1024;
                                }
                                info.Listener.OnDownloadProgress(info);
                                contentLength -= writeLength;
                                if (contentLength <= 0)
                                {
                                    info.DownloadStatus = DownloadStatus.Downloaded;
                                    info.Listener.OnDownloadCompleted(info);
                                    managerListener.OnDownloadCompleted(info);
                                }
                            }
                            stream.Flush();
                            stream.Close();
                        }
                        fileStream.Flush();
                        fileStream.Close();
                    }
                }
            }
            catch (Exception ex)
            {
                Logger.LogHelper.Error("下载文件出错", ex);
                info.Message        = ex.Message;
                info.Exception      = ex;
                info.DownloadStatus = DownloadStatus.DownloadFailed;
                info.Listener.OnDownloadFailed(info);
                managerListener.OnDownloadFailed(info);
            }
        }
示例#6
0
        private static async Task DownloadChunk(DownloadInfo info)
        {
            try
            {
                var sequence = 1;
                var path     = Path.Combine(info.SavePath, info.Name.Replace(".", ""));

                if (!Directory.Exists(path))
                {
                    Directory.CreateDirectory(path);
                }
                while (_downloadingFiles[info.Url].DownloadingFiles.Contains($"{info.Name.Split('.')[0]}_{sequence}.temp"))
                {
                    sequence++;
                }
                if (_downloadingFiles[info.Url].FileLength < (sequence - 1) * _oneThreadSize)
                {
                    return;
                }
                string fileName = $"{info.Name.Split('.')[0]}_{sequence}.temp";
                _downloadingFiles[info.Url].DownloadingFiles.Add(fileName);

                using (var httpClient = CreateHttpClient())
                {
                    long from = (sequence - 1) * _oneThreadSize;
                    long to   = Math.Min(sequence * _oneThreadSize, _downloadingFiles[info.Url].FileLength);
                    using (var fileStream = File.Open(Path.Combine(path, fileName), FileMode.Append, FileAccess.Write, FileShare.ReadWrite))
                    {
                        from += fileStream.Length;
                        long downloadSize = to - from;
                        if (from < to - 1)
                        {
                            httpClient.DefaultRequestHeaders.Add("Range", $"bytes={from}-{to - 1}");
                            var response = await httpClient.GetAsync(info.Url, info.CancellationTokenSource.Token);

                            using (var stream = await response.Content.ReadAsStreamAsync())
                            {
                                var bytes = new byte[_bytesLength];
                                int writeLength;
                                int readLength = _bytesLength;
                                if (downloadSize != 0 && downloadSize < readLength)
                                {
                                    readLength = (int)downloadSize;
                                }
                                while ((writeLength = (stream.Read(bytes, 0, readLength))) > 0)
                                {
                                    if (info.CancellationTokenSource.Token.IsCancellationRequested)
                                    {
                                        info.Listener.OnDownloadCancled(info);
                                    }

                                    fileStream.Write(bytes, 0, writeLength);
                                    downloadSize      -= writeLength;
                                    info.DownloadSize += writeLength;

                                    info.Listener.OnDownloadProgress(info);
                                    if (downloadSize != 0 && downloadSize < readLength)
                                    {
                                        readLength = (int)downloadSize;
                                    }
                                    if (downloadSize <= 0)
                                    {
                                        break;
                                    }
                                }
                                stream.Flush();
                                stream.Close();
                            }
                        }
                        fileStream.Flush();
                        fileStream.Close();
                    }
                }
                var fileCount = _downloadingFiles.Count();
                if (_downloadingFiles[info.Url].FileLength < fileCount * _oneThreadSize)
                {
                    return;
                }
                await DownloadChunk(info);
            }
            catch (Exception ex)
            {
                Logger.LogHelper.Error("下载文件出错", ex);
                info.Exception      = ex;
                info.Message        = ex.Message;
                info.DownloadStatus = DownloadStatus.DownloadFailed;
                info.Listener.OnDownloadFailed(info);
                info.CancellationTokenSource.Cancel();
            }
        }
示例#7
0
        public static async void DownloadWithMultiThreed(DownloadInfo info, IDownloadManagerListener managerListener)
        {
            try
            {
                var contentLength = info.FileSize;
                if (info.FileSize <= 0 || string.IsNullOrEmpty(info.Name))
                {
                    var file = await GetFileSize(info);

                    if (string.IsNullOrEmpty(info.Name))
                    {
                        info.Name = file.Item1;
                    }
                    if (file.Item2 <= 0)
                    {
                        DownloadUnKownSizeFile(info, managerListener);
                        return;
                    }
                }
                if (string.IsNullOrEmpty(info.Name))
                {
                    info.Name = Guid.NewGuid().ToString();
                }
                info.Listener.OnDownloadStart(info);
                var fileInfo = new FileInfo {
                    FileLength = contentLength
                };
                if (_downloadingFiles.ContainsKey(info.Url))
                {
                    _downloadingFiles.Remove(info.Url);
                }
                _downloadingFiles.Add(info.Url, fileInfo);

                int taskCount = (int)(_downloadingFiles[info.Url].FileLength / _oneThreadSize);
                var tasks     = new List <Task>();
                for (int i = 0; i < _maxThread; i++)
                {
                    if (taskCount <= 0)
                    {
                        break;
                    }
                    taskCount--;
                    var t = Task.Run(async() => { await DownloadChunk(info); });
                    tasks.Add(t);
                }
                Task.WaitAll(tasks.ToArray());
                if (info.DownloadStatus == DownloadStatus.Downloading)
                {
                    MergeFile(info);
                    info.DownloadStatus = DownloadStatus.Downloaded;
                    info.Listener.OnDownloadCompleted(info);
                    managerListener.OnDownloadCompleted(info);
                }
            }
            catch (Exception ex)
            {
                Logger.LogHelper.Error("下载文件出错", ex);
                if (info.Message == null)
                {
                    info.Exception = ex;
                    info.Message   = ex.Message;
                }
                info.DownloadStatus = DownloadStatus.DownloadFailed;
                info.Listener.OnDownloadFailed(info);
                managerListener.OnDownloadFailed(info);
            }
        }
示例#8
0
 public static void Pause(DownloadInfo downloadInfo)
 {
 }