fileupload檔案上傳

來源:互聯網
上載者:User

標籤:java   設計模式   開發工具   繼承   類   

       在使用java開發檔案上傳時,網路上有很多不一樣的工具。但是每次如果都需要開發一次,對於使用者來說,這個過程是浪費時間的。所以我們有必要選取其中一個適合自己的檔案上傳組件,然後對其進一步分裝,形成自己的開發工具類。下面我針對自己的工程,對fileupload進行了封裝。

       fileupload是apache的一個組件,要想使用fileupload,需要用到下面兩個jar:commons-fileupload-1.3.1.jar,commons-io-1.1.jar(版本不一樣,可能相關jar包不一致,大家根據最新來下載即可)。

       下載好相關的jar包,使用eclipse建立一個Dynamic Web Project,然後將jar添加到WEB-INF/lib下面。

        由於fileupload組件使用非常簡單,所以大家可以參考官網的api,這是學習fileupload最後的一種方式。相關連結:fileupload

        下面給出我自己的類和代碼:

package net.itaem.servlet;import java.io.File;import java.io.IOException;import java.util.HashMap;import java.util.Iterator;import java.util.List;import java.util.Map;import java.util.UUID;import javax.servlet.ServletConfig;import javax.servlet.ServletContext;import javax.servlet.ServletException;import javax.servlet.http.HttpServlet;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;import org.apache.commons.fileupload.FileItem;import org.apache.commons.fileupload.FileUploadException;import org.apache.commons.fileupload.disk.DiskFileItemFactory;import org.apache.commons.fileupload.servlet.ServletFileUpload;/** * 檔案上傳的基類,該類可以被繼承 * 在設定檔,必須要配置相關的上傳屬性 * 這是一個父類,主要處理檔案的儲存,但是對於普通的表單域,由子類來實現 * 每個子類必須實現processNormalField(FileItem fileItem)方法 * 這裡採用了模板設計模式... *  * */public abstract class FileuploadServletBase extends HttpServlet {/** *  */private static final long serialVersionUID = 1L;//儲存檔案檔案夾private static String saveDir = null;//緩衝大小private static int tempCachedSize = 20480;//允許上傳的檔案類型private static String[] permittedFileType = null;//單個檔案的大小private static int fileSize = 20480;//最大允許上傳的表達大小private static int maxSize = 204800;    //儲存上傳檔案的檔案夾private String savePath;//儲存上傳檔案的mapprivate Map<String, String> uploadedMap = new HashMap<String, String>();@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {doPost(req, resp);}@SuppressWarnings("rawtypes")@Overrideprotected void doPost(HttpServletRequest req, HttpServletResponse resp)throws ServletException, IOException {//設定編碼req.setCharacterEncoding("utf-8");resp.setCharacterEncoding("utf-8");//建立一個DiskFileItemFactoryDiskFileItemFactory factory = new DiskFileItemFactory();factory.setRepository(new File(savePath)); //配置儲存路徑factory.setSizeThreshold(tempCachedSize);  //配置緩衝大小//建立一個ServletFileUploadServletFileUpload upload = new ServletFileUpload(factory);upload.setSizeMax(maxSize); //設定總體表單大小upload.setFileSizeMax(fileSize); //設定單個檔案大小//處理表單try {List<FileItem> items = upload.parseRequest(req);Iterator itemsIterator = items.iterator();while(itemsIterator.hasNext()){FileItem fileItem = (FileItem)itemsIterator.next();if(!fileItem.isFormField()){  //檔案域//去掉不支援上傳的檔案類型boolean uploadedFlag = false;for(int i=0; i<permittedFileType.length; i++){if(permittedFileType[i].contains(fileItem.getContentType())){uploadedFlag = true;break;}}//如果檔案允許上傳,那麼儲存檔案到指定上傳檔案夾中if(uploadedFlag){String type = fileItem.getName().substring(fileItem.getName().lastIndexOf("."));File uploadedFile = newFile(type);//save the filefileItem.write(uploadedFile);//put the file name in a mapuploadedMap.put(fileItem.getFieldName(), uploadedFile.getCanonicalPath());}}else{  //普通表單域processNormalField(fileItem);   }}//上傳完畢,進行相關的操作,比如關聯資料庫,或者將上傳檔案名稱儲存在xml等檔案中finishedProcess();} catch (FileUploadException e) {e.printStackTrace();} catch (Exception e) {e.printStackTrace();}}    /** * 獲得一個隨機字串,作為上傳檔案的檔案名稱,防止檔案被複寫了 * @return 返回一個唯一的隨機字串 * */public String getRandomFileName(){UUID fileNameUUID = UUID.randomUUID();return fileNameUUID.toString();}@Overridepublic void init() throws ServletException {super.init();}/** * 初始化servlet,讀取設定檔的參數 * */@Overridepublic void init(ServletConfig config) throws ServletException {if(config.getInitParameter("saveDir") == null){throw new RuntimeException("參數saveDir不可為空");}else{saveDir = config.getInitParameter("saveDir").trim();}if(config.getInitParameter("permittedFileType") == null){throw new RuntimeException("參數permittedFileType不可為空");}else{permittedFileType = config.getInitParameter("permittedFileType").trim().split(",");}if(config.getInitParameter("fileSize") == null){throw new RuntimeException("參數fileSize不可為空");}else{fileSize = Integer.parseInt(config.getInitParameter("fileSize").trim());}if(config.getInitParameter("maxSize") == null){throw new RuntimeException("參數maxSize不可為空");}else{maxSize = Integer.parseInt(config.getInitParameter("maxSize").trim());}if(config.getInitParameter("tempCachedSize") == null){throw new RuntimeException("參數tempCachedSize不可為空");}else{tempCachedSize = Integer.parseInt(config.getInitParameter("tempCachedSize").trim());}//建立檔案夾,如果檔案夾不存在saveDir = createSaveDir(config.getServletContext(), saveDir);}/** * 建立檔案夾 * @param context 請求上下文 * @param dirName 檔案夾名字 * @return 返迴文件夾在當前工程中的路徑 * */private String createSaveDir(ServletContext context, String dirName) {String contextPath = context.getRealPath("/"); //獲得工程的savePath = contextPath + dirName;File dir = new File(savePath);if(!dir.exists()){   //如果檔案不存在,建立檔案夾dir.mkdir();   return savePath;}else{if(dir.isDirectory()){  //檔案夾存在,並且已經是檔案夾了,直接返回return savePath;}else{ throw new RuntimeException("該檔案" + savePath + "已經存在,請重新設定儲存上傳檔案的檔案夾名稱");}}}/** *  * 這是一個抽象類別,由基類實現,這個方法主要用來處理普通的表單 * 使用模板設計模式... * 處理普通的表單域 * @param fileItem 普通表單域 * */public abstract void processNormalField(FileItem fileItem);/** * @param type 檔案類型 * 穿件一個隨機檔案,檔案的尾碼有type決定 * @return 隨機檔案 * */public File newFile(String type){return new File(savePath + File.separator + getRandomFileName() + type);}/** * 將所有的檔案名稱作為一個map返回 * key:表單網域名稱 * value:上傳檔案名稱 * @return 返回所有上傳檔案的map * */public Map<String, String> getUploadedMap(){return uploadedMap;}/** * 通過表單域找到上傳檔案之後的檔案名稱 * @param filedName 表單網域名稱 * @return 上傳之後的檔案名稱 * */public String getUploadedName(String fieldName){if(fieldName == null) return null;return uploadedMap.get(fieldName);}/** * 表單處理完畢,接下來處理相關操作,比如將上傳之後的檔案名稱儲存到資料庫庫之類的操作d * 通常情況下都會進行相關關聯 * */public abstract void finishedProcess();}

       從類的定義中,我們可以看到,這個類是一個抽象類別,使用了方法樣板設計模式。

下面給出一個簡單實作類別:

package net.itaem.servlet;import java.util.Map;import org.apache.commons.fileupload.FileItem;/** * 檔案上傳的一個類 * 這裡處理了普通表單域 *  *  * */public class GenericFileUploadServlet extends FileuploadServletBase{/** *  */private static final long serialVersionUID = 155452356367458695L;@Overridepublic void processNormalField(FileItem fileItem) {        System.out.println(fileItem.getFieldName() + "--->" + fileItem.getString());        // do something here}/** * 表單處理完畢,接下來處理相關操作,比如將上傳之後的檔案名稱儲存到資料庫庫之類的操作d * */@Overridepublic void finishedProcess() {Map<String, String> uploadedMap = super.getUploadedMap();        //列印出每個表單域對應的上傳檔案名稱for(String fieldName: uploadedMap.keySet()){System.out.println(fieldName + "--->" + uploadedMap.get(fieldName));}} }

       總結:

       在實作類別GenericFileuploadServlet中,我們可以對普通的表單域進行處理,也可以對上傳之後的檔案作出想過處理。所以有了這個設計之後,每次我們可以手動在配置servlet中配置:儲存檔案夾的名字,緩衝大小,支援上傳的類型,最大支援上傳大小,單個檔案大小的資訊。下面給出我自己的配置:

<?xml version="1.0" encoding="UTF-8"?><web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd">  <display-name></display-name>    <servlet>      <servlet-name>fileupload</servlet-name>      <servlet-class>net.itaem.servlet.GenericFileUploadServlet</servlet-class>            <init-param>          <param-name>tempSaveDir</param-name>          <param-value>temp_upload</param-value>      </init-param>            <init-param>          <param-name>saveDir</param-name>          <param-value>upload</param-value>      </init-param>            <init-param>          <param-name>tempCachedSize</param-name>          <param-value>2048000</param-value>      </init-param>           <init-param>          <param-name>permittedFileType</param-name>          <param-value>text/html,application/octet-stream,video/mp4</param-value>      </init-param>             <init-param>          <param-name>fileSize</param-name>          <param-value>204800000</param-value>      </init-param>             <init-param>          <param-name>maxSize</param-name>          <param-value>20480000</param-value>      </init-param>             <load-on-startup>10</load-on-startup>  </servlet>    <servlet-mapping>      <servlet-name>fileupload</servlet-name>      <url-pattern>/fileupload.do</url-pattern>  </servlet-mapping>  <welcome-file-list>    <welcome-file>index.jsp</welcome-file>  </welcome-file-list></web-app>

        注意點:

       上傳之後的檔案,儲存檔案時,注意檔案名稱要具備唯一性。這裡使用UUID工具類來產生,哈哈,這個類在java.util包中。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.