Optional return value from JSP custom tag?

Hi,

I'm writing JSP custom tags, and I want to be able to optionally provide a variable name for a return value (like several core tags, including :url and :import).

It works fine if I require the return value variable, but I cannot seem to make it optional.

Here is the relevant part of working tag file mytag.tag:

<%@ tag body-content="scriptless" %>

<%@ attribute name="cond" required="true" %>

<%@ attribute name="var" required="true" rtexprvalue="false" %>

<%@ variable alias="ret" name-from-attribute="var" scope="AT_BEGIN" %>

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>

...

<c:set value="i am the return value" var="ret" />

When the above code is called like this:

<%@ taglib prefix="lmtags" tagdir="/WEB-INF/tags" %>

<lmtags:mytag cond="sunny" var="test" />

The value "i am the return value" is stored in a page-scoped variable called "test" in the calling JSP.

However, if I change the 'required' attribute from true to false on the 'var' attribute declaration, I get the following exception:

java.lang.RuntimeException: org.apache.jasper.JasperException: /WEB-INF/tags/mytag.tag(4,1) The attribute directive (declared in line 3 and whose name attribute is"var", the value ofthis name-from-attribute attribute) must be of type java.lang.String, is"required" and not a"rtexprvalue".

at org.apache.jasper.compiler.ImplicitTagLibraryInfo.getTagFile(ImplicitTagLibraryInfo.java:129)

at org.apache.jasper.compiler.Parser.parseCustomTag(Parser.java:1315)

at org.apache.jasper.compiler.Parser.parseElements(Parser.java:1577)

at org.apache.jasper.compiler.Parser.parseBody(Parser.java:1806)

(This is with Tomcat 5.5, jstl-1.1.2.jar, and standard-1.1.2.jar).

Is there a way to make the return value variable optional, so that a value is either returned as the name-from-attribute variable if passed, or output directly if not?

Thanks.

[2590 byte] By [simpsoraa] at [2007-11-27 8:54:47]
# 1

The compiler has a valid complaint. According to the JSP specification, if you declare a 'variable' and it has the name-from-attribute property, the attribute specified MUST be required, and not a runtime expression value.

Q: So how do the JSTL tags do it?

A: They don't actually use the "variable" functionality, and thus the "var" attribute does not have to be required.

In the JSTL code then you find this: (taken from the source for the c:url tag)

// store or print the output

if (var != null)

pageContext.setAttribute(var, result, scope);

else {

try {

pageContext.getOut().print(result);

} catch (java.io.IOException ex) {

throw new JspTagException(ex.getMessage());

}

}

In other words they fake it. The logic to store or output it is a part of the tag, and not functionality provided by the container.

The @variable directive lets you define a scripting variable on the page. That would let you use it in <%= expr %> tags. If all you want is an attribute, follow the example of the JSTL tags and do it manually.

Cheers,

evnafets

evnafetsa at 2007-7-12 21:14:41 > top of Java-index,Enterprise & Remote Computing,Web Tier APIs...