尊敬的专家, 我必须在XSLT中使用多个for循环。
目前,通过XSLT,我在'GroupDetail'处生成了带有额外节点的输出。
输入请求
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"
xmlns:v1="http://xmldefs. ag.com/Applications/eer/V1" xmlns:wsa="http://www.w3.org/2005/08/addressing">
<SOAP-ENV:Header>
<wsa:messageId>04383-34380-3439939</wsa:messageId>
</SOAP-ENV:Header>
<SOAP-ENV:Body>
<v1:ProcessDistr xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<v1:Group xmlns:ns2="http://xmldefs.ag.com/DD/Commons">
<v1:GroupID>437848</v1:GroupID>
<v1:GroupDetails>
<v1:GroupDetail>
<v1:language>De</v1:language>
<v1:description>Deutsch</v1:description>
</v1:GroupDetail>
<v1:GroupDetail>
<v1:language>En</v1:language>
<v1:description>English</v1:description>
</v1:GroupDetail>
</v1:GroupDetails>
<v1:Status>true</v1:Status>
<v1:Parent>45434554</v1:Parent>
</v1:Group>
<v1:Group xmlns:ns2="http://xmldefs.ag.com/DD/Commons">
<v1:GroupID>437849</v1:GroupID>
<v1:GroupDetails>
<v1:GroupDetail>
<v1:language>Tu</v1:language>
<v1:description>Turkish</v1:description>
</v1:GroupDetail>
<v1:GroupDetail>
<v1:language>Fr</v1:language>
<v1:description>French</v1:description>
</v1:GroupDetail>
</v1:GroupDetails>
<v1:Status>true</v1:Status>
<v1:Parent>45434555</v1:Parent>
</v1:Group>
</v1:ProcessDistr>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
收到的输出带有另一组“组”详细信息,并且也缺少“ messageId”。
收到的输出:
<?xml version="1.0" encoding="UTF-8"?>
<ProcessDistr >
<Group >
<GroupID>437848</GroupID>
<GroupDetails>
<GroupDetail>
<language>De</language>
<description>Deutsch</description>
</GroupDetail>
<GroupDetail>
<language>En</language>
<description>English</description>
</GroupDetail>
<GroupDetail>
<language>Tu</language>
<description>Turkish</description>
</GroupDetail>
<GroupDetail>
<language>Fr</language>
<description>French</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434554</Parent>
</Group>
<Group >
<GroupID>437849</GroupID>
<GroupDetails>
<GroupDetail>
<language>De</language>
<description>Deutsch</description>
</GroupDetail>
<GroupDetail>
<language>En</language>
<description>English</description>
</GroupDetail>
<GroupDetail>
<language>Tu</language>
<description>Turkish</description>
</GroupDetail>
<GroupDetail>
<language>Fr</language>
<description>French</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434555</Parent>
</Group>
<messageId/>
</ProcessDistr>
这是我开发的XSLT代码
使用的XSLT代码:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:prof="http://ixult.net/ProfileExchange"
xmlns:sap="http://www.sap.com/sapxsl" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsltc="http://xml.apache.org/xalan/xsltc"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:v1="http://xmldefs. ag.com/Applications/eer/V1"
xmlns:vwsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd" xmlns:ns2="http://xmldefs.vag.com/DD/Commons"
exclude-result-prefixes="vwsu v1 ns2 xsi wsa" xmlns:wsa="http://www.w3.org/2005/08/addressing">
<!-- Output -->
<xsl:output encoding="UTF-8" indent="yes" method="xml" omit-xml-declaration="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/">
<xsl:element name="ProcessDistr">
<xsl:for-each select="//soap:Body/v1:ProcessDistr/v1:Group">
<xsl:element name="Group">
<xsl:element name="GroupID"><xsl:value-of select="v1:GroupID"/></xsl:element>
<xsl:element name="GroupDetails">
<xsl:for-each select="//v1:GroupDetails/v1:GroupDetail">
<xsl:element name="GroupDetail">
<xsl:element name="language"><xsl:value-of select="v1:language"/></xsl:element>
<xsl:element name="Description">
<xsl:value-of select="v1:Description"/></xsl:element>
</xsl:element>
</xsl:for-each>
</xsl:element>
<xsl:element name="Status"><xsl:value-of select="v1:Status"/></xsl:element>
<xsl:element name="Parent"><xsl:value-of select="v1:Parent"/></xsl:element>
</xsl:element>
</xsl:for-each>
<xsl:element name="messageId"><xsl:value-of select="wsa:messageID"/>
</xsl:element>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
预期输出:
<?xml version="1.0" encoding="UTF-8"?>
<ProcessDistr >
<Group >
<GroupID>437848</GroupID>
<GroupDetails>
<GroupDetail>
<language>De</language>
<description>Deutsch</description>
</GroupDetail>
<GroupDetail>
<language>En</language>
<description>English</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434554</Parent>
</Group>
<Group >
<GroupID>437849</GroupID>
<GroupDetails>
<GroupDetail>
<language>Tu</language>
<description>Turkish</description>
</GroupDetail>
<GroupDetail>
<language>Fr</language>
<description>French</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434555</Parent>
</Group>
<messageId>04383-34380-3439939</messageId>
</ProcessDistr>
请帮助我输入此代码
非常感谢您。
致以最诚挚的问候, 卫星N
答案 0 :(得分:0)
您的XSLT的主要问题是(第20行):
<xsl:for-each select="//v1:GroupDetails/v1:GroupDetail">
以//
开头的路径将选择根节点的所有后代,而不管当前上下文如何。您只想处理当前v1:Group
的后代,因此需要将其更改为:
<xsl:for-each select="v1:GroupDetails/v1:GroupDetail">
还请注意,XML区分大小写:
<xsl:value-of select="v1:Description"/>
不会返回名为v1:description
的元素的值。
我还建议使用literal result elements代替xsl:element
指令。需要在运行时确定元素名称时,请使用xsl:element
。
答案 1 :(得分:0)
请帮助我输入此代码
尊敬的Satish,
提供的代码的主要问题不在第20行,尽管解决此问题有助于获得所需的输出。
主要问题是代码没有使用强大的XSLT处理模型,使用该模型可以在没有任何<xsl:for-each>
指令的情况下表示解决方案。而且,可以缩小代码并使之更紧凑,更易理解和可维护。
这里是一个入门解决方案(30行),显示了如何实现:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:soap-env="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:v1="http://xmldefs. ag.com/Applications/eer/V1" xmlns:wsa="http://www.w3.org/2005/08/addressing"
exclude-result-prefixes="soap-env wsa v1">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="node()|@*">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="/*">
<xsl:apply-templates select="soap-env:Body"/>
</xsl:template>
<xsl:template match="v1:ProcessDistr">
<ProcessDistr>
<xsl:apply-templates/>
<xsl:apply-templates select="/*/soap-env:Header/wsa:messageId"/>
</ProcessDistr>
</xsl:template>
<xsl:template match="v1:* | wsa:*">
<xsl:element name="{local-name()}">
<xsl:apply-templates select="node()|@*"/>
</xsl:element>
</xsl:template>
<xsl:template match="soap-env:*"><xsl:apply-templates/></xsl:template>
</xsl:stylesheet>
将此转换应用于提供的XML文档时:
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:wsu="http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"
xmlns:v1="http://xmldefs. ag.com/Applications/eer/V1" xmlns:wsa="http://www.w3.org/2005/08/addressing">
<SOAP-ENV:Header>
<wsa:messageId>04383-34380-3439939</wsa:messageId>
</SOAP-ENV:Header>
<SOAP-ENV:Body>
<v1:ProcessDistr xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<v1:Group xmlns:ns2="http://xmldefs.ag.com/DD/Commons">
<v1:GroupID>437848</v1:GroupID>
<v1:GroupDetails>
<v1:GroupDetail>
<v1:language>De</v1:language>
<v1:description>Deutsch</v1:description>
</v1:GroupDetail>
<v1:GroupDetail>
<v1:language>En</v1:language>
<v1:description>English</v1:description>
</v1:GroupDetail>
</v1:GroupDetails>
<v1:Status>true</v1:Status>
<v1:Parent>45434554</v1:Parent>
</v1:Group>
<v1:Group xmlns:ns2="http://xmldefs.ag.com/DD/Commons">
<v1:GroupID>437849</v1:GroupID>
<v1:GroupDetails>
<v1:GroupDetail>
<v1:language>Tu</v1:language>
<v1:description>Turkish</v1:description>
</v1:GroupDetail>
<v1:GroupDetail>
<v1:language>Fr</v1:language>
<v1:description>French</v1:description>
</v1:GroupDetail>
</v1:GroupDetails>
<v1:Status>true</v1:Status>
<v1:Parent>45434555</v1:Parent>
</v1:Group>
</v1:ProcessDistr>
</SOAP-ENV:Body>
</SOAP-ENV:Envelope>
产生了所需的正确结果:
<ProcessDistr>
<Group>
<GroupID>437848</GroupID>
<GroupDetails>
<GroupDetail>
<language>De</language>
<description>Deutsch</description>
</GroupDetail>
<GroupDetail>
<language>En</language>
<description>English</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434554</Parent>
</Group>
<Group>
<GroupID>437849</GroupID>
<GroupDetails>
<GroupDetail>
<language>Tu</language>
<description>Turkish</description>
</GroupDetail>
<GroupDetail>
<language>Fr</language>
<description>French</description>
</GroupDetail>
</GroupDetails>
<Status>true</Status>
<Parent>45434555</Parent>
</Group>
<messageId>04383-34380-3439939</messageId>
</ProcessDistr>
XSLT是一种很棒的语言,当使用它的全部功能时,它将为我们提供简短而优雅的解决方案。有很好的学习资源等待被发现。