如何在C#中直接读取ZIP文件中的XML文件?

3

在Java中,您可以传递类似于“zip:zip_file!xml_file”的网址,并且它将在zip文件内使用指定的XML文件。但是XmlUrlResolver没有此功能。是否有一种方法可以实现这一点?

2个回答

5

这里有一些使用ICSharpCode.SharpZipLib的代码:

public bool Process()
    {
        var importFile = new FileInfo("c:\\foo\myzip.zip");
        var success = true;
        using (var zipStream = new ZipInputStream(importFile.OpenRead()))
        {
            ZipEntry theEntry;
            while ((theEntry = zipStream.GetNextEntry()) != null)
            {
                var lowerName = theEntry.Name.ToLower();

                try
                {

                    if (lowerName.EndsWith(".xml") && !lowerName.StartsWith("__macosx"))
                    {

                        var doc = new XmlDocument();
                        doc.Load(zipStream);
                    }
                }
                catch (Exception e)
                {
                    success = false;
                    Log.Error(string.Format("Error parsing {0} ERROR {1}",lowerName,e.Message));
                }

            }
        }
        return success;
    }

这个过程会处理zip文件中的每个xml文件...除了那些烦人的Mac OsX元数据文件 :)

本来想推荐SharpZipLib。+1 :) - Roloc

4
有一个开源解决方案可以实现这一点。 (XmlZipResolver的代码在xml reports上。) 它继承自XmlUrlResolver,以添加此功能。
实际上,这很简单。类XmlZipResolver继承自XmlUrlResolver。因此,在以前创建XmlUrlResolver对象来访问XML文件的地方,现在需要创建一个XmlZipResolver对象,然后您可以像处理XmlUrlResolver对象一样处理它。并且只有当url以zip:或jar:(Java jar文件是zip文件)开头时,才使用附加代码处理XmlUrlResolver可以处理的任何url。
关键部分在于对GetEntity的调用,它将打开zip文件,然后获取zip文件中所请求的xml文件的流。此代码使用SharpZipLib来访问所有zip文件。
之后,所有成员函数的调用都非常简单,从嵌入式xml文件的流返回。因为GetEntity()返回一个对象,如果它返回一个基本的XmlUrlResolver对象,则不会调用该类中的方法。因此,所有剩余的成员函数都是针对zip文件中的文件编写的。
另外一个值得注意的事项是返回的流是一个包含三个对象的对象,即ZipFile、作为zip文件的Stream和作为zip条目的流的Stream。这个返回的对象继承自Stream。对于除Close()之外的每个调用,它只是将相同的调用传递给zip条目流对象。但是在关闭(因此间接关闭)时,它会关闭所有三个对象。
再次强调,XmlZipResolver的代码在xml reports上。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接