資源描述:
《javaservlet工作原理問答-java開發(fā)java經(jīng)驗(yàn)技巧》由會(huì)員上傳分享,免費(fèi)在線閱讀,更多相關(guān)內(nèi)容在工程資料-天天文庫。
1、JavaServletI*作原理問答-編程開發(fā)技術(shù)JavaServlet工作原理問答木文由ImportNew?honoka翻譯自stackoverflowo歡迎加入翻譯小組。轉(zhuǎn)載請見文末耍求。導(dǎo)讀本文來自stackoverflow的問答,討論了JavaServlet的工作機(jī)制,如何進(jìn)行實(shí)例化、共享變量和多線程處理。問題:Servlet是如何工作的?Servlet如何實(shí)例化、共享變量、并進(jìn)行多線程處理?假設(shè)我有一個(gè)運(yùn)行了大量Servlet的web服務(wù)器。通過Servlet之間傳輸信息得到Servlet上下文,并設(shè)置session
2、變量?,F(xiàn)在,如果有兩名或更多使用者向這個(gè)服務(wù)發(fā)送請求,接下來session變量會(huì)發(fā)生什么變化?究竟是所有用戶都是用共同的變量?述是不同的用戶使用的變量都不一樣?如果是后者,服務(wù)器如何區(qū)分不同用戶?另一個(gè)相似的問題,如果有*n*名用戶訪問一個(gè)特定的Servlet,那么該Servlet是僅在第一個(gè)用戶首次訪問的吋候?qū)嵗?,還是分別為每個(gè)用戶實(shí)例化?回答(BalusC):ServletContext當(dāng)Servlet容器(比如ApacheTomcat)啟動(dòng)后,會(huì)部署和加載所有web應(yīng)用。當(dāng)web應(yīng)用被加載,Servlet容器會(huì)創(chuàng)建一次
3、ServletContext,然后將其保存在服務(wù)器的內(nèi)存中。web應(yīng)用的web.xml被解析,找到其中所有servlet、filter和Listener或@WebServlet>@WebFilter和@WebListener注解的內(nèi)容,創(chuàng)建一次并保存到服務(wù)器的內(nèi)存中。對于所有過濾器會(huì)立即調(diào)用initOo當(dāng)Servlet容器停止,將卸載所有web應(yīng)用,調(diào)用所有初始化的Servlet和過濾器的destroy()方法,最后回收ServletContext和所有Servlet>FiIter與Listener實(shí)例。當(dāng)問題中的Servle
4、t配置的load-on-startup或者QWebServlet(loadOnStartup)設(shè)置了一個(gè)大于0的值,則同樣會(huì)在啟動(dòng)的時(shí)候立即調(diào)用init()方法。"load-on-startup”中的值表示那些Servlet會(huì)以相同順序初始化。如果配置的值相同,會(huì)遵循web.xml中指定的順序或@WebServlet類加載的順序。另外,如果不設(shè)置“l(fā)oad-on-startup”值,init()方法只在第一次HTTP請求命中問題中的Servlet時(shí)才被調(diào)用。HttpServletRequest與HttpServletRespo
5、nseServlet容器附加在一個(gè)web服務(wù)上,這個(gè)web服務(wù)會(huì)在某個(gè)端口號(hào)上監(jiān)聽HTTP請求,在開發(fā)環(huán)境中這個(gè)端口通常為8080,生產(chǎn)環(huán)境中通常為80o當(dāng)客戶端(web瀏覽器)發(fā)送了一個(gè)HTTP請求,Servlet容器會(huì)創(chuàng)建新的HttpServletRequest和HttpServletResponse對象,傳遞給已創(chuàng)建好并J_L請求的URL匹配url-pattcrn的Filter和Servlet實(shí)例中的方法,所有工作都在同一個(gè)線程屮處理。request對象可以訪問所有該HTTP請求中的信息,例如requestheader和
6、requestbody。response對象為你提供需要的控制和發(fā)送HTTP響應(yīng)方法,例如設(shè)置header和body(通常會(huì)帶有JSP文件中的HTML內(nèi)容)。提交并完成HTTP響應(yīng)后,將回收request和response對象。HttpSession當(dāng)用戶笫一次訪問該web應(yīng)用時(shí),會(huì)通過request.getSession()笫一次獲得HttpSessiorio之后Servlet容器將會(huì)創(chuàng)建HttpSession,生成一個(gè)唯一的ID(可以通過session.getTd()獲?。┎?chǔ)存在服務(wù)器內(nèi)存中。然后Servlet容器在該次
7、IITTP響應(yīng)的Set-Cookie頭部設(shè)置一個(gè)Cookie,以JSESSIONID作為Cookie名字,那個(gè)唯一的sessionID作為Cookie的值。按照HTTPcookie規(guī)則(正常web瀏覽器和web服務(wù)端必須遵循的標(biāo)準(zhǔn)),當(dāng)cookie有效吋,要求客戶端(瀏覽器)在后續(xù)請求的Cookie頭屮返冋這個(gè)cookie。使用瀏覽器內(nèi)置的HTTP流量監(jiān)控器,你可以查看它們(在Chrome、Fircfox23+、IE9+中按F12,然后杳看Net/Network標(biāo)簽)。Servlet容器將會(huì)確定每個(gè)進(jìn)入的HTTP請求的Cook
8、ie頭屮是否存在名為JSESSIONID的cookie,然后用它的值(sessionID)從服務(wù)端內(nèi)存中找到關(guān)聯(lián)的HttpSession。你可以在web.xml中設(shè)置session-timeout,默認(rèn)值為30分鐘。超時(shí)到達(dá)Z前HttpSession會(huì)一宜存活。所以當(dāng)客戶端不