title: XSLT Validation: for-each giving error "empty sequence is not allowed as the @select attribute of xsl:analyze-string"
body: <p>I am trying to validate the format of a date that repeats within an XML message.  I got this same "empty string" error when I only had one date in a template.  I was able to get that template to work.  But when I add a "for-each" construct to account for a date that may repeat in the XML message, I get the error "empty sequence is not allowed as the @select attribute of xsl:analyze-string".  Besides the fact that I don't understand why I'm getting this error just by adding the "for-each", I'm not sure why the validation code thinks there is an empty sequence.  Although it's possible for the date to be missing (which I thought I fixed the first time around, when not using the for-each construct), my test message does have the date I am trying to test.  I read through a few other answers on the site, but either I don't understand how to apply the fix or I don't know if the suggested fixes will address my problem (I'm not a programmer).  </p>
  
  <p>Could someone please help me fix this code so that I can test for this date that will repeat?  </p>
  
  <p>The structure of the message is </p>
  
  <pre><code>&lt;VXU_V04.ORDER&gt; One or more may be present, not a required group; I’m calling this “OrderGroup”
  &lt;RXA&gt; Required; only one RXA Segment per OrderGroup allowed
  &lt;RXA.3&gt; Required; only one RXA.3 field per RXA Segment allowed
  &lt;TS.1&gt; is a sub-components of RXA.3
  </code></pre>
  
  <p>Here is the relevant part of the sample message</p>
  
  <pre><code> &lt;VXU_V04.ORDER&gt;
      &lt;ORC&gt;
        &lt;ORC.1&gt;RE&lt;/ORC.1&gt;
        &lt;ORC.3&gt;
          &lt;EI.1&gt;197023&lt;/EI.1&gt;
          &lt;EI.2&gt;DCS&lt;/EI.2&gt;
        &lt;/ORC.3&gt;
        &lt;ORC.10&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Clerk&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;Myron&lt;/XCN.3&gt;
        &lt;/ORC.10&gt;
        &lt;ORC.17&gt;
          &lt;CE.1&gt;DCS&lt;/CE.1&gt;
          &lt;CE.2&gt;Dabig Clinical System&lt;/CE.2&gt;
          &lt;CE.3&gt;StateIIS&lt;/CE.3&gt;
        &lt;/ORC.17&gt;
      &lt;/ORC&gt;
      &lt;RXA&gt;
        &lt;RXA.1&gt;0&lt;/RXA.1&gt;
        &lt;RXA.2&gt;1&lt;/RXA.2&gt;
        &lt;RXA.3&gt;
          &lt;TS.1&gt;20090415132511&lt;/TS.1&gt;
        &lt;/RXA.3&gt;
        &lt;RXA.4&gt;
          &lt;TS.1&gt;20090415132511&lt;/TS.1&gt;
        &lt;/RXA.4&gt;
        &lt;RXA.5&gt;
          &lt;CE.1&gt;31&lt;/CE.1&gt;
          &lt;CE.2&gt;Hep B Peds NOS&lt;/CE.2&gt;
          &lt;CE.3&gt;CVX&lt;/CE.3&gt;
        &lt;/RXA.5&gt;
        &lt;RXA.6&gt;999&lt;/RXA.6&gt;
        &lt;RXA.9&gt;
          &lt;CE.1&gt;01&lt;/CE.1&gt;
          &lt;CE.2&gt;historical record&lt;/CE.2&gt;
          &lt;CE.3&gt;NIP0001&lt;/CE.3&gt;
        &lt;/RXA.9&gt;
      &lt;/RXA&gt;
    &lt;/VXU_V04.ORDER&gt;
    &lt;VXU_V04.ORDER&gt;
      &lt;ORC&gt;
        &lt;ORC.1&gt;RE&lt;/ORC.1&gt;
        &lt;ORC.3&gt;
          &lt;EI.1&gt;197027&lt;/EI.1&gt;
          &lt;EI.2&gt;DCS&lt;/EI.2&gt;
        &lt;/ORC.3&gt;
        &lt;ORC.10&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Clerk&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;Myron&lt;/XCN.3&gt;
        &lt;/ORC.10&gt;
        &lt;ORC.12&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Pediatric&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;MARY&lt;/XCN.3&gt;
          &lt;XCN.10&gt;L&lt;/XCN.10&gt;
          &lt;XCN.21&gt;MD&lt;/XCN.21&gt;
        &lt;/ORC.12&gt;
      &lt;/ORC&gt;
      &lt;RXA&gt;
        &lt;RXA.1&gt;0&lt;/RXA.1&gt;
        &lt;RXA.2&gt;1&lt;/RXA.2&gt;
        &lt;RXA.3&gt;
          &lt;TS.1&gt;20090531132511&lt;/TS.1&gt;
        &lt;/RXA.3&gt;
        &lt;RXA.4&gt;
          &lt;TS.1&gt;20090531132511&lt;/TS.1&gt;
        &lt;/RXA.4&gt;
        &lt;RXA.5&gt;
          &lt;CE.1&gt;48&lt;/CE.1&gt;
          &lt;CE.2&gt;HIB PRP-T&lt;/CE.2&gt;
          &lt;CE.3&gt;CVX&lt;/CE.3&gt;
        &lt;/RXA.5&gt;
        &lt;RXA.6&gt;999&lt;/RXA.6&gt;
        &lt;RXA.9&gt;
          &lt;CE.1&gt;00&lt;/CE.1&gt;
          &lt;CE.2&gt;new Immunization record&lt;/CE.2&gt;
          &lt;CE.3&gt;NIP0001&lt;/CE.3&gt;
        &lt;/RXA.9&gt;
        &lt;RXA.10&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Sticker&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;Nurse&lt;/XCN.3&gt;
        &lt;/RXA.10&gt;
        &lt;RXA.11&gt;
          &lt;LA2.4&gt;
            &lt;HD.1&gt;DCS_DC&lt;/HD.1&gt;
          &lt;/LA2.4&gt;
        &lt;/RXA.11&gt;
        &lt;RXA.15&gt;33k2a&lt;/RXA.15&gt;
        &lt;RXA.17&gt;
          &lt;CE.1&gt;PMC&lt;/CE.1&gt;
          &lt;CE.2&gt;sanofi&lt;/CE.2&gt;
          &lt;CE.3&gt;MVX&lt;/CE.3&gt;
        &lt;/RXA.17&gt;
      &lt;/RXA&gt;
      &lt;RXR&gt;
        &lt;RXR.1&gt;
          &lt;CE.1&gt;C28161&lt;/CE.1&gt;
          &lt;CE.2&gt;IM&lt;/CE.2&gt;
          &lt;CE.3&gt;NCIT&lt;/CE.3&gt;
          &lt;CE.4&gt;IM&lt;/CE.4&gt;
          &lt;CE.5&gt;IM&lt;/CE.5&gt;
          &lt;CE.6&gt;HL70162&lt;/CE.6&gt;
        &lt;/RXR.1&gt;
      &lt;/RXR&gt;
    &lt;/VXU_V04.ORDER&gt;
    &lt;VXU_V04.ORDER&gt;
      &lt;ORC&gt;
        &lt;ORC.1&gt;RE&lt;/ORC.1&gt;
        &lt;ORC.3&gt;
          &lt;EI.1&gt;197028&lt;/EI.1&gt;
          &lt;EI.2&gt;DCS&lt;/EI.2&gt;
        &lt;/ORC.3&gt;
        &lt;ORC.10&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Clerk&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;Myron&lt;/XCN.3&gt;
        &lt;/ORC.10&gt;
        &lt;ORC.12&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Pediatric&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;MARY&lt;/XCN.3&gt;
          &lt;XCN.10&gt;L&lt;/XCN.10&gt;
          &lt;XCN.21&gt;MD&lt;/XCN.21&gt;
        &lt;/ORC.12&gt;
      &lt;/ORC&gt;
      &lt;RXA&gt;
        &lt;RXA.1&gt;0&lt;/RXA.1&gt;
        &lt;RXA.2&gt;1&lt;/RXA.2&gt;
        &lt;RXA.3&gt;
          &lt;TS.1&gt;20090531132511&lt;/TS.1&gt;
        &lt;/RXA.3&gt;
        &lt;RXA.4&gt;
          &lt;TS.1&gt;20090531132511&lt;/TS.1&gt;
        &lt;/RXA.4&gt;
        &lt;RXA.5&gt;
          &lt;CE.1&gt;110&lt;/CE.1&gt;
          &lt;CE.2&gt;DTAP-Hep B-IPV&lt;/CE.2&gt;
          &lt;CE.3&gt;CVX&lt;/CE.3&gt;
        &lt;/RXA.5&gt;
        &lt;RXA.6&gt;999&lt;/RXA.6&gt;
        &lt;RXA.9&gt;
          &lt;CE.1&gt;00&lt;/CE.1&gt;
          &lt;CE.2&gt;new immunization record&lt;/CE.2&gt;
          &lt;CE.3&gt;NIP0001&lt;/CE.3&gt;
        &lt;/RXA.9&gt;
        &lt;RXA.10&gt;
          &lt;XCN.2&gt;
            &lt;FN.1&gt;Sticker&lt;/FN.1&gt;
          &lt;/XCN.2&gt;
          &lt;XCN.3&gt;Nurse&lt;/XCN.3&gt;
        &lt;/RXA.10&gt;
        &lt;RXA.11&gt;
          &lt;LA2.4&gt;
            &lt;HD.1&gt;DCS_DC&lt;/HD.1&gt;
          &lt;/LA2.4&gt;
        &lt;/RXA.11&gt;
        &lt;RXA.15&gt;xy3939&lt;/RXA.15&gt;
        &lt;RXA.17&gt;
          &lt;CE.1&gt;SKB&lt;/CE.1&gt;
          &lt;CE.2&gt;GSK&lt;/CE.2&gt;
          &lt;CE.3&gt;MVX&lt;/CE.3&gt;
        &lt;/RXA.17&gt;
      &lt;/RXA&gt;
      &lt;RXR&gt;
        &lt;RXR.1&gt;
          &lt;CE.1&gt;IM&lt;/CE.1&gt;
          &lt;CE.2&gt;IM&lt;/CE.2&gt;
          &lt;CE.3&gt;HL70162&lt;/CE.3&gt;
          &lt;CE.4&gt;C28161&lt;/CE.4&gt;
          &lt;CE.5&gt;IM&lt;/CE.5&gt;
          &lt;CE.6&gt;NCIT&lt;/CE.6&gt;
        &lt;/RXR.1&gt;
      &lt;/RXR&gt;
    &lt;/VXU_V04.ORDER&gt;
  </code></pre>
  
  <p>Here is my validation template. I've tried a few different things like having the "for-each" statement before each "analyze-string" function.  I've tried adding a count on TS1Field but I keep getting syntax errors when I try to incorporate the count check into this:  .</p>
  
  <p>I think this may be a similar issue I had where the template was not recognizing my sub-component (TS1Field).  I posted a question about that on this site and got a good answer which fixed another problem in another validation template.  However, when I try the same thing here, it's not working.  </p>
  
  <p>(By the way, I know I have descriptions for a different field in here - Patient Death Date - but that is from the template I used as a basis for this one.  I haven't gotten around to updating those messages yet.)</p>
  
  <pre><code>&lt;xsl:stylesheet version="2.0" xmlns:a="urn:hl7-org:v2xml" xmlns:dil="http://www.aegis.net/msg/filter/jaxb/rule" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"&gt;
      &lt;!--      
               Must be VALUED AND 
               Must not repeat
           --&gt;
      &lt;xsl:variable name="OrderGroup" select="/a:VXU_V04/a:VXU_V04.ORDER"/&gt;
      &lt;xsl:variable name="RXASegment" select="/a:VXU_V04/a:VXU_V04.ORDER/a:RXA"/&gt;
      &lt;xsl:variable name="RXA3Field" select="/a:VXU_V04/a:VXU_V04.ORDER/a:RXA/a:RXA.3"/&gt;
      &lt;xsl:variable name="TS1Field" select="/a:VXU_V04/a:VXU_V04.ORDER/a:RXA/a:TS.1"/&gt;
      &lt;xsl:template match="/"&gt;
          &lt;dil:filterruleresult&gt;
               &lt;xsl:choose&gt;
                   &lt;xsl:when test= "count($OrderGroup)= 0"&gt;
                      &lt;dil:message type="info"&gt;VXU Order Group not found.&lt;/dil:message&gt;
                   &lt;/xsl:when&gt;
               &lt;/xsl:choose&gt;
               &lt;xsl:for-each select="$OrderGroup"&gt;
                       &lt;xsl:choose&gt;
                         &lt;xsl:when test="count(a:RXA)= 0"&gt;  
                            &lt;dil:message type="error"&gt;When Order Group present, RXA Segment is required.&lt;/dil:message&gt;
                         &lt;/xsl:when&gt;
                         &lt;xsl:when test="count(a:RXA)&gt; 1"&gt;  
                          &lt;dil:message type="error"&gt;Only one Pharmacy/Treatment Administration Segment (RXA) allowed per Order Group.&lt;/dil:message&gt;
                         &lt;/xsl:when&gt;
                         &lt;xsl:otherwise&gt;
                            &lt;xsl:for-each select="a:RXA"&gt;
                               &lt;xsl:choose&gt;
                                   &lt;xsl:when test="count(a:RXA.3)= 0"&gt;
                                  &lt;dil:message type="error"&gt;RXA-3 Date/Time Start of Administration not found but is required.&lt;/dil:message&gt;
                                   &lt;/xsl:when&gt; 
                                   &lt;xsl:when test="count(a:RXA.3)&gt; 1"&gt;
                                  &lt;dil:message type="error"&gt;Only one Date/Time Start of Administration (RXA-3) allowed per Order Segment.&lt;/dil:message&gt;
                                   &lt;/xsl:when&gt; 
                                   &lt;xsl:when test="count(a:RXA.3)= 1"&gt;
                                       &lt;dil:message type="info"&gt;Valid value of '&lt;xsl:value-of select="./a:RXA.3"/&gt;' found for Administered Amount (RXA-6).&lt;/dil:message&gt;
                                   &lt;/xsl:when&gt;
                                 &lt;/xsl:choose&gt;
                            &lt;/xsl:for-each&gt;     
                                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                                              &lt;xsl:analyze-string regex="([&amp;quot;|'])(.*?)\1" select="$TS1Field"&gt;
                                  &lt;xsl:matching-substring&gt;
                                      &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) '&lt;xsl:value-of select="$TS1Field"/&gt;' found in message, but contains invalid apostrophes or quotes within the value text.&lt;/dil:message&gt;
                                  &lt;/xsl:matching-substring&gt;
                                  &lt;xsl:non-matching-substring&gt;
                                      &lt;dil:message type="info"&gt;Patient Death Date and Time (PID-29) '&lt;xsl:value-of select="$TS1Field"/&gt;' found in message.  If any validation errors are found, they will follow this message. &lt;/dil:message&gt;
                                  &lt;/xsl:non-matching-substring&gt;
                              &lt;/xsl:analyze-string&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,1,4) !=''"&gt;
                                      &lt;xsl:analyze-string regex="^(19|20)\d{{2}}$" select="substring($TS1Field,1,4)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for year not a valid year as required.  Valid years have century of 19 or 20.  Found value '&lt;xsl:value-of select="substring($TS1Field,1,4)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,5,2) !=''"&gt;
                                      &lt;xsl:analyze-string regex="0[1-9]|1[0-2]" select="substring($TS1Field,5,2)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for month not a valid month as required.  Valid months are 01-12.  Found value '&lt;xsl:value-of select="substring($TS1Field,5,2)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,7,2) !=''"&gt;
                                      &lt;xsl:analyze-string regex="0[1-9]|1[0-9]|2[0-9]|3[0-1]" select="substring($TS1Field,7,2)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for day not a valid day value as required.  Valid days are 01-31.  Found value '&lt;xsl:value-of select="substring($TS1Field,7,2)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,9,2) !=''"&gt;
                                      &lt;xsl:analyze-string regex="0[0-9]|1[0-9]|2[0-3]" select="substring($TS1Field,9,2)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for hour not a valid hour value as required.  Valid values are 00-23.  Found value '&lt;xsl:value-of select="substring($TS1Field,9,2)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,11,2) !=''"&gt;
                                      &lt;xsl:analyze-string regex="0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]" select="substring($TS1Field,11,2)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for hour not a valid for minute not a valid minute value as required.  Valid values are 00-59.  Found value '&lt;xsl:value-of select="substring($TS1Field,11,2)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,13,2) !=''"&gt;
                                      &lt;xsl:analyze-string regex="0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]" select="substring($TS1Field,13,2)"&gt;
                                          &lt;xsl:non-matching-substring&gt;
                                              &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value for seconds not a valid seconds value as required.  Valid values are 00-59.  Found value '&lt;xsl:value-of select="substring($TS1Field,13,2)"/&gt;' in message.&lt;/dil:message&gt;
                                          &lt;/xsl:non-matching-substring&gt;
                                      &lt;/xsl:analyze-string&gt;
                                  &lt;/xsl:when&gt;
                              &lt;/xsl:choose&gt;
                     &lt;/xsl:for-each&gt;         
                     &lt;xsl:for-each select="a:RXA/a:RXA.3"&gt;
                              &lt;xsl:choose&gt;
                                  &lt;xsl:when test="substring($TS1Field,15,1) !=''"&gt;
                                      &lt;dil:message type="error"&gt;Patient Death Date and Time (PID-29) value is too long.  Valid format is CCYYMMDD.  Found value '&lt;xsl:value-of select="$TS1Field"/&gt;' in message.&lt;/dil:message&gt;
                                  &lt;/xsl:when&gt;
                                              &lt;/xsl:choose&gt;
                                     &lt;/xsl:for-each&gt;  
                         &lt;/xsl:otherwise&gt;
                        &lt;/xsl:choose&gt; 
               &lt;/xsl:for-each&gt;      
          &lt;/dil:filterruleresult&gt;
      &lt;/xsl:template&gt;
  &lt;/xsl:stylesheet&gt;
  </code></pre>
  
  <p>Any suggestions would be greatly appreciated.</p>
  
  <p>Thank you! </p>