Servlet

Servlet
XXXServlet extends HttpServlet(模板方法設計模式) extends GenericServlet(Servlet適配器類型) implements Servlet

javax.servlet.Servlet接口方法
    public void init(ServletConfig config) throws ServletException {}
    public void service(ServletRequest request, ServletResponse response) throws ServletException, IOException {}
    public void destroy() {}
    public ServletConfig getServletConfig() {return null;}
    public String getServletInfo() {return null;}

Servlet對象的生命週期表示:Servlet對象從最初的創建,到最終的銷燬。
Servlet對象的創建,Servlet對象的方法被調用,Servlet對象的銷燬,都是由WEB容器來負責管理的,
javaweb程序員不需要管理這些,主要負責:Servlet類的編寫,service方法的實現,Servlet類在web.xml文件中的配置。
Servlet對象“默認情況”下,在服務器啓動階段是不會實例化的。不會創建對象。
Servlet對象的生命週期:
    1) 用戶打開瀏覽器在瀏覽器地址欄上輸入URL:http://localhost:8080/oa/save,回車
    2) WEB服務器截取請求路徑,得知用戶要訪問的資源是:/oa/save
    3) WEB服務器從整個容器中檢索/oa/save請求路徑對應的Servlet對象
    4) 若找到了該Servlet對象
        4-1) web容器負責調用該Servlet對象的service方法提供服務,處理請求
    5) 若沒有找到該Servlet對象
        5-1) 通過請求路徑/save找到對應的Servlet完整類名(web.xml文件支持的,web.xml文件在服務器啓動階段解析,路徑和類名已經綁定在一起了)
        5-2) 通過反射機制調用Servlet類的無參數構造方法完成Servlet對象的實例化操作。(Servlet對象已經創建完畢)
        5-3) web容器調用該Servlet對象的init方法完成初始化操作。
        5-4) web容器調用該Servlet對象的service方法提供服務,處理請求
    6) 若“服務器關閉”或“webapp重新部署”或“長時間沒有用戶再訪問該Servlet”,WEB容器
    會銷燬該Servlet對象佔用的內存空間,web容器在銷燬該Servlet對象之前,web容器負責
    調用該Servlet對象的destroy方法,完成銷燬之前的準備工作。

Servlet對象是單實例的,不符合單例模式,是一種僞單例,真單例的構造方法必須是私有化的。
Servlet對象是在多線程環境下運行的一個對象。【單實例多線程環境下運行的一個java對象】
之所以Servlet對象是單實例的,是因爲該對象的創建是由WEB容器負責的,javaweb程序員不能干涉

總結:
1) 無參數構造方法只調用一次,對象只創建一個,對象是單例的
2) init方法只被調用一次,在對象創建之後馬上執行它,完成初始化操作
3) service方法,只要用戶發送請求一次,則執行一次
4) destroy方法也是隻執行一次
    注意:
    init方法在執行的時候,對象已經存在了。
    destroy方法在執行的時候,對象還沒有被回收,還存在。

重點:
    在Servlet類中最好不要手動編寫任何構造函數,這樣做可能會導致無參數構造函數不存在,
    這樣通過反射機制創建對象的時候,會出現實例化異常。Servlet對象創建失敗。

錯誤代號:【HTTP狀態號】
    404    - 資源找不到,通常是路徑問題,還有可能是項目本身啓動失敗
    405 - 表示前端發送的請求方式和後臺要求的請求方式不同。請求方式錯誤
    500 - 服務器內部錯誤,通常是服務器中的java程序出現了異常


javax.servlet.ServletConfig接口方法
    - String getInitParameter(String name)  通過初始化參數的name獲取value
    - Enumeration getInitParameterNames()    獲取所有初始化參數的name
    - ServletContext getServletContext()    獲取ServletContext對象
    - String getServletName() 【使用較少】

ServletConfig對象是“Servlet對象的配置信息對象”
Servlet對象的配置信息在web.xml文件中的<servlet></servlet>標籤內部
ServletConfig對象封裝了當前Servlet對象的配置信息。
通過ServletConfig對象可以獲取該Servlet對象的相關配置信息。
一個Servlet對象對應一個ServletConfig對象,100個Servlet對象對應100個ServletConfig對象。

javax.servlet.ServletContext接口方法
    - void setAttribute(String name, Object object)    向Servlet上下文中綁定一個數據object,起名name (map.put(key,value))
    - Object getAttribute(String name)                       從Servlet上下文中取object,通過name (Object value = map.get(key))
    - void removeAttribute(String name)                    移除Servlet上下文中的某個數據,通過name  (map.remove(key))

    - String getInitParameter(String name)                通過上下文參數的name獲取上下文參數value
    - Enumeration getInitParameterNames()             獲取所有上下文參數的name

    - String getRealPath(String path)                                獲取絕對路徑
    - InputStream getResourceAsStream(String path)     直接獲取文件輸入流

ServletContext是一個Servlet上下文對象
ServletContext對象是所有Servlet共享的一個四周環境對象
Context單詞翻譯:上下文  
例如:contextPath就是上下文路徑: /prj-servlet-06 【webapp的根路徑】
ServletContext可以完成多個Servlet之間共享同一些數據。
ServletContext對象中封裝了web.xml文件中所有信息,
ServletContext對象只有一個,web.xml文件也是隻有一個
web.xml文件也是在服務器啓動階段被解析,ServletContext也是在服務器啓動階段被創建。
在同一個webapp中,ServletContext對象只有一個
在web服務器啓動階段被創建
在web服務器關閉的時候被銷燬
ServletContext對象是一個應用級別的對象。
注:100個app對應100個ServletContext
        一個Servlet對應一個ServletConfig,所有的Servlet共享一個ServletContext
        通過ServletContext對象可以完成:跨用戶傳遞數據


HTTP協議是什麼?
    - HTTP協議是一種超文本傳輸協議
    - W3C制定的
    - 瀏覽器和服務器之間提前制定好的一種數據傳送格式
HTTP協議包括:請求協議和響應協議
    - 請求協議:瀏覽器向服務器發送數據的時候,數據傳送格式
    - 響應協議:服務器向瀏覽器發送數據的時候,數據傳送格式

請求協議包括以下四部分:
    - 請求行
    - 消息報頭
    - 空白行
    - 請求體
響應協議包括以下四部分:
    - 狀態行
    - 消息報頭
    - 空白行
    - 響應體[響應正文]

只有一種方式是POST請求,使用form表單提交數據,並且同時form標籤的method屬性設置爲method="POST",剩下任何一種請求,一律都是GET方式。

請求協議:基於get方式
    GET /prj-servlet-08/user/login?username=admin&password=123 HTTP/1.1                請求行
    Accept: text/html, application/xhtml+xml, */*                                                                   消息報頭
    Referer: http://localhost:8080/prj-servlet-08/                                                                  消息報頭
    Accept-Language: zh-CN                                                                                               消息報頭
    User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)             消息報頭
    Accept-Encoding: gzip, deflate                                                                                       消息報頭
    Host: localhost:8080                                                                                                       消息報頭
    Connection: Keep-Alive                                                                                                  消息報頭
                                                                                                                                            空白行
                                                                                                                                            請求體
    注:
          第一:請求行由三部分組成:請求方式、URI、協議版本號
          第二:若請求是GET請求,在請求行中發送數據,格式:uri?name=value&name=value.....
          第三:GET請求最終瀏覽器地址欄上會將提交的數據顯示出來

請求協議:基於POST方式
    POST /prj-servlet-08/user/login HTTP/1.1                                                                     請求行
    Accept: text/html, application/xhtml+xml, */*                                                                 消息報頭
    Referer: http://localhost:8080/prj-servlet-08/                                                                 消息報頭
    Accept-Language: zh-CN                                                                                              消息報頭
    User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)            消息報頭
    Content-Type: application/x-www-form-urlencoded                                                       消息報頭
    Accept-Encoding: gzip, deflate                                                                                      消息報頭
    Host: localhost:8080                                                                                                      消息報頭
    Content-Length: 27                                                                                                        消息報頭
    Connection: Keep-Alive                                                                                                 消息報頭
    Cache-Control: no-cache                                                                                               消息報頭
                                                                                                                                           空白行
    username=admin&password=123                                                                                 請求體
    
    注:
          第一:請求行由三部分組成:請求方式、URI、協議版本號
          第二:若請求是POST請求,在請求體中發送數據,格式:name=value&name=value.....
          第三:POST請求最終瀏覽器地址欄上不會將提交的數據顯示出來,因爲不是在請求行上發送的數據
        
    HTTP協議中包含8種請求方法:
          GET               請求獲取Request-URI 所標識的資源
          POST             在Request-URI 所標識的資源後附加新的數據
          HEAD             請求獲取由Request-URI 所標識的資源的響應消息報頭
          PUT                請求服務器存儲一個資源,並用Request-URI 作爲其標識
          DELETE         請求服務器刪除Request-URI 所標識的資源
          TRACE           請求服務器回送收到的請求信息,主要用於測試或診斷
          CONNECT     保留將來使用
          OPTIONS       請求查詢服務器的性能,或者查詢與資源相關的選項和需求

GET和POST只和請求有關係,和響應無關。無論發送的請求是GET請求還是POST請求,響應協議只有一種格式:
    HTTP/1.1 200 OK                                                                                                狀態行
    Server: Apache-Coyote/1.1                                                                                 消息報頭
    Content-Type: text/html;charset=UTF-8                                                              消息報頭
    Content-Length: 129                                                                                            消息報頭
    Date: Sat, 30 Jan 2016 03:28:29 GMT                                                                消息報頭
                                                                                                                                 空白行
    <html><head><title>login result</title></head><body><h1 align='center'>        響應體
    <font color='red'>login success!</font></h1></body></html>
    
    注:
        第一:狀態行由三部分組成:協議版本號、響應狀態號、狀態描述信息
            * 響應狀態號:【HTTP協議規定的】
                  - 404        資源找不到    
                  - 500        服務器內部錯誤
                  - 200        請求響應完整成功結束
                  ...
            狀態代碼由三位數字組成,第一個數字定義了響應的類別,且有五種可能取值:
                 1xx:指示信息--表示請求已接收,繼續處理
                 2xx:成功--表示請求已被成功接收、理解、接受
                 3xx:重定向--要完成請求必須進行更進一步的操作
                 4xx:客戶端錯誤--請求有語法錯誤或請求無法實現
                 5xx:服務器端錯誤--服務器未能實現合法的請求
            常見狀態代碼、狀態描述、說明:
                 200  OK      客戶端請求成功
                 400  Bad Request  客戶端請求有語法錯誤,不能被服務器所理解
                 401  Unauthorized  請求未經授權
                 403  Forbidden  服務器收到請求,但是拒絕提供服務
                 404  Not Found  請求資源不存在
                 500  Internal Server Error  服務器發生不可預期的錯誤
                 503  Server Unavailable    服務器當前不能處理客戶端的請求,一段時間後, 可能恢復正常
                 405  瀏覽器客戶端發送的請求和底層的方法doPost/doGet不一致導致的。
    
        第二:消息報頭包括
              * 響應的服務器版本
              * 響應的內容類型以及字符編碼方式
              * 響應長度,字節爲單位
              * 響應時間
        
        第三:空白行
              分離消息報頭和響應體的關建行
        
        第四:響應體會顯示到網頁中。瀏覽器解釋執行HTML代碼

GET請求和POST請求在表面上的區別:        
    - GET請求最終提交的數據會顯示到瀏覽器地址欄上,在請求行上提交數據
    - POST請求在請求體中提交數據,不會顯示到瀏覽器地址欄上

    - GET請求只能提交普通字符串,因爲GET請求在請求行上提交數據
    - POST請求不但可以提交普通字符串,而且還可以提交圖片等文件

    - GET請求提交的字符串長度有限制,只能提交少量數據,這也是因爲GET請求在請求行上提交數據
    - POST請求提交數據理論上無長度限制,可以提交大數據,這也是因爲POST請求在請求體中提交數據

    - GET請求最終的請求結果,會存放到瀏覽器緩存中。【支持Cache】
    - POST請求最終的請求結果,不會被放到瀏覽器緩存中。【不支持Cache:no cache】
    注:緩存是一種優化策略,減少IO,提高程序執行效率的重要手段,瀏覽器也不例外,爲了降低服務器的壓力,瀏覽器也是               支持緩存機制的。
    
GET請求和POST請求怎麼選擇呢?
    - 大多數都是使用GET請求
    - 提交的數據中有敏感信息,必須使用POST
    - 提交的數據不是普通字符串,例如文件上傳,必須使用POST
    - 提交的數據長度過長,必須使用POST
    - 若請求是讀取服務器端的資源,一般都是使用GET請求。讀取的資源不會頻繁的發生變化,所以這種請求有必要緩存起來。        以提高訪問效率
    - 若請求是修改服務器端的資源,一般都是使用POST請求。因爲每一次修改之後的結果大部分都是不一樣的,沒有必要緩              存。

 

javax.servlet.http.HttpServlet接口
    POST請求,請重寫doPost方法
    GET請求,請重寫doGet方法

javax.servlet.http.HttpServletRequest接口方法
    - String getParameter(String name)            通過參數的name獲取參數的value【實際上:獲取Map集合中一維數組的首元素】
    - String[] getParameterValues(String name)    通過參數Map集合的key獲取value,返回的是一個一維數組,適合於checkbox                                                                                 數據的獲取
    - Map<String,String[]> getParameterMap()    通過request獲取參數Map集合
    - Enumeration getParameterNames()            獲取所有參數name

    - Object getAttribute(String name)
    - void setAttribute(String name, Object o)
    - void removeAttribute(String name)

    - String getRemoteAddr()                    通過request對象獲取客戶端IP地址

    - String getContextPath()                    獲取應用程序的根路徑

    - String getMethod()                            獲取請求方式

    - String getRequestURI()                    獲取URI
    - StringBuffer getRequestURL()          獲取URL

    - String getServletPath()                     獲取servlet路徑(url-pattern標籤中的路徑)

    - HttpSession getSession()                    獲取session對象,若沒有獲取到session對象,則新建session對象
    - HttpSession getSession(boolean create)    獲取session對象,若沒有獲取到session對象,參數爲true則新建session對象,                                                                             參數爲false則返回null

    - void setCharacterEncoding(String env)       解決POST請求中的亂碼

    - Cookie[] getCookies()                        從request對象中獲取所有提交的Cookie

    - RequestDispatcher getRequestDispatcher(String path)    獲取請求轉發器,轉發器指向要轉發的路徑,調用轉發器對象的                                                                                                       forward方法,完成請求轉發
      javax.servlet.RequestDispatcher接口
             - void forward(ServletRequest request,ServletResponse response);

HttpServletRequest是一個請求對象,該對象中包裝了HTTP請求協議的全部信息。
表單提交的數據都在request對象中,面向request可以獲取表單中的數據。
一次請求對應一個request對象。10次請求對應10個不同的request對象。


亂碼可能出現在哪裏?
    1) 數據“傳遞”過程中的亂碼
    2) 數據“展示”過程中的亂碼
    3) 數據“保存”過程中的亂碼

瀏覽器在提交表單數據的時候,採用ISO-8859-1的這種編碼方式提交數據的。
只能解決POST請求中的亂碼問題:
    - request.setCharacterEncoding("UTF-8");
    - 以上代碼在從request對象中獲取任何數據之前設置有效果
    - 以上的代碼只對請求體中的數據進行編碼,無法對請求行上的數據進行編碼,所以只能解決POST,不能解決GET
只能解決GET請求中的亂碼問題:
    - 修改CATALINA_HOME/conf/server.xml文件
    - <Connector port="80" protocol="HTTP/1.1" connectionTimeout="20000" redirectPort="8443" URIEncoding="UTF-8"/>
    - server.xml文件中的Connector標籤中可以編寫什麼屬性呢?
          * 參考:C:\tomcat7\webapps\docs\config\http.html
          * port 設置端口號
          * URIEncoding 設置URI的編碼方式
          * maxThreads 設置Tomcat服務器可支持的最大線程數量
          * ....
GET和POST通用:
    String username = request.getParameter("username");
    //將username通過ISO-8859-1的編碼方式進行解碼還原,迴歸最原始的二進制碼
    byte[] bytes = username.getBytes("ISO-8859-1");
    //再找一種編碼方式,要求這種編碼方式和瀏覽器上的編碼方式一致,進行重新編碼【重新組裝】
    username = new String(bytes,"UTF-8");

響應時解決亂碼問題:
    - response.setContentType("text/html;charset=UTF-8");


javax.servlet.http.HttpServletResponse接口方法
    - PrintWriter getWriter()
    java.io.PrintWriter
        - print(String str)


Servlet的線程安全,對於多線程來說,JVM內存中方法區和堆區內存空間是共享的,棧內存空間是獨立的,一個線程一個棧。
- 局部變量內存不共享,所以局部變量不存在線程安全問題
- 靜態變量和實例變量,靜態變量在方法區中,實例變量堆內存的java對象內部,靜態變量和實例變量存在線程安全問題
解決方案:
      第一種方案:儘量使用局部變量代替實例變量
      第二種方案:若必須使用實例變量,那麼可以考慮,讓對象變成多例,不再是單例。
      第三種方案:若必須使用實例變量,必須是單例的,這個時候必須使用線程同步機制:synchronized
      注意:使用線程同步機制,是不得以的時候再使用,因爲這種方式會讓程序的吞吐量降低,用戶排隊訪問,用戶體驗差。


轉發機制(forward)和重定向機制(redirect)
轉發:
    request.getRequestDispatcher("/b").forward(request,response);
    轉發是一次請求
    轉發是request對象觸發的
    轉發的資源路徑中不需要添加contextPath
    轉發只能完成項目內部資源的跳轉
重定向:
    response.sendRedirect("/prj-servlet-16/b");
    重定向是兩次請求
    重定向是response對象觸發的
    重定向的資源路徑需要添加contextPath
    重定向可以完成跨項目資源跳轉
    重定向可以解決頁面刷新問題(操作數據的請求若使用轉發,每次刷新都會在數據庫操作一次)


Cookie:
    - Cookie這種機制是HTTP協議規定的,只要是基於HTTP協議,就有Cookie的存在。
    - Cookie可以保存會話狀態,但是這個會話狀態是保留在客戶端上。
    - 只要Cookie清除,或者Cookie失效,這個會話狀態就沒有了。
    - Cookie是保存在瀏覽器客戶端上的
    - Cookie可以保存在瀏覽器的緩存中,瀏覽器關閉Cookie消失
    - Cookie也可以保存在客戶端的硬盤文件中,瀏覽器關閉Cookie還在,除非Cookie失效。

javax.servlet.http.Cookie類
    創建Cookie對象
    Cookie cookie = new Cookie(String cookieName,String cookieValue);
    設置Cookie的關聯路徑
    cookie.setPath(request.getContextPath() + "/king");
    設置Cookie的有效期爲1小時
    cookie.setMaxAge(60 * 60);
    將Cookie對象發送給瀏覽器客戶端
    response.addCookie(cookie);

服務器可以一次向瀏覽器發送多個Cookie
默認情況下,服務器發送Cookie給瀏覽器之後,瀏覽器將Cookie保存在緩存當中,只要不關閉瀏覽器,Cookie永遠存在,並且有效。
當瀏覽器關閉之後,緩存中的Cookie被清除。
瀏覽器會不會提交發送這些Cookie給服務器,和請求路徑有關係。
請求路徑和Cookie是緊密關聯的。
不同的請求路徑會發送提交不同的Cookie
假如獲取Cookie時的路徑是 :
    http://127.0.0.1:8080/PrjCookies/servlet/getCookie
將來發送Cookie的路徑包括如下路徑 :
    http://127.0.0.1:8080/PrjCookies/servlet/getCookie(相同路徑)
    http://127.0.0.1:8080/PrjCookies/servlet/xxxxx(同目錄)
    http://127.0.0.1:8080/PrjCookies/servlet/xxxxx/xxxx(子目錄)

默認情況下,沒有設置Cookie的有效時長,該Cookie被默認保存在瀏覽器的緩存當中,只要瀏覽器不關閉Cookie存在,
只要關閉瀏覽器Cookie消失,我們可以通過設置Cookie的有效時長,以保證Cookie保存在硬盤文件當中。但是這個有效時長
必須是>0的。換句話說,只要設置Cookie的有效時長大於0,則該Cookie會被保存在客戶端硬盤文件當中。有效時長過去之後,
則硬盤文件當中的Cookie失效。
cookie有效時長 = 0 直接被刪除
cookie有效時長 < 0 不會被存儲
cookie有效時長 > 0 存儲在硬盤文件當中 


url-pattern的編寫方式和路徑的總結:
1、路徑的編寫形式:
- <a href="/項目名/資源路徑"></a>
- <form action="/項目名/資源路徑"></form>
- 重定向:response.sendRedirect("/項目名/資源路徑");
- 轉發:request.getRequestDispatcher("/資源路徑").forward(request,response);
- 歡迎頁面
      <welcome-file-list>
          <welcome-file>資源路徑</welcome-file>
      </welcome-file-list>
- servlet路徑
      <servlet>
          <servlet-name>hello</servlet-name>
          <servlet-class>com.bjpowernode.javaweb.servlet.HelloServlet</servlet-class>
      </servlet>
      <servlet-mapping>
          <servlet-name>hello</servlet-name>
          <url-pattern>/資源路徑</url-pattern>
      </servlet-mapping>
- Cookie設置path
       cookie.setPath("/項目名/資源路徑");
- ServletContext
       ServletContext application = config.getServletContext();
       application.getRealPath("/WEB-INF/classes/db.properties");
       application.getRealPath("/資源路徑");
    
2、url-pattern的編寫方式
    精確匹配
        <url-pattern>/hello</url-pattern>
        <url-pattern>/system/hello</url-pattern>
    擴展匹配
        <url-pattern>/abc/*</url-pattern>
    後綴匹配
        <url-pattern>*.action</url-pattern>
        <url-pattern>*.do</url-pattern>
    全部匹配
        <url-pattern>/*</url-pattern>


javax.servlet.http.HttpSession接口方法
    -void setAttribute(String name, Object value)
    -Object getAttribute(String name)
    -void removeAttribute(String name)
    -void invalidate()   銷燬session

Cookie可以將會話狀態保存在客戶端,HttpSession可以將會話狀態保存在服務器端。
HttpSession對象是一個會話級別的對象,一次會話對應一個HttpSession對象。
在WEB容器中,WEB容器維護了大量的HttpSession對象,換句話說,在WEB容器中應該有一個“session列表”,
    - 打開瀏覽器,在瀏覽器上發送首次請求
    - 服務器會創建一個HttpSession對象,該對象代表一次會話
    - 同時生成HttpSession對象對應的Cookie對象,並且Cookie對象的name是JSESSIONID,Cookie的value是32位長度的字符串
    - 服務器將Cookie的value和HttpSession對象綁定到session列表中
    - 服務器將Cookie完整發送給瀏覽器客戶端
    - 瀏覽器客戶端將Cookie保存到緩存中
    - 只要瀏覽器不關閉,Cookie不會消失
    - 當再次發送請求的時候,會自動提交緩存當中的Cookie
    - 服務器接收到Cookie,驗證該Cookie的name確實是:JSESSIONID,然後獲取該Cookie的value
    - 通過Cookie的value去session列表中檢索對應的HttpSession對象。
和HttpSession對象關聯的這個Cookie的name是比較特殊的,在java中就叫做:jsessionid

- 瀏覽器禁用Cookie,則瀏覽器緩存中不再保存Cookie
- 導致在同一個會話中,無法獲取到對應的會話對象
- 禁用Cookie之後,每一次獲取的會話對象都是新的
瀏覽器禁用Cookie之後,若還想拿到對應的Session對象,必須使用URL重寫機制,怎麼重寫URL:
    http://localhost/prj-servlet-21/user/accessMySelfSession;jsessionid=D3E9985BC5FD4BD05018BF2966863E94
重寫URL會給編程帶來難度/複雜度,所以一般的web站點是不建議禁用Cookie的。建議瀏覽器開啓Cookie

- 瀏覽器關閉之後,服務器不會銷燬session對象
- 因爲B/S架構的系統基於HTTP協議,而HTTP協議是一種無連接/無狀態的協議
- 什麼是無連接/無狀態?
* 請求的瞬間瀏覽器和服務器之間的通道是打開的,請求響應結束之後,通道關閉
* 這樣做的目的是降低服務器的壓力。

session對象在什麼時候被銷燬?
- web系統中引入了session超時的概念。
- 當很長一段時間(這個時間可以配置)沒有用戶再訪問該session對象,此時session對象超時,web服務器自動回收session對象。
- 可配置:web.xml文件中,默認是30分鐘
    <session-config>
        <session-timeout>120</session-timeout>
    </session-config>
一般多數情況下,是這樣描述的:用戶打開瀏覽器,在瀏覽器上進行一些操作,然後將瀏覽器關閉,表示一次會話結束。
- 本質上的描述:從session對象的創建,到最終session對象超時之後銷燬,這個纔是真正意義的一次完整會話。

ServletContext、HttpSession、HttpServletRequest接口的對比:        
以上都是範圍對象:
ServletContext application; 是應用範圍
HttpSession session; 是會話範圍
HttpServletRequest request; 是請求範圍

三個範圍的排序:
application > session > request

application完成跨會話共享數據、
session完成跨請求共享數據,但是這些請求必須在同一個會話當中、
request完成跨Servlet共享數據,但是這些Servlet必須在同一個請求當中【轉發】

使用原則:有小到大嘗試,優先使用小範圍。
例如:登錄成功之後,已經登錄的狀態需要保存起來,可以將登錄成功的這個狀態保存到session對象中。
登錄成功狀態不能保存到request範圍中,因爲一次請求對應一個新的request對象。
登錄成功狀態也不能保存到application範圍中,因爲登錄成功狀態是屬於會話級別的,不能所有用戶共享。

 

---------------------------------------------------------------------------------------------------------------------------------------------

 

web.xml:
    web.xml文件在服務器啓動階段被解析,若web.xml文件編寫有錯誤,啓動Tomcat服務器的時候,當前webapp啓動失敗。
    修改web.xml文件並保存之後,Tomcat服務器會自動重新解析web.xml文件,這個時候,就相當於項目重新部署了。

    當前web站點沒有設置任何歡迎頁面的話,歡迎頁面是:index.html、index.htm、index.jsp,
    因爲在CATALINA_HOME/conf/web.xml文件中有全局配置,在當前webapp中配置的歡迎頁面屬於局部配置,局部優先(就近原則)
    注意:
        歡迎頁面可以設置多個,第一個優先級最高,以此類推
        歡迎頁面路徑問題:不需要以“/”開始,但是從WebRoot作爲起點
        歡迎頁面也可以是一個Servlet

web.xml文件中的標籤:
    #上下文參數,這些配置信息自動被封裝到ServletContext對象中
    <context-param>
        <param-name>xxx</param-name>
        <param-value>xxx</param-value>
    </context-param>
    <servlet>
        <servlet-name>xxx</servlet-name>
        <servlet-class>xxx.xxx.xxx.xxx</servlet-class>
        #該標籤表示在服務器啓動階段加載Servlet,完成實例化和初始化。數字越小,優先級越高
        <load-on-startup>0</load-on-startup>
        #初始化參數可以被自動封裝到ServletConfig對象中
        <init-param>
            <param-name>xxx</param-name>
            <param-value>xxx</param-value>
        </init-param>
    </servlet>
    <servlet-mapping>
        <servlet-name>xxx</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>
    <session-config>
        <session-timeout>120</session-timeout>
    </session-config>
    <welcome-file-list>
        <welcome-file>xxx.html</welcome-file>
        <welcome-file>xxx/xxx.html</welcome-file>
        <welcome-file>(url-pattern)</welcome-file>
    </welcome-file-list>

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章