Servlets: The Servlet Life Cycle Ethan Cerami New York University
10/17/08
Servlet Life Cycle
1
Road Map
Overview of the Life Cycle Birth of a Servlet Life of a Servlet Threading Issues Death of a Servlet Tips for Debugging Servlets
10/17/08
Servlet Life Cycle
2
Overview of Servlet Life Cycle
10/17/08
Servlet Life Cycle
3
Life of a Servlet
Birth: Create and initialize the servlet
Life: Handle 0 or more client requests
Important method: init() Important methods: service(), doGet(), and doPost().
Death: Destroy the servlet
10/17/08
Important method: destroy()
Servlet Life Cycle
4
Birth of a Servlet
10/17/08
Servlet Life Cycle
5
The 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.
10/17/08
Servlet Life Cycle
6
Simple Example The init() method is a good place to put any initialization variables. For example, the following servlet records its Birth Date/time…
10/17/08
Servlet Life Cycle
7
import java.io.*; import java.util.*; import javax.servlet.*; import javax.servlet.http.*; public class Birth extends HttpServlet { Date birthDate; // Init() is called first public void init() throws ServletException { birthDate = new Date(); } 10/17/08
Servlet Life Cycle
8
// Handle an HTTP GET Request public void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException { response.setContentType("text/plain"); PrintWriter out = response.getWriter(); out.println ("I was born on: "+birthDate); out.close(); } }
10/17/08
Servlet Life Cycle
9
Another Example This servlet initializes a set of Lottery Numbers… Listing 3.7 in Text: LotteryNumbers.java
10/17/08
Servlet Life Cycle
10
Life of a Servlet
10/17/08
Servlet Life Cycle
11
Life of a Servlet The first time a servlet is called, the Servlet is instantiated, and its init() method is called. Only one instance of the servlet is instantiated. This one instance handles all browser requests.
10/17/08
Servlet Life Cycle
12
Service() Method
Each time the server receives a request for a servlet, the server spawns a new thread and calls the servlet’s service () method.
Browser Browser
service()
Web Server
service() service()
Single Instance of Servlet
Browser
10/17/08
Servlet Life Cycle
13
Let’s Prove it…
To prove that only one instance of a servlet is created, let’s create a simple example. The Counter Servlet keeps track of the number of times it has been accessed. This example maintains a single instance variable, called count. Each time the servlet is called, the count variable is incremented. If the Server created a new instance of the Servlet for each request, count would always be 0!
10/17/08
Servlet Life Cycle
14
import java.io.*; import javax.servlet.*; import javax.servlet.http.*;
Only one instance of the counter Servlet is created. Each browser request is public class Counter extends HttpServlet { therefore incrementing the // Create an instance variable same count variable. int count = 0; // Handle an HTTP GET Request public void doGet(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException { response.setContentType("text/plain"); PrintWriter out = response.getWriter(); count++; out.println ("Since loading, this servlet has " + "been accessed "+ count + " times."); out.close(); } }10/17/08 Servlet Life Cycle 15
The 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.
10/17/08
Servlet Life Cycle
16
Thread 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…
10/17/08
Servlet Life Cycle
17
package coreservlets; import java.io.*; import javax.servlet.*; import javax.servlet.http.*;
This code is problematic. Can result in a race condition, where two users can actually get the same User-ID! For example:
public class UserIDs extends HttpServlet { User 1 makes request: private int nextID = 0; String id = "User-ID-" + nextID;
public void doGet( Gets nextId of 45. HttpServletRequest request, HttpServletResponse response) Now User 2 makes request, throws ServletException, IOException {and pre-empts user 1: response.setContentType("text/html"); PrintWriter out = response.getWriter(); String id = "User-ID-" + nextID; Gets nextId of 45 (same one!) String title = "Your ID"; String docType = … Admittedly, this case is rare, String id = "User-ID-" + nextID; but it’s especially problematic. out.println("
" + id + "
"); Imagine if user Id was tied to nextID = nextID + 1; credit card number! out.println("