2012-04-12 133 views
3

属性我有一个源XML像下面:如何替换元素名称空间前缀和使用XSLT

<SampleRequest xmlns="http://sample.com/s" 
     xmlns:s1="http://sample.com/s1" 
     xmlns:s2="http://sample.com/s2" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xsi:schemaLocation="http://sample.com/s schema.xsd"> 
<data> 
<s1:customer s1:firstName="Jim" s1:lastName="Ellison"/> 
<s2:address> 
    123 test street 
</s2:address> 
</data> 
</SampleRequest> 

我需要将其转换为以下

<SampleRequest xmlns="http://sample.com/t" 
     xmlns:t1="http://sample.com/t1" 
     xmlns:t2="http://sample.com/t2" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
     xsi:schemaLocation="http://sample.com/t targetSchema.xsd"> 
<data> 
<t1:customer t1:firstName="Jim" t1:lastName="Ellison"/> 
<t2:address> 
    123 test street 
</t2:address> 
</data> 
</SampleRequest> 

两个个XML具有相同的模式,但也不同的命名空间。

我尝试使用下面的XSLT

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
      xmlns="http://sample.com/s" 
      xmlns:s1="http://sample.com/s1" 
      xmlns:s2="http://sample.com/s2" 
      xmlns:t1="http://sample.com/t1" 
      xmlns:t2="http://sample.com/t2" 
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
      xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="s1 s2"> 
<xsl:output method="xml" encoding="UTF-8" indent="yes"/> 
<xsl:strip-space elements="*"/> 
<xsl:template match="/"> 
    <SampleRequest xmlns="http://sample.com/t" 
     xmlns:t1="http://sample.com/t1" 
     xmlns:t2="http://sample.com/t2" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> 
     <xsl:attribute name="xsi:schemaLocation" namespace="http://www.w3.org/2001/XMLSchema-instance"> 
      http://sample.com/t targetSchema.xsd 
     </xsl:attribute> 
     <xsl:copy> 
      <xsl:apply-templates select="@* | node()"/> 
     </xsl:copy> 
    </SampleRequest> 
</xsl:template> 
<xsl:template match="s1:*"> 
    <xsl:element name="t1:{local-name()}" namespace="http://sample.com/t1">  
     <xsl:apply-templates select="* | node()"/> 
    </xsl:element> 
</xsl:template> 

<xsl:template match="s2:*"> 
    <xsl:element name="t2:{local-name()}" namespace="http://sample.com/t2"> 
     <xsl:apply-templates select="* | node()"/> 
    </xsl:element> 
</xsl:template> 
</xsl:stylesheet> 

而且我得到以下结果

<?xml version="1.0" encoding="UTF-8"?><SampleRequest xmlns="http://sample.com/t" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:t2="http://sample.com/t2" xmlns:t1="http://sample.com/t1" xsi:schemaLocation=" http://sample.com/t targetSchema.xsd"> 
<t1:customer/> 
<t2:address> 
    123 test street 
</t2:address> 
</SampleRequest> 

似乎所有的属性都丢失。 我对XSLT非常陌生,每位都有帮助赞赏

回答

7

XSLT有两个问题。首先,在匹配s1和s2元素的位置,您不会尝试将模板应用于任何属性。您需要替换这一说法

<xsl:apply-templates select="* | node()"/> 

这种说法

<xsl:apply-templates select="@* | node()"/> 

其次,你没有任何模板匹配这样的属性。你需要一个模板,像这样:

<xsl:template match="@s1:*"> 
    <xsl:attribute name="t1:{local-name()}"> 
     <xsl:value-of select="." /> 
    </xsl:attribute> 
</xsl:template> 

试试这个XSLT

<xsl:stylesheet version="1.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns="http://sample.com/s" 
    xmlns:s1="http://sample.com/s1" 
    xmlns:s2="http://sample.com/s2" 
    xmlns:t1="http://sample.com/t1" 
    xmlns:t2="http://sample.com/t2" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    exclude-result-prefixes="s1 s2"> 

    <xsl:output method="xml" encoding="UTF-8" indent="yes"/> 

    <xsl:strip-space elements="*"/> 

    <xsl:template match="/"> 
     <SampleRequest 
     xmlns="http://sample.com/t" 
     xmlns:t1="http://sample.com/t1" 
     xmlns:t2="http://sample.com/t2" 
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> 
     <xsl:attribute name="xsi:schemaLocation">http://sample.com/t targetSchema.xsd</xsl:attribute> 
     <xsl:copy> 
      <xsl:apply-templates select="@* | node()"/> 
     </xsl:copy> 
     </SampleRequest> 
    </xsl:template> 

    <xsl:template match="s1:*"> 
     <xsl:element name="t1:{local-name()}"> 
     <xsl:apply-templates select="@* | node()"/> 
     </xsl:element> 
    </xsl:template> 

    <xsl:template match="@s1:*"> 
     <xsl:attribute name="t1:{local-name()}"> 
     <xsl:value-of select="."/> 
     </xsl:attribute> 
    </xsl:template> 

    <xsl:template match="s2:*"> 
     <xsl:element name="t2:{local-name()}"> 
     <xsl:apply-templates select="@* | node()"/> 
     </xsl:element> 
    </xsl:template> 

    <xsl:template match="@s2:*"> 
     <xsl:attribute name="t2:{local-name()}"> 
     <xsl:value-of select="."/> 
     </xsl:attribute> 
    </xsl:template> 
</xsl:stylesheet> 

当适用于您的示例XML,下面是输出:

<SampleRequest 
    xsi:schemaLocation="http://sample.com/t targetSchema.xsd" 
    xmlns:t1="http://sample.com/t1" 
    xmlns:t2="http://sample.com/t2" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns="http://sample.com/t"> 
    <t1:customer t1:firstName="Jim" t1:lastName="Ellison"/> 
    <t2:address> 123 test street </t2:address> 
</SampleRequest> 
相关问题