1. 程式人生 > >【java web】Servlet生命周期

【java web】Servlet生命周期

控制臺顯示 encoding port protect err 我們 sys 技術 vax

在Java web中 Servlet 是根基。雖然工作中幾乎沒人再去寫Servlet了,框架為我們完成了這些工作。我們只要專註於業務邏輯的實現。但是理解Servlet還是很有必要的。

1. Servlet的架構圖

技術分享圖片

Servlet Container 指的是Tomcat這樣可以處理Servlet的服務器。

2. Servlet是怎麽處理請求的?

做一個實驗,首先用Eclipse新建一個項目,如下

技術分享圖片

需要我們自己編輯的有四個文件

index.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8
" pageEncoding="UTF-8"%> <!DOCTYPE html> <html> <head> <meta charset="ISO-8859-1"> <title>Insert title here</title> </head> <body> <form action="LoginServlet" method="get"> <label>用戶名</label> <input name="username" type
="text"> <br/> <label>密碼</label> <input name="password" type="password"> <input type="submit" value="登陸"> </form> </body> </html>

doGet.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!
DOCTYPE html> <html> <head> <meta charset="ISO-8859-1"> <title>Insert title here</title> </head> <body> Get Success </body> </html>

doPost.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
post success
</body>
</html>

著重講一下LoginServlet.java, 新建一個Servlet, Eclipse會默認生成doGet 和 doPost方法。 init()方法和destory()方法是從HttpServlet繼承的, 我們只做一個打印,直接調用HttpServlet的實現,這樣不會影響Servlet的運行

package com.yeyeck.controller;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * Servlet implementation class LoginServlet
 */
@WebServlet("/LoginServlet")
public class LoginServlet extends HttpServlet {
    
    private static final long serialVersionUID = 1L;
    
    
    @Override
    public void init() throws ServletException {
        System.out.println("init() worked");
        super.init();
    }
    
    
    @Override
    public void destroy() {
        System.out.println("destroy() worked");
        super.destroy();
    }
    
    @Override
    protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        System.out.println("service() worked");
        super.service(req, resp);
    }
       
    /**
     * @see HttpServlet#HttpServlet()
     */
    public LoginServlet() {
        super();
        // TODO Auto-generated constructor stub
    }

    /**
     * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        System.out.println("doGet() worked");
        System.out.println("hash: " + this.hashCode());
        // TODO Auto-generated method stub
        System.out.println(request.getParameter("username"));
        System.out.println(request.getParameter("password"));
        response.sendRedirect("doGet.jsp");
//        response.getWriter().append("登陸成功");
    }

    /**
     * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // TODO Auto-generated method stub
        
        System.out.println("doPost() worked");
        System.out.println("hash: " + this.hashCode());
        System.out.println(request.getParameter("username"));
        System.out.println(request.getParameter("password"));
        response.sendRedirect("doPost.jsp");
    }

}

把項目部署到Tomcat跑起來,瀏覽器鍵入訪問地址

技術分享圖片

會看到

技術分享圖片

右鍵檢查,會看到表單現在的提交方式是get

技術分享圖片技術分享圖片

在輸入框內隨便輸入一些數據,提交。觀察Eclipse控制臺

技術分享圖片

頁面跳轉到

技術分享圖片

從控制臺輸出,我們可以看到,這次get請求,依次調用了 init()、service()、 doGet()方法

回到index,再請求一次,控制臺顯示

技術分享圖片

可以發現,第二次請求,只調用了 service() 和 doGet() 方法, 並且兩次打印的hash值是一樣的

我們再把index.jsp的表單改成post方式提交, ctrl+save

index.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="ISO-8859-1">
<title>Insert title here</title>
</head>
<body>
<form action="LoginServlet" method="post">
<label>用戶名</label>
<input name="username" type="text">
<br/>
<label>密碼</label>
<input name="password" type="password">
<input type="submit" value="登陸">
</form>

</body>
</html>

回到首頁右鍵檢查, 此時的請求方式已經變為post

技術分享圖片

隨便輸入一些數據,提交。控制臺顯示如下

技術分享圖片

發現又多了一些打印,這次post請求調用了 service() 和 doPost() 方法, 而且打印的hash值依然沒有變。

關閉tomcat

技術分享圖片

回到console, 顯示如下

技術分享圖片

發現調用了destory()方法

以上過程表明

  1. Hash值始終沒變

  2. 只有第一次請求的時候調用了 init() 方法

  3. 每次請求都調用了service() 方法

  4. 調用完service() 方法後,會根據數據提交的方式,選擇調用doPost() 或者 doGet() 方法

  5. Tomcat關閉的時候,會調用destroy()方法。

所以

  1. servlet是單例的

  2. init()方法只會在第一次請求這個Servlet的時候調用, Servlet()的生命周期開始

  3. 每次請求都會調用service() 方法, 並且在調用完service() 方法後,會根據數據提交的方式,選擇調用doPost() 或者 doGet() 方法

  5. 僅在tomcat關閉的時候調用destroy()方法, Servlet的生命周期結束

【java web】Servlet生命周期