jsp custom tags keyton weissinger key focus, inc. [email protected] 27 march 2001 oreilly...
TRANSCRIPT
JSP Custom TagsJSP Custom Tags
Keyton WeissingerKey Focus, Inc.
27 March 2001O’Reilly Conference on Enterprise Java
Santa Clara, CA
2JSP Custom Tags
Agenda, Part IAgenda, Part I
• Tags? Actions? Huh?
• Tag Interface
• Tag Attributes
• Tags and Scripting Variables
• BREAK
3JSP Custom Tags
Agenda, Part IIAgenda, Part II
• Body Tags
• Nested Tags
• Iterating Tags
• Tags and the JSP Container
• Packaging and Deployment
• Wrap-up and Q&A
4JSP Custom Tags
Tags? Actions? Huh?Tags? Actions? Huh?
A brief introduction to custom tags.
5JSP Custom Tags
DefinitionsDefinitions
• A “tag” is an XML element that can be used in a JSP to incorporate functionality without using scriptlet code.
• An “action” is the task performed by the tag.
6JSP Custom Tags
Definitions, cont.Definitions, cont.
• A “tag handler” is basically a JavaBean that implements the Tag interface and has property setter methods corresponding to each tag attribute. The JSP container uses this class to process the tag.
• A “tag library” or “taglib” is a collection of one or more custom tags.
7JSP Custom Tags
Tag SyntaxTag Syntax
A custom tag consists of a start tag
with a taglib-identifying prefix (possibly
containing attributes), a body (which
can be empty) and an end tag:
<log:logMessage categoryName="testCat" priority="fatal">
The body contents…
</log:logMessage>
8JSP Custom Tags
Alternate Tag SyntaxAlternate Tag Syntax
If a tag does not contain any body
contents, it can be used like this:
<log:logMessage categoryName="testCat" priority="fatal" message="test"/>
9JSP Custom Tags
The The <%@taglib%> Directive Directive
Before using a tag library, you must
inform the JSP container about the tag
library using the <%@taglib%>
directive before the first use of a tag:
<%@ taglib uri="/logtags" prefix="log" %>
The taglib directive also allows you to
specify a prefix to use with a given tag
library in its use in your JSP.
10JSP Custom Tags
Tag LibrariesTag Libraries
• One or more tags can be packaged together as a “tag library.”
• A tag library is described in a tag library descriptor (.TLD) file.
• Tags from different libraries can be called from the same JSP, but each must be declared separately with its own <%@taglib%> directive and must be uniquely identified with its own prefix.
11JSP Custom Tags
What Can Tags Do?What Can Tags Do?
A custom tag can:
• Know about its JSP environment.
• Perform simple tasks.
• Perform formatting or other customization of output.
• Introduce variables usable from scriptlets later in the JSP.
• Work together either as nested pairs or separately.
12JSP Custom Tags
Why Are Tags Important?Why Are Tags Important?
• Simplification of complex tasks across multiple JSPs in a web application.
• Complex code hiding.
• Design tool incorporation.
• Portable to any JSP container.
• Incorporation of functionality into JSPs not using Java as the scripting language.
13JSP Custom Tags
Tag InterfaceTag Interface
All tag handler classes must implement the
Tag interface.
14JSP Custom Tags
Tag InterfaceTag Interface
public interface Tag {
void setPageContext(PageContext pc)
void setParent(Tag t)
Tag getParent()
int doStartTag() throws
JspException
int doEndTag() throws JspException
void release()
}
15JSP Custom Tags
Tag Interface ConstantsTag Interface Constants
The Tag interface also includes the
following constants:public final static int SKIP_BODY = 0;
public final static int EVAL_BODY_INCLUDE = 1;
public final static int SKIP_PAGE = 5;
public final static int EVAL_PAGE = 6;
16JSP Custom Tags
Return ValuesReturn Values
int doStartTag()• SKIP_BODY• EVAL_BODY_INCLUDE
int doEndTag()• SKIP_PAGE• EVAL_PAGE
17JSP Custom Tags
TagSupport Class AdditionsTagSupport Class Additions
public static final Tag findAncestorWithClass(Tag from,
Class klass)
public void setId(String id)
public String getId()
public void setValue(String k, Object o)
public Object getValue(String k)
public void removeValue(String k)
public Enumeration getValues()
In addition to those methods in Tag, the
TagSupport class also provides the following:
18JSP Custom Tags
Tag Library Descriptor FilesTag Library Descriptor Files
• The JSP container generates code in the JSP implementation class for a tag according to information you set in the TLD.
• The TLD is an XML document.
• It contains a single <tag/> element for each tag in the library.
19JSP Custom Tags
TLD ElementsTLD Elements
The TLD has the following elements:• The <taglib/> element contains all the
other elements in the TLD.• <tlibversion/>• <uri/>• <jspversion/> • <shortname/>
20JSP Custom Tags
TLD Elements, cont.TLD Elements, cont.
The <taglib/> element contains a <tag/>
element for each tag in the library. The possible
sub-elements of <tag/> are as follows:• <name/>• <tagclass/>• <teiclass/>• <bodycontent/>• <info/>• <attribute/>
21JSP Custom Tags
TLD ExampleTLD Example<?xml version="1.0" encoding="ISO-8859-1" ?>
<!DOCTYPE taglib PUBLIC "-//Sun Microsystems, Inc.//DTD JSP Tag Library 1.1//EN"
"http://java.sun.com/j2ee/dtds/web-jsptaglibrary_1_1.dtd">
<taglib>
<tlibversion>1.0</tlibversion>
<jspversion>1.1</jspversion>
<shortname>logtags</shortname>
<uri></uri>
<info>Log4J Wrapper Tags</info>
<tag>
<name>initLog</name>
<tagclass>
com.oreilly.jsp.taglibs.logtags.InitLogTag
</tagclass>
<info>Logging system initialization tag.</info>
</tag>
</taglib>
22JSP Custom Tags
Example BackgroundExample Background
• Log4j is an open source project.
• Allows developers to fully control logging of an application.
• Fully runtime configurable.
• Gentle learning curve.
• See http://jakarta.apache.org/log4j/
23JSP Custom Tags
Example BackgroundExample Background
• A category is a named entity that categorizes a part of the logging space.
• An appender is a logging output destination.
• A layout is a formatter for output to an appender.
• Priority is the minimum level of messages to be logged for a category.
24JSP Custom Tags
Example BackgroundExample Background
root appender1
category1 appender2
category2 appender3
category 3 appender4
25JSP Custom Tags
ExampleExample
Simple Tag Demo
26JSP Custom Tags
Tag AttributesTag Attributes
A tag can have zero or more attributes.
Attribute values provide information to the tag’s
tag handler class at execution time.
27JSP Custom Tags
Tag AttributesTag Attributes
• Each attribute has a corresponding setXxxx() method.
• Each attribute value included in the tag triggers a call to its corresponding setter. No particular order.
• The setter called can be determined by capitalizing the first letter of the attribute name and adding the word “set” as a prefix.
28JSP Custom Tags
<log:logMessage
message=“test msg”/>
would call
setMessage(String pMessage)
with the String value “test msg”
Tag Attribute SettersTag Attribute Setters
29JSP Custom Tags
Attribute Data TypesAttribute Data Types
• The signature of the attribute setter method in the tag handler class dictates the data type expected for that attribute.
30JSP Custom Tags
<log:initLog override=“true”/>
would call
setOverride(boolean pOverride)
with the boolean value true.
Tag Attribute SettersTag Attribute Setters
31JSP Custom Tags
Tag Attribute Value ConversionTag Attribute Value Conversion
• boolean or Boolean
• byte or Byte
• char or Character
• double or Double
• int or Integer
• float or Float
• long or Long
• Boolean.valueOf(String)
• Byte.valueOf(String)
• String.charAt(int)
• Double.valueOf(String)
• Integer.valueOf(String)
• Float.valueOf(String)
• Long.valueOf(String)
Property Type Conversion Method
32JSP Custom Tags
JSP Container Call SequenceJSP Container Call Sequence
The JSP container call sequence goes as
follows:
1. Instantiates tag handler.
2. Calls setup methods (setPageContext(), etc).
3. Calls each setXxxx() method depending on each attribute’s presence in the tag.
4. Calls doStartTag().
5. Calls doEndTag().
33JSP Custom Tags
Call Sequence DiagramCall Sequence Diagram
<%@ taglib …%>
<log:category
priority=“fatal” 1-> setPriority()
> 2-> doStartTag()
Body contents.
</log:category> 3-> doEndTag()
34JSP Custom Tags
Runtime Attribute ValuesRuntime Attribute Values
Attribute values can be the result of a
runtime expression:
<%
Collection roomsCol = new ArrayList();
%>
<log:logCollection collection="<%=roomsCol%>“/>
NOTE: This is how to handle other data types.
35JSP Custom Tags
<attribute/><attribute/> Element Element
There is an <attribute/> element in the
TLD for each attribute for each tag:
<attribute>
<name>message</name>
<required>true</required>
<rtexprvalue>true</rtexprvalue>
</attribute>
36JSP Custom Tags
Example BackgroundExample Background
root appender1
category1 appender2
category2 appender3
category 3 appender4
37JSP Custom Tags
Example BackgroundExample Background
A log4j category’s “priority” setting
specifies the “level” required for a
message to be logged for a given
category:
• Debug
• Info
• Warn
• Error
• Fatal
38JSP Custom Tags
Example BackgroundExample Background
Each category has methods corresponding to the various priorities. You use the appropriate method to log a message of a given priority for the category of interest:
• myCat.debug(“Here’s a message.”);• myCat.info(“Here’s a message.”);• myCat.warn(“Here’s a message.”);• myCat.error(“Here’s a message.”);• myCat.fatal(“Here’s a message.”);
39JSP Custom Tags
ExampleExample
Tag Attribute Demo
40JSP Custom Tags
Tags and Scripting VariablesTags and Scripting Variables
Tags can introduce variables that can be used later in a JSP scriptlet or another
custom tag.
41JSP Custom Tags
Tag-Introduced Scripting VariablesTag-Introduced Scripting Variables
This mechanism allows your tag to
introduce a variable that you can use in
scriptlets later in the JSP:
<log:category id=“myCat”/>
<%
myCat.debug(“Hello!”);
%>
42JSP Custom Tags
Introduction of Scripting VariablesIntroduction of Scripting Variables
To have your tag introduce a scripting
variable, you must perform the
following steps:
1. Somewhere in your tag handler class you must add your variable to one of the JSP scopes.
2. Create a TagExtraInfo class for your tag handler class and reference it in your TLD.
43JSP Custom Tags
Creating a Scripting VariableCreating a Scripting Variable
<log:category id=“myCat”/>
From TagSupport base class:
void setId(String id) {
this.id = id;
}
From your tag’s doStartTag() method:
Category rootCat = Category.getRoot();
pageContext.setAttribute(id, rootCat, Page.APPLICATION_SCOPE);
44JSP Custom Tags
TagExtraInfoTagExtraInfo Class Class
public class CategoryTagExtraInfo extends TagExtraInfo {
public VariableInfo[] getVariableInfo(TagData data) {
return new VariableInfo[] {
new VariableInfo(
data.getAttributeString("id"),
"org.apache.log4j.Category",
true,
VariableInfo.AT_END)
};
}
}
45JSP Custom Tags
Tags can introduce scripting variables with one of three scopes
represented by the three VariableInfo constants, NESTED,
AT_BEGIN, and AT_END. The following diagram explains these
three scopes:
NESTED AT_BEGIN AT_END
doStartTag()
doEndTag()
Variable ScopeVariable Scope
46JSP Custom Tags
TLD Addition for TEI ClassTLD Addition for TEI Class
You must also add a <teiclass/>
element to your TLD:
<teiclass>
com.foo.CategoryTagExtraInfo
</teiclass>
47JSP Custom Tags
Example BackgroundExample Background
SimpleAppenderTag
CategoryTag
LogMessageTag
<log:simpleAppender id="myAppender" … />
<log:category id="testCat"
appender="myAppender“ … />
<log:logMessage categoryName="testCat" … />
48JSP Custom Tags
ExampleExample
Scripting Variable Demo
49JSP Custom Tags
BREAKBREAK
15 minutes.
50JSP Custom Tags
Body TagsBody Tags
Body Tags process their tag body
contents. The body contents can contain
JSP content.
51JSP Custom Tags
BodyTag SyntaxBodyTag Syntax
An example call to a body tag:<log:logMessage priority=“fatal”>
There was a fatal exception.
Time:
<%=Calendar.getInstance().getTime()%>
</log:logMessage>
52JSP Custom Tags
BodyTag InterfaceBodyTag Interface
public interface BodyTag extends Tag
{
public final static int EVAL_BODY_TAG = 2;
void setBodyContent(
BodyContent b);
void doInitBody() throws JspException;
int doAfterBody() throws JspException;
}
53JSP Custom Tags
BodyContent ClassBodyContent Class
• The tag accesses its body contents through a BodyContent object which is set by the JSP container.
• BodyContent is a subclass of JspWriter which is used to write content to the response body.
• BodyContent also has several methods to manipulate (flush, clear, return as a string) the contents of the body.
54JSP Custom Tags
JSP Container Call SequenceJSP Container Call Sequence
The JSP container call sequence is different
for a body tag than it is for a simple tag:
1. Instantiates tag handler, calls setup functions.
2. Calls setters.
3. JSP container calls doStartTag().
4. Calls setBodyContent().
5. Calls doInitBody().
6. Calls doAfterBody().
7. JSP container calls doEndTag().
55JSP Custom Tags
Call Sequence DiagramCall Sequence Diagram
<%@ taglib …%>
<log:logMessage
priority=“fatal” 1-> setPriority()
> 2-> doStartTag()
Body contents. 3->setBodyContent()
4-> doInitBody()
5-> doAfterBody()
</log:logMessage> 6-> doEndTag()
56JSP Custom Tags
BodyTag MethodsBodyTag Methods
• In most cases, it is not necessary to override the setBodyContent() method already provided in the BodyTagSupport base class.
• Use the doInitBody() method to initialize any variables you need for the doAfterBody(). Again this is rarely needed.
• The doAfterBody() is where you will do the real work of your body tag.
57JSP Custom Tags
BodyContent and BodyContent and outout
• BodyContent allows you to write to a JspWriter without interfering with the JspWriter affiliated with the JSP itself.
• This allows you to write to an output buffer and decide whether or not to write the buffer’s content to the response stream after you have completed your tag’s processing.
58JSP Custom Tags
The The outout Variable Variable
<%@taglib%>
out = JspWriter (JSP)
<tag1> out = BodyContent (tag1)
<tag2> out = BodyContent (tag2)
...
</tag2>
</tag1> out = BodyContent (tag1)
out = JspWriter (JSP)
59JSP Custom Tags
The The outout Variable, Part 1 Variable, Part 1
1. At the beginning of a JSP, the JSP container sets the out variable to the JspWriter returned by the pageContext’s getOut() method.
2. The container experiences body tag 1.
a) Creation of Stack of JspWriters.
b) Place JSP out on stack.
c) Reset out to BodyContent for tag1.
60JSP Custom Tags
The The outout Variable, Part 2 Variable, Part 2
1. The JSP container experiences the second body tag, body tag 2, which is nested inside body tag 1.
a) Place out from body tag 1 onto stack.
b) Reset out to BodyContent for body tag 2.
2. The JSP container experiences the end of body tag 2.
a) Reset out to body tag 1’s BodyContent from stack.
61JSP Custom Tags
The The outout Variable, Part 3 Variable, Part 3
1. The JSP container experiences the end of body tag 1.
a) Reset out to the JSP’s JspWriter object from stack.
62JSP Custom Tags
The The outout Variable Variable
<%@taglib%>
out = JspWriter (JSP) <tag1> out = BodyContent (tag1)
<tag2> out = BodyContent (tag2)
</tag2>
</tag1> out = BodyContent (tag1)
out = JspWriter (JSP)
63JSP Custom Tags
Output of Body ContentOutput of Body Content
If your tag’s body content should be output into the response body,
you must use the writeOut() method of the BodyContent
Object (from doEndTag()):
if (null != bodyContent) {
JspWriter lastOut =
bodyContent.getEnclosingWriter();
bodyContent.writeOut(lastOut);
}
64JSP Custom Tags
Return ValuesReturn Values
int doStartTag()• SKIP_BODY• EVAL_BODY_INCLUDE (NOT ALLOWED)• EVAL_BODY_TAG
int doAfterBody()• EVAL_BODY_TAG• SKIP_BODY
int doEndTag()• SKIP_PAGE• EVAL_PAGE
65JSP Custom Tags
BodyTag TLD Features BodyTag TLD Features
To instruct the JSP container that the current
tag is a body processing tag, you must set the
<bodycontent/> element:• empty• tagdependent• JSP (default)
66JSP Custom Tags
ExampleExample
Body Tag Demo
67JSP Custom Tags
Nested TagsNested Tags
Nested actions are tags that are processed as part of the tag body
content. Typically these tags rely on certain
properties of the surrounding tag.
68JSP Custom Tags
Nested TagsNested Tags
Nested tags can take two forms:
• Nested tags may or may not use a variable introduced by the surrounding tag.
• Some nested tags rely on their surrounding tags for some information without which it will not function.
69JSP Custom Tags
ExampleExample
Nested Tag Demo
70JSP Custom Tags
Iterating TagsIterating Tags
Tags can iterate over their bodies
repeatedly until a condition is met.
71JSP Custom Tags
Iterating TagsIterating Tags
Iterating tags differ from other body
tags:
• Iterating tags return EVAL_BODY_TAG from doAfterBody() until some condition is met.
72JSP Custom Tags
Example BackgroundExample Background
LogCollectionTag:
• Takes a collection and the name of a message variable.
• Iterates through the collection and creates a logging message for each object.
• Creates a scripting variable to be used by a nested LogMessageTag.
• Repeats until the end of the collection.
73JSP Custom Tags
ExampleExample
Iterating Tag Demo
74JSP Custom Tags
Tags and the JSP ContainerTags and the JSP Container
Discussion of the JSP implementation class
created by the container for a JSP containing
custom tags.
75JSP Custom Tags
ExampleExample
JSP Implementation Class Demo
76JSP Custom Tags
Packaging and DeploymentPackaging and Deployment
Tag libraries are typically packaged together into a JAR
file and deployed to a JSP container.
77JSP Custom Tags
Deployment: Three OptionsDeployment: Three Options
To deploy and use your tag library, you have
three options:
1. Set the uri attribute of the taglib directive to the location of the TLD file.
2. Set the uri attribute of the taglib directive to the location of the JAR file.
3. Set the uri attribute of the taglib directive to a symbolic name set in the web.xml file.
78JSP Custom Tags
Option OneOption One
1. Deploy your files:WEB-INF/
/classes
*.class
/tlds
logtags.tld
2. In your JSP, set the uri attribute of the taglib directive to the location of the TLD file:
<%@ taglib uri=“/WEB-INF/tlds/logtags.tld” prefix=“log” %>
79JSP Custom Tags
Option Two – File SetupOption Two – File Setup
To create a JAR file, first arrange the files in
the following folder organization:META-INF/
taglib.tld
com/
oreilly/
jsp/
taglibs/
logtags/
*.class
80JSP Custom Tags
Option Two – JAR CreationOption Two – JAR Creation
Change to the previously created folder
(containing the META-INF and com folders)
and execute the following:
jar cvf logtags.jar META-INF com
81JSP Custom Tags
Option Two - DeploymentOption Two - Deployment
Copy the JAR file to the lib sub-directory of
WEB_INF folder for your JSP container:
WEB-INF/
lib/
logtags.jar
82JSP Custom Tags
Option Two - UseOption Two - Use
In your JSP, set the uri attribute of the taglib directive to the location of your JAR file:
<%@ taglib uri=“/WEB-INF/lib/logtags.jar” prefix=“log” %>
83JSP Custom Tags
Option Three – Symbolic NameOption Three – Symbolic Name
You can also create a symbolic name in a taglib element
in your web application’s web.xml file:<web-app>
<taglib>
<taglib-uri>
/logtags
</taglib-uri>
<taglib-location>
/WEB-INF/tlds/logtags.tld
</taglib-location>
</taglib>
</web-app>
84JSP Custom Tags
Option Three – Symbolic Name UseOption Three – Symbolic Name Use
To use a symbolic name in your JSP, just
set the uri attribute of the taglib directive to
the symbolic name:
<%@ taglib uri=“/logtags” prefix=“log” %>
85JSP Custom Tags
ExampleExample
Deployment Demo
86JSP Custom Tags
ReviewReview
To create a tag library:
1. Create a tag handler class that implements Tag or BodyTag.
2. In the tag handler class create setters for each attribute your tag will use.
3. In the tag handler class place processing in the doStartTag, doEndTag, doInitBody and doAfterBody methods as needed.
87JSP Custom Tags
Review, cont.Review, cont.
4. Create a subclass of TagExtraInfo if your tag introduces a scripting variable for use later in the JSP.
5. In the TagExtraInfo subclass, add code for each variable introduced.
6. Compile your tag.
7. Create a tag library descriptor (TLD) file.
8. In the TLD file, add a <tag/> element for each tag in your library.
88JSP Custom Tags
Review, cont.Review, cont.
9. Inside each <tag/> element, set the appropriate sub-elements for attributes, etc.
10.Optionally create a JAR file using your tag handler classes and your TLD file.
11.Deploy your tag library into the appropriate subfolder of your web application.
89JSP Custom Tags
Review, cont.Review, cont.
12.For each tag library you wish to use in your JSP, use the <%@taglib%> directive to instruct the JSP container how to process your tags.
13.Use your tags in the JSP, being careful to include required attributes, etc.
14.Enjoy the accolades of those around you for being so smart as to use tag libraries!
90JSP Custom Tags
Wrap-up and Q&AWrap-up and Q&A
Questions?