Servlet-jsp從入門(mén)到精通(一)

web技術(shù)的發(fā)展

  1. 早期的web應(yīng)用主要是靜態(tài)頁(yè)面的瀏覽,這些靜態(tài)頁(yè)面使用HTML語(yǔ)言編寫(xiě),放在服務(wù)器上,用戶使用瀏覽器通過(guò)HTTP協(xié)議請(qǐng)求服務(wù)器上的web頁(yè)面,服務(wù)器上的web服務(wù)器軟件接受到用戶發(fā)送的請(qǐng)求后,讀取請(qǐng)求URI所標(biāo)識(shí)的資源,加上消息包頭發(fā)送給客戶端的瀏覽器,瀏覽器解析響應(yīng)中的HTML數(shù)據(jù),向用戶呈現(xiàn)多姿多彩的HTML頁(yè)面。

  2. 但是隨著網(wǎng)絡(luò)的發(fā)展,很多線下業(yè)務(wù)開(kāi)始向網(wǎng)上發(fā)展,基于Internet的web應(yīng)用也變得越來(lái)越復(fù)雜用戶所訪問(wèn)的資源已不僅僅局限于服務(wù)器硬盤(pán)上存放的靜態(tài)網(wǎng)頁(yè),更多的應(yīng)用需要根據(jù)用戶的請(qǐng)求動(dòng)態(tài)生成網(wǎng)頁(yè)信息,復(fù)雜的還需要從數(shù)據(jù)庫(kù)中提取信息,經(jīng)過(guò)一定的運(yùn)算,生成一個(gè)頁(yè)面返回給客戶如何才能實(shí)現(xiàn)?

  3. 利用已經(jīng)實(shí)現(xiàn)HTTP協(xié)議的服務(wù)器端軟件,這些軟件預(yù)先給我們留出了擴(kuò)展的接口,我們只需要按照一定的規(guī)則取提供相應(yīng)的擴(kuò)展功能,當(dāng)這類web服務(wù)器接受到客戶端請(qǐng)求后,判斷請(qǐng)求是否是訪問(wèn)我們提供的擴(kuò)展功能,如果是,將請(qǐng)求交由我們編寫(xiě)的程序去處理,處理完成后,程序?qū)⑻幚斫Y(jié)果交回web服務(wù)器軟件,web服務(wù)器軟件拿到結(jié)果后,再將結(jié)果作為相應(yīng)信息返回給客戶端。

  4. 早起使用的web服務(wù)器擴(kuò)展機(jī)制是CGI,它允許用戶調(diào)用web服務(wù)器上的CGI程序,CGI全稱 CommonGateway Interface 公共網(wǎng)關(guān)接口,大多數(shù)的CGI程序使用Perl來(lái)編寫(xiě),也有通過(guò)C,Python或PHP編寫(xiě),用戶通過(guò)單擊某個(gè)連接或者直接在瀏覽器的地址欄輸入U(xiǎn)RL來(lái)訪問(wèn)CGI程序,web服務(wù)器接受到請(qǐng)求后,發(fā)現(xiàn)這個(gè)請(qǐng)求是給CGI程序的,于是就啟動(dòng)并運(yùn)行這個(gè)CGI程序,對(duì)用于請(qǐng)求進(jìn)行處理。CGI程序解析請(qǐng)求中的CGI數(shù)據(jù),處理數(shù)據(jù),并且產(chǎn)生一個(gè)響應(yīng),這個(gè)響應(yīng)被返回給web服務(wù)器,web服務(wù)器包裝這個(gè)響應(yīng),以HTTP響應(yīng)的形式發(fā)送給Web瀏覽器。但是CGI編寫(xiě)困難,對(duì)用戶請(qǐng)求的響應(yīng)時(shí)間較長(zhǎng)以進(jìn)程方式運(yùn)行導(dǎo)致性能受限制。

  5. 1997年,SUN公司推出了Servlet技術(shù),作為java陣營(yíng)的CGI解決方案,作為對(duì)微軟ASP(1996年推出)的推出,SUN公司于1998年推出了JSP技術(shù),允許在HTML頁(yè)面中嵌入java腳本代碼,從而實(shí)現(xiàn)動(dòng)態(tài)網(wǎng)頁(yè)的功能。此外,PHP(1994年發(fā)明)技術(shù)也是類似于APS,JSP服務(wù)器端頁(yè)面編寫(xiě)技術(shù)

    • Servlet
      java Servlet(java服務(wù)器小程序)是一個(gè)基于java技術(shù)的web組件,運(yùn)行在服務(wù)器端,由Servlet容器所管理,用于生成動(dòng)態(tài)的內(nèi)容,Servlet是平臺(tái)獨(dú)立的java類,編寫(xiě)一個(gè)Servlet實(shí)際上就是按照Servlet規(guī)范編寫(xiě)一個(gè)Java類,Servlet被編譯為平臺(tái)獨(dú)立的字節(jié)碼,可以被動(dòng)態(tài)地加載到支持java技術(shù)的web服務(wù)器中運(yùn)行。

      Servlet容器

      Servlet容器也叫Servlet引擎,是Web服務(wù)器或者應(yīng)用服務(wù)器的一部分,用戶在發(fā)送請(qǐng)求和響應(yīng)之上提供網(wǎng)絡(luò)服務(wù),解碼基于MIME的請(qǐng)求,格式化基于MIME的請(qǐng)求,Servlet不能獨(dú)立運(yùn)行,必須被部署到Servlet容器中,由容器實(shí)例化和調(diào)用Servlet的方法,Servlet容器在Servlet的生命周期內(nèi)包含和管理Servlet

    • 對(duì)比CGI

      1. Servlet是單實(shí)例多線程的運(yùn)行方式,每個(gè)請(qǐng)求在一個(gè)獨(dú)立的線程中運(yùn)行,提供服務(wù)的Servlet實(shí)例只有一個(gè)
      2. Servlet 具有可升級(jí)性,能響應(yīng)更多的請(qǐng)求,因?yàn)閟ervlet容器使用一個(gè)線程而不是操作系統(tǒng)進(jìn)程,線程占用的資源要小
        3.Servlet使用標(biāo)準(zhǔn)的API,被更多的web服務(wù)器所支持。
        4.Servlet使用java語(yǔ)言編寫(xiě),擁有更多的java程序語(yǔ)言的優(yōu)點(diǎn)
        5.Servlet可以訪問(wèn)java平臺(tái)豐富的類庫(kù),使得各種應(yīng)用的開(kāi)發(fā)更為容易
        6.Servlet容器給Servlet提供額外的功能。
    • Tomcat
      Tomcat是一個(gè)免費(fèi)的開(kāi)源代碼的Servlet容器,是Apache軟件基金會(huì)的一個(gè)頂級(jí)項(xiàng)目,由Apache,SUN和其他一些公司及個(gè)人共同開(kāi)發(fā)而成,由于SUN的參與與支持,最新的Servlet和JSP規(guī)范總是能在Tomcat中得到體現(xiàn)。Tomcat支持Servlet2.5

    • Tomcat的安裝

    • 安裝jdk,并且配置環(huán)境變量 path,CLASSPATH,JAVA_HOME

    • 解壓tomcat即可

    • Tomcat的目錄結(jié)構(gòu)

    • bin 存放啟動(dòng)和關(guān)閉Tomcat的腳本文件

    • conf 存放Tomcat服務(wù)器的各種配置文件,server.xml web.xml等

    • lib 存放Tomcat服務(wù)器和所有web應(yīng)用程序需要訪問(wèn)的JAR文件

    • logs 存放Tomcat的日志文件

    • temp 存放Tomcat運(yùn)行時(shí)產(chǎn)生的臨時(shí)文件

    • webapps 當(dāng)發(fā)布web應(yīng)用程序時(shí),通常把Web應(yīng)用程序的目錄及文件放到這個(gè)目錄下

    • work Tomcat將JSP生成的Servlet源文件和字節(jié)碼文件存放到這個(gè)目錄下

Servlet詳解

Servlet API

Servlet接口
  1. init(ServletConfig config)
    在Servlet實(shí)例化之后,Servlet容器會(huì)調(diào)用init()方法,來(lái)初始化該對(duì)象,主要是為了讓servlet對(duì)象在處理客戶請(qǐng)求前完成一些初始化工作。例如建立數(shù)據(jù)庫(kù)的連接,獲取配置信息等。對(duì)于每個(gè)Servlet實(shí)例,init()方法只能被調(diào)用一次。Servlet容器通過(guò)config參數(shù)向Servlet傳遞配置信息。可以通過(guò)config獲取web應(yīng)用程序的初始化參數(shù),還可以獲取ServletContext對(duì)象

  2. service(ServletRequest req,ServletResponse res)
    容器調(diào)用service()方法處理客戶端的請(qǐng)求,在調(diào)用service()方法被容器調(diào)用之前,必須確保Init()方法正確完成,容器會(huì)構(gòu)造一個(gè)ServletRequest對(duì)象和ServletResponse對(duì)象作為參數(shù)傳遞給service()方法。

  3. destroy();
    當(dāng)容器檢測(cè)到一個(gè)Servlet對(duì)象應(yīng)該從服務(wù)中被移除的時(shí)候,容器會(huì)調(diào)用該對(duì)象的destory方法,以便讓Servlet對(duì)象可以釋放它所使用的資源,保存數(shù)據(jù)到數(shù)據(jù)庫(kù)中。

  4. ServletConfig getServletConfig()
    返回容器調(diào)用init()方法時(shí)傳遞給Servlet對(duì)象的ServletConfig對(duì)象

  5. String getServletInfo()
    返回一個(gè)String類型的字符串,包含了關(guān)于Servlet的信息,例如版權(quán),作者等。

ServletRequest

ServletRequest 對(duì)象,用來(lái)封裝請(qǐng)求數(shù)據(jù)
  1. Object getAttribute(String name)
    返回以name為名字的屬性的值,如果不存在,返回null
  2. Enumeration getAttributeNames();
    返回請(qǐng)求中所有可用的屬性的名字。返回一個(gè)枚舉集合
  3. void removeAttribute(String name);
    移除請(qǐng)求中名字為name的屬性
  4. void setAttribute(String key,Object val);
    在請(qǐng)求中保存一個(gè)鍵值對(duì)。
  5. getCharacterEncoding()
    返回請(qǐng)求正文使用的字符編碼的名字
  6. int getContentLength()
    以字節(jié)為單位,返回請(qǐng)求正文的長(zhǎng)度。
  7. String getContentType()
    返回正文的MIME類型
  8. ServletInputStream getInputStream()
  9. BufferedReader getReader()
  10. String getLocalAddr()
    返回接收到請(qǐng)求的網(wǎng)絡(luò)接口的IP地址。
  11. String getRemoteAddr()
    返回發(fā)送請(qǐng)求的客戶端或最后一個(gè)代理服務(wù)器的IP地址
  12. String getRemoteHost()
    返回發(fā)送請(qǐng)求的客戶端或者最后一個(gè)代理服務(wù)器的完整限定名
  13. String getLocalName()
    返回接收到請(qǐng)求的IP接口的主機(jī)名
  14. int getLocalPort()
    返回接收到請(qǐng)求的網(wǎng)絡(luò)接口的IP端口號(hào)
  15. int getRemotePort()
    返回發(fā)送請(qǐng)求的客戶端或最后一個(gè)代理服務(wù)器的IP源端口。
  16. String getParameter(String name)
    返回請(qǐng)求中name參數(shù)的值,如果name參數(shù)有多個(gè)值,該方法返回值列表中的第一個(gè)值。如果請(qǐng)求中沒(méi)有找到該參數(shù),返回null
  17. Enumeration getParameterNames()
    返回請(qǐng)求中包含的所有的參數(shù)的名字。
  18. String[] getParameterValues(String name);
    返回請(qǐng)求中name參數(shù)所有的值
  19. String getProtocal()
    返回請(qǐng)求使用的協(xié)議的名字和版本 例如: HTTP/1.1
  20. RequestDispatcher getRequestDispatcher(String path)
    返回RequestDispather對(duì)象,作為path所定位的資源的封裝。
  21. String getServerName()
    返回請(qǐng)求發(fā)送到服務(wù)器的主機(jī)名
  22. int getServerPort()
    返回請(qǐng)求發(fā)送到服務(wù)器的端口號(hào)
  23. setCharacterEncoding(String env)
    覆蓋在請(qǐng)求正文中所使用的字符編碼的名字。
ServletResponse對(duì)象,用來(lái)封裝響應(yīng)數(shù)據(jù)
  1. flushBuffer() 強(qiáng)制把任何在緩存中的內(nèi)容發(fā)送到客戶端
  2. int getBufferSize() 返回實(shí)際用于響應(yīng)的緩存的大小,如果沒(méi)有使用緩存,這個(gè)方法返回0
  3. String getCharacterEncoding()
    返回響應(yīng)中發(fā)送的正文所使用的字符編碼(MIME字符集)
  4. String getContentType()
    返回響應(yīng)中發(fā)送的正文所使用的MIME類型
  5. ServletOutputStream getOutputStream()
  6. PrintWriter getWriter()
  7. boolean isCommitted() 返回一個(gè)布爾值,指示是否已經(jīng)提交了響應(yīng)。
  8. void reset() 清除在緩存中的任何數(shù)據(jù),包括狀態(tài)代碼和消息報(bào)頭。
  9. void resetBuffer() 清除在緩存中的響應(yīng)內(nèi)容,保留狀態(tài)代碼和消息包頭。
  10. void setBufferSize(int size)
    設(shè)置響應(yīng)正文的緩存大小。
  11. void setCharacterEncoding(String charset)
    設(shè)置發(fā)送到客戶端的響應(yīng)的字符編碼
  12. void setContentLength(int len)
    設(shè)置內(nèi)容正文的長(zhǎng)度
  13. void setContentType(String type)
    設(shè)置要發(fā)送到客戶端的響應(yīng)的內(nèi)容類型。例如:"text/html;charset=UTF-8"
ServletConfig
  1. Servlet容器使用ServletConfig對(duì)象在Servlet初始化期間向它傳遞配置信息,一個(gè)ServletConfig對(duì)象。

  2. String getInitParameter(String name);
    返回名字為name的初始化參數(shù)的值,初始化參數(shù)在web.xml配置文件中進(jìn)行配置。

  3. Enumeration getInitParameterNames()
    返回Servlet所有初始化參數(shù)的名字的枚舉集合。

  4. ServletContext getServletContext()
    返回Servlet上下文對(duì)象的引用。

  5. String getServletName()
    返回Servlet實(shí)例的名字,這個(gè)名字是web應(yīng)用程序的部署描述符中指定。

  6. 編寫(xiě)一個(gè)Servlet實(shí)際上就是編寫(xiě)一個(gè)實(shí)現(xiàn)了javax.servlet.Servlet接口的類。

GenericServlet
  1. 如果要編寫(xiě)一個(gè)通用的Servlet,只需要從GenericServlet繼承,并且實(shí)現(xiàn)抽象方法service();

      String getInitParameter(String name)
      Enumeration getInitParameterNames();
      ServletContext getServletContext()
      init(ServletConfig config)
    
HttpServlet
  1. 在絕大多數(shù)的網(wǎng)絡(luò)應(yīng)用中,都是客戶端通過(guò)HTTP協(xié)議去訪問(wèn)服務(wù)器端的資源我們編寫(xiě)的Servlet也主要是應(yīng)用于HTTP協(xié)議的請(qǐng)求和響應(yīng),為了快速開(kāi)發(fā)應(yīng)用于HTTP協(xié)議的Servlet類,sun公司在javax.servlet.http包中給我們提供了一個(gè)抽象類HttpServlet,它繼承自GenericServlet類,用于創(chuàng)建適合WEB站點(diǎn)的HTTP Servlet

     public void service(ServletRequest req,ServletResponse res);
     protected void service(HttpServletRequest req,HttpServletResponse resp)
       針對(duì)HTTP1.1定義的7種請(qǐng)求方法GET,POST,HEAD,PUT,DELETE,TRACE,OPTION,
     HttpServlet提供了7個(gè)處理方法
       doGet(HttpServletRequest req,HttpServletResponse resp)
       doPost(HttpServletRequest req,HttpServletResponse resp)
       ......
    
  2. 當(dāng)容器接受到一個(gè)針對(duì)HttpServlet對(duì)象的請(qǐng)求時(shí),調(diào)用該對(duì)象中的方法順序如下:

    1. 調(diào)用公共的service()方法
    2. 在公共的service()方法中,首先將參數(shù)類型轉(zhuǎn)換為HttpServletRequest和HttpServletResponse,然后調(diào)用保護(hù)的service()方法,將轉(zhuǎn)換后的對(duì)象作為參數(shù)傳遞進(jìn)去
    3. 在保護(hù)的service方法中,首先調(diào)用HttpServletRequest對(duì)象的getMethod方法,獲取HTTP請(qǐng)求方法的名稱,然后根據(jù)請(qǐng)求方法的類型,調(diào)用相應(yīng)的doXxx()方法
HttpServletRequest

繼承自javax.servlet.servletRequest,在該接口中新增的方法如下:

  • String getContextPath()
    返回請(qǐng)求URI中表示請(qǐng)求上下文的部分,上下文路徑是請(qǐng)求URI的開(kāi)始部分
  • Cookie[] getCookies()
    返回客戶端在此次請(qǐng)求中發(fā)送的所有的Cookie對(duì)象
  • String getHeader(String name)
    返回名字為name的請(qǐng)求報(bào)頭的值
  • Enumeration getHeaderNames()
    返回此次請(qǐng)求中包含的所有的報(bào)頭名字的枚舉集合
  • Enumeration getHeaders(String name)
    返回名字為name的請(qǐng)求報(bào)頭的所有值的枚舉集合
  • String getMethod()
    返回此次請(qǐng)求所使用的HTTP方法的名字
  • String getServletPath()
    返回請(qǐng)求URI中調(diào)用Servlet的部分
  • HttpSession getSession()
    返回和此次請(qǐng)求相關(guān)聯(lián)的Session
  • HttpSession getSession(boolean create)
    返回此次請(qǐng)求相關(guān)聯(lián)的Session,如果沒(méi)有給客戶端分配Session,并且create參數(shù)為true,則創(chuàng)建一個(gè)新的Session,如果為false,此次請(qǐng)求沒(méi)有一個(gè)有效的HttpSession,返回null
HttpServletResponse

該接口繼承ServletResponse,新增的方法入下

  • addCookie(Cookie cookie)
  • addHeader(String name,String value);
  • boolean containsHeader(String name)
  • encodeRedirectURL(String url)
  • 使用SessionID 對(duì)于重定向的url編碼,以便用于sendRedirect()方法中
  • encodeURL(String url) 使用SessionID 指定的url編碼
  • sendRedirect(String location) 發(fā)送一個(gè)臨時(shí)的重定向響應(yīng)到客戶端,讓客戶端訪問(wèn)新的url

Servlet生命周期

Servlet運(yùn)行在Servlet容器中,其聲明周期由容器來(lái)管理,其聲明周期通過(guò)javax.servlet.Servlet接口中的init(),service(),destory()方法表示Servlet的生命周期包含了4個(gè)階段

  1. 加載和實(shí)例化
    Servlet容器負(fù)責(zé)加載和實(shí)例化Servlet,當(dāng)Servlet容器啟動(dòng)時(shí),或者是在容器檢測(cè)到這個(gè)Servlet來(lái)響應(yīng)第一個(gè)請(qǐng)求時(shí),創(chuàng)建Servlet實(shí)例。
  2. 初始化
    在Servlet實(shí)例化之后,容器將調(diào)用Servlet的init()方法初始化這個(gè)對(duì)象。對(duì)于每個(gè)Servlet實(shí)例,init()方法只被調(diào)用一次,
  3. 請(qǐng)求處理
    Servlet容器調(diào)用Servlet的service()方法對(duì)請(qǐng)求進(jìn)行處理。service執(zhí) 行之前init()方法必須成功執(zhí)行。
  4. 服務(wù)終止
    當(dāng)容器檢測(cè)到一個(gè)Servlet實(shí)例應(yīng)該從服務(wù)中被移除的時(shí)候,容器就會(huì)調(diào)用實(shí)例的destory()方法。釋放資源。
跳轉(zhuǎn)
RequestDispatcher接口
  1. 該對(duì)象由Servlet容器創(chuàng)建,用于封裝一個(gè)由路徑標(biāo)識(shí)的服務(wù)器資源。利用該對(duì)象可以將請(qǐng)求轉(zhuǎn)發(fā)給其他的Servlet或jsp頁(yè)面。

  2. forword(ServletRequest req,ServletResponse resp)
    該方法用于將請(qǐng)求從一個(gè)Servlet傳遞給服務(wù)器上的另外的Servlet,jsp或者h(yuǎn)tml文件,在forword方法調(diào)用之后,之前在響應(yīng)緩存中沒(méi)有提交的內(nèi)容將會(huì)被自動(dòng)清除。該方法將請(qǐng)求轉(zhuǎn)發(fā)給其他Servlet,將又被調(diào)用的Servlet負(fù)責(zé)對(duì)請(qǐng)求做出響應(yīng),原先Servlet執(zhí)行終止。

  3. include(ServletRequest req,ServletResponse resp)
    該方法用于將請(qǐng)求轉(zhuǎn)發(fā)給其他Servlet,被調(diào)用的Servlet對(duì)該請(qǐng)求做出的響應(yīng)將并入原來(lái)的響應(yīng)對(duì)象中,原先的Servlet還可以繼續(xù)輸出響應(yīng)信息。

  4. forword(),include()屬于內(nèi)部請(qǐng)求,瀏覽器地址不發(fā)生改變,客戶端僅向服務(wù)器端發(fā)送一次請(qǐng)求

sendRedirect()

該方法由HttpServletResponse對(duì)象提供,
表示重定向到另外一個(gè)請(qǐng)求中。屬于外部請(qǐng)求。重定向相當(dāng)于重新向服務(wù)器發(fā)送請(qǐng)求,瀏覽器地址發(fā)送改變

serlvet-jsp從入門(mén)到精通(二)

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

推薦閱讀更多精彩內(nèi)容

  • Spring Cloud為開(kāi)發(fā)人員提供了快速構(gòu)建分布式系統(tǒng)中一些常見(jiàn)模式的工具(例如配置管理,服務(wù)發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 134,837評(píng)論 18 139
  • 從三月份找實(shí)習(xí)到現(xiàn)在,面了一些公司,掛了不少,但最終還是拿到小米、百度、阿里、京東、新浪、CVTE、樂(lè)視家的研發(fā)崗...
    時(shí)芥藍(lán)閱讀 42,340評(píng)論 11 349
  • 0 系列目錄# WEB請(qǐng)求處理 WEB請(qǐng)求處理一:瀏覽器請(qǐng)求發(fā)起處理 WEB請(qǐng)求處理二:Nginx請(qǐng)求反向代理 本...
    七寸知架構(gòu)閱讀 14,024評(píng)論 22 190
  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語(yǔ)法,類相關(guān)的語(yǔ)法,內(nèi)部類的語(yǔ)法,繼承相關(guān)的語(yǔ)法,異常的語(yǔ)法,線程的語(yǔ)...
    子非魚(yú)_t_閱讀 31,739評(píng)論 18 399
  • 簡(jiǎn)用論道線下互聯(lián)網(wǎng)▏作者:劉益群 “真是沒(méi)生意,現(xiàn)在進(jìn)店的客人比以前少多了……” “剛開(kāi)業(yè)的那段時(shí)間客人還蠻多的,...
    簡(jiǎn)用云閱讀 468評(píng)論 0 0