我想复制所有子节点的 only header 元素,并添加到每个子节点前缀“v11”(包括标题元素)
来源xml:
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<ns3:createReservationRequest xmlns:ns3="ns3URL" xmlns:ns2="ns2URL">
<header>
<language isoCountryCode="US" isoLanguageCode="en"/>
<channel name="DT">
<subChannel name="WEBWB">
<subChannel name="WEBWB">
<subChannel name="Functester">
<subChannel name="ecom"/>
</subChannel>
</subChannel>
</subChannel>
</channel>
</header>
<ns3:agentInfo>
<ns2:agentDutyCode>PR</ns2:agentDutyCode>
</ns3:agentInfo>
</ns3:createReservationRequest>
</soap:Body>
</soap:Envelope>
期望的结果xml:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:v1="v1URL"
xmlns:v11="v11URL">
<soapenv:Body>
<v1:createBookerEventRequest>
<v11:header>
<v11:channel name="DT">
<v11:subChannel name="WEBWB">
<v11:subChannel name="WEBWB">
<v11:subChannel name="Functester">
<v11:subChannel name="ecom"/>
</v11:subChannel>
</v11:subChannel>
</v11:subChannel>
</v11:channel>
</v11:header>
</v1:createBookerEventRequest>
</soapenv:Body>
</soapenv:Envelope>
我尝试使用here中的示例来实现此功能。我写了以下xsl:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:v11="v11URL">
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes"/>
<xsl:template match="/">
<xsl:copy>
<xsl:apply-templates select="//*[local-name()='header']/*"/>
</xsl:copy>
</xsl:template>
<xsl:template match="//*[local-name()='header']/*">
<xsl:element name="v11:{name()}" inherit-namespaces="no">
<xsl:apply-templates select="node()|@*"/>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
但它不会将子通道复制到结果xml中。并且还将不需要的“xmlns:v11 =”http://example.com/schema/common/ATPCommonServiceTypes/v1“属性添加到标题子节点。感谢任何帮助
答案 0 :(得分:2)
这是我的(编辑过的)建议:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:v1="v1URL"
xmlns:v11="v11URL"
xmlns:ns3="ns3URL"
exclude-result-prefixes="soap ns3">
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* , node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="/*">
<xsl:copy>
<xsl:copy-of select="document('')/xsl:stylesheet/namespace::*[local-name() = ('v1', 'v11')]"/>
<xsl:apply-templates select="@* , node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="*[not(namespace-uri())]">
<xsl:element name="v11:{local-name()}">
<xsl:apply-templates select="@* , node()"/>
</xsl:element>
</xsl:template>
<xsl:template match="ns3:createReservationRequest">
<v1:createBookerEventRequest>
<xsl:apply-templates select="@* , node()"/>
</v1:createBookerEventRequest>
</xsl:template>
<xsl:template match="ns3:agentInfo"/>
</xsl:stylesheet>
答案 1 :(得分:2)
我向xmlns
添加了agentDutyCode
声明,因为它缺少名称空间声明:
<ns2:agentDutyCode xmlns:ns2="ns2URL">PR</ns2:agentDutyCode>
将源与此样式表一起使用(评论中说明的模板):
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:v11="v11URL"
xmlns:v1="v1URL"
xmlns:ns3="ns3URL"
exclude-result-prefixes="ns3">
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes"/>
<xsl:strip-space elements="*"/>
<!-- Copies Envelope and Body preserving their namespace -->
<xsl:template match="soap:Envelope | soap:Body">
<xsl:copy>
<xsl:apply-templates select="node()|@*"/>
</xsl:copy>
</xsl:template>
<!-- Creates the createReservationRequest element -->
<xsl:template match="ns3:createReservationRequest">
<v1:createBookerEventRequest>
<xsl:apply-templates/>
</v1:createBookerEventRequest>
</xsl:template>
<!-- Ignores language and agentInfo subtrees -->
<xsl:template match="language"/>
<xsl:template match="ns3:agentInfo"/>
<!-- Matches all other elements -->
<xsl:template match="*">
<xsl:element name="v11:{local-name()}" inherit-namespaces="no">
<xsl:apply-templates select="node()|@*"/>
</xsl:element>
</xsl:template>
<!-- Copies attributes -->
<xsl:template match="@*">
<xsl:copy>
<xsl:value-of select="."/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
您将得到以下结果:
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
<v1:createBookerEventRequest xmlns:v11="v11URL" xmlns:v1="v1URL">
<v11:header>
<v11:channel name="DT">
<v11:subChannel name="WEBWB">
<v11:subChannel name="WEBWB">
<v11:subChannel name="Functester">
<v11:subChannel name="ecom"/>
</v11:subChannel>
</v11:subChannel>
</v11:subChannel>
</v11:channel>
</v11:header>
</v1:createBookerEventRequest>
</soap:Body>
</soap:Envelope>
以下是 XSLT Fiddle ,您可以在其中查看结果。