Title: CS6320
1CS6320 Servlet Structure and Lifecycle
2The Servlet Interface
- Java provides the interface Servlet
- Specific Servlets implement this interface
- Whenever the Web server is asked to invoke a
specific Servlet, it activates the method
service() of an instance of this Servlet
3Example Generic Servlet
- import java.io.
- import java.servlet.
- public class HelloWorldServlet extends
GenericServlet - public void service(ServletRequest req,
ServletResponse res) - throws ServletException, IOException
- PrintStream out newPrintStream(res.getOutputStre
am()) - out.println("Hello world!")
-
- public String getServletInfo()
- return "Hello World Servlet"
-
-
4Servlet Hierarchy
service(ServletRequest,
ServletResponse)
Servlet
Generic Servlet
doGet(HttpServletRequest , HttpServletResponse) do
Post(HttpServletRequest HttpServletResponse) doPut
doTrace
HttpServlet
YourOwnServlet
5HTTP Request Methods
- POST - application data sent in the request body
- GET - application data sent in the URL
- HEAD - client sees only header of response
- PUT - place documents directly on server
- DELETE - opposite of PUT
- TRACE - debugging aid
- OPTIONS - list communication options
6Class HttpServlet
- Class HttpServlet handles requests and responses
of HTTP protocol - The service() method of HttpServlet checks the
request method and calls the appropriate
HttpServlet method - doGet, doPost, doPut, doDelete, doTrace,
doOptions or doHead - This class is abstract
7Creating a Servlet
- Extend the class HTTPServlet
- Implement doGet or doPost (or both)
- Both methods get
- HttpServletRequest methods for getting form
(query) data, HTTP request headers, etc. - HttpServletResponse methods for setting HTTP
status codes, HTTP response headers, and get an
output stream used for sending data to the client - Many times, we implement doPost by calling doGet,
or vice-versa
8HelloWorld.java
import java.io. import javax.servlet. import
javax.servlet.http. public class
TextHelloWorld extends HttpServlet public
void doGet(HttpServletRequest req,
HttpServletResponse res) throws ServletException,
IOException PrintWriter out
res.getWriter() out.println("Hello
World") public void doPost(HttpServletReque
st req, HttpServletResponse res) throws
ServletException, IOException doGet(req,
res)
9The Response Returning HTML
- By default, no content type is given with a
response - In order to generate HTML
- Tell the browser you are sending HTML, by setting
the Content-Type header - Modify the printed text to create a legal HTML
page - You should set all headers before writing the
document content. Can you guess why?
10HelloWorld.java
public class HelloWorld extends HttpServlet
public void doGet(HttpServletRequest request,
HttpServletResponse response) throws
ServletException, IOException PrintWriter
out response.getWriter()
out.println("lthtmlgtltheadgtlttitlegtHello
Worldlt/titlegtlt/headgt\n") out.println("ltbodygt"
) out.println("lth2gt" new java.util.Date()
"lt/h2gt\n") out.println("lth1gtHello
Worldlt/h1gt\nlt/bodygtlt/htmlgt")
11Life of a Servlet
- Birth Create and initialize the servlet
- Important method init()
- Life Handle 0 or more client requests
- Important methods service(), doGet(), and
doPost(). - Death Destroy the servlet
- Important method destroy()
12Servlet Life Cycle
Deal with requests call the service method
Calling the init method
Destroy the Servlet call the destroy method
Servlet Instance
ServletConfig
Garbage Collection
Servlet Class
13The init() method
- The init() method is called when the servlet is
first requested by a browser request. - It is not called again for each request.
- Used for one-time initialization.
- The method init is overloaded and has a parameter
of type ServletConfig - ServletConfig has methods to get external
initialization parameters - In Tomcat, these parameters are set in web.xml
- To make initializations, override init() and not
init(ServletConfig) - init() is automatically called by after
performing default initializations
14Service() Method
- Each time the server receives a request for a
servlet, the server spawns a new thread and calls
the servlets service () method.
Browser
service()
Single Instance of Servlet
Web Server
service()
Browser
service()
Browser
15The Service Method
- By default the service() method checks the HTTP
Header. - Based on the header, service calls either
doPost() or doGet(). - doPost and doGet is where you put the majority of
your code. - If your servlets needs to handle both get and
post identically, have your doPost() method call
doGet() or vice versa.
16Thread Synchronization
- By default, multiple threads are accessing the
same servlet object at the same time. - You therefore need to be careful to synchronize
access to shared data. - For example, the code on the next slide has a
problem
17package coreservlets import java.io. import
javax.servlet. import javax.servlet.http. pub
lic class UserIDs extends HttpServlet private
int nextID 0 public void
doGet( HttpServletRequest request,
HttpServletResponse response) throws
ServletException, IOException
response.setContentType("text/html")
PrintWriter out response.getWriter()
String title "Your ID" String docType
String id "User-ID-" nextID
out.println("ltH2gt" id "lt/H2gt") nextID
nextID 1 out.println("lt/BODYgtlt/HTMLgt")
This code is problematic. Can result in a race
condition, where two users can actually get the
same User-ID! For example User 1 makes
request String id "User-ID-" nextID Gets
nextId of 45. Now User 2 makes request, and
pre-empts user 1 String id "User-ID-"
nextID Gets nextId of 45 (same
one!) Admittedly, this case is rare, but its
especially problematic. Imagine if user Id was
tied to credit card number!
18How to Solve Synchronization Problems
- You have a few options for solving servlet
synchronization issues - Never use instance variables (or protect them) in
your servletsuse local variables. If you dont
have shared instance variables, you dont have
shared synchronization problems. - Synchronize code explicitly with Java
synchronization blocks. - Note recommended - Use the SingleThreadInterface
19Java Synchronization
- Use a synchronization block whenever
accessing/modifying a shared variable. - For example
- synchronized (this)
- String id "User-ID-" nextID
- out.println("ltH2gt" id "lt/H2gt")
- nextID nextID 1
-
20SingleThreadModel Interface
- To prevent multi-threaded access, you can have
your servlet implement the SingleThreadModel - public class YourServlet extends HttpServlet
implements - SingleThreadModel
-
-
- This will guarantee that your servlet will only
process one browser request at a time. - It therefore addresses most synchronization
issues. - Unfortunately, however, it can result in severe
slowing of performance, and most people strongly
recommend against using it. - In fact, the SingleThreadModel interface is now
deprecated in the Servlet 2.4 API.
21Death of a Servlet
- Before a server shuts down, it will call the
servlets destroy() method. - You can handle any servlet clean up here. For
example - Updating log files.
- Closing database connections.
- Closing any socket connections.
- The server may remove a loaded Servlet, Why?
- asked to do so by administrator(e.g. Server
shutdown) - Servlet was idle a long time
- server needs to free resources
- The server removes a Servlet only if all threads
have finished or a grace period has passed
22Example Persistent Counter
- To create a persistent record, we can store the
count value within a counter.txt file. - init() Upon start-up, read in the current
counter value from counter.txt. - destroy() Upon destruction, write out the new
counter value to counter.txt
23import java.io. import java.util. import
javax.servlet. import javax.servlet.http. pub
lic class CounterPersist extends HttpServlet
String fileName "counter.txt" int count
public void init () try FileReader
fileReader new FileReader (fileName)
BufferedReader bufferedReader new
BufferedReader (fileReader) String initial
bufferedReader.readLine() count
Integer.parseInt (initial) catch
(FileNotFoundException e) count 0 catch
(IOException e) count 0 catch
(NumberFormatException e) count 0
At Start-up, load the counter from file. In the
event of any exception, initialize count to 0.
Continued.
24 // Handle an HTTP GET Request public void
doGet(HttpServletRequest request,
HttpServletResponse response) throws
IOException, ServletException response.setCont
entType("text/plain") PrintWriter out
response.getWriter() count out.println
("Since loading, this servlet has " "been
accessed " count " times.") out.close()
Each time the doGet() method is called, increment
the count variable.
Continued.
25 // At Shutdown, store counter back to file
public void destroy() try FileWriter
fileWriter new FileWriter (fileName) String
countStr Integer.toString (count) fileWriter.
write (countStr) fileWriter.close() catch
(IOException e) e.printStackTrace()
When destroy() is called, store new counter
variable back to counter.txt.
Any problems with this code?