2016-07-03 48 views
-2

我們輸入XML。對於許多行項目(OrderLineID元素),StockCode元素爲空。對於XML中的所有空的StockCode元素,必須有Comment元素值。同樣,對於所有這些空註釋元素,都必須存在StockCode值存在。XSLT:檢查空元素和空元素的條件,然後僅將值分配給其他元素

注意的OrderDetail在這裏重複的節點。

方案

我們必須拆分OrderDescription字符串。這種方式總是尋找空的StockCode元素。然後僅將分隔字符串值分配給Comment元素。否則,對於所有具有價值StockCode不應該指定分割字符串評論元素

輸入XML:

<SalesOrders xmlns:xsd="http://www.w3.org/2001/XMLSchema-instance" xsd:noNamespaceSchemaLocation="SORTOIDOC.XSD"> 
     <Orders> 
     <OrderHeader> 
      <Customer>000016</Customer> 
      <OrderDate>2016-04-19</OrderDate> 
      <SalesForceOrderNumber>ORD-411324</SalesForceOrderNumber> 
     </OrderHeader> 
     <OrderDetails> 
      <StockLine> 
      <StockCode>ABB-CDE-FGH-01</StockCode> 
      <OrderDescription>EDIORDER-SAVE COMMENTS 
    C3 Generic 
    LOC 0833 
    Expected arrival 01/07/2016 
    OTYPE NE 
    TRKPC 01 GM/00007643020008361321</OrderDescription> 
      <OrderLineID>OR-1561179</OrderLineID> 
      </StockLine> 
      <StockLine> 
        <StockCode>BCD-EFGH-01</StockCode> 
        <OrderLineID>OR-1561186</OrderLineID> 
        </Comment> 
        </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561180</OrderLineID> 
      </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561181</OrderLineID> 
      </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561182</OrderLineID> 
      </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561183</OrderLineID> 
      </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561184</OrderLineID> 
      </StockLine> 
      <StockLine> 
      <StockCode></StockCode> 
      </Comment> 
      <OrderLineID>OR-1561185</OrderLineID> 
      </StockLine> 
     </OrderDetails> 
     </Orders> 
    </SalesOrders> 

現有XSLT進行改造:

XSLT2.0

<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> 
    <xsl:strip-space elements="*"/> 

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

    <xsl:template match="StockLine"> 
     <xsl:variable name="i" select="position()" /> 
     <xsl:copy> 
      <xsl:copy-of select="StockCode"/> 
      <Comment> 
       <xsl:value-of select="normalize-space(tokenize(../StockLine[1]/OrderDescription, '\n')[$i])"/> 
      </Comment> 
      <xsl:copy-of select="OrderLineID"/> 
     </xsl:copy> 
    </xsl:template> 

    </xsl:stylesheet> 

Expec泰德輸出值:

<SalesOrders xmlns:xsd="http://www.w3.org/2001/XMLSchema-instance" xsd:noNamespaceSchemaLocation="SORTOIDOC.XSD"> 
       <Orders> 
       <OrderHeader> 
        <Customer>000016</Customer> 
        <OrderDate>2016-04-19</OrderDate> 
        <SalesForceOrderNumber>ORD-411324</SalesForceOrderNumber> 
       </OrderHeader> 
       <OrderDetails> 
        <StockLine> 
        <StockCode>ABB-CDE-FGH-01</StockCode> 
        </Comment> 
        <OrderDescription>EDIORDER-SAVE COMMENTS 
      C3 Generic 
      LOC 0833 
      Expected arrival 01/07/2016 
      OTYPE NE 
      TRKPC 01 GM/00007643020008361321</OrderDescription> 
        <OrderLineID>OR-1561179</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <StockCode>BCD-EFGH-01</StockCode> 
        <OrderLineID>OR-1561186</OrderLineID> 
        </Comment> 
        </StockLine> 
        <StockLine> 
        <Comment>EDIORDER-SAVE COMMENTS</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561180</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <Comment>C3 Generic</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561181</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <Comment>LOC 0833</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561182</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <Comment>Expected arrival 01/07/2016</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561183</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <Comment> OTYPE NE</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561184</OrderLineID> 
        </StockLine> 
        <StockLine> 
        <Comment>TRKPC 01 GM/00007643020008361321</Comment> 
        </StockCode> 
        <OrderLineID>OR-1561185</OrderLineID> 
        </StockLine> 
       </OrderDetails> 
       </Orders> 
      </SalesOrders> 
+0

讓我知道它是否可讀。<>它是在我的問題身上製作隱形詞。請刪除投票或建議是否需要更改! – NEO

+0

請從問題中移除投票,否則請提出改變。 – NEO

+0

您認爲「StockCode元素爲空」是什麼? ''一個空的元素? –

回答

1

這裏是我的建議權標化一次,並傳遞值作爲參數:

<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    exclude-result-prefixes="xs"> 

    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> 
    <xsl:strip-space elements="*"/> 

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

    <xsl:template match="OrderDetails"> 
     <xsl:copy> 
      <xsl:variable name="descriptions" as="xs:string*" select="tokenize(StockLine[1]/OrderDescription, '\n')"/> 
      <xsl:apply-templates> 
       <xsl:with-param name="descriptions" as="xs:string*" select="$descriptions" tunnel="yes"/> 
      </xsl:apply-templates> 
     </xsl:copy> 
    </xsl:template> 

    <xsl:template match="StockLine/StockCode[not(normalize-space())]"> 
     <xsl:param name="descriptions" tunnel="yes"/> 
     <xsl:variable name="pos" as="xs:integer"> 
      <xsl:number count="StockLine[StockCode[not(normalize-space())]]"/> 
     </xsl:variable> 
     <xsl:copy> 
      <xsl:value-of select="normalize-space($descriptions[$pos])"/> 
     </xsl:copy> 
    </xsl:template> 

</xsl:stylesheet> 

如果你想創建新的,而不是Comment元素填充空StockCode然後使用這樣的方法:

<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    exclude-result-prefixes="xs"> 

    <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> 
    <xsl:strip-space elements="*"/> 

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

    <xsl:template match="OrderDetails"> 
     <xsl:copy> 
      <xsl:variable name="descriptions" as="xs:string*" select="tokenize(StockLine[1]/OrderDescription, '\n')"/> 
      <xsl:apply-templates> 
       <xsl:with-param name="descriptions" as="xs:string*" select="$descriptions"/> 
      </xsl:apply-templates> 
     </xsl:copy> 
    </xsl:template> 

    <xsl:template match="StockLine[StockCode[not(normalize-space())]]"> 
     <xsl:param name="descriptions"/> 
     <xsl:variable name="pos" as="xs:integer"> 
      <xsl:number count="StockLine[StockCode[not(normalize-space())]]"/> 
     </xsl:variable> 
     <xsl:copy> 
      <xsl:copy-of select="*"/> 
      <Comment><xsl:value-of select="normalize-space($descriptions[$pos])"/></Comment> 
     </xsl:copy> 
    </xsl:template> 

</xsl:stylesheet> 
+0

應用給定的XSLT:應該分裂到而不是這裏是附加輸出後XSLT http://xsltransform.net/pPzifqt – NEO

+0

我的問題是這個問題的擴展:http:// stackoverflow.com/questions/38156641/xslt-string-wraphow-do-i-wrap-words-in-a-string-at-new-line-character-n?lq=1 – NEO

+0

一切看起來不錯只有StockCode價值應該下降註釋元素和StockCode應保持爲空值。 – NEO

1

要改變你的例子輸入你只需要做好StockCode節點上的模板匹配,像這樣:

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/> 
<xsl:strip-space elements="*"/> 

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



<xsl:template match="StockCode[not(node())]"> 
    <xsl:variable name="i"><xsl:number count="StockCode[not(node())]" select="../StockCode[not(node())]" level="any" /></xsl:variable> 
    <xsl:copy> 
      <xsl:value-of select="normalize-space(tokenize(ancestor::OrderDetails/StockLine[1]/OrderDescription, '\n')[number($i)])"/> 
    </xsl:copy> 
</xsl:template> 

</xsl:stylesheet> 

模板將只適用於沒有內容StockCodes。由於這是唯一的模板,所以其他節點在輸出中將保持不變(由於身份模板)。 匹配模板將計算所有以前的StockCode節點爲空,並將其用作索引來查找描述的標記化文本。

+0

謝謝你給我的解決方案 – NEO