我创建了一个 BizTalk 自定义管道组件,它将所有消息部分压缩到一个 zip 流中。在一些失败之后,我在一个单独的测试项目中创建了以下测试方法。
基本上,我得到一个 XML 文件,其中包含一个文件名和一个 UUID,我用它来调用存储过程并获取数据库条目的 Base64 编码内容。base64 内容似乎有效,因为在对其进行解码并将其保存到文件系统后,Windows 资源管理器可以毫无问题地读取文件。
将存档流保存到文件系统后,当我尝试提取文件时,我从 7Zip 收到以下错误消息:“数据意外结束”。如果我尝试仅使用 7Zip 打开文件,则没有问题。我什至可以从 7Zip 资源管理器中打开文件。
如果我尝试使用以下代码从 C# 读取文件,则会收到错误消息:“找不到中央目录记录的结尾。”
解压代码:
private static void ReadDat() {
var path = @"...\zip\0e00128b-0a6e-4b99-944d-68e9c20a51c2.zip";
var stream = System.IO.File.OpenRead(path);
// End of Central Directory record could not be found:
var zipArchive = new ZipArchive(stream, ZipArchiveMode.Read, false);
foreach(var zipEntry in zipArchive.Entries) {
var stream = zipEntry.Open();
Console.WriteLine(stream.Length);
}
}
Run Code Online (Sandbox Code Playgroud)
邮政编码:
private static void StreamUuidList() {
var path = @"...\2017-08-05T132705.xml";
var xdoc = XDocument.Load(System.IO.File.OpenRead(path));
var files = xdoc.Root.Descendants().Where(d => d.Name.LocalName.Equals("NodeName"));
using (var archiveStream = new MemoryStream())
using (var archive = new ZipArchive(archiveStream, ZipArchiveMode.Create, true)) {
foreach (var file in files) {
var fileName = file.Elements().Where(e => e.Name.LocalName.Equals("FileName")).FirstOrDefault()?.Value ?? "";
var streamUuid = file.Elements().Where(e => e.Name.LocalName.Equals("StreamUUID")).FirstOrDefault()?.Value ?? "";
// validation here...
// get base64 content and convert content
var base64Content = GetStreamContent(streamUuid);
var data = Convert.FromBase64String(base64Content);
var dataStream = new MemoryStream(data);
dataStream.Seek(0, SeekOrigin.Begin);
// debug - save to file location
using (var fileStream = new FileStream($@"...\files\{fileName}", FileMode.Create)) {
dataStream.CopyTo(fileStream);
}
dataStream.Seek(0, SeekOrigin.Begin);
// create zip entry
var zipFile = archive.CreateEntry(fileName, GetCompressionLevelFromString("Optimal"));
using (var zipFileStream = zipFile.Open()) {
// copy data from mesage part stream into zip entry stream
dataStream.Seek(0, SeekOrigin.Begin);
dataStream.CopyTo(zipFileStream);
}
Console.WriteLine(fileName + ": " + streamUuid);
}
// debug - save to file location
archiveStream.Seek(0, SeekOrigin.Begin);
using (var fileStream = new FileStream($@"...\zip\{Guid.NewGuid()}.dat", FileMode.Create)) {
archiveStream.CopyTo(fileStream);
}
// debug end
}
}
Run Code Online (Sandbox Code Playgroud)