<Root>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<milderror></milderror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
</Root>
您好,
我不确定如何使用xslt。 xml文件的“Envelope”元素始终存在偶数次,原因是,xml将根据对(第一,第二,第三和第四等)指示我们成功,错误或警告。最重要的是“criticalerror”元素,也就是说,如果该元素存在于该对中,则该对被视为错误,该元素也可以出现两次。
下一个优先级是“milderror”元素,它代表警告。第三个优先事项是“成功”要素。因此,只有当两者都包含“成功”时才被视为成功。
对于上述情况,第一对成功,第二对是错误,第三对是错误,第四对是警告。有两个错误,一个是成功,一个是警告。这将产生如下的xml。同样,错误具有更高的优先级(首先在xml中出现),然后警告
<Root>
<error></error>
<error></error>
<warning></warning>
<success></success>
</Root>
现在,对于每个配对场景(成功,错误和警告),每个动作都有上面的xml,每个动作有三个(这就是我的设计),这是datapower中的一个动作
为了我的每个动作的成功,我需要从顶部xml中获取“ineed”元素,对应于成功对,即“apple”,这可以出现在一对或两者中,在一对顶部xml。对于一对,它是相同的,但是可以在任何一个或两个中发生。
我所拥有的只是上下文loopcount变量(在本例中为1),为了成功,将为所有成功场景迭代
类似于错误场景(在这种情况下循环2次),需要从顶部xml获取相应的“ineed”元素。 Loopcount变量1,下一次loopcount变量为2
同样适用于警告场景。
答案 0 :(得分:1)
这是一个完整的解决方案:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/*">
<Root>
<xsl:apply-templates select="Envelope[position() mod 2 = 1]">
<xsl:sort select=
"not((.|following-sibling::Envelope[1])/criticalerror)"/>
<xsl:sort select=
"not((.|following-sibling::Envelope[1])/milderror)"/>
</xsl:apply-templates>
</Root>
</xsl:template>
<xsl:template match=
"Envelope
[position() mod 2 = 1
and
success
and
following-sibling::Envelope[1]/success
]">
<success>
<xsl:call-template name="getTitle"/>
</success>
</xsl:template>
<xsl:template match=
"Envelope
[position() mod 2 = 1
and
(.|following-sibling::Envelope[1])/criticalerror
]">
<error>
<xsl:call-template name="getTitle"/>
</error>
</xsl:template>
<xsl:template match=
"Envelope
[position() mod 2 = 1
and
(.|following-sibling::Envelope[1])/milderror
and
not((.|following-sibling::Envelope[1])/criticalerror)
]">
<warning>
<xsl:call-template name="getTitle"/>
</warning>
</xsl:template>
<xsl:template name="getTitle">
<xsl:value-of select=
"(.|following-sibling::Envelope[1])
/Header/ineed[normalize-space()]
[1]
"/>
</xsl:template>
<xsl:template match="text()"/>
</xsl:stylesheet>
将此转换应用于提供的XML文档:
<Root>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<criticalerror></criticalerror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<milderror></milderror>
</Envelope>
<Envelope>
<Header>
<ineed>apple</ineed>
</Header>
<success></success>
</Envelope>
</Root>
产生了想要的正确结果:
<Root>
<error>apple</error>
<error>apple</error>
<warning>apple</warning>
<success>apple</success>
</Root>
<强>解释强>:
未使用<xsl:for-each>
,仅<xsl:apply-templates>
。
模板仅明确应用于每对Envelope
元素的第一个Envelope
。
在两个select
中指定处理元素的处理顺序(在xsl:apply-templates
xsl:sort
属性中指定的节点列表中)的顺序说明 - 首先是错误,然后是警告,然后是其他任何事情(成功)。
我们使用以下事实:当对布尔值进行排序时,false()
先于true()
。
调用名为getTitle
的模板,以输出相应的ineed
元素对中包含的第一个非空Envelope
元素的有用字符串值。
答案 1 :(得分:0)
你为什么要使用for-each?据我所知,你不需要循环计数器。你想选择每一对中的第一个元素(我不喜欢这个设计,但让我们放手)就像这样:
然后为这些元素编写模板。在该模板中,您可以使用XPath表达式“following-sibling :: Envelope [1]”获取该对的第二个元素。
如果您需要对奇数元素进行排序,您可能需要执行以下操作:
等等。