-
-
從狹義上來講,Servlet指的是javax.servlet.Servlet接口及其子接口,也可以指實現了Servlet接口的實現類。
-
Servlet(Server Applet)作爲服務器端的一個組件,它的本意是“服務器端的小程序”。
-
Servlet的實例對象由Servlet容器負責創建;
-
Servlet的方法由容器在特定情況下調用;
-
-
① 搭建Web開發環境
② 創建動態Web工程
③ 創建javax.servlet.Servlet接口的實現類:com.atguigu.servlet.MyFirstServlet
<!-- 聲明一個Servlet,配置的是Servlet的類信息 --> <servlet> <!-- 這是Servlet的別名,一個名字對應一個Servlet。相當於變量名 --> <servlet-name>MyFirstServlet</servlet-name> <!-- Servlet的全類名,服務器會根據全類名找到這個Servlet --> <servlet-class>com.servlet.MyFirstServlet</servlet-class> </servlet> <!-- 建立Servlet的請求映射信息 --> <servlet-mapping> <!-- Servlet的別名,說明這個Servlet將會響應下面url-pattern的請求 --> <servlet-name>MyFirstServlet</servlet-name> <!-- Servlet響應的請求路徑。如果訪問這個路徑,這個Servlet就會響應 --> <url-pattern>/MyFirstServlet</url-pattern> </servlet-mapping>
說明:
<url-pattern>:這個url-pattern可以配置多個,這時表示的就是訪問這些url都會觸發這個Servlet進行響應,運行瀏覽器,訪問剛纔配置的url路徑,Servlet的service方法就會被調用。
<url-pattern>中的文本內容必須以 / 或 *. 開始書寫路徑。相當於將資源映射到項目根目錄下形成虛擬的資源文件。
<servlet-mapping>中的<url-pattern>
⑥ 在WebContent目錄下創建index.html
⑦ 在index.html中加入超鏈接 <a href="MyFirstServlet">To Servlet</a>
⑧ 點擊超鏈接測試Servlet
如果配置文件一旦修改,需要重啓服務器來重新部署web項目。
-
接收請求 【解析請求報文中的數據:請求參數】
-
處理請求 【DAO和數據庫交互】
-
完成響應 【設置響應報文】
簡單的敘述生命週期,就是對象在容器中從開始創建到銷燬的過程。
Servlet對象是Servlet容器創建的,生命週期方法都是由容器調用的。這裏指的就是Tomcat
-
-
作用:是在Servlet對象創建後,執行一些初始化操作。例如,讀取一些資源文件、配置文件,或建立某種連接(比如:數據庫連接)
-
init()方法只在創建對象時執行一次,以後再接到請求時,就不執行了
-
-
-
在每次接到請求後都會執行。
-
Servlet的作用,主要在此方法中體現。
-
④ Servlet對象銷燬:destroy()
-
服務器重啓、服務器停止執行或Web應用卸載時會銷燬Servlet對象,會調用public void destroy()方法。
-
Servlet請求過程
-
第一次請求
-
調用構造器,創建對象
-
執行init()方法
-
執行service()方法
-
-
後面請求
-
-
對象銷燬前
-
執行destroy()方法
-
-
-
每一個Servlet都有一個唯一對應的ServletConfig對象,代表當前Servlet的配置信息。
-
對象由Servlet容器創建,並傳入生命週期方法init(ServletConfig config)中。可以直接獲取使用。
-
代表當前Web應用的ServletContext對象也封裝到了ServletConfig對象中,使ServletConfig對象成爲了獲取ServletContext對象的一座橋樑。
-
ServletConfig對象的主要功能
-
獲取Servlet名稱:getServletName()
-
獲取全局上下文ServletContext對象:getServletContext()
-
-
-
-
由於一個Web應用程序中的所有Servlet都共享同一個ServletContext對象,所以ServletContext對象也被稱爲 application 對象(Web應用程序對象)。
-
對象由Servlet容器在項目啓動時創建,通過ServletConfig對象的getServletContext()方法獲取。在項目卸載時銷燬。
-
ServletContext對象的主要功能
① 獲取項目的上下文路徑(帶/的項目名):
-
虛擬路徑:瀏覽器訪問Web應用中資源時所使用的路徑。
-
本地路徑:資源在文件系統中的實際保存路徑。
-
<web-app> <!-- Web應用初始化參數 --> <context-param> <param-name>ParamName</param-name> <param-value>ParamValue</param-value> </context-param> </web-app>
獲取Web應用初始化參數
-
-
GenericServlet實現Servlet接口
-
HttpServlet繼承GenericServlet
-
-
創建Servlet的最終方式
-
-
-
如果想要進行初始化操作,可以重寫GenericServlet提供的無參的init()方法,這樣就不會影響ServletConfig對象的獲取。
-
-
-
對GenericServlet進行進一步的封裝和擴展,在service(ServletRequest req, ServletResponse res)方法中,將ServletRequest和ServletResponse轉換爲HttpServletRequest和HttpServletResponse,根據不同HTTP請求類型調用專門的方法進行處理。
-
今後在實際使用中繼承HttpServlet抽象類創建自己的Servlet實現類即可。重寫doGet(HttpServletRequest req, HttpServletResponse resp)和doPost(HttpServletRequest req, HttpServletResponse resp)方法實現請求處理,不再需要重寫service(ServletRequest req, ServletResponse res)方法了。
-
-
-
瀏覽器請求服務器時會封裝請求報文交給服務器,服務器接受到請求會將請求報文解析生成request對象。
-
功能
1.使用HttpServletRequest對象獲取請求參數,即瀏覽器向服務器提交的數據
//一個name對應一個值 String userId = request.getParameter("userId");
//一個name對應一組值 String[] soccerTeams = request.getParameterValues("soccerTeam"); for(int i = 0; i < soccerTeams.length; i++){ System.out.println("team "+i+"="+soccerTeams[i]); }
2.獲取url地址參數
String path = request.getContextPath();//重要 System.out.println("上下文路徑:"+path); System.out.println("端口號:"+request.getServerPort()); System.out.println("主機名:"+request.getServerName()); System.out.println("協議:"+request.getScheme());
3.獲取請求頭信息
String header = request.getHeader("User-Agent"); System.out.println("user-agent:"+header); String referer = request.getHeader("Referer"); System.out.println("上個頁面的地址:"+referer);//登錄失敗,返回登錄頁面讓用戶繼續登錄
4.請求的轉發
//獲取請求轉發對象 RequestDispatcher dispatcher = request.getRequestDispatcher("success.html"); dispatcher.forward(request, response);//發起轉發
5.向請求域中保存數據
//將數據保存到request對象的屬性域中 request.setAttribute("attrName", "attrValueInRequest"); //兩個Servlet要想共享request對象中的數據,必須是轉發的關係 request.getRequestDispatcher("/ReceiveServlet").forward(request, response);
//從request屬性域中獲取數據 Object attribute = request.getAttribute("attrName"); System.out.println("attrValue="+attribute);
功能
1.使用PrintWriter對象向瀏覽器輸出數據
//通過PrintWriter對象向瀏覽器端發送響應信息 PrintWriter writer = res.getWriter(); writer.write("Servlet response"); writer.close();
2.設置響應頭
response.setHeader("Content-Type", "text/html;charset=UTF-8");
- 設置好以後,會在瀏覽器的響應報文中看到設置的響應頭中的信息。
3.重定向請求
//注意路徑問題,加上/會失敗,會以主機地址爲起始,重定向一般需要加上項目名 response.sendRedirect(“success.html”);
- 通過重定向將頁面的地址交給瀏覽器並設置響應狀態碼爲302,瀏覽器會自動進行跳轉。
- 轉發的情況下,兩個Servlet可以共享同一個Request對象中保存的數據。
- 當需要將後臺獲取的數據傳送到JSP上顯示的時候,就可以先將數據存放到Request對象中,再轉發到JSP從屬性域中獲取。此時由於是“轉發”,所以它們二者共享Request對象中的數據。
- 轉發的情況下,可以訪問WEB-INF下的資源。
- 轉發以“/”開始表示項目根路徑,重定向以”/”開始表示主機地址。
//1.使用RequestDispatcher對象封裝目標資源的虛擬路徑 RequestDispatcher dispatcher = request.getRequestDispatcher("/index.html"); //2.調用RequestDispatcher對象的forward()方法“前往”目標資源 //[注意:傳入的參數必須是傳遞給當前Servlet的service方法的 //那兩個ServletRequest和ServletResponse對象] dispatcher.forward(request, response); }
- 重定向的情況下,原Servlet和目標資源之間就不能共享請求域數據了。
- HttpServletResponse代表HTTP響應,對象由Servlet容器創建。
//1.調用HttpServletResponse對象的sendRedirect()方法 //2.傳入的參數是目標資源的虛擬路徑 response.sendRedirect("index.html");
轉發 | 重定向 | |
---|---|---|
瀏覽器感知 | 在服務器內部完成,瀏覽器感知不到 | 服務器以302狀態碼通知瀏覽器訪問新地址,瀏覽器有感知 |
瀏覽器地址欄 | 不改變 | 改變 |
整個過程發送請求次數 | 一次 | 兩次 |
執行效率 | 效率高 | 效率低 |
API(或發起者) | Request對象 | Response對象 |
能否共享request對象數據 | 能 | 否 |
WEB-INF下的資源 | 能訪問 | 不能訪問 |
目標資源 | 不侷限於當前web應用 |
說明:默認情況下,瀏覽器是不能訪問服務器web-inf下的資源的,而服務器是可以訪問的。
解決亂碼的方法:就是統一字符編碼
- GET請求參數是在地址後面的。我們需要修改tomcat的配置文件。需要在server.xml文件修改Connector標籤,添加URIEncoding="utf-8"屬性。
- 一旦配置好以後,可以解決當前工作空間中所有的GET請求的亂碼問題。
request.setCharacterEncoding("utf-8");
- POST請求亂碼問題的解決,只適用於當前的操作所在的類中。不能類似於GET請求一樣統一解決。因爲請求體有可能會上傳文件。
- 向瀏覽器發送響應的時候,要告訴瀏覽器,我使用的字符集是哪個,瀏覽器就會按照這種方式來解碼
//方法一:
response.setHeader("Content-Type", "text/html;charset=utf-8");
//方法二:
response.setContentType("text/html;charset=utf-8");
相對路徑和絕對路徑
絕對路徑:虛擬路徑以“/”開始,就是絕對路徑。
<!-- 給頁面中的相對路徑設置基準地址 --> <base href="http://localhost:8080/Test_Path/"/>
總結:
* /的有無
* 有: 採用的是絕對路徑
* 無: 採用的是相對路徑
* /的含義:
* 用服務器解析代表:當前項目下 (http://localhost:8080/上下文項目名/)
* 用瀏覽器解析代表:當前主機下(http://localhost:8080/)
* /的幾種使用位置:
* 用在轉發:採用服務器解析 (相對和絕對沒有區別)
* 用在重定向:採用瀏覽器解析
* 相對路徑:response.sendRedirect("pages/user/login_success.html");
* 局對路徑:response.sendRedirect(request.getContextPath()+"/pages/user/login_success.html");
* 用在頁面上:採用瀏覽器解析
* 建議採用絕對路徑去加載靜態資源(css/js/image/video...)
* 方式一:<link href="/上下文項目名/static/css/style.css" type="text/css" rel="stylesheet" >
* 方式二:在head標籤中新增一個base標籤並設置href屬性 ★
* <base href="/BookStore02/"> 在當前頁面中所有的路徑錢統一添加指定前綴