ASP.net利用DotNetZip压缩文件,用流输出文件细节

将文件加载到zip文件之后,需要提供下载,最开始的方法是先将打包好的压缩文件保存到文件夹中,然后再重新通过文件路径来返回文件提供下载。但是在上传到服务器之后发现,通过文件路径返回文件提供下载的方法行不通,接着就想到最好是将压缩文件zip加载到流中,然后返回流就能下载文件。

public ActionResult AcodTypeToExport()
        {
            var worksList = db.Pictures.Include("User").Where(u => SqlFunctions.PatIndex(startwithStr, u.User.user_number) > 0).ToList();
            List pathList = new List();
            foreach (var item in worksList)
            {
                string path = item.picture_path;
                pathList.Add(path);
            }
            Admin admin = (Admin)Session["_admin"];
            if (admin == null)
                return Redirect("/Admins/Account/login");
            string filename = admin.ad_number + "_" + admin.ad_name;

            DownLoadController down = new DownLoadController();
            List pathlist = down.BatchDownload(pathList, filename);
            if (pathlist.Count() > 0)
            {
                using (ZipFile zip = new ZipFile(System.Text.Encoding.Default))
                {
                    for (int i = 0; i < pathlist.Count(); i++)
                    {
                        zip.AddFile(pathlist[i], "Images");
                    }
                    Stream ms = new MemoryStream();
                    zip.Save(ms);
                    ms.Seek(0, SeekOrigin.Begin);//将ms流重置,让后面调用可以获取到正确的流,否则可能会获取不到文件
                    return File(ms, "application/zip", "zip.zip");
                }
            }
            return null;
        }

我在这些地方犯过的错,当时因为不太懂流的这个概念,所以处处碰壁

注意:

1、使用MemoryStream的时候,误以为所有要使用到流的类时都需要使用using来引用或是调用流的关闭和释放的方法,就当我这么做了之后,就发现运行时会报一个“使用的流已经关闭”之类的异常,后来在百度上搜索,查看之前自己写的代码,就明白了,使用using他相当于是会自动关闭流,所以才会抛出流已关闭的异常。然而在这里使用是不能关闭流,所以直接使用MemoryStream类,不需要用using来引用,就不会抛出之前的异常了;

2、解决了上面的问题之后又出来一个新的问题,就是下载的zip文件里根本没有文件,于是搜百度,看到ms需要重置流的位置才行,就是将ms流的开始位置至于0处,就能正确的将整个文件下载下来了,这个问题是这里看到的https://q.cnblogs.com/q/16755/


你可能感兴趣的:(利用DotNetZip压缩文件)