2011-08-30 147 views
5

我是新來的XSLT,並試圖使用XSLT映射一個XML到另一個XML,這是我的第一個XMLXML到XML映射使用XSLT

<root> 
    <record> 
     <element name="LoginId">a</element> 
     <element name="name">Admin Manager</element> 
     <element name="password">12345</element> 
     <element name="Age">28</element> 
     <element name="Sex">M</element> 
    </record> 
    <record> 
     <element name="LoginId">b</element> 
     <element name="name">HR exec</element> 
     <element name="password">pass1</element> 
     <element name="Age">26</element> 
     <element name="Sex">F</element> 
    </record> 
    <record> 
     <element name="LoginId">c</element> 
     <element name="name">PR Manager</element> 
     <element name="password">pass2</element> 
     <element name="Age">27</element> 
     <element name="Sex">M</element> 
    </record> 
</root> 

我需要這個XML轉換爲以下

<?xml version="1.0" encoding="UTF-8"?> 
<final> 
    <test> 
     <UID>a</UUID> 
     <Name>HR manager</Name> 
     <Groups>admingroup</Groups> 
     <Password>12345</Password> 
    </test> 
    <test> 
     <UID>b</UUID> 
     <Name>HR exec</Name> 
     <Groups>admingroup</Groups> 
     <Password>pass1</Password> 
    </test> 
    <test> 
     <UID>c</UUID> 
     <Name>PR manager</Name> 
     <Groups>admingroup</Groups> 
     <Password>pass2</Password> 
    </test> 
</final> 

我試圖下面的XSLT用於轉化

<?xml version="1.0" encoding="UTF-8" ?> 
- <xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> 
- <xsl:template match="/"> 
- <test> 
- <xsl:for-each select="root/record"> 
    <xsl:apply-templates select="element" /> 
    </xsl:for-each> 
    </test> 
    </xsl:template> 
- <xsl:template match="element"> 
- <test> 
    <Employee /> 
- <UID> 
    <xsl:value-of select="@LoginId" /> 
    </UID> 
- <xsl:choose> 
- <xsl:when test="@name = ''"> 
- <Name> 
    <xsl:text>demo employee</xsl:text> 
    </Name> 
    </xsl:when> 
- <xsl:otherwise> 
- <Name> 
    <xsl:value-of select="@name" /> 
    </Name> 
    </xsl:otherwise> 
    </xsl:choose> 
- <Groups> 
    <xsl:text>admingroup</xsl:text> 
    </Groups> 
- <Password> 
    <xsl:value-of select="@password" /> 
    </Password> 
    </test> 
    </xsl:template> 
    </xsl:transform> 

但這XSLT是產生下面的XML輸出

<?xml version="1.0" encoding="UTF-8"?> 
<impex> 
    <final> 
     <Employee /> 
     <UID /> 
     <Name>LoginId</Name> 
     <Groups>admingroup</Groups> 
     <Password /> 
    </final> 

total 15 <final></final> with similar output 

我可以很容易地做到這一點在Java中,但一些如何在XSLT和我面臨的唯一問題做的是<element>標籤都有不同的屬性的重複值

在這方面的任何幫助將非常妄作

+0

+1以及結構問題。 –

回答

2

即使您已經擁有@ Martin提供的優秀解決方案(+1),我在這裏修復了您的轉換,以向您展示您錯誤的位置。這可能有助於您進一步瞭解XSLT(和XPath)的工作原理。

<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> 
    <xsl:output indent="yes"/> 

    <xsl:template match="/"> 
     <final> 
       <xsl:apply-templates select="root/record" /> 
     </final> 
    </xsl:template> 

    <xsl:template match="record"> 
     <test> 
      <Employee /> 
      <UID> 
       <xsl:value-of select="element[@name='LoginId']" /> 
      </UID> 
      <xsl:choose> 
       <xsl:when test="element[@name='name']=''"> 
        <Name> 
         <xsl:text>demo employee</xsl:text> 
        </Name> 
       </xsl:when> 
       <xsl:otherwise> 
        <Name> 
         <xsl:value-of select="element[@name='name']"/> 
        </Name> 
       </xsl:otherwise> 
      </xsl:choose> 
      <Groups> 
       <xsl:text>admingroup</xsl:text> 
      </Groups> 
      <Password> 
       <xsl:value-of select="element[@name='password']" /> 
      </Password> 
     </test> 
    </xsl:template> 

</xsl:transform> 

注意xsl:choose的做法是正確的,即使正常的最好方式XSLT是模板規則:

<xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0"> 
    <xsl:output indent="yes"/> 

    <xsl:template match="/"> 
     <final> 
      <xsl:apply-templates select="root/record" /> 
     </final> 
    </xsl:template> 

    <xsl:template match="record"> 
     <test> 
      <Employee /> 
      <UID> 
       <xsl:value-of select="element[@name='LoginId']" /> 
      </UID> 
      <Name> 
       <xsl:apply-templates select="element[@name='name']"/> 
      </Name> 
      <Groups> 
       <xsl:text>admingroup</xsl:text> 
      </Groups> 
      <Password> 
       <xsl:value-of select="element[@name='password']" /> 
      </Password> 
     </test> 
    </xsl:template> 

    <xsl:template match="element[@name='name'][.='']"> 
      <xsl:text>demo employee</xsl:text> 
    </xsl:template> 

    <xsl:template match="element[@name='name'][.!='']"> 
      <xsl:value-of select="."/> 
    </xsl:template> 

</xsl:transform> 
+1

謝謝..因爲這會幫助我更清楚地理解事情。 –

+0

不客氣。確保接受最適合您的問題的答案。 –

2

我想接近它是這樣的:

<xsl:stylesheet 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    version="2.0"> 

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

    <xsl:template match="root"> 
    <final> 
     <xsl:apply-templates/> 
    </final> 
    </xsl:template> 

    <xsl:template match="record"> 
    <test> 
     <xsl:apply-templates select="element[@name = ('LoginId', 'name')]"/> 
     <Groups>admingroup</Groups> 
     <xsl:apply-templates select="element[@name = 'password']"/> 
    </test> 
    </xsl:template> 

    <xsl:template match="element[@name = 'LoginId']"> 
    <UID> 
     <xsl:value-of select="."/> 
    </UID> 
    </xsl:template> 

    <xsl:template match="element[@name = 'name']"> 
    <Name> 
     <xsl:value-of select="."/> 
    </Name> 
    </xsl:template> 

    <xsl:template match="element[@name = 'password']"> 
    <Password> 
     <xsl:value-of select="."/> 
    </Password> 
    </xsl:template> 

</xsl:stylesheet> 

這樣撒克遜9.3從您的樣品輸入產生以下結果:

<final> 
    <test> 
     <UID>a</UID> 
     <Name>Admin Manager</Name> 
     <Groups>admingroup</Groups> 
     <Password>12345</Password> 
    </test> 
    <test> 
     <UID>b</UID> 
     <Name>HR exec</Name> 
     <Groups>admingroup</Groups> 
     <Password>pass1</Password> 
    </test> 
    <test> 
     <UID>c</UID> 
     <Name>PR Manager</Name> 
     <Groups>admingroup</Groups> 
     <Password>pass2</Password> 
    </test> 
</final> 
0

使用源模式到目標架構與變換地圖。 XSLT更適合於XML轉換成其他格式,用於顯示數據的緣故..

結帳的BizTalk