1 Servlet3.0新特性概述
使用要求:MyEclipse10.0或以上版本,發布到Tomcat7.0或以上版本,創建JavaEE6.0應用!
Servlete3.0的主要新特性如下三部分:
使用@WebServlet、@WebFilter、@WebListener三個注解來替代web.xml文件中的Servlet、Filter、Listener的配置;
Servlet異步處理:當Servlet處理比較費時的問題時,這會讓客戶感覺到很卡(原來(Servlete2.5),在服務器沒有結束響應之前,瀏覽器是看不到響應內容的,只有響應結束時,瀏覽器才能顯示結果!)。當使用異常處理時可以把已經處理好的內容先一步響應給客戶端瀏覽器,然后使用另一個線程來完成費時的操作,也就是把內容一部分一部分的顯示出來;
上傳組件:不用再使用commons-fileupload等第三方的上傳組件,使用Servlet3.0的上傳組件會更方便。
2 @WebServlet、@WebFilter、@WebListener(使用前提:刪除web.xml文件,好處:配置信息少,缺點:不方便修改)
@WebServlet( urlPatterns="/AServlet", initParams={ //初始化參數@WebInitParam(name="p1", value="v1"),@WebInitParam(name="p2", value="v2")},//標記容器是否在啟動的時候就加載這個servlet(實例化并調用其init()方法),值代表優先級,正數的值越小,優先級越高,啟動時就越先加載loadOnStartup=1 ) public class AServlet extends HttpServlet {public void doGet(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {resp.getWriter().print("hello servlet3.0!!");} }
@WebFilter(urlPatterns="/*") public class AFilter implements Filter {@Overridepublic void doFilter(ServletRequest request, ServletResponse repsonse,FilterChain chain) throws IOException, ServletException {System.out.println("過濾器。。。。。。。。。。。。");chain.doFilter(request, repsonse);}@Overridepublic void destroy() {}@Overridepublic void init(FilterConfig arg0) throws ServletException {} }
@WebListener public class AListener implements ServletContextListener {@Overridepublic void contextDestroyed(ServletContextEvent arg0) {System.out.println("死掉了");}@Overridepublic void contextInitialized(ServletContextEvent arg0) {System.out.println("出生了");} }
3 Servlet異步處理
Servlet異步處理就是讓Servlet在處理費時的請求時不要阻塞,而是一部分一部分的顯示。也就是說,在使用Servlet異步處理之后,頁面可以一部分一部分的顯示數據,而不是一直卡,等到請求響應結束后一起顯示。
在使用異步處理之前,一定要在@WebServlet注解中給出asyncSupported=true,不然默認Servlet是不支持異步處理的。如果存在過濾器,也要設置@WebFilter的asyncSupportedt=true。注意,響應類型必須是text/html,所以要設置:response.setContentType(“text/html;charset=utf-8”);
使用異步處理大致可以分為兩步:Servlet正常響應數據,Servlet異常響應數據。
在Servlet正常響應數據時,沒什么可說的,可通知response.getWriter().print()來向客戶端輸出,但輸出后要使用response.getWriter().flush()刷新,不然數據只是在緩沖區中,不能向客戶端發送數據的。
異步響應數據需要使用request.startAsync()方法獲取AsyncContext對象。然后調用AsyncContext對象的start()方法啟動異步響應,start()方法需要一個Runnable類型的參數。在Runnable的run()方法中給出異步響應的代碼。注意在異步處理線程中使用response做響應后,要使用response.getWriter().flush()來刷新流,不然數據是不能響應到客戶端瀏覽器的。
@WebServlet(urlPatterns="/AServlet", asyncSupported=true) public class AServlet extends HttpServlet {public void doGet(final HttpServletRequest req, final HttpServletResponse resp)throws ServletException, IOException {resp.setContentType("text/html;charset=utf-8");//兼容IE!如果輸出不足512B,IE沒有異步效果!for(int i = 0; i <= 512; i++) {resp.getWriter().print("a");}resp.getWriter().flush();//得到異步上下文對象final AsyncContext ac = req.startAsync(req, resp);/*** 設置超時時間為10秒,Tomcat需要知道異步響應是否結束,如果響應不結束,雖然客戶端瀏覽器會看到響應的數據,但是鼠標上只是有個圈圈的不行的轉啊轉的,表示還沒有結束響應。Tomcat會等待到超時為止,這個超時的時間可以通過AsyncContext類的getTimeout()方法獲取,Tomcat默認為20000毫秒。當然也可以通過此方法方法設置*/ac.setTimeout(1000*10);//給上下文對象一個Runnable對象,讓它執行這個任務ac.start(new Runnable() {public void run() {println("現在馬上開始<br/>", resp);sleep(2000);for(char c = 'A'; c <= 'Z'; c++) {println(c+"", resp);sleep(250);}ac.complete();// 通知Tomcat我們已經執行結束了! }});}public void println(String text, HttpServletResponse resp) {try {resp.getWriter().print(text);resp.getWriter().flush();} catch (IOException e) {}}public void sleep(long ms) {try {Thread.sleep(ms);} catch (InterruptedException e) {}} }
4 文件上傳
Servlet3.0提供了文件上傳的處理方案。只需要在Servlet上添加@MultipartConfig注解即可。
當然也可以為@MultipartConfig注解指定屬性值,它有四個屬性:
int filesizeThreshold:指定緩存的大小,當超出這個大小后,文件會保存到磁盤上;
String location:指定臨時文件的目錄;
long maxFilesize:指定上傳單個文件的大小限制,如果上傳的誰的超出了這個大小,那么就會拋出異常;
long maxRequestSize:指定整個表單的大小限制。
當在Servlet上使用了@MultipartConfig注解后,那么就可以使用request.getPart(“fieldName”)來獲取<input:file>的內容,其中Part表示一個文件表單項。
<form action="<c:url value='/AServlet'/>" method="post" enctype="multipart/form-data">用戶名:<input type="text" name="username"/><br/>簡 歷:<input type="file" name="resume"/><br/><input type="submit" value="注冊"/> </form>
@WebServlet(urlPatterns="/AServlet") @MultipartConfig(maxFileSize=1024*1024) public class AServlet extends HttpServlet {@Overridepublic void doPost(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {req.setCharacterEncoding("UTF-8");//getParameter()方法可以使用了!!!String username = req.getParameter("username");//可以使用了!!!//獲取文件表單字段,對應的Part對象Part part = req.getPart("resume");//從Part中獲取需要的數據System.out.println(part.getContentType());//獲取上傳文件的MIME類型System.out.println(part.getSize());// 獲取上傳文件的字節數System.out.println(part.getName());// 獲取文件字段名稱System.out.println(part.getHeader("Content-Disposition"));// 獲取頭,這個頭中包含了上傳文件的名稱part.write("C:/xxx.jpg");// 保存上傳文件// 截取上傳文件名稱String filename = part.getHeader("Content-Disposition");int start = filename.lastIndexOf("filename=\"") + 10;int end = filename.length() - 1;filename = filename.substring(start, end);System.out.println(filename);} }