User1218
User1218

Reputation: 27

Convert xml date output yyyy-mm-ddThh:mm:ss to dd-mmm-yy using xsl1.0

My XML outputs a due date in the format of yyyy-mm-ddThh:mm:ss.

I would like it to show dd-mmm-yy instead, for example 20-Nov-15.

This is what I am working on in my XSL1.0 stylesheet (simplified):

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" xmlns:user="urn:user-scripts" xmlns:aras="http://www.aras-corp.com">
<xsl:output method="html" omit-xml-declaration="yes" standalone="yes" indent="yes"/>
<xsl:template match="/">

<html>
<body>
    <table>
        <tr>
            <td>Action Item No</td>
            <td>Need Date</td>
        </tr>

        <xsl:for-each select="//Item">
            <tr>
                <td>
                    <xsl:value-of select="action_id"/>
                </td>
                <td>
                    <xsl:value-of select="due_date"/>
                </td>
            </tr>
        </xsl:for-each>
    </table>
</body>
</html>
</xsl:template>
</xsl:stylesheet>

Please advise how I can accomplish the new date format dd-mmm-yy in my XSL stylesheet, and exactly where to put in the code (it'd be great if you can paste the whole structure back to me so I can comprehend... total rookie here!)

Thank you!

Upvotes: 1

Views: 911

Answers (1)

Daniel Haley
Daniel Haley

Reputation: 52878

One option, that doesn't require any extensions, is to use substring() to get the pieces of date that you need and use an element structure to hold the month translations.

Example...

XML Input (complete guess since you didn't supply an example)

<Item>
    <action_id>A123</action_id>
    <due_date>2015-11-20T10:00:15</due_date>
</Item>

XSLT 1.0

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:local="local" exclude-result-prefixes="local">
    <xsl:output method="html" omit-xml-declaration="yes" standalone="yes" indent="yes"/>

    <local:months>
        <local:month>Jan</local:month>
        <local:month>Feb</local:month>
        <local:month>Mar</local:month>
        <local:month>Apr</local:month>
        <local:month>May</local:month>
        <local:month>Jun</local:month>
        <local:month>Jul</local:month>
        <local:month>Aug</local:month>
        <local:month>Sep</local:month>
        <local:month>Oct</local:month>
        <local:month>Nov</local:month>
        <local:month>Dec</local:month>
    </local:months>

    <xsl:template match="/">
        <html>
            <body>
                <table>
                    <tr>
                        <td>Action Item No</td>
                        <td>Need Date</td>
                    </tr>
                    <xsl:for-each select="//Item">
                        <tr>
                            <td>
                                <xsl:value-of select="action_id"/>
                            </td>
                            <td>
                                <xsl:variable name="year" 
                                    select="substring(due_date,3,2)"/>
                                <xsl:variable name="monthNbr" 
                                    select="number(substring(due_date,6,2))"/>
                                <xsl:variable name="month"
                                    select="document('')/*/local:months/local:month[position() = $monthNbr]"/>
                                <xsl:variable name="day" 
                                    select="substring(due_date,9,2)"/>
                                <xsl:value-of select="concat($day,'-',$month,'-',$year)"/>
                            </td>
                        </tr>
                    </xsl:for-each>
                </table>
            </body>
        </html>
    </xsl:template>
</xsl:stylesheet>

HTML Output

<html>
   <body>
      <table>
         <tr>
            <td>Action Item No</td>
            <td>Need Date</td>
         </tr>
         <tr>
            <td>A123</td>
            <td>20-Nov-15</td>
         </tr>
      </table>
   </body>
</html>

I broke the substring()'s out into multiple xsl:variable's to make it easier to see what's going on, but they aren't absolutely necessary.


EDIT

Here's an alternative that uses xsl:choose instead the local element structure...

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

    <xsl:template match="/">
        <html>
            <body>
                <table>
                    <tr>
                        <td>Action Item No</td>
                        <td>Need Date</td>
                    </tr>
                    <xsl:for-each select="//Item">
                        <tr>
                            <td>
                                <xsl:value-of select="action_id"/>
                            </td>
                            <td>
                                <xsl:variable name="year" 
                                    select="substring(due_date,3,2)"/>
                                <xsl:variable name="monthNbr" 
                                    select="number(substring(due_date,6,2))"/>
                                <xsl:variable name="month">
                                    <xsl:choose>
                                        <xsl:when test="$monthNbr=1">Jan</xsl:when>
                                        <xsl:when test="$monthNbr=2">Feb</xsl:when>
                                        <xsl:when test="$monthNbr=3">Mar</xsl:when>
                                        <xsl:when test="$monthNbr=4">Apr</xsl:when>
                                        <xsl:when test="$monthNbr=5">May</xsl:when>
                                        <xsl:when test="$monthNbr=6">Jun</xsl:when>
                                        <xsl:when test="$monthNbr=7">Jul</xsl:when>
                                        <xsl:when test="$monthNbr=8">Aug</xsl:when>
                                        <xsl:when test="$monthNbr=9">Sep</xsl:when>
                                        <xsl:when test="$monthNbr=10">Oct</xsl:when>
                                        <xsl:when test="$monthNbr=11">Nov</xsl:when>
                                        <xsl:when test="$monthNbr=12">Dec</xsl:when>
                                    </xsl:choose>
                                </xsl:variable>
                                <xsl:variable name="day" 
                                    select="substring(due_date,9,2)"/>
                                <xsl:value-of select="concat($day,'-',$month,'-',$year)"/>
                            </td>
                        </tr>
                    </xsl:for-each>
                </table>
            </body>
        </html>
    </xsl:template>
</xsl:stylesheet>

Here's another alternative that just uses another substring() (might be better than the first even)...

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

    <xsl:variable name="months" select="'JanFebMarAprMayJunJulAugSepOctNovDec'"/>

    <xsl:template match="/">
        <html>
            <body>
                <table>
                    <tr>
                        <td>Action Item No</td>
                        <td>Need Date</td>
                    </tr>
                    <xsl:for-each select="//Item">
                        <tr>
                            <td>
                                <xsl:value-of select="action_id"/>
                            </td>
                            <td>
                                <xsl:variable name="year" 
                                    select="substring(due_date,3,2)"/>
                                <xsl:variable name="monthNbr" 
                                    select="number(substring(due_date,6,2))"/>
                                <xsl:variable name="month" 
                                    select="substring($months,($monthNbr*3)-2,3)"/>
                                <xsl:variable name="day" 
                                    select="substring(due_date,9,2)"/>
                                <xsl:value-of select="concat($day,'-',$month,'-',$year)"/>
                            </td>
                        </tr>
                    </xsl:for-each>
                </table>
            </body>
        </html>
    </xsl:template>
</xsl:stylesheet>

Upvotes: 1

Related Questions