2012-10-01 23 views
7

मेरे डेटा मॉडल इस प्रकार है:एक्सएमएल रिकॉर्ड में सबसे हाल ही तिथि प्राप्त

<Club> 
<Captain> 
<Name></Name> 
<DateOfBirth>15-01-1985</DateOfBirth> 
</Captain> 
<PlayingStaff> 
<Player> 
<DateOfBirth>14-01-1993</DateOfBirth> 
</Player> 
<Player> 
<DateOfBirth>07-12-1975</DateOfBirth> 
</Player> 
<Player> 
<DateOfBirth>11-11-1991</DateOfBirth> 
</Player> 
</PlayingStaff> 
</Club> 

मैं इस सवाल का जवाब यहाँ दी का उपयोग कर की कोशिश की है: XSLT: Getting the latest date लेकिन यह मुझे किसी भी मूल्य दे रही है नहीं है।

मैं सबसे कम उम्र के खिलाड़ी को बाहरी समारोह में जाने की कोशिश कर रहा हूं।

मैं Biztalk में यह कर रहा हूँ तो मैं XSLT1

से चिपक है

मेरा काम अब तक इस प्रकार है के रूप में:

<xsl:variable name="youngestPlayer"> 
      <xsl:for-each select="$ClubRoot/*[local-name()='PlayingStaff']/*[local-name()='Player']"> 
       <xsl:sort select="./*[local-name()='DateOfBirth']" order="descending"/> 
       <xsl:if test="position() = 1"> 
        <xsl:value-of select="DateOfBirth"/> 
       </xsl:if> 
      </xsl:for-each> 
     </xsl:variable> 
     <xsl:variable name="IsYoungestPlayerUnderAgeLimit" select="externalfunctionreturningboolean"> 
      <xsl:element name="blahhh"><xsl:value-of select="$IsYoungestPlayerUnderAgeLimit"/></xsl:element> 
      <xsl:element name="blahhh"><xsl:value-of select="$youngestPlayer"/></xsl:element> 

यह एक बड़ा टेम्पलेट का हिस्सा है - मैं नहीं कर सकते वास्तव में यह परिवर्तन है, लेकिन ClubRoot का मान "<xsl:variable name="ClubRoot" select="/*[1]"/>" सुनिश्चित करने के लिए मैं अपने बच्चे नोड्स पढ़ सकते है।

मैं हमेशा हो रही है

<blahhh>false</blahhh> 
<blahhh/> 

मेरे डीबग मानों के रूप में ... इसलिए मैं उस मूल्य को नहीं उठा रहा हूं जो मुझे उम्मीद है

क्या कोई यह बता सकता है कि मैं गलत कहां गया हूं?

उपर्युक्त डेटा से, मैं अपने सबसे छोटे खिलाड़ी चर में 14-01-1993 के मूल्य की अपेक्षा करता हूं। लेकिन यह खाली है।

उत्तर

6

समस्या यह है कि XSLT1.0 में वास्तव में तिथियों की अवधारणा नहीं है, इसलिए आप प्रभावी रूप से डेटऑफबर्थ तत्वों द्वारा प्रभावी रूप से सॉर्ट कर रहे हैं जैसे कि वे सामान्य स्ट्रिंग थे। आप सुनिश्चित हो सकते हैं दिनांकों हमेशा तुम्हारे वर्ष, माह और दिन से सॉर्ट करने के

<xsl:sort select="number(substring(DateOfBirth, 7, 4))" order="descending"/> 
<xsl:sort select="number(substring(DateOfBirth, 3, 2))" order="descending"/> 
<xsl:sort select="number(substring(DateOfBirth, 1, 2))" order="descending"/> 

तो स्ट्रिंग परिवर्तन इस्तेमाल कर सकते हैं प्रारूप डीडी-MM-YYYY में आते हैं, निम्नलिखित XSLT

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="xml" indent="yes"/> 
    <xsl:template match="/Club"> 
     <xsl:for-each select="PlayingStaff/Player"> 
     <xsl:sort select="number(substring(DateOfBirth, 7, 4))" order="descending"/> 
     <xsl:sort select="number(substring(DateOfBirth, 3, 2))" order="descending"/> 
     <xsl:sort select="number(substring(DateOfBirth, 1, 2))" order="descending"/> 

     <xsl:if test="position() = 1"> 
      <xsl:value-of select="DateOfBirth"/> 
     </xsl:if> 
     </xsl:for-each> 
    </xsl:template> 
</xsl:stylesheet> 
दिया

अपने XML के लिए आवेदन किया तो निम्न उत्पादन

14-01-1993 
+2

का अनुवाद() फ़ंक्शन का उपयोग कर, आप XSL की गिनती कम कर सकते हैं तक है है: प्रकार 3 से 1 के निर्देश, और 'xsl: sort/@ select expression' को सरल बनाएं। –

1

कारण है कि तारीख अपने लिंक किए गए संदर्भ में छँटाई 'में काम किया' था, क्योंकि यह yyyy-MM-dd प्रारूप में था, के रूप में y करने का विरोध किया है हमारे dd-MM-yyyy प्रारूप।

टिम सी/शॉन के प्रस्ताव का एक विकल्प सी # स्क्रिप्ट फ़ंक्शंस का उपयोग करना है (क्योंकि आप बिज़टॉक का उपयोग कर रहे हैं) तिथि को अपने लिंक के अनुसार एक क्रमबद्ध करने के लिए वापस करने के लिए - लेकिन ध्यान दें कि यह देशी के रूप में प्रदर्शन करने की संभावना नहीं है xslt कार्यों। ध्यान दें कि बिज़टॉक के पार्सर को बताने के लिए आपको अपने चर पर msxsl:node-set का उपयोग करने की आवश्यकता हो सकती है कि यह एक टुकड़ा है।

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
       xmlns:userCSharp="http://schemas.microsoft.com/BizTalk/2003/userCSharp" 
       xmlns:msxsl="urn:schemas-microsoft-com:xslt" 
       exclude-result-prefixes="userCSharp msxsl" 
       > 
    <xsl:output method="xml" indent="yes"/> 

    <xsl:template match="/"> 
     <xsl:variable name="ClubRoot" select="/*[1]"/> 
     <xsl:variable name="orderedPlayers"> 
      <xsl:for-each select="msxsl:node-set($ClubRoot)/*[local-name()='PlayingStaff']/*[local-name()='Player']"> 
       <xsl:sort select="userCSharp:makeSortableDate(string(*[local-name()='DateOfBirth']), 'dd-MM-yyyy')" order="descending"/> 
       <xsl:copy-of select="node() | @*"/> 
      </xsl:for-each> 
     </xsl:variable> 

     <xsl:variable name="youngestPlayerDOB"> 
      <xsl:value-of select="msxsl:node-set($orderedPlayers)[1]/DateOfBirth/text()" /> 
     </xsl:variable> 

     <xsl:element name="blahhh"> 
      <xsl:variable name="IsYoungestPlayerUnderAgeLimit" select="userCSharp:externalfunctionreturningboolean($youngestPlayerDOB)" /> 
      <xsl:value-of select="$IsYoungestPlayerUnderAgeLimit"/> 
     </xsl:element> 
     <xsl:element name="blahhh"> 
      <xsl:value-of select="$youngestPlayerDOB"/> 
     </xsl:element> 
    </xsl:template> 

    <msxsl:script language="C#" implements-prefix="userCSharp"> 
     <![CDATA[ 
     public System.String makeSortableDate(System.String yourDate, string format) 
     { 
      return (System.DateTime.ParseExact(yourDate, format, System.Globalization.CultureInfo.InvariantCulture).ToString("yyyy-MM-dd")); 
     } 

     public bool externalfunctionreturningboolean(System.String dobString) 
     { 
      System.DateTime someDate; 
      if (System.DateTime.TryParse(dobString, out someDate)) 
      { 
       // NB : Doesn't work out leap years correctly! 
       if ((System.DateTime.Now - someDate).Days < 21 * 365.25) 
       { 
        return true; 
       } 
      } 
      return false; 
     } 
    ]]> 
    </msxsl:script> 

</xsl:stylesheet> 

मैं समारोह में एक हैक लिया जाता है और अनुमान लगाया है कि कम उम्र की सीमा 21 से ऊपर रिटर्न

<blahhh>true</blahhh> 
<blahhh>14-01-1993</blahhh> 
संबंधित मुद्दे