Thanks again for your work with MODSRDF!

To avoid a lengthy e-mail, I will try to modularize my suggestions, which 
will also help cooperation to discuss different features of the XSLT in 
different threads.

To mitigate confusions when refering to line numbers, this first e-mail 
focuses on a question concerning a feature at the end of the XSLT file.

To begin with, to be able to compile the XSLT, I temporarily modified it 

I discarded the xsl:otherwise immediately below the XML comment with the 
text on line 1234

> remaining admin metadata elements

Furthermore, on line 1634, primaryTitleIdentifier is used but not defined 
and I temporarily discarded the xsl:if immediately surrounding it, too.

After these two temporary removals, which I won't discuss in any detail 
within this e-mail, let's now focus on the duck-type design pattern I 
suggest to use within this XSLT.

Near the line 1894 at the end of the modsrdf.xsl XSLT, the value of the 
rdf:datatype is choosen according to attribute values in the input file. 
This does not only assumes that the attribute values in the input file are 
appropriately chosen. As it is formulated today, xsd:date is choosen as 
the value of the rdf:datatype when the input file states that its datatype 
is iso8601, which may give erroneous results because iso8601 is neither 
equal to nor a subset of xsd:date.

My suggestion is to use a RegEx to test the value given in the input MODS 
file and use it to choose an appropriate value for the rdf:datatype 
attribute accordingly.

Based on the RegExes at and

I suggest to define the following variables:

xsl:variable name="dateRegex" select="'-?([1-9][0-9]{3}[0-9]*|0[0-9]{3})-(0[1-9]|1[0-2])-(0[1-9]|[12][0-9]|3[01])'"

xsl:variable name="timeRegex" select="'T(([01][0-9]|2[0-3]):[0-5][0-9]:[0-5][0-9](\.[0-9]+)?|(24:00:00(\.0+)?))'"

xsl:variable name="zoneRegex" select="'(Z|(\+|-)((0[0-9]|1[0-3]):[0-5][0-9]|14:00))'"

Thereafter, the value of the rdf:datatype on line 1894 can be established 
within xsl:when statements similar to

xsl:when test="matches($value, concat('^', $dateRegex, $zoneRegex, '?$'))"

xsl:value-of select="'xsd:date'"/


xsl:when test="matches($value, concat('^', $dateRegex, $timeRegex, $zoneRegex, '?$'))"

xsl:value-of select="'xsd:dateTime'"/


etc. In this e-mail, I removed angle brackets to avoid possible 
misrenderings in some e-mail user agents. Also, I did not give any 
complete solution: maybe, we would want several xsl:when and also an 
xsl:otherwise as a catch-up at the end of the xsl:choose but I assume that 
you will understand the description of the design suggestion I give here.

An other (somewhat more complex) suggestion would be to use a parameter to 
let the user choose which design pattern to use at run-time.

Comments are welcome! I hope this helps!