近两日研究了Abp.io 中模板项目的生成原理,是从Github下载源码包,进行修改、替换,然后生成新的zip包提供下载。

项目内部使用了  这个包 Ionic.Zip  Version="1.9.1.8“   ,这个包 不支持 .NetCore 。

无法编译,项目文件中有:  <AssetTargetFallback>$(AssetTargetFallback);portable-net45+win8+wp8+wpa81;</AssetTargetFallback>

但还不清楚是什么作用。

报着学习的态度,尝试替换 Ionic.Zip 替换为 ZipArchive .官网上看了看文档,还比较顺利。。 也能生成Zip ,但生成的Zip始终报错,”文件末端错误 “。 只能一个一个步骤找原因。



这个是直接读,直接写,没有问题。--- 
1  public static void TestReadZipAndWriteToNewZip()
{
string path = @"D:\dev\Study\abpio\abp_io\src\Volo.AbpWebSite.Web\TemplateFiles\";
string srcFile = path + "test.zip";
string destFile = path + "test_dest.zip"; using (var readStream = File.OpenRead(srcFile))
{
using (var archive = new ZipArchive(readStream, ZipArchiveMode.Read))
{
using (var writeFileStream = new FileStream(destFile, FileMode.CreateNew))
{
using (var outZip = new ZipArchive(writeFileStream, ZipArchiveMode.Create))
{
foreach (var entry_item in archive.Entries)
{
var new_entry = outZip.CreateEntry(entry_item.FullName);
using (var stream = new_entry.Open())
{
entry_item.Open().CopyTo(stream);
}
} }
} }
}
}
里边可以注意到多层包裹,整个Zip要有Stream .内部的ZipArctiveEntry也要有留的。
从 ZipArctiveEntry 中读取 内容到字节数组
public static byte[] GetBytes(this ZipArchiveEntry zipFile)
{
using (var ms = new MemoryStream())
{
using (var stream = zipFile.Open())
{
stream.CopyTo(ms);
return ms.ToArray();
}
}
}
转换为可以处理的 内存文件列表 
 public static FileEntryList ToFileEntryList(this ZipArchive zipFile, string rootFolder = null)
{
var zipEntries = zipFile.Entries.ToList(); if (rootFolder != null)
{
zipEntries = zipFile.Entries.Where(entry =>
entry.FullName.StartsWith(rootFolder)).ToList();
}
var fileEntries = new List<FileEntry>();
foreach (var zipEntry in zipEntries)
{
var fileName = zipEntry.FullName;
if (rootFolder != null)
{
fileName = fileName.RemovePreFix(rootFolder);
} if (fileName.IsNullOrEmpty())
{
continue;
}
fileEntries.Add(new FileEntry(fileName, zipEntry.GetBytes(), zipEntry.IsDirectory());
} return new FileEntryList(fileEntries);
}
 private static FileEntryList GetEntriesFromZipFile(string filePath, string rootFolder = null)
{
using (var templateFileStream = File.OpenRead(filePath))
{ using (var archive = new ZipArchive(templateFileStream, ZipArchiveMode.Read))
{ return archive.ToFileEntryList(rootFolder);
}
}
}



private static byte[] CreateZipFileFromEntries(FileEntryList entries)
{
using (var stream = new MemoryStream())
{
using (var resultZipFile = new ZipArchive(stream,ZipArchiveMode.Create))
{
entries.CopyToZipFile(resultZipFile); }
//重点在这里: 生成的Zip的流数据返回,一定要在 ZipArchive 的生存期外边!!!!
//如果是直接 写入 FileStream 无所谓 。但要作为 Byte[] 返回 一定要等到释放,或者说,完成压缩后。
//猜测是 在销毁的时候写入Stream的, 没有看到 ZipArchive 的源码,只能猜测。
                     return stream.ToArray(); 
}
} 虽然花费了不少时间,但总算解决了,~~~~

使用 ZipArchive 生成Zip文件备注的更多相关文章

  1. java 生成zip文件并导出

    总结一下,关于Java下载zip文件并导出的方法,浏览器导出. String downloadName = "下载文件名称.zip"; downloadName = Browser ...

  2. 013-Go通archive/zip生成ZIP文件

    package main import( "io/ioutil" "os" "bytes" "archive/zip" ...

  3. Java 生成ZIP文件

    public static byte[] fileToZip(){ ZipOutputStream append = null; ByteArrayOutputStream bos = new Byt ...

  4. 【.NET深呼吸】Zip文件操作(2):动态生成Zip文档

    通过前面一篇烂文的介绍,大伙儿知道,ZipArchive类表示一个zip文档实例,除了用上一篇文章中所列的方法来读写zip文件外,还可以直接通过ZipArchive类,动态生成zip文件. 文件流操作 ...

  5. salesforce 零基础学习(五十三)多个文件生成一个zip文件(使用git上封装的代码)

    此篇参考git代码:https://github.com/pdalcol/Zippex 学习salesforce可以访问一个朋友的网站:https://www.xgeek.net 首先感谢git上提供 ...

  6. java直接生成zip压缩文件精简代码(跳过txt文件)

    /** * @param args */ public static void main(String[] args) throws Exception{ ZipOutputStream zos = ...

  7. 通过javascript在网页端生成zip压缩包并下载

    zip.js是什么 zip.js的github项目地址:http://gildas-lormeau.github.io/zip.js/ 通过zip.js封装一个能在网页端生成zip文件的插件, 直接在 ...

  8. 动态生成Zip

    动态生成Zip文档   通过前面一篇烂文的介绍,大伙儿知道,ZipArchive类表示一个zip文档实例,除了用上一篇文章中所列的方法来读写zip文件外,还可以直接通过ZipArchive类,动态生成 ...

  9. 使用gulp在开发过程中合理导出zip文件

    最近一段时间一直在做桌面混合应用,跟以往做web端不同的是,无法再通过在浏览器上输入内部的域名来随时跟踪开发版本的状况了,只能通过打包代码让产品或领导随时跟踪进度. 这里就涉及到一些问题了: 1,需要 ...

随机推荐

  1. python 字典嵌套字典赋值异常

    针对dict中 嵌套dict 出现复制异常 lists={} test=['s1','s2','s3'] data = {'value': '',} for i in range(2): lists[ ...

  2. Yii2 mysql查询 int自动变string解决办法

    原因是PDO以string查询数据导致. 这个与YII没关系,是PDO的默认处理,解决方法只需在配置中的db配置中加上attributes的相关配置就行了,如下: 'components' => ...

  3. day 04

    今天学些的内容 流程控制 1.在python一般代码执行顺序都从上到下依次解释执行称为顺序结构. 2.然而遇到需要一些条件判断的时候需要选择不同的执行路线去解释执行 这种流程控制称为 分支结构 也可叫 ...

  4. kubernets controller 和 CRD 具体组件分析

    (dlv) b k8s.io/sample-controller/pkg/client/informers/externalversions.(*sharedInformerFactory).Info ...

  5. CH 5102Mobile Service题解

    题目: 用动态规划很容易将完成任务量作为dp的阶段,通过指派服务员,从当前i-1个任务转移到i个任务: 我们可以用一个四维数组f[i][x][y][z]来表示在完成当前任务i时,三个机器人分别在x,y ...

  6. [Python数据挖掘]第5章、挖掘建模(上)

    一.分类和回归 回归分析研究的范围大致如下: 1.逻辑回归 #逻辑回归 自动建模 import pandas as pd from sklearn.linear_model import Logist ...

  7. Oracle基础体系浅析

    不论是开发.管理.优化还是设计,对Oracle的基本原理的了解都是必不可少的,于是对自己最近关于Oracle的学习作出一点点的总结. 庖丁解牛之所以能做到"合于桑林之舞,乃中经首之会&quo ...

  8. java开发工具STS的下载及安装

    将下载后的压缩文件解压,在解压后的sts-bundle下的sts-3.9.1RELEASE目录中STS.exe便是可执行程序,用于启动STS,将该文件发送到桌面快捷方式,当我们想使用STS时可以快速的 ...

  9. IDEA调用其它模块module的类方法

    IDEA支持调用本project中其他模块的包里面的方法(需要配置该模块和src同级的.iml文件,配置完需要等一会才生效,尝试切换到桌面以...) 这样会使IDEA的project的模块间有依赖,该 ...

  10. wireshark基础学习—第二部分wireshark的基础操作

    抓取报文: 下载和安装好Wireshark之后,启动Wireshark并且在接口列表中选择接口名,然后开始在此接口上抓包.例如,如果想要在无线网络上抓取流量,点击无线接口.点击Capture Opti ...