国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 學院 > 開發設計 > 正文

如何設計用JSF和MyFaces上傳文件(圖)

2019-11-18 12:26:27
字體:
來源:轉載
供稿:網友

  用戶可以很方便使用瀏覽器上傳文件,但是當前的java Web標準(如servlets, jsp, and JSF)并沒有提供任何上傳的功能。幸好第三方框架,比如 Apache Commons File Upload, Apache MyFaces, and Oracle ADF Faces,提供了簡單的API和客戶標簽,實現了這個功能。文章的前半部分將介紹上傳組件是如何工作的,你將看到MyFaces and Commons File Upload 的部分源碼(實際上,前者采用的是后者的代碼)。了解這些源碼的內在機制將使我們更有效的使用這些框架,并且可以根據需要修改他們!在文章的后半部分,介紹了一個讓用戶通過瀏覽器上傳文件的例子。
  
  基于WEB的文件上傳
  
  “上傳”這個詞的使用比較廣泛。一個web治理員在他的主頁發布了一個文件,他可以說他上傳了一個文件;當一個網絡工程師創建了一個Html form和一些腳本使普通用戶可以通過瀏覽器上傳文件,他說他實現了上傳的功能。
  
  這兩種方式之中有些共同的地方,因為一個web治理員可以通過一個基于web的接口來發布文件(頁面,圖像,腳本等等)。那些免費提供個人主頁的公司,比如yahoo,實現了基于web的文件上傳功能,因為客戶需要上傳頁面。這樣任何人只要接入網絡,就可以通過瀏覽器發布他的個人站點。但是,還有許多更好的方式讓你發布你的網頁內容,比如FTP或secure FTP。在這種情況下,你就需要一個對應的應用程序,比如FTP客戶端,而不是瀏覽器來發布你的網站。
  
  這篇文章將從網絡開發者的角度來討論文件上傳。一個基于web的mail應用程序,比如yahoo mail,實現了上傳功能,這樣用戶才能發送信息和附件。另一個好的例子是一個job網站必須讓你能夠發送簡歷給招聘人員。在你的應用程序中,你可以對上傳的文件作任何你想做的事情,比如把這些文件的內容儲存到數據庫中或者把他們當作附件發送出去。這篇文章的例子計算了上傳文件的hash值?,F在,讓我們看看如何在一個web應用程序中實現上傳功能。
  
  一個html表單包含一個或多個<input type="file"> 元素,這個元素將在頁面上生成文件輸入框,用戶可以在這里填寫文件路徑。用戶點擊輸入字段后面的瀏覽(browse)按鈕后,會彈出一個對話框讓用戶選擇路徑:
  
 如何設計用JSF和MyFaces上傳文件(圖)(圖一)

  當用戶點擊表單的Sumbit按鈕,瀏覽器對表單數據進行編碼,其中包括文件的內容,名字,路徑以及其他的表單參數。然后,瀏覽器把編碼過的數據傳遞給web服務器,服務器再把這些數據傳遞給相應的頁面,比如<form>標簽里的action屬性值。假如是java網絡應用程序,action屬性值可能是個servlet或者是個jsp頁面。
  
  因為默認的表單編碼和get方法不適合上傳文件,所以一個包含文件輸入框的表單必須定義編碼為multipart/form-data ,并且在<form>標簽里使用POST方法:
  <form enctype="multipart/form-data" method="POST" action="...">
  ...
  <input type="file" name="...">
  ...
  </form>
  
  但是,事情并不象看起來那么簡單,實現了servlet and JSP 標準的應用服務器并沒有被要求處理 multipart/form-data編碼。所以你需要一個解析器來處理請求的輸入流,比如Apache Commons File Upload組件,它是個java包,能從已編碼的數據中讀取出上傳文件的內容。這個包的API很靈活,答應你把小文件存在內存里而大文件儲存在磁盤上一個臨時文件夾里。你不但可以定義大文件和小文件的界限,還可以定義上傳文件所占空間的最大值。
  
  org.apache.commons.fileupload里有個DiskFileUpload類,它的parseRequest()函數獲得一個HttpServletRequest,返回一個List,其中包含了org.apache.commons.fileupload.FileItem的實例。servlet請求的getInputStream()函數返回一個數據流,已編譯的表單數據就是從這里讀取出來的。FileItem很輕易讓人誤解,因為這個接口的實例不僅包括上傳文件,還有其他的請求參數。
  
  Commons File Upload 包提供的API可以解析數據,但是servlet請求的getParameter()函數和getParameterValues()函數卻不能工作。因為這兩個函數被運行在常用的輸入框, 復選框, 單選按鈕, 和下拉列表后面的標準JSF組件調用,所以這個問題需要解決。Servlets API提供的兩個功能(filters和request wrappers) 可以解決這個問題。下面的章節描述了在沒有破壞原有JSF結構的情況下,Apache MyFaces 如何實現了一個filter功能,從而添加了更多需要的支持。另外,MyFaces提供的API可以創建javaBean,和生成<input type="file">元素的JSF組件相對應。
  
  配置 JSF 和MyFaces Extensions
  
  目前最主要的實現JSF規范的框架有JSF Reference Implementation (RI)以及Apache提供的MyFaces。雖然還有別的,但這兩個是最流行的。很多開發者更傾向于JSF RI,因為這是來自于sun的官方產品。但MyFaces有一些有趣的擴展的功能,比如上傳文件。假如你喜歡,你可以同時使用MyFaces的擴展功能和JSF RI。你只需要把myfaces-extensions.jar和JSF RI的jar文件以及 commons-fileupload-1.0.jar 放在web應用程序的WEB-INF/lib 目錄下即可。下面是你需要的jar文件:
  
 如何設計用JSF和MyFaces上傳文件(圖)(圖二)

  org.apache.myfaces.component.html.util包的MultipartRequestWrapper類創建了MyFaces和Commons File Upload連接的橋梁。這個類繼續了HttpServletRequestWrapper,重寫了getParameterMap(), getParameterNames(), getParameter(), 和getParameterValues() 函數,所以他們能正確處理multipart/form-data 編碼數據。另外,MultipartRequestWrapper提供的兩個函數,getFileItem() 和getFileItems(),使你可以通過org.apache.commons.fileupload.FileItem 接口訪問上傳文件。
  
  MyFaces的 ExtensionsFilter 類在org.apache.myfaces.component.html.util 包里,當它發現multipart/form-data編碼的時候,它會創建 MultipartRequestWrapper 的實例。所以你不需理會他是如何解析表單數據的,但是知道它是如何開始解析對你想要修改上傳文件的處理方式是有用的。在一個傳統的應用程序中,你只需要在web.xml描述符中配置好ExtensionsFilter ,它就能在JSF的FacesServlet之前截獲HTTP請求:
  
  <?xml version="1.0" encoding="UTF-8"?>
  <!DOCTYPE web-app PUBLIC  "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"  "http://java.sun.com/dtd/web-app_2_3.dtd"><web-app>  <context-param>
  <param-name>javax.faces.STATE_SAVING_METHOD</param-name>
  <param-value>client</param-value>
  </context-param>
  <servlet>
  <servlet-name>FacesServlet</servlet-name>
  <servlet-class>
  javax.faces.webapp.FacesServlet
  </servlet-class>
  <load-on-startup>1</load-on-startup>
  </servlet>
  <servlet-mapping>
  <servlet-name>FacesServlet</servlet-name>
  <url-pattern>/faces/*</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
  <servlet-name>FacesServlet</servlet-name>
  <url-pattern>*.faces</url-pattern>
  </servlet-mapping>
  <filter>
  <filter-name>ExtensionsFilter</filter-name>
  <filter-class>
  org.apache.myfaces.component.html.util.ExtensionsFilter
  </filter-class>
  <init-param>
  <param-name>uploadMaxFileSize</param-name>
  <param-value>10m</param-value>
  </init-param>
  <init-param>
  <param-name>uploadThresholdSize</param-name>
  <param-value>100k</param-value>
  </init-param>
  </filter>
  <filter-mapping>
  <filter-name>ExtensionsFilter</filter-name>
  <servlet-name>FacesServlet</servlet-name>
  </filter-mapping>
  <welcome-file-list>
  <welcome-file>index.jsp</welcome-file>
  </welcome-file-list></web-app>
  
  前面例子中,filter的兩個參數告訴MyFaces把小于100K的文件保存在內存中,而對于大于10M的文件則忽略。大小在uploadThresholdSize值和uploadMaxFileSize值之間的文件則作為臨時文件存在硬盤上。假如你上傳很大的文件,當前的MyFaces版本會忽略所有的表單數據,就好象你提交了一個空表單。假如你想把上傳失敗的消息告訴用戶,你就得修改MyFaces中MultipartRequestWrapper類的源碼。讓我們找到捕捉SizeLimitExceededException的地方,并使用FacesContext.getCurrentInstance().addMessage()來警告用戶。
  
  正如前面所說的,MyFaces Extensions 里有個能在JSF頁面里使用的上傳組件。下面的章節將說明如何使用。
  
  為了在web頁面里使用JSF和MyFaces,你必須使用<%@taglib%>指令聲明他們的標簽庫。
  
  <%@ taglib uri="http://java.sun.com/jsf/core" prefix="f"%><%@ taglib uri="http://java.sun.com/jsf/html" prefix="h"%><%@ taglib uri="http://myfaces.apache.org/extensions" prefix="x"%>
  
  JSF的<h:form>標簽沒有method屬性,因為它只支持post方法,但他有enctype屬性,當你想上傳文件時,你可以用它來定義表單數據的編碼類型:
  <f:view>
  <h:form id="MyForm" e

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 仪陇县| 云林县| 祁阳县| 沽源县| 十堰市| 新兴县| 通江县| 米易县| 湖北省| 安义县| 阳东县| 九龙城区| 凤城市| 玉田县| 渭南市| 和平县| 康定县| 广灵县| 顺昌县| 兖州市| 正蓝旗| 永修县| 齐齐哈尔市| 临汾市| 新丰县| 兴山县| 安顺市| 揭阳市| 白城市| 石台县| 阜康市| 贵溪市| 中阳县| 仪陇县| 辽阳县| 阿荣旗| 定兴县| 廊坊市| 海淀区| 克拉玛依市| 清徐县|