Servlet的簡單實現和核心類物件 方法
Servlet的實現和相關的方法 |
---|
一、關於servlet
servlet 是執行在 Web 伺服器中的小型 Java 程式。
servlet 通常通過 HTTP(超文字傳輸協議)接收和響應來自 Web 客戶端的請求。
要實現此介面,可以編寫一個擴充套件 javax.servlet.GenericServlet 的一般 servlet,
或者編寫一個擴充套件 javax.servlet.http.HttpServlet 的 HTTP servlet。
此介面定義了初始化 servlet 的方法、為請求提供服務的方法和從伺服器移除 servlet 的方法。
這些方法稱為生命週期方法,它們是按以下順序呼叫的:
1. 構造 servlet,然後使用 init 方法將其初始化。
2. 處理來自客戶端的對 service 方法的所有呼叫。
3. 從服務中取出 servlet,然後使用 destroy 方法銷燬它,最後進行垃圾回收並終止它。
(二)如果建立工程沒預設自動配置servlet 的xml 則手動配置如下:
圖1
(三)servlet的生命週期
servlet的生命週期。
什麼時候建立一個servlet?
什麼時候去銷燬一個servlet?
Servlet的生命週期
1.先呼叫 Servlet的構造方法 2.呼叫 init 方法 初始化Servlet 3.呼叫 Servlet中的service方法 處理請求操作 4.呼叫 destory方法 執行Servlet銷燬的操作
《1》init方法:當伺服器建立一個serlvet的時候,會去呼叫init方法。
當我們第一次去訪問一個servlet的時候,會去建立這個servlet物件。並且只會建立一次。
《2》Dopost 或 doget 方法 則每訪問一次就會執行一次
《3》destory 在關閉伺服器的時候被登出 此servlet資源將被釋放
eclipse自動建立servlet時注意其訪問的url
圖2
《4》、Servlet類的繼承體系:
圖3
二、與Servlet相對於的 幾個核心物件和類
(1)、ServletConfig類(一個Servlet對應一個config物件)
ServletConfig類,見名知義。它是Servlet類的配置檔案類。封裝了Servlet的配置檔案的資訊。
它常用的功能有三個。
1.獲取Servlet在web.xml檔案中配置的Servlet名稱
(也就是servlet-name的值<servlet-name>ConfigServlet</servlet-name>)。
2.獲取Servlet初始化資訊。(web.xml檔案中<Servlet>標籤中 <init-param>的初始化資訊 )
3.獲取ServletContext域物件
String servlet_name = config.getServletName();
String param_value = config.getInitParameter("username");
ServletContext context = config.getServletContext();
2) web.xml檔案中的配置資訊:
<servlet>
<servlet-name>ConfigServlet</servlet-name>
<servlet-class>com.atguigu.servlet.ConfigServlet</servlet-class>
<!-- 給servlet新增初始化引數 -->
<init-param>
<!-- param-name 是初始化引數的名 -->
<param-name>username</param-name>
<!-- param-value 是初始化引數的值 -->
<param-value>root</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>ConfigServlet</servlet-name>
<url-pattern>/configServlet</url-pattern>
</servlet-mapping>
★★★
注意事項:
當我們繼承HttpServlet類實現Servlet程式的時候,
重寫Servlet中的init方法,
我們要在方法內第一行呼叫super.init(config),
否則會在其他呼叫getServletConfig方法或者getServletContext方法的時候拋空指標異常
(2)、servletContext說明(ServletContext對應一個Web工程
★★☆
當Tomcat啟動的時候,有多少個動態web工程,就會建立多少個ServletContext。
一個動態web工程,對應一個ServletContext。
那麼一個動態web工程中,所有的Servlet都可以共享一個ServletContext物件。
什麼是ServletContext?
第一:ServletContext是一個介面。
第二:ServletContext是一個域物件! 就是儲存資料的範圍。
它的範圍是整個工程共享。
第三:每個Web工程,都對應一個ServletContext物件!
ServletContext有什麼作用?
第一:ServletContext可以獲取web.xml檔案中的配置上下文引數,
是整個工程的上下文引數。(不是Servlet中的init-param引數)
第二:ServletContext可以獲取web工程在伺服器的工程名
第三:ServletContext可以獲取web工程中資料夾或檔案在伺服器硬碟上的絕對路徑(經常用來和上傳和下載一起使用)
第四:ServletContext可以設定web工程的全域性屬性
1) Servlet中的示例程式碼:
public class ContextServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
protected void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
// 獲取ServletConfig物件
ServletConfig config = getServletConfig();
// 獲取Servlet的上下文物件
ServletContext context = config.getServletContext();
// 獲取web.xml檔案中配置的引數的值
// 正確。ServletContext只能獲取context-param配置的引數
String passwordValue = context.getInitParameter("password");
System.out.println("獲取context-param引數:" + passwordValue);
// ServletContext無法獲取Servlet中配置的init-param引數
String usernameValue = context.getInitParameter("username");
System.out.println("獲取servlet配置的init-param引數:" + usernameValue);
}
2) web.xml中的配置資訊
<!-- 配置由ServletContext獲取的引數 -->
<context-param>
<!-- 配置引數的名 -->
<param-name>password</param-name>
<!-- 配置引數的值 -->
<param-value>root</param-value>
</context-param>
<servlet>
<!-- 配置Servlet中的別名 -->
<servlet-name>ContextServlet</servlet-name>
<!-- 配置Servlet的全類名 -->
<servlet-class>com.atguigu.servlet.ContextServlet</servlet-class>
</servlet>
<servlet-mapping>
<!-- 配置Servlet的別名 -->
<servlet-name>ContextServlet</servlet-name>
<!-- 配置Servlet的訪問路徑 -->
<url-pattern>/contextServlet</url-pattern>
</servlet-mapping>
3)ServletContext物件獲取佈署後的工程名
圖4
4)、ServletContext獲取工程目錄或檔案在伺服器硬碟上的絕對路徑
// 獲取ServletConfig物件
ServletConfig config = getServletConfig();
// 獲取Servlet的上下文物件
ServletContext context = config.getServletContext();
//獲取/表示的路徑表示從http://127.0.0.1:8080/工程名/ 所表示的硬碟絕對路徑
// /也就是WebContent下的內容
String path = context.getRealPath("/");
System.out.println("/的硬碟路徑:" + path);
//獲取/imgs表示的路徑
// /imgs也就是表示WebContent目錄下的imgs目錄,釋出後的硬碟絕對路徑。
String imgspath = context.getRealPath("/imgs");
System.out.println("/imgs的硬碟路徑:" + imgspath);
//獲取/imgs表示的路徑
// /imgs也就是表示WebContent目錄下的imgs目錄裡wrong.png檔案,釋出後的硬碟絕對路徑。
String wrongpath = context.getRealPath("/imgs/wrong.png");
System.out.println("/imgs/wrong.png的硬碟路徑:" + wrongpath);
5)ServletContext設定全域性共享屬性
我們可以建立兩個Servlet程式。分別是:ContextAttrServlet1和ContextAttrServlet2.
a) 在ContextAttrServlet1 中直接通過ServletContext獲取一個沒有設定的屬性值。
b) 然後在ContextAttrServlet2 中,通過ServletContext設定一個全域性的屬性值。
c) 然後通過不同的訪問順序測試ServletContext物件管理的全域性共享屬性。
程式碼:
ContextAttrServlet1的程式碼:
圖5
ContextAttrServlet1的配置資訊:
<servlet>
<description></description>
<display-name>ContextAttrServlet1</display-name>
<servlet-name>ContextAttrServlet1</servlet-name>
<servlet-class>com.atguigu.servlet.ContextAttrServlet1</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>ContextAttrServlet1</servlet-name>
<url-pattern>/contextAttrServlet1</url-pattern>
</servlet-mapping>
ContextAttrServlet2的程式碼
圖6
ContextAttrServlet2的配置資訊
<servlet>
<description></description>
<display-name>ContextAttrServlet2</display-name>
<servlet-name>ContextAttrServlet2</servlet-name>
<servlet-class>com.atguigu.servlet.ContextAttrServlet2</servlet-class>
ContextAttrServlet2
/contextAttrServlet2
6) 訪問測試過程:
1.先訪問http://127.0.0.1:8080/day07/contextAttrServlet1 檢視全 局的username屬性,因為還沒設定,所以獲取是null
2.然後訪問http://127.0.0.1:8080/day07/contextAttrServlet2 設定全域性的username屬性值。
3.最後再訪問http://127.0.0.1:8080/day07/contextAttrServlet1 由於 contextAttrServlet2中已經設定了屬性值,這時候再訪問可以獲取到值。
控制檯列印資訊:
圖7