briggleshiggle
briggleshiggle

Reputation: 41

Conditional Statement Fails to Work - XPath 2.0

I am trying to complete a homework assignment that has me performing two conditional statements in XPath 2.0 with the following format in the ovedueCell and categoryCell class. Every time I run the code I get the error: "Required attribute 'select' is missing.

    if (test1) then result1
   else if (test2) then result2
   else if (test3) then result3
   else result4

I am also having issues with the formatDate function underneath the body and h2 tag.

      <?xml version="1.0" encoding="UTF-8" ?>
   <!--
   New Perspectives on XML, 3rd Edition
   Tutorial 8
   Tutorial Project

   Denison Public Library XSLT Style Sheet
   Author: Brigitte Arcoite
   Date:   08/04/2019

   Filename:         library.xsl
   Supporting Files: book.png, dvd.png

   -->

 <xsl:stylesheet version="3.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
 xmlns:xs="http://www.w3.org/2001/XMLSchema"
 exclude-result-prefixes="xs">

 <xsl:output method="html"
  doctype-system="about:legacy-compat"
  encoding="UTF-8"
  indent="yes" />

  <xsl:variable name="thisDate" select="2017-04-12" as="xs:date" />
  <xsl:template match="/">

  <html>
     <head>
        <title>Denison Public Library</title>
        <link href="libstyles.css" rel="stylesheet" type="text/css" 
     />
     </head>

     <header>
        <h1>Denison Public Library</h1>
        <h2>Ennis, Montana</h2>
     </header>

     <body>
         <h2>
             <xsl:value-of select="formatDate($thisDate, '[MNn] [D], 
         [Y]')" />    
         </h2>
           <h1>Checked Out Items</h1>
           <table id="checkoutList">
              <thead>                  
                 <tr>
                    <th>Call No.</th>
                    <th>Title</th>
                    <th>Due Date</th>
                    <th>Overdue? (Y/N)</th>
                    <th>Overdue Category</th>
                 </tr>
              </thead>  
              <tbody>           
              <xsl:apply-templates select="itemlist/item" />
              </tbody>
           </table>
     </body>

  </html>
  </xsl:template>

  <xsl:template match="item">
  <tr>
     <td class="callnoCell">
        <xsl:value-of select="callno" />
     </td>
     <td class="titleCell">
        <xsl:value-of select="title" />
     </td>
     <td class="duedateCell">
        <xsl:value-of select="status/@return" />
     </td>
     <td class="overdueCell">
        <xsl:variable name="overdue" select="
        if($thisDate>status/@return) 
        then $overdue='Y' 
        else $overdue='N'" />
            <xsl:value-of select="$overdue" />
     </td>
     <td class="categoryCell">
        <xsl:variable name="lostDate" select="$thisdate- 
         dayTimeDuration(90)" as="xs:date" />
         <xsl:variable name="longoverdueDate" select="$thisdate- 
         dayTimeDuration(30)" as="xs:date" />
         <xsl:variable name="category" select="
         if($lostDate>status/@return) then $category='Lost'
         else if ($longoverdueDate>status/@return then 
         $category='Long Overdue'
         else if (status/@return>$thisDate) $category='Overdue' 
         else $category=''           " />
         <xsl:value-of select="$category" />
     </td>
    </tr>
   </xsl:template>

  </xsl:stylesheet>

Upvotes: 0

Views: 146

Answers (1)

Michael Kay
Michael Kay

Reputation: 163342

The function name should be spelt format-date not formatDate.

The calls on dayTimeDuration() should be prefixed xs:, and you need spaces around the minus sign (because hyphens can appear in names).

References to $thisdate should be $thisDate.

I suspect (but I'm guessing) that this code:

<xsl:variable name="overdue" select="
                    if($thisDate>status/@return) 
                    then $overdue='Y' 
                    else $overdue='N'" />

should be

<xsl:variable name="overdue" select="
                    if($thisDate>status/@return) 
                    then 'Y' 
                    else 'N'" />

(But better, why not make it a boolean variable rather than a string set to 'Y' or 'N'?)

Similarly,

<xsl:variable name="category" select="
                    if($lostDate>status/@return) then $category='Lost'
                    else if ($longoverdueDate>status/@return then 
                    $category='Long Overdue'
                    else if (status/@return>$thisDate) $category='Overdue' 
                    else $category=''           " />

should be

<xsl:variable name="category" select="
                    if($lostDate>status/@return) then 'Lost'
                    else if ($longoverdueDate>status/@return then 
                    'Long Overdue'
                    else if (status/@return>$thisDate) then 'Overdue' 
                    else ''           " />

With those changes we get rid of all syntax errors, but there's still a semantic error:

<xsl:variable name="thisDate" select="2017-04-12" as="xs:date" />

reports that the value is an integer rather than a date. This shows the value of declaring the types of your variables (something that you have done here but not everywhere). It should be select="xs:date('2017-04-12')".

P.S. I can't explain why you got the particular error message "select attribute is missing". Perhaps there was another problem that you fixed.

Upvotes: 1

Related Questions