繁体   English   中英

在 C# 中使用从程序集导入加载 Xslt

[英]Load Xslt with import from assembly in C#

我有一个 xslt 文件 myxslt.xslt,其中包含一个导入,看起来有点像这样:

<?xml version="1.0" encoding="utf-8"?>    
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:import href="someOtherXsltFile.xslt"/>
  <!--Do some transformations -->  
</xsl:stylesheet>

我正在尝试使用程序集将这些文件导入到我的 C# 应用程序中:

Assembly assembly = Assembly.GetExecutingAssembly();

        using (Stream xsltStream = assembly.GetManifestResourceStream(mynamespace.myxslt.xslt))
        {
            using (XmlReader xsltReader = XmlReader.Create(xsltStream))
            {
                xslt.Load(xsltReader);
            }
        }

正如我在这个答案中看到的: 将(嵌入式资源)架构添加到 XmlReaderSettings 而不是文件名?

Stream 和 XmlReader 加载正常。

但是,当我尝试加载 xslt 时,我的应用程序抛出了找不到文件异常。 它无法加载的文件是someOtherXsltFile.xslt

这两个文件都作为嵌入式资源加载,并且都在assembly.GetManifestResourceNames的列表中可见。

我宁愿不更改 xslt 文件中的任何内容,因为这些是我尝试转换的消息随附的标准文件。

有没有办法使用从程序集中导入来加载我的 xslt?

感谢 stuartd 发布的链接( 如何解析 XSL 包含在从字符串加载 XSL 的转换中? )我设法找出了解决方案。

我的导入现在看起来像这样:

        Assembly assembly = Assembly.GetExecutingAssembly();

        using (Stream xsltStream = assembly.GetManifestResourceStream(mynamespace.myxslt.xslt))
        {
            using (XmlReader xsltReader = XmlReader.Create(xsltStream))
            {
                var resolver = new MyXmlUrlResolver();
                xslt.Load(xsltReader,null,resolver);
            }
        }

MyXmlUrlResolver定义如下:

private class MyXmlUrlResolver : XmlUrlResolver
    {
        private const string basePad = "MyNamespace.mysubnamespace.";

        public override object GetEntity(Uri absoluteUri, string role, Type ofObjectToReturn)
        {
            switch (absoluteUri.Scheme)
            {
                case "file":
                    {
                        string origString = absoluteUri.OriginalString;
                        Assembly assembly = Assembly.GetExecutingAssembly();
                        // the filename starts after the last \
                        int index = origString.LastIndexOf('\\');                            
                        string filename = origString.Substring(index + 1);

                        string resourceName = basePad + filename;

                        var stream = assembly.GetManifestResourceStream(resourceName);

                        return stream;
                    }
                default:
                    {
                        return (Stream)base.GetEntity(absoluteUri, role, ofObjectToReturn);
                    }
            }
        }
    }

这将加载 xslt,包括其所有导入。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM