| 9.1 Dealing with Syntax ErrorsThe first type of error you will encounter is the one 
                  you, or your coworkers, create by simple typos; in other 
                  words, syntax errors. The JSP container needs every JSP 
                  element to be written exactly as it's defined in the 
                  specification in order to process the JSP page. When it finds 
                  something that's not right, it tells you. How easy it is to 
                  understand what it tells you depends on the type of error, the 
                  JSP container implementation, and sometimes, on how fluent you 
                  are in computer gibberish.  9.1.1 Element Syntax ErrorsAll container implementations 
                  report syntax errors, but details such as the wording of the 
                  messages, how much information the message contains, and where 
                  the message is written differ between them. In this chapter, I 
                  show examples only of the messages produced by Tomcat.  Let's first look at how Tomcat reports some 
                  typical syntax errors in JSP directives and action elements. 
                  Example 
                  9-1 shows a version of the easy.jsp page from Chapter 
                  5 with a syntax error.  Example 9-1. Improperly 
                  terminated directive (error1.jsp) <%@ page contentType="text/html" >
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out value="${1 + 2 + 3}" />
  
  </body>
</html>The syntax error here is that the page 
                  directive on the first line isn't closed properly with 
                  %>; the percent sign is missing. Figure 
                  9-1 shows what Tomcat has to say about it.    Tomcat reports the error by sending an error 
                  message to the browser. This is the default behavior for 
                  Tomcat, but it's not mandated by the JSP specification. The 
                  specification requires only that a response with the HTTP status code 
                  for a severe error (500) is returned, but how a JSP container 
                  reports the details is vendor-specific. For instance, the 
                  error message can be written to a file instead of the browser. 
                  If you use a container other than Tomcat, check the container 
                  documentation to see how it reports these types of errors. 
 The actual error message in Figure 
                  9-1 is what is called an exception 
                  stack trace. When something 
                  goes really wrong in a Java method, it typically throws an 
                  exception. An exception is a special Java object, and throwing 
                  an exception is the method's way of saying it doesn't know how 
                  to handle a problem. Sometimes another part of the program can 
                  take care of the problem in a graceful manner, but in many 
                  cases the best that can be done is to tell the user about it 
                  and move on. That's what the Tomcat container does when it 
                  finds a problem with a JSP page during the translation phase; 
                  it sends the exception stack trace to the browser. The stack 
                  trace contains a message about what went wrong and where the 
                  problem occurred. The message is intended to be informative 
                  enough for a user to understand, but the actual trace 
                  information is of value only to a programmer. As you can see 
                  in Figure 
                  9-1, the message is:  /ch9/error1.jsp(0,33) Unterminated <%@ tag The first part of the message is the name of 
                  the JSP page. The numbers within parentheses indicate on which 
                  line and character position in the file the error was found 
                  (both the line and the position are numbered from 0), and then 
                  the message states what the problem is. So this message tells 
                  us that a directive (an element starting with <%@) 
                  on the first line isn't terminated as expected at position 33. 
                  In this case it's both the correct diagnosis and the right 
                  location.  It's not always this easy to interpret the 
                  error message. Example 
                  9-2 shows another version of easy.jsp with a 
                  different syntax error.  Example 9-2. Improperly 
                  terminated action (error2.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out value="${1 + 2 + 3}" >
  
  </body>
</html>The syntax error here is almost the same as 
                  the "unterminated tag" in Example 
                  9-1, but now it's the <c:out> action element that's not terminated properly 
                  (it's missing the closing slash required for an empty 
                  element). The message reported by Tomcat in this case is:  End of content reached while more parsing required: tag nesting error? This message isn't really helpful, because 
                  the line and position information is missing, and it gives no 
                  clue about which action element is in error. The error in this 
                  case is that, since the action element doesn't have a body, a 
                  single tag ending with /> should be used, but in 
                  Example 
                  9-2 it's terminated with just >. Because 
                  that's valid syntax for a JSP action that contains a body, the 
                  JSP container can't tell that it's a syntax error at this 
                  point. Instead, it treats it as the opening tag for an element 
                  with a body and complains that it can't find the closing tag 
                  before the file ends. The error message could be a lot more 
                  informative, for instance include the name of the action 
                  element that is missing the closing tag, and maybe even the 
                  position of the opening tag. Let's hope this is fixed in the 
                  Tomcat version you use.  Another common error is a typo in an attribute name. The value 
                  attribute for the <c:out> action is misspelled 
                  in Example 
                  9-3.  Example 9-3. Mistyped 
                  attribute name (error3.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out valu="${1 + 2 + 3}" />
  
  </body>
</html>Tomcat reports the problem like this: /ch9/error3.jsp(10,16) According to the TLD attribute value is mandatory 
for tag out In this case, the typo is in the name of a 
                  mandatory attribute, so Tomcat reports it as missing. If the 
                  typo is in the name of an optional attribute, Tomcat reports 
                  it as an invalid attribute name.  Example 
                  9-4 shows a type of error that results in a message that 
                  is hard to figure out unless you know what's going on.  Example 9-4. Missing end 
                  quote in attribute value (error4.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out value="${1 + 2 + 3} default="Doh!" />
  
  </body>
</html>If you look carefully at the 
                  <c:out> element, you see that the closing quote 
                  for the value attribute is missing. If another 
                  attribute is specified for the same element, like the 
                  default attribute used here, Tomcat reports the 
                  problem like this:  /ch9/error4.jsp(10,56) Attribute Doh! has no value What's happening is that Tomcat includes 
                  everything up to the second quote as the value of the 
                  value attribute. It then assumes that the next word 
                  (Doh! in this example) is an attribute, and because 
                  it's not followed by an equal sign, it reports that it doesn't 
                  have a value.  Let's close this section with one of the most 
                  frustrating scenarios of all, namely forgetting to include a taglib directive for the tag 
                  library used in the page. This doesn't result in an error 
                  message at all, but all custom action elements are treated as 
                  template text and just added to the response without being 
                  executed. Before pulling all your hair trying to understand 
                  why none of your actions are being executed, make sure you 
                  have included the taglib directive. An easy way to 
                  see if this is the problem is to use the browser's 
                  View Source function: if the source for the 
                  response sent to the browser includes action elements, they 
                  where not processed by the web container, most likely due to a 
                  missing or incorrect taglib directive.  The examples here are the most common ones 
                  for JSP element syntax errors. Tomcat can give you pretty good 
                  information about what's wrong in most of these cases, but 
                  this is still an area where I expect many improvements to be 
                  implemented in later versions of Tomcat as well as in other 
                  JSP containers. The JSP authoring tools that emerge now may 
                  also help. By providing GUI-based interfaces that generate the 
                  action elements automatically, they can eliminate this type of 
                  syntax problem.  9.1.2 JSTL Expression Language 
                  Syntax ErrorsHow well JSTL EL syntax errors are reported 
                  varies between JSTL implementations and web containers, 
                  because the EL isn't yet part of the JSP specification. The 
                  JSTL Reference Implementation (RI) is doing a pretty good of 
                  job of reporting EL syntax errors. In a web container that 
                  implements an optional JSP feature (described in Chapter 
                  21), it even includes information about the exact line and 
                  column in the JSP source file. Unfortunately, Tomcat 4 doesn't implement this feature 
                  yet, but will hopefully do so in a future version.  We look at a few EL syntax error examples in 
                  this section so you can see what to expect when you use the 
                  JSTL RI and Tomcat 4.0.4. Later versions, and other 
                  implementations may do better (or worse), but these examples 
                  illustrate what to look for.  Example 
                  9-5 shows a page with a subtle syntax error: the curly 
                  braces are missing in the EL expression.  Example 9-5. Missing both 
                  curly braces (error5.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out value="$1 + 2 + 3" />
  
  </body>
</html>This is an easy mistake to make, but it's not 
                  recognized as a syntax error at all. To the EL, this means 
                  that the value is a plain-text value, not an expression. When 
                  used with the <c:out> action, it's easy to 
                  figure out what's wrong because the text value is added to the 
                  response as-is instead of the being evaluated: $1 + 2 + 
                  3. But if you make this mistake with an attribute value 
                  that should provide the action with input to process in some 
                  way, the problem may not be so easy to spot. For instance, if 
                  you forget the curly braces for the <c:forEach> 
                  items attribute, it takes it as a text value and 
                  loops once over its body with the text as a single element. 
                   Let's see what happens if you forget only the 
                  end curly brace, as shown in Example 
                  9-6.  Example 9-6. Missing end 
                  curly brace (error6.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>JSP is Easy</title>
  </head>
  <body bgcolor="white">
  
    <h1>JSP is as easy as ...</h1>
  
    1 + 2 + 3 = <c:out value="${1 + 2 + 3" />
  
  </body>
</html>Tomcat 4 and the JSTL RI report this error as 
                  shown in Figure 
                  9-2.    The error message is produced by the JSTL RI 
                  translation-phase validator and contains four pieces of 
                  information:  
                    
                    The action name:  tag = 'out'
                    The attribute name: attribute = 'value'
                    A generic message that includes the 
                    complete EL expression:  An error occurred while parsing custom action attribute "value" with value "${1 + 2 + 3"
                    A more detailed message about the 
                    problem:  Encountered "", expected one of ...").  This isn't so bad. The first three pieces of 
                  information make it fairly easy to find the attribute value 
                  that's in error. And the fourth message; well, it makes more 
                  and more sense when you've seen messages like this a few 
                  times. What's missing is the actual line number for the error. 
                  Hopefully Tomcat will implement the optional feature I 
                  mentioned earlier in a future version, so that the error 
                  location can also be included in the report.  Figure 
                  9-2 is a good example of how all true syntax errors are 
                  reported by the JSTL RI (only the detailed messages differ), 
                  but some types of errors can't be found until the request-time 
                  phase, even though they may be regarded as syntax errors. Example 
                  9-7 illustrates one such case.  Example 9-7. Misspelled 
                  property name (error7.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>Looking for information</title>
  </head>
  <body bgcolor="white">
  
    <h1>Looking for information</h1>
  
    The Current URI: <c:out value="${pageContext.request.requestUri}" />
  
  </body>
</html>The problem here is that the property name is 
                  misspelled: it should be requestURI ("URI" in all 
                  caps) instead of requestUri. In this particular 
                  example, the EL could actually figure this out at translation 
                  time, because pageContext is an implicit variable, so 
                  all its properties are known. But the type of an application 
                  variable is known only at request time, so it's not possible 
                  to notice a misspelled property name for the general case. The 
                  JSTL RI has opted for consistency in how to handle this type 
                  of error. The way this error is reported is by throwing an 
                  exception with this message:  An error occurred while evaluating custom action attribute "value" with 
value "${pageContext.request.requestUri}": Unable to find a value for
"requestUri" in object of class "org.apache.catalina.connector.HttpRequestFacade" 
using operator "."It contains enough details about the error, 
                  such as the attribute name and value, to make it feasible to 
                  match it with its source in the page. Because it's not caught 
                  until request time, it's unfortunately impossible to include 
                  the line number in a JSP 1.2 container.  Example 
                  9-8 shows an almost identical error, but it results in a 
                  completely different result.  Example 9-8. Misspelled 
                  parameter name (error8.jsp) <%@ page contentType="text/html" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jstl/core" %>
<html>
  <head>
    <title>Looking for information</title>
  </head>
  <body bgcolor="white">
  
    <h1>Looking for information</h1>
  
    The missing parameter: <c:out value="${param.misspelled}" />
  
  </body>
</html>Here it's the name of a request parameter that is misspelled, and it's not 
                  reported as an error. Instead the expression evaluates to 
                  null, which the <c:out> action 
                  converts to an empty string. This is by design, and it makes 
                  it easier to handle the typical case in which a missing 
                  parameter should be handled the same as a parameter with an 
                  empty string as the value. If a missing parameter resulted in 
                  an exception, you would have to do a lot more testing in all 
                  JSP pages, with <c:if> actions and expressions 
                  like this all over the place:  <c:if test="${!empty param.someParam}">
  <!-- Here it's safe to use the parameter -->
</c:if>The downside is that it makes it harder to 
                  find parameter-name spelling errors. The EL handles all types 
                  of name/value pair collections, such as the implicit variables 
                  representing scopes (pageScope, 
                  requestScope, sessionScope, and 
                  applicationScope) as well as any application variable 
                  of type java.util.Map, the same way.  |