Java Servlet and JSP
Java Servlet and JSP
Table of Contents:
1. Web Basics
1.1. HTTP GET Request
1.2. HTTP POST Request: Sending and Using Two Parameters
1.3. HTTP Response
1.4. An Servlet Example
2. Servlet and Container
2.1. What is container?
2.2. Why Container?
2.3. How does container work?
2.4. Servlet name and Deployment Descriptor (DD) mapping
2.5. Tomcat is a web container, not a J2EE application server.
3. Servlet Lifecycle and API
3.1. Servlet’s life
3.2. Three Life cycle moments
3.3. ServletConfigobject
3.4. ServletContextobject
3.5. Idempotent (or Not)
3.6. Example: servlet code to download a JAR
3.7. Request Redirect
3.8. Redirect vs. Request Dispatch
3.9. Summary
4. Web App: Attributes and Listeners
4.1. Servlet Init Parameters
4.2. Context Init Parameters
4.3. Context Listener and why?
4.4. Other type of Listeners
4.5. Attribute, Scope and API.
4.6. More on RequestDispatcher
5. Session Management
5.1. How does Session work?
5.2. Session ID
5.3. If client doesn’t take cookies: URL Rewriting
5.4. Timeout/Invalidate Sessions
5.5. Cookie API
5.6. Final note on session
6. JSP Is Just a Servlet
6.1. JSP Basic
6.2. JSP Implicit objects
6.3. API for generated servlet
6.4. Lifecycle of JSP
users.nccs.gov/~fwang2/web/jsp.html 1/30
12/27/12 Java Servlet and JSP
1. Web Basics
1.1. HTTP GET Request
GET request append form data to the end of the URL. An Example:
We need to know:
users.nccs.gov/~fwang2/web/jsp.html 2/30
12/27/12 Java Servlet and JSP
HTML form
Servlet class
We need to know:
This time, the parameters are put in the message body, not limited as in HTTP Get Request.
HTTP/1.1 200 OK
Content-Type: text/html
...
<html> ....
</html>
The content-type response header is known as MIME type - it tells to browser what kind of data it is about to get so
browser knows how to render it.
users.nccs.gov/~fwang2/web/jsp.html 3/30
12/27/12 Java Servlet and JSP
200: OK
301: moved and redirect
401: unauthorized
403: forbidden
404: not found
500: internal error
// test.java
import javax.servlet.*;
import javax.servlet.http.*;
import java.io.*;
// compile
% javac -classpath $CATALINA_HOME/common/lib/servlet-api.jar \
-d classes src/TestServ.java
// deploy
As you can see, a servlet has doGetand doPostto handle GET request and POST request, it doesn’t have a main()
method, that is where the container comes in.
When a request for a servlet comes in, the server (such as Apache) hands the request not to servlet itself, but to the
Container in which the servlet is deployed. It is the container that gives the servlet the HTTP request and response, and
it is the container that calls servlet’s method such as doGet()and doPost().
users.nccs.gov/~fwang2/web/jsp.html 4/30
12/27/12 Java Servlet and JSP
As container “sees” the request for a servlet, it creates two objects: HttpServletResponseand
HttpServletRequest
The container finds the correct servlet based on the URL in the reqeust, create or allocates a thread for that
request, and passes the request and response object to the servlet thread.
The container calls the servlet’s service()method. Depending on the type of request, it calls either the doGet()
or doPost()method.
The doGet()method generates the dynamic page and stuffs the page into the response object.
After servlet thread completes, the container converts the repose object into HTTP response, sends it back to the
client, then deletes the request and response object.
One key function of container is to locate corresponding servlet. A servlet is known to have three names:
public URL name: this is the name clients knows about. For example, /search/facets.
<servlet>
<servlet-name>internal name X</servlet-name>
<servlet-class>foo.bar.Servlet1</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Internal name X</servlet-name>
<url-pattern>/public_whatever</url-pattern>
</servlet-mapping>
Note /public_whateveris what client sees and uses to get to the servlet.
J2EE is a super spec: it includes not only servlet 2.4/2.5 spec, JSP 2.0/2.1 spec, but also Enterprise JavaBean 2.1
spec for EJB container.
Tomcat only supports servlet and JSP, that is for web component, not EJB, which is for business component.
Thus Tomcat is known as web container, not J2EE applicaton server.
users.nccs.gov/~fwang2/web/jsp.html 5/30
12/27/12 Java Servlet and JSP
The real application server such as JBoss, BEA’s web logic, IBM’s WebSphere.
There is only one main state of servlet: initialized. If a servlet is not initialized, then it is either being initialized
(running its constructor, or init()method), being destroyed (running its destroy()method), or doesn’t exisit.
init(): The container calls init() on servlet instance after servlet instance is created, but before servlet can service
any client request.
3.3. ServletConfigobject
Use it to pass deploy-time information to servlet (database, bean lookup name etc.)
3.4. ServletContextobject
GET is not suppose to change anything on the server, so GET is, idempotent. In HTTP/servlet context, it means
the same request can be made twice with no negative consequences.
POST is not default. For example, in the form tag, if you don’t specify, the submit request is GET request.
users.nccs.gov/~fwang2/web/jsp.html 6/30
12/27/12 Java Servlet and JSP
response.getContentType("application/jar");
OutputStream os = response.getOutputStream();
while ((read = is.read(bytes) != -1) {
os.write(bytes, 0, read);
}
os.flush(); os.close();
}
The getResourceAsStream()requires forward slash, which is the root of web app. That is
You can handle request in a servlet, you can also dispatch request to some other components in your web app,
typicall a JSP. You can ALSO redirect as:
if (I_can_do_it) {
// handle the request
} else {
response.sendRedirect("http://www.google.com");
}
http://www.hotdot.com/myApp/cool/bar
sendRedirect("foo/bar")
Then container will build the full URL (needed for the Location header it puts in the HTTP response):
http://www.hotdot.com/myApp/foo/bar
However, you start with a forward slash, such as sendRedirect(/foo/bar'), then the full URL will be:
http://www.hotdot.com/foo/bar
users.nccs.gov/~fwang2/web/jsp.html 7/30
12/27/12 Java Servlet and JSP
Important: You can’t do sendRedirect()after you write to response. If you do that, you will see
IllegalStateException.
The biggest difference is that “redirect” makes the client do the work, while “request dispatch” make something else on
the server do the work.
Request dispatch: user puts in a URL, request comes to server, servlet decides the request should go to a JSP,
the servlet calls:
The brwoser gets the response in the usual way, the render it for user. The browser location doesn’t change, user
doesn’t know JSP generates the response.
3.9. Summary
The Container initializes a servlet by loading the class, invoking the servlet’s no-arg constructor, and calling the
servlet’s init()method.
The init()method, which developer can override, is called only once in a servlet’s life and always before the
servlet can service any client requests.
The init()method give the servlet access to the ServletConfigand ServletContextobjects, which the
servlet needs to get information about the servlet configuration and web app, respectively.
Most of a servlet’s life is spent running a service method for a client request.
Every request to a servlet runs in a separate thread! There is only one instance of any particular servlet class.
Your servlet will almost always extend javax.servlet.http.HttpServlet, from which it inherits an
implementation of the service method that takes an HttpServletRequestand an HttpServletResponse.
Your servlet must override at least one service method, doGet(), doPost(), etc.
users.nccs.gov/~fwang2/web/jsp.html 8/30
12/27/12 Java Servlet and JSP
# web.xml
<servlet>
<servlet-name> ... </servlet-name>
<servlet-class> ... </servlet-class>
<init-param>
<param-name>adminEmail</param-name>
<param-value> [email protected]</param-value>
</init-param>
</servlet>
out.println(getServletConfig().getInitParameter("adminEmail"));
A few caveats:
You can’t use servlet init parameter unitl it is initialized - that means you can’t use it in your servlet constructor.
Servlet init parameters are read only one - when Container initialize the servlet.
You can have multiple init-paramfor the servlet, and you can use getInitParameterNames()to get a list of
names and further use getInitParameter()to get each value.
If you want all other parts of your web app have access to that email address, you can put it as part of context parameter.
# web.xml
<servlet>
...
</servlet>
<context-param>
<param-name>adminEmail</param-name>
<param-value> [email protected]</param-value>
</context-param>
Note that we are not nesting context-paraminside servletanymore, it is for the whole web app. In the servlet code:
out.println(getServletContext().getInitParameter("adminEmail"));
Context parameter can’t be anything except Strings. What if you want the whole web app have access to a shared
database connection? You can’t put that code in a servlet, since then you must have ways to guarantee the servlet must
run before anybody else.
users.nccs.gov/~fwang2/web/jsp.html 9/30
12/27/12 Java Servlet and JSP
What in need is a listener for a context initialization event, so it can run some code before the rest of the app can
service a request.
Write the listener class: its gets the context init parameter, create some domain object, Dog; and set Dog as
context attribute.
The attribute class: say we will define Dog.java - its job is to be the attribute value that ServletContextListner
instantiates and sets in the ServletContext, for other servlet to retrieve.
Deployment descriptor
<servlet>
<servlet-name> ListnerTester </servlet-name>
<servlet-class> example.ListenerTester </servlet-class>
</servlet>
<servlet-mapping>
<servlet-name> ListnerTester </servlet-name>
<url-pattern> /ListenerTest.do </url-pattern>
</servlet-mapping>
users.nccs.gov/~fwang2/web/jsp.html 10/30
12/27/12 Java Servlet and JSP
<context-param>
<param-name> breed </param-name>
<param-value> Great Dane </param-value>
</context-param>
<listener>
<listener-class>
example.MyServletContextListener
</listener-class>
</listener>
Besides context event, you can listen for events related to context attributes, servlet requests and attributes, and HTTP
session and session attributes. (P182)
You want to know if an attribute in a web app context has been added, removed, or replaced.
ServletContextAttributeListener.
You want to know each time a request comes in, so you can log it. ServletRequestListener.
You want to know when a request attribute has been added, remove, or replaced.
ServletRequestAttributeListener.
You have a attribute class (a class for an object that will stored as an attribute) and you want to objects of this type
to be notified when they are bound or removed from a sesson. HttpSessionBindingListener.
You want to know when a sessiion attribute has been added, removed or replaced.
HttpSessionAttributeListener.
You have a attribute class (a class for an object that will stored as an attribute) and you want to objects of this type
to be notified when the session to which they are bound is migrating to and from antoher VM.
HttpSessionActivationListener.
A plain old HttpSessionAttributeLiseneris just a class that wants to know when any type of attribute has been
added, removed, or replaced in a session. But the HttpSessionBindingListenerexists so taht the attribute itself can
find out when it has been added or removed from a session. Example:
users.nccs.gov/~fwang2/web/jsp.html 11/30
12/27/12 Java Servlet and JSP
find out when it has been added or removed from a session. Example:
What is an attribute? An attribute is an object set or bound into one of three other servlet API objects:
ServletContext, HttpServletRequest, or HttpSession. The most important thing to know about attribute
is who can see it and how long it lives.
Note that Attributes are not parameters: the name/value pair for attribute, where value is object, instead of string in
the case of parameter.
Fortunately, all three attribute scopes, that are handled by ServletContext, HttpServletRequest, and
HttpSessionhas the exact same API:
A few caveats:
Context and Session scope attributes are not thread-safe: somebody with access it can change it …
Request attribute make sense when you want other component such as JSP to take over all or part of the request.
Typically, the controller communicate with the model, and get back dagta that the view needs in order to build the
response. There is no reason to put the data in a context or session attribute, since it applies only to the request, so
we put it in the request scope:
request.setAttribute("styles", result);
users.nccs.gov/~fwang2/web/jsp.html 12/30
12/27/12 Java Servlet and JSP
Since we use relative path here, the Container looks for “result.jsp” in the same logical location the request is “in”.
RequestDispatcher view =
getServletContext().getRequestDispatcher("/results.jsp");
Same as above, except you must use forward slash for absolute path.
5. Session Management
A session is keep client-specific state across multiple requests.
The Container sends the request to a new thread of the BeerApp servlet, this servlet thread finds the ssession
associated with user X, and store his choice in the session as attribute.
The servlet runs business logic, and return a response, in this case, another question: “how expensive?”
X consider the new question, and select “expensive” and submit his answer.
The container sends the request to a new thread of BeerApp servlet, and this thread finds the session associated
with user X, and store his choice “expensive” in the session as attribute.
Meanwhile, another user Y might go through same process, but this time, the BeerApp thread starts a new Session
for user Y. The key points are:
- different clients
- same servlet
- different request
- different threads
- different session
5.2. Session ID
HTTP is stateless, so as far as the Container’s concerned, each request is from a new client. How will container
recognize client X from client Y?
The idea is simple: on the client’s first request, the Container generates a unique session ID and gives it back to the client
with the response. the client sends back the session ID with each subsequent request. The container sees the ID,
users.nccs.gov/~fwang2/web/jsp.html 13/30
12/27/12 Java Servlet and JSP
finds the matching session, and assocaites the session with the request.
Server response:
HTTP/1.1 200 OK
Set-Cookie: JSESSIONID=0ABCDEF2324
...
Enable cookies: All the cookie setting work behind the scenes by container, all you need to is:
If you want to know if the sssion already existed or was just created, you can:
if (session == null) {
session = request.getSession();
...
}
URL rewriting always work. It takes the session ID that in the cookie and sticks it right onto the end the every
URL that comes to this app.
URL + ;jsessionid=1234567
The session ID comes back as “extra” info to the end of request URL. It kicks in only if cookies fails and ONLY if
There is no way to get automatic URL rewriting with your static pages, so if you depend on sessions, you must use
dynamically generated pages.
<session-config>
<session-timeout> 15 </session-timeout>
</session-config>
session.setMaxInactiveInterval(20*60); // seconds
Invalidate: ends the session, this includes unbinding all session attributes currently stored in this session.
session.invalidate();
Cookie can be used for stuff other than session, the best thing about it is, user doesn’t have to be involved. And you can
tell a cookie to stay alive even after the browser shuts down.
cookie.setMaxAge(30*60); // in seconds
response.addCookie(cookie);
users.nccs.gov/~fwang2/web/jsp.html 15/30
12/27/12 Java Servlet and JSP
There is whole bunch of events related to session such as sesson created, destory, session attributes added, removed,
replaced, session is passivated in one VM, activated on another etc. where you can attach listeners.
Use page directive to import packages. A directive is a way for you to give special instructions to the Container at
page translation time. Directives come in three flavors: page, include, and taglib.
JSP expression:
JSP scriptlet:
JSP declarition: all scriptlet and experssion code lands in a service()method. That means variable declared in a
scriptlet are always LOCAL variables. For instance variables or method definition, you need:
users.nccs.gov/~fwang2/web/jsp.html 16/30
12/27/12 Java Servlet and JSP
The container makes the following implicit object available to JSP when they do the servlet translation:
“page” is a new fourth scope, “page-level”, and page-scoped attributes are stored in pageContext. It encapulates other
implicit objects.
_jspService(): this method is called from the servlet’s service()method, which means it runs in separate
thread for each request. You can’t override this method!
Your jsp is deployed, the container doesn’t do anything else until the first time it is requested.
Upon request, container tries to translate the .jsp into .java source; then container tries to compile .java into
.class.
If all successful, the container loads the newly generated servlet class.
The container instantiates the servlet and causes the servlet’s jspInit()method to run. It is now a full-fledge
servlet, ready to accept client request.
The container creates a new thread to handle this client’s request, and the servlet’s _jspService()method runs.
Eventually, the servlet sends a response back to the client (or forward to request to another web app component).
// Servlet Controller
public doPost(...)
{
String name = request.getParameter("userName");
request.setAttribute("name", name);
...
users.nccs.gov/~fwang2/web/jsp.html 17/30
12/27/12 Java Servlet and JSP
...
RequestDispatcher view = request.getRequestDispacher("/result.jsp");
view.forward(request, response);
}
// JSP (view)
<html><body>
<%= request.getAttribute("name");
Application
// servlet
getServletContext().setAttribute("foo", barObj);
// JSP
application.setAttribute("foo", barObj);
Request
// servlet
request.setAttribute("foo", barObj);
// JSP
request.setAttribute("foo", barObj);
Session
// servlet
reqeust.getSession().setAttribute("foo", barObj);
// JSP
session.setAttribute("foo", barObj);
Page
// servlet
don't apply
// JSP
pageContext.setAttribute("foo", barObj);
You can use pageContext to get and set attributes in any scope:
users.nccs.gov/~fwang2/web/jsp.html 18/30
12/27/12 Java Servlet and JSP
or you can use it to find attribute in any scope if you don’t where it is:
You can:
or
Here:
id="person"declares identifier for the bean object. This matches to the name used when servlet code said:
request.setAttribute("person", p);
class="foo.Persondeclares the fully qualified class type for the bean object.
name="person"identifies the actual bean object, this will match the idvalue from jsp:useBeantag.
property=nameidentifies the property name (things with getter and setting in the bean class).
You can send request parameters straight into a a bean, without scripting: The html code:
users.nccs.gov/~fwang2/web/jsp.html 19/30
12/27/12 Java Servlet and JSP
<form action="TestBean.jsp">
name: <input type="text" name="userName">
ID#: <input type="text" name="userID">
<input type="submit">
</form>
Inside TestBean.jsp:
Note that param attribute: the param value comes from the name attribute of the form input field.
It can be simplified further, though I don’t know if that is a good idea, by following some conventions:
Now the HTML needs to be (basically BOTH parameters matches the property name of the bean):
<form ...>
name: <input type="text" name="name">
ID#$: <input type="text" name="empID">
...
</form>
This
users.nccs.gov/~fwang2/web/jsp.html 20/30
12/27/12 Java Servlet and JSP
${person.dog.name}
OR it can be an attribute in page scope, request scope, session scope, application scope.
You can use dot operator to access bean properties and map values. However, what if it (e.g. Person) is an array or list?
Here are the rules:
If the expression has a variable folloed by a bracket [], the left hand variable can be a map, a bean, a List or an
array.
If the thing inside the brackets is a String literal (i.e., in quotes), it can be a Map key, or a bean property, or an
index into a List or array.
String index will be coerced into an int for arrays and Lists
The in JSP
users.nccs.gov/~fwang2/web/jsp.html 21/30
12/27/12 Java Servlet and JSP
<form ...>
Name: <input type="text" name="name">
ID#: <input type="text" name="empID">
Now, even though there are multiple values for the foodparameter, the way above line is written, you only get the
first value. Here is how you can get to the rest:
Even name doesn’t have mutliple values, I can still access by:
${paramValues.name[0]}
${cookie.userName.value}
<context-param>
<param-name>mainEmail</param-name>
<param-value>[email protected]</param-value>
</context-param>
The implicit requestScopeis just a Map of the request scope attributes, not the request object itself. Say you want to
know the HTTP method, which is a property of the request object, not an attribute at the request scope, you need to go
through pageContext:
users.nccs.gov/~fwang2/web/jsp.html 22/30
12/27/12 Java Servlet and JSP
through pageContext:
The above code works because pageContexthas a requestproperty, and requesthas a methodproperty.
The same can be said for other Map scope objects: for example, applicationScopeIS NOT a reference to
ServletContext, it is just where the application-scope attrbutes are bound.
7.7. EL functions
7.8. EL operators
Arithmetic
+ - * / % mod
Logical
and &&
or ||
not !
Relational
Equals: ==
Not Equals !=
Less than <
Greater than >
Less or euqal <=
Greater or equal >=
Reserved words
e.g. ${empty A}
return true if A is null or empty.
users.nccs.gov/~fwang2/web/jsp.html 23/30
12/27/12 Java Servlet and JSP
<jsp:include>and <jsp:param>: customize content. First, let’s show the JSP that does the include:
The header that is being included can use the new param as:
<em><strong>${param.subTitle}</strong></em>
Hello ${param.userName}.
7.10. EL Summary
EL expression are always with curly braces, and prefixed with dollar $sign.
The first named variable in the expression is either an implicit object or an attribute in oe of the four scope (page,
request, session, or application).
The dot operator lets you access values by using a Map key or bean proerty name. Whatever comes to the right of
the dot operator must follow normal java naming rules for identifiers, in other words, must start with a letter,
underscore, or dollar sign.
The []operator is more powerful than dot, as you can put expression including named variable within the
brackets.
Don’t confuse the implicit EL scope objects (maps of atttributes) with the objects to which the attributes are
bound.
EL functions allow you to call a public static method in a plain old java class. The function name doesn’t have to
match the actual method name. The mappingis done through TLD (Tag library descriptor) file. To use such a
function in JSP, you must delcare namespace using taglibdirective.
8. Using JSTL
JSP standard tag library, also known as custom tags.
Servlet code:
JSP code:
The key feature is that the tag assign each element in the collection to the variable you declare with the varattribute. The
LoopTagStatusclass has a countproperty that gives you the current value of the iteration.
An example: if user is a member, you want to allow them to comment, by including a comment box:
Assuming a servlet somewhere set the userTypeattribute based on the user’s login information.
<c:choose>
<c:when test="${userPref == 'performance' }">
...
</c:when>
...
<c:otherwise>
...
</c:otherwise>
</c:choose>
If there is NOT a session-scoped attribute named “userLevel”, this tag creates one (assuming the valueattribute
is not null). If the value is null, then the attribute will be removed.
Target MUST evaluate to a object, either a bean or a Map, and it must not be NULL. If the target is a map, then
it set the value of a key named “dogName”.
Remove value
Nothing prints after the remove, the scope is optional, the default is the page scope.
In session management, we mention that if client doesn’t take cookie, servlet has to encode it to do URL rewriting. So if
we have to do it in JSP, here is how it is done:
<c:url>does URL rewritting, but not URL encoding (deal with white space character for example). To do both, we
need:
Assuming that:
users.nccs.gov/~fwang2/web/jsp.html 26/30
12/27/12 Java Servlet and JSP
${inputURL}
/myApp/inputComments.jsp?firstName=Crouching+Pixels&lastName=Hidden+Cursor
9.2. result.jsp
9.3. servlet
String c = request.getParameter("color");
BeerExpert be = new BeerExpert()
users.nccs.gov/~fwang2/web/jsp.html 27/30
12/27/12 Java Servlet and JSP
}
}
10. Deployment
10.1. Configure Error Page
<error-page>
<exception-type>java.lang.Throwable</exception-type>
<location>/errorPage.jsp</location>
</error-page>
<error-page>
<error-code>404</error-code>
<location>/notFoundError.jsp</location>
</error-page>
11. Appendix
11.1. Servletinterface
service(ServletRequest, ServletResponse);
init(ServletConfig);
destroy();
getServletConfig();
getServletInfo();
users.nccs.gov/~fwang2/web/jsp.html 28/30
12/27/12 Java Servlet and JSP
An abstract class that implements most of the basic servlet methods you need, but you rarely extend this class.
service(ServletRequest, ServletResponse);
init(ServletConfig);
destroy();
...
getInitParameter(String);
getInitParameterNames();
getServletContext();
Also an abstract class, but reflect the HTTP-ness of the servlet. Notice that service()method doesn’t just take any
servlet request, it is a HTTP-specific request and response.
service(HttpServletRequest, HttpServletResponse);
doGet(HttpServletRequest, HttpServletResponse);
doPost(HttpServletRequest, HttpServletResponse);
doHead(HttpServletRequest, HttpServletResponse);
doOptions(HttpServletRequest, HttpServletResponse);
doPut(HttpServletRequest, HttpServletResponse);
doTrace(HttpServletRequest, HttpServletResponse);
doDelete(HttpServletRequest, HttpServletResponse);
getLastModified(HttpServletRequest);
11.4. ServletRequestinterface
getAttribute(String);
getContentLength();
getInputStream();
getLocalPort();
getParameter();
getParameterNames();
...
getContextPath();
getCookies();
getHeader(String); # request.getHeader("User-Agent") The client's platform and browser info
getQueryString();
getSession();
getMethod();
users.nccs.gov/~fwang2/web/jsp.html 29/30
12/27/12 Java Servlet and JSP
11.6. ServletResponseinterface
getBufferSize();
setContentType();
getOutputStream();
getWriter();
...
addCookies();
addHeader();
enccodeRedirectURL();
sendError();
setStatus();
...
11.8. ServletContextinterface
getInitParameter(String);
getInitParameterNames();
getAttribute(String);
getAttributeNames()
setAttribute(String, Object);
removeAttribute(String)
...
getRequestDispathcer(String);
users.nccs.gov/~fwang2/web/jsp.html 30/30