I have Two Dates Say :
start date: 30-04-2016 and,
end date: 27-08-2016
I want to write a Xpath Query which will return all the record which
have <StartDate> and <EndDate> In between the above two dates(Both
Inclusive).
Here is a single, pure XPath 2.0 expression that selects all such <record> elements:
/*/record
[xs:date(string-join(reverse(tokenize(StartDate, '-')), '-')) ge xs:date('2016-04-30')
and xs:date(string-join(reverse(tokenize(EndDate, '-')), '-')) le xs:date('2016-08-27')]
XSLT-based verification:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:template match="/">
<xsl:copy-of select=
"/*/record
[xs:date(string-join(reverse(tokenize(StartDate, '-')), '-'))
ge xs:date('2016-04-30')
and xs:date(string-join(reverse(tokenize(EndDate, '-')), '-'))
le xs:date('2016-08-27')]"/>
</xsl:template>
</xsl:stylesheet>
When this transformation is applied on the following XML document (the provided fragment with a top element parent):
<t>
<record>
<name>John</name>
<StartDate>01-05-2016</StartDate>
<EndDate>30-10-2016</EndDate>
</record>
<record>
<name>Jerry</name>
<StartDate>29-04-2016</StartDate>
<EndDate>30-06-2016</EndDate>
</record>
<record>
<name>Mike</name>
<StartDate>05-06-2016</StartDate>
<EndDate>25-08-2016</EndDate>
</record>
</t>
the Xpath expression is evaluated and the selected nodes (in this case just one) are copied to the output:
<record>
<name>Mike</name>
<StartDate>05-06-2016</StartDate>
<EndDate>25-08-2016</EndDate>
</record>
II. XPath 1.0 solution
The equivalent XPath 1.0 expression is:
/*/record
[concat(substring(StartDate,7), substring(StartDate,4,2), substring(StartDate,1,2))
>= 20160430
and not(concat(substring(EndDate,7), substring(EndDate,4,2), substring(EndDate,1,2))
> 20160827)]
XSLT 1.0 - based verification:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/">
<xsl:copy-of select=
"/*/record
[concat(substring(StartDate,7), substring(StartDate,4,2), substring(StartDate,1,2))
>= 20160430
and not(concat(substring(EndDate,7), substring(EndDate,4,2), substring(EndDate,1,2))
> 20160827)]"/>
</xsl:template>
</xsl:stylesheet>
When this transformation is applied on the same XML document as above, the same wanted, correct result is produced:
<record>
<name>Mike</name>
<StartDate>05-06-2016</StartDate>
<EndDate>25-08-2016</EndDate>
</record>