┌─────────┐ ┌─────────┐ │░░░░░░░░░│ │O ░░░░░░░│ ├─────────┤ ├─────────┤ │░░░░░░░░░│ │ │ ├─────────┤ │ │ │░░░░░░░░░│ └─────────┘ └─────────┘ │ request 1 │ │─────────────────────>│ │ request 2 │ │─────────────────────>│ │ response 1 │ │<─────────────────────│ │ request 3 │ │─────────────────────>│ │ response 3 │ │<─────────────────────│ │ response 2 │ │<─────────────────────│ ▼ ▼
我們注意到HTTP協定是一個請求-回應協議,它總是發送一個請求,然後接收一個回應。能不能一次發送多個請求,然後再接收多個回應呢? HTTP 2.0
可以支援瀏覽器同時發出多個請求,但每個請求需要唯一標識,伺服器可以不按請求的順序傳回多個回應,由瀏覽器自己把收到的回應和請求對應起來。可見,HTTP 2.0
進一步提高了傳輸效率,因為瀏覽器發出一個請求後,不必等待回應,就可以繼續發下一個請求。
HTTP 3.0
為了進一步提高速度,將拋棄TCP
協議,改為使用無需建立連接的UDP
協議,目前 HTTP 3.0
仍處於實驗推廣階段。
在JavaEE
平台上,處理TCP
連接,解析HTTP
協定這些底層工作統統扔給現成的Web
伺服器去做,我們只需要把自己的應用程式跑在Web
伺服器上。為了實現這個目的,JavaEE
提供了Servlet
API
#Servlet API
編寫自己的
Servlet#來處理
HTTP請求,
Web伺服器實作
Servlet API
實作底層功能.
// WebServlet注解表示这是一个Servlet,并映射到地址 hello.do @WebServlet(urlPatterns = "/hello.do") public class HelloServlet extends HttpServlet { protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { // 设置响应类型: resp.setContentType("text/html"); // 获取输出流: PrintWriter pw = resp.getWriter(); // 写入响应: pw.write("<h2>Hello, world!</h2>"); // 最后不要忘记flush强制输出: pw.flush(); } }
一個
Servlet總是繼承自
HttpServlet,然後覆寫
doGet()或
doPost()方法。注意到
doGet()方法傳入了
HttpServletRequest和
HttpServletResponse兩個對象,分別代表
HTTP請求和回應。我們使用
Servlet API時,不會直接與底層
TCP交互,也不需要解析
HTTP協議,因為
HttpServletRequest
就已經封裝好了請求和回應。以傳送回應為例,我們只需要設定正確的回應類型,然後取得PrintWriter,寫入回應即可。
文件,運行這個文件,需要使用支援Servlet
API因此,我們首先要找到一個支援Servlet API的Web伺服器。
Jetty:由Eclipse開發的開源免費伺服器;
#GlassFish:一個開源的全功能JavaEE伺服器。
在透過一個URL路徑發起對一個Servlet
請求的過程中,其本質是在呼叫執行Servlet
實例的doXXX()
方法。此Servlet實例所建立和使用的過程,稱為Servlet的生命週期。整個生命週期包括:實例化、初始化、服務、銷毀。
#請求的路徑(例如:home.do),找出該Servlet
的實例。如果實例不存在,則透過呼叫建構方法,完成Servlet
初始化:
透過該Servlet的實例,
呼叫init()
方法,執行初始化的邏輯。 服務:
透過該Servlet
的
方法,如果子類別沒有重寫該方法,則呼叫HttpServlet父類別的service()
方法,在父類別的該方法中進行請求方式的判斷,如果是GET
請求,則呼叫
方法;如果是POST
請求,則呼叫doPost()
方法;
doXXX()方法,則呼叫子類別重寫後的doXXX()
方法;如果子類別沒有重寫doXXX ()方法,則呼叫父類別的
doXXX()
405狀態碼的錯誤頁面。
405狀態碼:
代表請求的方式伺服器不提供支援。 ###### 4###.銷毀###:伺服器關閉或重新啟動時,會銷毀所有的Servlet實例,會呼叫Servlet實例的###destroy()###方法。 ############package com.my.hyz.web.servlet; 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; //@WebServlet("/home.do") public class HomeServlet extends HttpServlet { public HomeServlet() { System.out.println("实例化"); } @Override public void init() throws ServletException { System.out.println("初始化"); //super.init(); } @Override protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("调用Service实例"); } @Override public void destroy() { System.out.println("销毁咯!!!!"); } @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { // TODO Auto-generated method stub System.out.println("哎呦get到了"+this.hashCode()); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("哎呦post到了"); } }
以上是Java中的Servlet怎麼實現的詳細內容。更多資訊請關注PHP中文網其他相關文章!