Home

JSP and Beyond

a pragmatic primer on building web-based solutions with Java technologies


Developing Custom Tags

Custom Tags were introduced with the introduction of the JSP 1.1. They represented a major step forward in being able to further separate HTML markup from complex Java code. Given this, you might ask why they are so great when we have Java Beans and the Include JSTL tag? Don’t they provide that same functionality?

So far we have examined an inline Java code <% some Java code here %>, JavaBeans and JSTL as various ways to place dynamic content into the presentation layer. Inline Java code is messy and breaks JSPs best practices, and JavaBeans are not meant to return HTML markup to a JSP, but rather to provide objects from which data can be stored and retrieved.

Custom tags give you the best of both worlds and then some. In this examination we will cover the JSP 2.0 tags which, without diving into details, are much easier to develop and use than the first series of tags that JSP introduced.

Custom Tags allow you to place XML-style markup within your HTML which provides rich functionality, completely separating complex code from your JSP presentation layer. Custom Tags let developers develop and designers design, strictly isolating both job functions.

Custom Tags let tag developers access intrinsic objects related to the JSP, unlike a JavaBean where these objects are not easily accessible.

So what do you need to do to create a custom tag?

1. Create a TLD file that tells the application server what your tags do. An example of this is the description, price and comments for a product that you might purchase on Amazon. It lets the system know what your tag’s name is, what class contains the code for it and what inputs it might take.

2. Create a class that implements the javax.Servlet.jsp.tagext.SimpleTagSupport interface. This allows the class to do all of the heavy lifting behind the scenes in order to produce HTML output to send back into your page template.

3. Place the tag markup inside the JSP markup along with a reference to the TLD in the page of your choice, and let it work its magic!

Custom tags are so powerful that it is worthwhile to spend some additional time walking through an example of building a trivial one. Let’s walk through an example of creating a “Hello World” custom tag.

Keeping in the spirit of our pragmatic approach to this development, let’s use NetBeans to make the custom tag. It is an excellent way for you to see what needs to happen to properly build the tag with minimal effort. Once you have built the tag, we can review the files that the IDE created in order for you to gain a deeper understanding of the code.

The latest version of the NetBeans IDE can be downloaded from:
http://www.netbeans.org/downloads/

1. Launch NetBeans and Open an existing Web Project (you can use the JSPandBeyond project)

2. Go to “File” > “New File…”

3. Select “Tag Library Descriptor” and the click “Next >”

4. Fill out the “TLD Name” field. Our example uses “jspandbeyondtags”. Then select a folder to place the new TLD in. “WEB-INF/tlds” is the default folder, and for consistency you should place it there. Click “Finish” to complete the wizard and have the TLD created.

The new TLD should look like the image below. You can see how much work the IDE was able to do for us, helping to minimize errors and save time.

Now that you have the basic skeleton of the TLD file, let’s create the tag file that will be added to the TLD to be used within your JSPs.
1. Go to “File” > “New File…”

2. Select “Web” as the Category and “Tag Handler” as the “File Types” as shown below, then click “Next >”. The “Tag Handler” will represent a tag in your application and is a java class that implements the SimpleTagSupport interface.

3. Fill in the “Class Name” field. In our example we are using “customtagtest”. Then select the Package that the new class will go into. For our example we are selecting “JSPBeyond”. The click “Next >”. Packages are a helpful way to bundle related class files.

4. The next screen “TLD Information” does a very nice job of setting the contents in the TLD file automatically for the new tag. Notice the checkbox at the top of the wizard that says “Add Corresponding Tag to the Tag Library Descriptor”. This will automatically append / adjust the file with the information about our new tag. We will also need to browse through the TLD that we want to add the information into. In this case we are going to select “jspandbeyondtags.tld”.

5. We will also add an “attribute” by clicking “New…” in the attributes section, and then create an attribute Name called “username” as a String.

6. Click “Finish” to save your new custom tag. Notice how when the wizard closes, you now have a new class within the JSPBeyond package called “customtagtest”.

Now that the wizard is completed, you have a Java file that can be used to make your tag function. The bolded area below is where you can write all of the code to send HTML into your JSP where the tag has been placed. Also notice that the line containing “private java.lang.String username;” references the attribute that we added.

package JSPBeyond;

import javax.Servlet.jsp.tagext.*;
import javax.Servlet.jsp.JspWriter;
import javax.Servlet.jsp.JspException;

public class customtagtest extends SimpleTagSupport {

/**
* Initialization of username property.
*/
private java.lang.String username;

/**Called by the container to invoke this tag.
* The implementation of this method is provided by the tag library developer,
* and handles all tag processing, body iteration, etc.
*/
public void doTag() throws JspException {

JspWriter out=getJspContext().getOut();

try {
// TODO: insert code to write html before writing the body content.
// e.g.:
//
// out.println(”<strong>” + attribute_1 + “</strong>”);
// out.println(” <blockquote>”);

JspFragment f=getJspBody();
if (f != null) f.invoke(out);

// TODO: insert code to write html after writing the body content.
// e.g.:
//
// out.println(” </blockquote>”);

} catch (java.io.IOException ex) {
throw new JspException(ex.getMessage());
}

}

/**
* Setter for the username attribute.
*/
public void setUsername(java.lang.String value) {
this.username = value;
}
}

Now that you have your custom tag class and TLD file, let’s create a JSP that leverages it. This is the Directive that needs to be added to the JSP to let it know that you have custom tags that it can use

<%@ taglib prefix=”customtagtest” uri=”/WEB-INF/tlds/jspandbeyondtags” %>

Notice the prefix “customtagtest” that indicates that this will be the name of the tag that will be used to implement your custom functionality. For our sample we have changed the bold area to only include “out.println(”<strong>Welcome to JSP ” + username + “!</strong>”);”. After doing this you can right click on our project “JSPandBeyond” and select “Clean and Build Project”. This compiles the code.

In the above code sample we have added a line of code that references our TLD file, and NetBeans is able to recognize our custom tag. By recognizing the tag, NetBeans lets you know what attributes are part of your custom tag and what information you can send into those attributes. In our sample we are able to set an attribute for “username” with the following code:

<customtagtest:customtagtest username=”Bob”></customtagtest:customtagtest>

This code within the JSP will result in the following output when our JSP is requested in a browser.

Here are the underlying files that were created in the process that made it possible to use our new custom tag. Notice that there is now a tag name called “customtagtest” that has been added.

jspandbeyondtags.tld

<?xml version=”1.0″ encoding=”UTF-8″?>
<taglib version=”2.0″ xmlns=”http://java.sun.com/xml/ns/j2ee” xmlns:xsi=”http://www.w3.org/2001/XMLSchema-instance” xsi:schemaLocation=”http://java.sun.com/xml/ns/j2ee web-jsptaglibrary_2_0.xsd”>
<tlib-version>1.0</tlib-version>
<short-name>jspandbeyondtags</short-name>
<uri>/WEB-INF/tlds/jspandbeyondtags</uri>
<tag>
<name>customtagtest</name>
<tag-class>JSPBeyond.customtagtest</tag-class>
<body-content>scriptless</body-content>
<attribute>
<name>username</name>
<rtexprvalue>true</rtexprvalue>
<type>java.lang.String</type>
</attribute>
</tag>
</taglib>

TagSample.jsp

<%@page contentType=”text/html”%>
<%@page pageEncoding=”UTF-8″%>
<%@ taglib prefix=”customtagtest” uri=”/WEB-INF/tlds/jspandbeyondtags” %>

<html>
<head>
<meta http-equiv=”Content-Type” content=”text/html; charset=UTF-8″>
<title>JSP Page</title>
</head>
<body>

<h1>JSP Page</h1>

<customtagtest:customtagtest username=”Bob”></customtagtest:customtagtest>

</body>
</html>

customtagtest.java

package JSPBeyond;

import javax.Servlet.jsp.tagext.*;
import javax.Servlet.jsp.JspWriter;
import javax.Servlet.jsp.JspException;

/**
*
* @author jbrunswi
* @version
*/

public class customtagtest extends SimpleTagSupport {

/**
* Initialization of username property.
*/
private java.lang.String username;

/**Called by the container to invoke this tag.
* The implementation of this method is provided by the tag library developer,
* and handles all tag processing, body iteration, etc.
*/
public void doTag() throws JspException {

JspWriter out=getJspContext().getOut();

try {

out.println(”<strong>Welcome to JSP ” + username + “!</strong>”);

} catch (java.io.IOException ex) {
throw new JspException(ex.getMessage());
}

}

/**
* Setter for the username attribute.
*/
public void setUsername(java.lang.String value) {
this.username = value;
}
}

Although there is some initial setup required, once you have the basics for tag creation established it is easy to quickly add additional functionality.