2013-09-27 89 views
0

我的基本XML就像如何更改節點名和XML複製節點的數據到另一個使用XSLT

<?xml version="1.0" encoding="iso-8859-1"?> 
<Report version="1.0"> 
    <sourceName Identification="xyz"/> 
    <sourcesys Identification="mycomp"> 
    <Manager> 
     <ManagerNo>1023114455</ManagerNo> 
     <Address>Delhi,India</Address> 
     <Currency> 
     <CurrencyType>Rupee</CurrencyType> 
     </Currency> 
    </Manager> 
    <Manager> 
     <ManagerNo>236784455</ManagerNo> 
     <Address>California,USA</Address> 
     <Currency> 
     <CurrencyType>Dollar</CurrencyType> 
     </Currency> 
    </Manager> 
    </sourcesys> 
</Report> 

我想這個XML轉換爲以下一個

<?xml version="1.0" encoding="UTF-8" standalone="yes"?> 
<ManagerDetails xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> 
    <ManagerDetail> 
    <ManagerNo>1023114455</ManagerNo> 
    <Address> 
     <PermenantAdd>California,USA</PermenantAdd> 
    </Address> 
    <CurrencyID>Rupee</CurrencyID> 
    </ManagerDetail> 
    <ManagerDetail> 
    <ManagerNo>236784455</ManagerNo> 
    <Address> 
     <PermenantAdd>Delhi,India</PermenantAdd> 
    </Address> 
    <CurrencyID>Dollar</CurrencyID> 
    </ManagerDetail> 
</managerDetails> 

這裏是標籤的映射:

  • sourcesys = managerDetails
  • 經理=管理rDetail
  • ManagerNo = ManagerNo
  • 地址= PermenantAdd
  • CurrencyType = CurrencyID

你怎麼會做這個使用XSLT?

+0

你的基礎XML絕對正確嗎?根元素是** a1:Report **,這意味着它是名稱空間的一部分,但沒有顯示名稱空間聲明,這意味着它無效。此外,** sourceName **元素在基本XML中沒有子元素,但在輸出中,當它轉換爲** ManagerDetails **時,它確實有子元素。 –

+0

@TimC:對不起,我忘了指定命名空間a1:Report。你可以認爲它是暫時定義的。對於SourceName的錯誤映射,我感到抱歉。我已更新問題請檢查。並請幫助我編寫xslt,因爲我第一次使用xslt。全新的xsl/xml/xslt – Ganeshkumar

回答

1

對於這樣的轉變,你應該於identity template來構建其自身的副本的所有節點在XSLT

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

這意味着你只需要編寫您希望轉換的節點的模板(這就是說,全部由ManagerNo元素組成)。

要變換sourcesys(同樣爲經理),例如,你可以這樣做

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

要刪除元素,如SOURCENAME你會只是忽略它的模板

<xsl:template match="sourceName"/> 

要處理地址這是不同略低因爲您需要添加新元素。在這種情況下,我會寫匹配的文本節點模板,並添加元素出現,比如:

<xsl:template match="Address/text()"> 
    <PermenantAdd> 
     <xsl:value-of select="." /> 
    </PermenantAdd> 
</xsl:template> 

最後,CurrencyTypeCurrencyID,這是直接的,但你而且還需要一個模板來跳過父貨幣元素,並處理它的孩子,像這樣:

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

試試這個XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="xml" indent="yes"/> 

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

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

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

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

    <xsl:template match="sourceName"/> 

    <xsl:template match="Address/text()"> 
     <PermenantAdd> 
     <xsl:value-of select="." /> 
     </PermenantAdd> 
    </xsl:template> 

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

    <xsl:template match="CurrencyType"> 
     <CurrencyID> 
     <xsl:apply-templates select="@*|node()"/> 
     </CurrencyID> 
    </xsl:template> 
</xsl:stylesheet> 

另請注意,有一個模板<xsl:template match="/*">跳過根元素,並且它是否具有命名空間也無所謂。

編輯:如果你不希望跨屬性複製爲sourcesys,而是使用新的屬性,嘗試更換像這樣

<xsl:template match="sourcesys"> 
     <ManagerDetails href="..."> 
     <xsl:apply-templates select="node()"/> 
     </ManagerDetails> 
    </xsl:template> 

通知模板如何XSL:申請模板現在缺少@*,所以它不會複製任何其他屬性。

如果你想

+0

非常感謝您的快速回復並給出簡要說明。我運行xslt,但在元素中,XSLT正在複製的「Idenification」屬性。我不想在中使用該屬性。相反,我想要一些硬編碼值的「href」屬性。我嘗試過,但沒能弄到:(。 – Ganeshkumar

+0

我已經做了一個編輯,直到我的答案結束,以顯示它!如果你有任何更多的需求,你不知道如何解決,最好問一下一個全新的問題現在這個答案已經被接受了,謝謝! –

1

試試這個:

<?xml version="1.0" encoding="utf-8"?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="xml" indent="yes" standalone="yes" encoding="utf-8" version="1.0"/> 

    <xsl:template match="/"> 
    <xsl:element name="ManagerDetails"> 
     <xsl:apply-templates /> 
    </xsl:element> 
    </xsl:template> 

    <xsl:template match="/Report/sourcesys/Manager"> 
    <xsl:element name="ManagerDetail"> 
     <xsl:apply-templates /> 
    </xsl:element> 
    </xsl:template> 

    <xsl:template match="/Report/sourcesys/Manager/ManagerNo"> 
    <xsl:copy-of select="."/> 
    </xsl:template> 

    <xsl:template match="/Report/sourcesys/Manager/Address"> 
    <xsl:copy> 
     <xsl:element name="PermenantAdd"> 
     <xsl:value-of select="."/> 
     </xsl:element> 
    </xsl:copy> 
    </xsl:template> 

    <xsl:template match="/Report/sourcesys/Manager/Currency/CurrencyType"> 
    <xsl:element name="CurrencyID"> 
     <xsl:value-of select="."/> 
    </xsl:element> 
    </xsl:template> 

    <xsl:template match="text()"></xsl:template> 

</xsl:stylesheet> 
+0

我真的很貼心你的解決方案。它按照我的要求完美地工作。非常感謝幫助我的傢伙:)。如果將來我喜歡刪除像** 那樣的完整xpath,那麼該怎麼做? – Ganeshkumar

相關問題