Servlet呼叫過程詳解
Servlet是java程式設計中的核心內容,對於初學者而言清晰的瞭解servlet的呼叫過程,明白從客戶端到伺服器的互動過程是至關重要的。下面通過一個簡單的登陸例項的程式碼與圖的結合詳述一下servlet是怎樣被呼叫的。在介紹這個過程之前我們先來簡單瞭解下java開發相關的相關資訊。servlet的呼叫過程是由客戶端,容器(以Tomcat為例),xml檔案,java類,html檔案幾者合作參與完成,我們所要說的servlet的呼叫過程其實也就是這幾者之間的關係,他們之間的順序作用關係如下:
1.客戶端通過傳送請求給Tomcat,Tomcat傳送客戶端的請求頁面給客戶端。
2.使用者對請求頁面進行相關操作後將頁面提交給Tomcat,Tomcat將其封裝成一個HttpRequest物件,然後對請求進行處理,。
3.Tomcat截獲請求,根據action屬性值查詢xml檔案中對應的servlet-name,再根據servlet-name查詢到對應的java類(如果是第一次,Tomcat則會將servlet編譯成java類檔案,所以如果servlet有很多的話第一次執行的時候程式會比較慢)。
4.Tomcat例項化查詢到的java類,注意該類只例項化一次。
5.呼叫java類物件的service()方法(如果不對service()方法進行重寫則根據提交的方式來決定執行doPost()方法還是doGet()方法)。
6.通過request物件取得客戶端傳過來的資料,對資料進行處理後通過response物件將處理結果寫回客戶端。
下面是我們的程式碼示例:
(1)客戶端程式碼
<!DOCTYPE html>
<html>
<head>
<title>Login.html</title>
<script language="javascript" type="text/javascript">
function CheckEmpty (){
var username = document.getElementById("username1").value;
var password = document.getElementById("password1").value;
if(username == ""){
alert("使用者名稱不能為空");
return;
} else if(password == "")
{
alert("密碼不能為空");
return;
}
formSub();
}
function formSub(){
LoginForm.submit();
}
</script>
</head>
<body >
<form action="LoginServlet" method="post" name="LoginForm">
使用者名稱:<input tyep="text" id="username1" name="username"><p>
密 碼:<input type="password" id="password1" name="password"><br>
<input type="button" value="登陸" onClick="return CheckEmpty()">
</form>
</body>
</html>
注意上面程式碼中的紅色部分,這就是我們進行servlet定位的url,配置檔案也就是通過這個url來從眾多的servlet中找到我們所需要的servlet的。這個url並沒有固定的書寫,只要與配置檔案中的url-pattern對應就沒有問題。
(2)配置檔案程式碼
<?xml version="1.0" encoding="UTF-8"?>
<web-app version="2.4"
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
http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
<welcome-file-list>
<welcome-file>Login.html</welcome-file>
</welcome-file-list>
<servlet>
<servlet-name>MyLoginServlet</servlet-name>
<servlet-class>LoginServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>MyLoginServlet</servlet-name>
<url-pattern>/LoginServlet</url-pattern>
</servlet-mapping>
</web-app>
配置檔案所起的作用更像是是一個排程站,他負責將不同的頁面與不同的servlet進行對接,以便於servlet可以對客戶端提交過來的資料進行處理。
(3)servlet程式碼
import java.io.IOException;
import java.io.PrintWriter;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class LoginServlet extends HttpServlet {
//建構函式
public LoginServlet() {
super();
}
//解構函式
public void destroy() {
super.destroy(); // Just puts "destroy" string in log
// Put your code here
}
//重寫doGet方法
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
actionFuc(request,response,"Get");
}
// 重寫doPost方法
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
actionFuc(request,response,"Post");
}
//重寫service方法
public void service(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException{
actionFuc(request,response,"Service");
}
//重寫初始化方法
public void init() throws ServletException {
// Put your code here
}
/**
* 我們自己定義的測試函式,該函式用來測試不同的提交方法(get提交還是post提交),
* 以及驗證service方法被重寫後就不會再呼叫doGet和doPost方法
*/
private void actionFuc(HttpServletRequest request, HttpServletResponse response,String method)
throws IOException{
String username = request.getParameter("username");
String password = request.getParameter("password");
System.out.println("username=" + username);
System.out.println("password=" + password);
response.setContentType("text/html");
response.getWriter().println(method + "Login Success!");
}
}
通過對service方法進行重寫進一步驗證了,當請求被提交給servlet的時候首先呼叫的是java類物件的service方法,如果該方法不被重寫則會根據頁面的提交方式呼叫doGet或doPost方法,但是當service被重寫後則會執行service方法體中的內容,不再呼叫doGet或doPost方法。