【问题标题】:How to create a generic XSLT to add nodes如何创建通用 XSLT 以添加节点
【发布时间】:2021-08-20 10:24:14
【问题描述】:

我有多个不同格式的 XML 文件,所有这些文件在通过之前都需要有一个特定的标签,因此我想编写一个通用的 XSLT,它将接受任何 XML 输入并简单地在之前添加额外的标签和在有效载荷之后。例如:

输入 XML(示例 1)

<?xml version="1.0" encoding="UTF-8"?>

<Order>
    <data1>
        <test>1</test>
        <test2>2</test2>
        <test3>3</test3>
    </data1>
</Order>

它也可以是另一个带有&lt;Invoice&gt; 或其他任何内容的 XML。

需要的输出

<?xml version="1.0" encoding="UTF-8"?>
<soap:envelope>
<soap:body>
<Order>
    <data1>
        <test>1</test>
        <test2>2</test2>
        <test3>3</test3>
    </data1>
</Order>
</soap:body>
</soap:envelope>

使用以下 XSLT,我需要知道传入的是哪个节点(订单或发票)以匹配模式 - 但这可以是通用的吗?

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    version="1.0">
    <xsl:output method="xml" indent="yes"/>
    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>
<!-- I do not want to specify the node here -->
    <xsl:template match="Order">
        <soap:envelope>
        <soap:body>
            <xsl:copy-of select="*"/>              
        </soap:body>
        </soap:envelope>
    </xsl:template>
  </xsl:stylesheet>

【问题讨论】:

  • 由于 是动态的,请尝试匹配根本身。

标签: templates generics select xslt nodes


【解决方案1】:

您显示的输出不是格式良好的 XML 文档:如果不将前缀绑定到命名空间,您将无法使用它。您的 XSLT 也有同样的缺陷,不能在不产生错误的情况下使用(至少不能使用符合标准的处理器)。

我猜你想用:

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

<xsl:template match="/">
    <soap:envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope">
        <soap:body>
            <xsl:copy-of select="."/>              
        </soap:body>
    </soap:envelope>
</xsl:template>

</xsl:stylesheet>

生成有效的SOAP 消息:

<?xml version="1.0" encoding="UTF-8"?>
<soap:envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope">
   <soap:body>
      <Order>
         <data1>
            <test>1</test>
            <test2>2</test2>
            <test3>3</test3>
         </data1>
      </Order>
   </soap:body>
</soap:envelope>

【讨论】:

  • 谢谢!是的,我在原始消息中跳过了名称空间,但这非常有效。目前无法投票,但已接受答案。
  • @michael :如果在样式表声明中而不是在元素本身中使用命名空间,那么在这种情况下有什么区别?即,&lt;xsl:stylesheet xmlns:soap="---"&lt;soap:envelope xmlns:soap="---"
  • @sspsujit 在这种情况下没有区别。
【解决方案2】:

您需要为此匹配root

<xsl:template match="/">
    <soap:envelope>
    <soap:body>
        <xsl:copy-of select="."/>              
    </soap:body>
    </soap:envelope>
</xsl:template>

测试:https://xsltfiddle.liberty-development.net/jxWZS7L

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-07-31
    • 1970-01-01
    • 1970-01-01
    • 2020-08-08
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多