要求:文件是存储在腾讯云的COS上的,现在需要批量下载,并打包成一个zip的压缩包。

原理:使用HttpWebRequest把网络文件流放在内存中,ZipOutputStream进行打包成zip,需要注意的是打包在内存中进行,防止内存溢出。

首先NuGet安装SharpZipLib包(ICSharpCode.SharpZipLib.Zip.dll)。

贴代码:

using ICSharpCode.SharpZipLib.Zip;
using System;
using System.Collections.Generic;
using System.IO;
using System.Net;
using System.Web;

namespace MyTest
{
    class Program
    {
        static void Main(string[] args)
        {
            // http  网络文件地址
            List<string> urls = new List<string>();
            var ms = DownloadFileByHttpUrl(urls);
            //保存到本地,主要是为了看下是否打包成功
            string zipName = "a.zip";
            SaveFile(ms, zipName);
            Console.ReadKey();
        }

        /// <summary>
        /// 批量下载,把http文件打包成zip压缩包流
        /// </summary>
        /// <param name="HttpUrlList"></param>
        /// <returns></returns>
        public static MemoryStream DownloadFileByHttpUrl(List<string> HttpUrlList)
        {
            if (HttpUrlList == null || HttpUrlList.Count == 0)
            {
                return null;
            }
            try
            {
                var random = new Random();
                var zipMs = new MemoryStream();
                ZipOutputStream zipStream = new ZipOutputStream(zipMs);
                zipStream.SetLevel(9);//压缩率0~9
                foreach (var url in HttpUrlList)
                {
                    if (!string.IsNullOrWhiteSpace(url))
                    {
                        var urlStr = HttpUtility.UrlDecode(url);
                        string fileExt = Path.GetExtension(urlStr).ToLower();
                        string fileNameWithoutExtension = Path.GetFileNameWithoutExtension(urlStr);
                        var strName = fileNameWithoutExtension.Substring(fileNameWithoutExtension.LastIndexOf("/") + 1) + random.Next(1000, 9999) + fileExt;

                        zipStream.PutNextEntry(new ZipEntry(strName));

                        HttpWebRequest request = (HttpWebRequest)WebRequest.Create(urlStr);
                        request.AllowAutoRedirect = true;
                        WebProxy proxy = new WebProxy();
                        proxy.BypassProxyOnLocal = true;
                        proxy.UseDefaultCredentials = true;
                        request.Proxy = proxy;

                        WebResponse response = request.GetResponse();
                        using (Stream stream = response.GetResponseStream())
                        {
                            Byte[] buffer = new Byte[1024];
                            int current = 0;
                            while ((current = stream.Read(buffer, 0, buffer.Length)) != 0)
                            {
                                zipStream.Write(buffer, 0, current);
                            }
                            zipStream.Flush();
                        }
                    }
                }
                zipStream.Finish();
                zipMs.Position = 0;
                return zipMs;
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

        /// <summary>
        /// 保存文件到本地
        /// </summary>
        /// <param name="stream"></param>
        /// <param name="file_name"></param>
        private static void SaveFile(MemoryStream stream, string file_name)
        {
            try
            {
                byte[] srcBuf = new Byte[stream.Length];
                stream.Read(srcBuf, 0, srcBuf.Length);
                stream.Seek(0, SeekOrigin.Begin);
                string filePath = "D:\\FileZip";
                if (!Directory.Exists(filePath))
                {
                    Directory.CreateDirectory(filePath);
                }
                using (FileStream fs = new FileStream(filePath + "\\" + file_name, FileMode.Create, FileAccess.Write))
                {
                    fs.Write(srcBuf, 0, srcBuf.Length);
                    fs.Close();
                }
            }
            catch (Exception ex)
            {
                throw ex;
            }
        }

    }
}
View Code