1. 程式人生 > >Servlet基礎教程

Servlet基礎教程

目錄

請求方式

轉發器

5、重定向

Servlet簡介

    Java Servlet 是執行在 Web 伺服器或應用伺服器上的程式,它是作為來自 Web 瀏覽器或其他 HTTP 客戶端的請求和 HTTP 伺服器上的資料庫或應用程式之間的中間層。使用 Servlet,您可以收集來自網頁表單的使用者輸入,呈現來自資料庫或者其他源的記錄,還可以動態建立網頁。

1、Servlet的生命週期

Servlet 的生命週期可分為:例項化,初始化,就緒,銷燬。

 init(): 在Servlet的生命週期中,僅執行一次init()方法。它是在伺服器裝入Servlet時執行的,負責初始化Servlet物件。可以配置伺服器,以在啟動伺服器或客戶機首次訪問Servlet時裝入Servlet。無論有多少客戶機訪問Servlet,都不會重複執行init()。

service(): 它是Servlet的核心,負責響應客戶的請求。每當一個客戶請求一個HttpServlet物件,該物件的Service()方法就要呼叫,而且傳遞給這個方法一個“請求”(ServletRequest)物件和一個“響應”(ServletResponse)物件作為引數。在HttpServlet中已存在Service()方法。預設的服務功能是呼叫與HTTP請求的方法相應的do功能。

destroy(): 僅執行一次,在伺服器端停止且解除安裝Servlet時執行該方法。當Servlet物件退出生命週期時,負責釋放佔用的資源。一個Servlet在執行service()方法時可能會產生其他的執行緒,因此需要確認在呼叫destroy()方法時,這些執行緒已經終止或完成。Servlet的工作過程

階段1:例項化                即容器呼叫構造器建立Servlet物件.                時機1:容器收到請求後,建立Servlet物件                時機2:容器啟動後,立即建立Servlet物件                    web.xml中需要配置                    <load-on-startup>1</load-on-startup> 階段2:初始化                容器在建立Servlet物件後,會立即呼叫init方法進行物件的初始化。一般情況下,我們不需要重寫此方法,因為父型別GenericServlet裡提供了init方法的實現邏輯。此方法儲存了另外一個物件ServletConfig的引用,如果你想初始化一些自定義的屬性,我們可以將初始化的值配置在web.xml裡。        

<init-param>
      <param-name>company</param-name>
      <param-value>華育興業</param-value>
</init-param>

通過ServletConfig提供的 getInitParameter(String name)來獲取值       

public void init() throws ServletException {
		System.out.println("----初始化");
		ServletConfig config = getServletConfig();
		String company = config.getInitParameter("company");
	}

階段3:就緒              初始化之後,容器呼叫Servlet物件的service方法進行資源分配。階段4:銷燬              容器會根據自己的演算法來進行Servlet物件的銷燬,銷燬前一定會呼叫destroy()方法。因此我們可以重寫此方法來完成一些業務邏輯。解除安裝程式時,一定會銷燬Servlet物件      

public void destroy() {
		System.out.println("程式解除安裝了");
	}

練習程式碼:

public class HelloServlet  extends HttpServlet{
	private String company;
	private String manager;
	
	public HelloServlet() {
		System.out.println("建立servlet物件");
	}

	@Override
	protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
		System.out.println("處理業務邏輯");
		System.out.println("company:"+company);
		System.out.println("manager:"+manager);
	}

	@Override
	public void init() throws ServletException {
		System.out.println("----初始化");
		ServletConfig config = getServletConfig();
		company = config.getInitParameter("company");
		manager = config.getInitParameter("manager");
	}
	
	@Override
	public void destroy() {
		System.out.println("程式解除安裝了");
	}
}

2、Servlet的執行原理   

  1. 瀏覽器依據IP和PORT與伺服器建立連線
  2. 傳送請求資料包到伺服器
  3. 伺服器建立Servlet元件物件
  4. 使用HttpServletRequest處理請求資料包(讀取頁面上的資料)
  5. 使用HttpServletResponse封裝響應資料(將程式中的資料傳送到頁面上)
  6. 伺服器傳送響應資料包
  7. 瀏覽器進行解析,生成頁面

Servlet的組織結構

appName     ---》WEB-INF          ---》classes              ---》xxx.class檔案     ---》lib(可選)     ---》web.xml     ---》index.html(可選)

3、Servlet處理HTTP協議/請求方式

Servlet處理引數值

Servlet處理頁面上出入的值request呼叫下面方法

 處理1:1形式的引數與引數值       String getParameter(String name)       如果name不存在,返回null    處理1:M形式的引數與引數值       String[] getParameterValues(String name)       如果name不存在,返回null

Servlet如何處理HTTP協議

當瀏覽器向伺服器端傳送請求後,伺服器端會維護兩個物件,用來封裝和處理請求資料包的資料,及其響應資料。分別是HttpServletRequestHttpServletResponse物件     1、HttpServletRequest物件封裝和處理請求資料包的資料(接收頁面發來的資料)        提供了以下方法        String getParameter(String name)        String[] getParameterValues(String name)        String getHeader(String str)        Enumration<E> getHeaders()        RequestDispatcher getRequestDispatcher(String url)        .......     2、HttpServletResponse物件封裝和處理服務端要響應給瀏覽器的資料(將封裝好的資料傳送給瀏覽器)        提供了以下方法        void setContentType(String str)        void sendRedirect(String url)        .......

請求方式

瀏覽器向伺服器傳送請求的種類有八種:       GET,POST,OPTIONS,HEAD,PUT,DELETE,TRACE,CONNECT       (1)常用的兩種getpost           get向特定資源傳送請求(如返回登陸介面),在位址列上直接寫地址,表單的預設提交           post向指定資源提交資料(提交表單,上傳檔案),要想使用此種方式提交,表單的method屬性設定POST       (2)兩者的區別           get提交的資料會顯示在位址列上,資料量小,最多為4kb。不安全           post提交的資料不會在位址列上顯示。因此我們可以提交大量的資料,相對安全

轉發器

     概念:一個web元件將未完成的任務交給另一個web元件繼續做,通常是一個servlet將資料獲取之後轉交給jsp進行展現.

     下面講的是三種轉發中較為常用的一種轉發方式和步驟

     轉發步驟:

         1、繫結資料

                request.setatteribute(string name,obj)   name繫結名 obj:繫結值   伺服器端使用

          2、獲取轉發器

                requestdispatatcher rd = request.getrequestdispatcher(string url)  url 要轉發到的路徑

           3、啟動轉發

                rd.forward(request,response)   

                   注:轉發的本質是一個web元件通知容器呼叫另外一個web元件,(即呼叫service方法,所以需要傳遞request,response)

  頁面獲取資料:

               obj request.setAttribute(string name);//依據繫結名獲取繫結值,返回時時object型別的,需要強轉後使用

練習程式碼:

protected void service(HttpServletRequest req, HttpServletResponse resp){
   
    //伺服器端
    String str = "轉發器測試";
	/** 繫結資料*/
	req.setAttribute("key", emp);
	/** 獲取轉發器*/
	RequestDispatcher rd = req.getRequestDispatcher("emplist.jsp");
    /**啟動轉發*/
	rd.forward(req, resp);
}
/**========================================================================*/
//頁面
<% String str = (String) request.getAttribute("key"); %>

4、Servlet處理請求資源路徑

web.xm基礎l配置

<servlet>
	<!--名稱(隨便起) -->
	<servlet-name>count</servlet-name>
	<!-- 要執行的servlet的路徑 -->
	<servlet-class>com.hyxy.session.CountServlet</servlet-class>
</servlet>
<servlet-mapping>
	<!--也是名稱(要和上面的名稱一致) -->
	<servlet-name>count</servlet-name>
	<!-- 瀏覽器上要訪問的路徑名稱(絕對路徑下必須要有/ 後面的名稱可以隨便起) -->
	<url-pattern>/count</url-pattern>
</servlet-mapping>

1、什麼是請求資源路徑          瀏覽器中的網址  http://ip:port/appName/url-pattern,請求資源路徑:appName/url-pattern2、處理原理          瀏覽器依據ip和port確定伺服器,之後依據appName確定應用程式所在的目錄,servlet容器預設瀏覽器請求的是一個Servlet元件, 所以會校驗web.xml裡的url-pattern,進行匹配,執行相關的Servlet元件。3、精確匹配          伺服器在進行web.xml裡的url-pattern的校驗時,會嚴格匹配請求路徑是否一致,如果匹配成功,就會執行相關資源          如: <url-pattern>/hello.html</url-pattern>嚴格匹配成功後,即使程式中有hello.html頁面,也不會返回這個頁面,而是執行相關Servlet。4、萬用字元匹配          萬用字元: *  ,匹配0個或多個字元,必須使用斜槓               如:<url-pattern>/*</url-pattern>                            http://ip:port/appName/abc.html   匹配成功                     http://ip:port/appName/service/add.html   匹配成功                     http://ip:port/appName/listEmp   匹配成功      5、字尾匹配           在寫web.xml裡的url-pattern的值時,我們可以使用“  * . 字尾的方式,字尾可以是1或多個字元組成的。          如:<url-pattern>*.action</url-pattern>               http://ip:port/appName/abc.html   匹配失敗                   http://ip:port/appName/emp/abc.action   匹配成功               http://ip:port/appName/listEmp.action  匹配成功                   優先順序: 精確匹配最高                     假如:web.xml中有三個Servlet元件,其url-pattern如下          <url-pattern>/abc.do</url-pattern>          <url-pattern>/*</url-pattern>          <url-pattern>*.do</url-pattern>                      瀏覽器地址:http://ip:port/appName/abc.do 會執行精確匹配的Servlet元件如果精確匹配,萬用字元匹配,字尾匹配都沒有成功,容器會查詢是否有此檔案,如果有此檔案,打包資料返回給瀏覽器。如果沒有,返回404.     

Servlet元件的合併

一般情況下,Servlet元件充當的角色為控制角色,控制角色的           作用是接收請求後進行分發到不同的資源裡。因此一個Servlet就可以           對請求資源路徑進行分析,使用分支結構來處理不同的資源。                              如何合併:       (1)採用字尾匹配進行修改web.xml       (2)獲取請求資源路徑進行分析,然後使用if分支進行處理

5、重定向

    1.概念:伺服器處理完業務邏輯後,向瀏覽器傳送一個狀態碼302,同時傳送一個訊息頭Location,此訊息頭的值是一個新地址。當瀏覽器接收這些資訊後,會立即向伺服器傳送該地址的請求     2、重定向的原理:可以參考:https://blog.csdn.net/kobejayandy/article/details/13745545     3、如何重定向             response.sendRedirect(String url)    url:是重定向的新地址     4、重定向的特點             位址列的地址會發生改變。             重定向之前不能關閉流             兩次請求不共享request和response物件  

6、異常錯誤處理

    錯誤程式碼及其解決方法:            伺服器在處理完業務邏輯後,會響應瀏覽器,響應的內容包含了狀態編碼(數字型別)            200:表示成功處理業務。            404:伺服器處理的路徑存在問題,找不到相關請求資源                     如:                       (1)在位址列上的路徑有問題(大小寫不對)                       (2)<url-pattern>的值與位址列路徑不一致                       (3)兩個servlet-name不一致                       (4)沒有部署專案                       (5)專案的組織結構有問題            405:容器找不到Servlet元件的service方法                       (1)方法名寫錯                       (2)方法的引數型別有問題                       (3)方法的異常,返回值有問題            500:容器找不到Servlet元件                       (1)沒有繼承HttpServlet或實現Servlet介面                       (2)<servlet-class>寫的不錯                       (3)service裡的邏輯出現了問題

    處理中文引數值

           中文會出現亂碼,原因是編碼與解碼的字符集不一致造成            中文亂碼解決方式                      方式1:服務端先編碼再解碼,適合 get/post  req.setCharacterEncoding("utf-8")  伺服器端預設使用iso-8859-1解碼瀏覽器端常用的為utf-8進行編碼                   方式2:只適合post request.setCharacterEncoding("utf-8")  位置:處理請求引數前               傳送響應時:                   response.setContentType("text/html;charset=utf-8")  位置:寫在獲取流之前 

再寫程式碼時先將request.setCharacterEncoding("utf-8")response.setContentType("http/html;charset=utf-8") 寫上這樣就能避免出現亂碼