commons-fileupload的优化实用类

commons-fileupload这东西上传和保存文件很方便,但读取里面的field的值的时候就很麻烦,总是循环一遍并比较名字才能取到值,极其不便,于是不得不做了个实用类,进行封装,用起来好多了,并且可以直接保存文件,我觉得还是挺方便的,共享一下吧。

 

原先取域的值的时候,代码类似如下:

for (FileItem item : items) {
				if (item.isFormField()) {
					fieldName = item.getFieldName();
					if (fieldName.equals("email")) {
						email= item.getString("UTF-8").trim();
					} else if (fieldName.equals("username")) {
						username = item.getString("UTF-8").trim();
					} 

 

    有一两个field问题不大,但如果有几十个呢,上百个呢?代码就很冗长和乏味了。

 

    用了我写的UploadForm,取值就跟读取普通表单的field一样容易,如:

String email = uploadForm.getStringField("email");

   

    完整代码如下,重要的地方写了注释:

    

import com.liferay.portal.kernel.log.Log;
import com.liferay.portal.kernel.log.LogFactoryUtil;
import com.liferay.portal.kernel.util.*;
import com.liferay.portal.util.PortalUtil;

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;
import org.apache.commons.lang.StringUtils;

import javax.portlet.PortletRequest;
import javax.servlet.http.HttpServletRequest;

import java.io.*;
import java.io.File;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.UUID;

public class UploadForm {
    private static Log log = LogFactoryUtil.getLog(UploadForm.class);
    private HttpServletRequest request;
    private HashMap<String, Object> fields = new HashMap<String, Object>();
    private List<FileItem> oriFileItems = new ArrayList<FileItem>();


    public UploadForm(HttpServletRequest request) {
        this.request = request;
        init();
    }

    public UploadForm(PortletRequest request) {
        this(PortalUtil.getHttpServletRequest(request));
    }

    private void init() {
        DiskFileItemFactory factory = new DiskFileItemFactory();
        ServletFileUpload uploader = new ServletFileUpload(factory);
        try {
            List<FileItem> items = uploader.parseRequest(request);
            for (FileItem item : items) {
                oriFileItems.add(item);
                String fieldName = item.getFieldName();
                log.debug("field name: " + fieldName);
                if (item.isFormField()) {
                    String fieldValue = null;
                    try {
                        fieldValue = item.getString("utf-8");
                    } catch (UnsupportedEncodingException e) {
                        log.error(e);
                    }

                    if (fields.get(fieldName) != null) {
                        Object value = fields.get(fieldName);
                        if (value instanceof List) {
                            ((List) value).add(item.getString());
                        } else {
                            fields.put(fieldName, ListUtil.fromArray(new String[]{String.valueOf(value), fieldValue}));
                        }
                    } else {
                        try {
                            fields.put(fieldName, item.getString("utf-8"));
                        } catch (UnsupportedEncodingException e) {
                            log.error(e);
                        }
                    }
                } else { //it's a file
                    if (fields.get(fieldName) != null) {
                        Object value = fields.get(fieldName);
                        if (value instanceof List) {
                            ((List) value).add(item.getString());
                        } else {
                            fields.put(fieldName, ListUtil.fromArray(new Object[]{value, item}));
                        }
                    } else {//first time checked
                        fields.put(fieldName, item);
                    }

                }
            }
        } catch (FileUploadException e) {
            log.error(e);
        }
    }

    /**
     * get the values of form fields
     *
     * @param fieldName
     * @return return "" if nothing is input for non-checkbox or non-radiobutton,
     *          return null if nothing is selected for checkbox or radiobutton
     */
    public String getStringField(String fieldName) {
        return MapUtil.getString(fields, fieldName);
    }

    public long getLongField(String fieldName) {
        if (StringUtils.isNotEmpty(getStringField(fieldName))) {
            return Long.parseLong(getStringField(fieldName));
        } else {
            return -1;
        }
    }

    public int getIntField(String fieldName) {
        if (StringUtils.isNotEmpty(getStringField(fieldName))) {
            return Integer.parseInt(getStringField(fieldName));
        } else {
            return -1;
        }
    }

    public float getFloatField(String fieldName) {
        if (StringUtils.isNotEmpty(getStringField(fieldName))) {
            return Float.parseFloat(getStringField(fieldName));
        } else {
            return -1;
        }
    }

    public double getDoubleField(String fieldName) {
        if (StringUtils.isNotEmpty(getStringField(fieldName))) {
            return Double.parseDouble(getStringField(fieldName));
        } else {
            return -1;
        }
    }

    /**
     * 取多值field的值,如checkbox
     * @param fieldName
     * @return
     */
    public String[] getStringFields(String fieldName) {
        if (!fields.containsKey(fieldName)) {
            return new String[0];
        }

        Object value = fields.get(fieldName);
        if (value instanceof List) {
            List<String> listValue = (List) value;
            return listValue.toArray(new String[0]);
        } else {
            return new String[]{String.valueOf(fields.get(fieldName))};
        }
    }

    /**
     * 取多值字段的原始FileItem
     * @param fieldName
     * @return
     */
    public FileItem[] getFileItemFields(String fieldName){
        if (!fields.containsKey(fieldName)){
            return new FileItem[]{};
        }

        if (fields.get(fieldName) instanceof List){
            List<FileItem> listField = (List)fields.get(fieldName);
            return listField.toArray(new FileItem[0]);
        }else{
            return new FileItem[]{((FileItem) fields.get(fieldName))};
        }
    }

    public Object getField(String fieldName) {
        return fields.get(fieldName);
    }

    /**
     * 保存文件
     *
     * @param fieldName 表单项的名字
     * @param saveName  保存文件名,含扩展名,不含文件夹部分
     * @param folder    保存的文件夹
     * @return
     */
    public FileWrapper saveFile(String fieldName, String saveName, String folder) {
        if (fields.get(fieldName) instanceof List){
            throw new IllegalArgumentException("Duplicated file selector['"+fieldName+"'] found! Ensure only one exists");
        }

        FileItem fileItem = (FileItem) fields.get(fieldName);
        if (!FileUtil.exists(folder)) {
            FileUtil.mkdirs(folder);
        }

        String fullPath = folder.replaceAll("\\\\", "/") + "/" + saveName;
        if (FileUtil.exists(fullPath)) {
            return null;
        } else {
            try {
                File file = new File(fullPath);
                fileItem.write(file);
                FileWrapper rspFile = new FileWrapper(file);
                rspFile.setOldName(fileItem.getName());
                return rspFile;
            } catch (Exception e) {
                log.error(e);
                return null;
            }
        }
    }

    /**
     * 用原先的文件名保存文件
     *
     * @param fieldName
     * @param folder
     * @return
     */
    public FileWrapper saveFile(String fieldName, String folder) {
        FileItem fileItem = (FileItem) fields.get(fieldName);
        return saveFile(fieldName, fileItem.getName(), folder);
    }

    /**
     * 用UUID作为文件名保存文件
     *
     * @param fieldName
     * @param folder
     * @return
     */
    public FileWrapper saveFileWithUUID(String fieldName, String folder) {
        FileItem fileItem = (FileItem) fields.get(fieldName);
        String oriFileName = fileItem.getName();
        String fileName = oriFileName.contains(".") ? UUID.randomUUID().toString() + "." + FileUtil.getExtension(oriFileName)
                : UUID.randomUUID().toString();
        return saveFile(fieldName, fileName, folder);
    }

    public FileWrapper saveFileItem(FileItem fileItem, String saveName, String folder) {
        if (StringUtils.isEmpty(fileItem.getName())){
            return null;
        }

        if (!FileUtil.exists(folder)) {
            FileUtil.mkdirs(folder);
        }

        String fullPath = folder.replaceAll("\\\\", "/") + "/" + saveName;
        if (FileUtil.exists(fullPath)) {
            return null;
        } else {
            try {
                File file = new File(fullPath);
                fileItem.write(file);
                FileWrapper rspFile = new FileWrapper(file);
                rspFile.setOldName(fileItem.getName());
                return rspFile;
            } catch (Exception e) {
                log.error(e);
                return null;
            }
        }

    }

    public FileWrapper saveFileWithUUID(FileItem fileItem, String folder) {
        String oriFileName = fileItem.getName();
        if (StringUtils.isEmpty(oriFileName)){
        	return null;
        }
        
        String fileName = oriFileName.contains(".") ? UUID.randomUUID().toString() + "." + FileUtil.getExtension(oriFileName)
                : UUID.randomUUID().toString();
        return saveFileItem(fileItem,fileName,folder);
    }

    public List<FileWrapper> saveFilesWithUUID(List<FileItem> fileItemList, String folder) {
        List<FileWrapper> files=new ArrayList<FileWrapper>();
        for (FileItem fileItem : fileItemList) {
            files.add(saveFileWithUUID(fileItem, folder));
        }

        return files;
    }

    public List<FileWrapper> saveFilesWithUUID(String fieldName, String folder) {
        FileItem[] fileItems=getFileItemFields(fieldName);
        List<FileWrapper> files=new ArrayList<FileWrapper>();

        for (FileItem fileItem : fileItems) {
            files.add(saveFileWithUUID(fileItem, folder));
        }

        return files;
    }

    /**
     * 按名称关键字搜索字段并返回FileItem数组,对于有些field,名字前缀一样,但可能加个不同的序号
     * 适合于动态添加的表单域
     * @param fieldNameKeyword
     * @return
     */
    public FileItem[] getFileItemArrByKeyword(String fieldNameKeyword){
        List<FileItem> fileItemList=new ArrayList<FileItem>();
        for (FileItem fileItem : oriFileItems) {
            if (fileItem.getFieldName().toLowerCase().contains(fieldNameKeyword.toLowerCase())){
                fileItemList.add(fileItem);
            }
        }

        return getFileItemListByKeyword(fieldNameKeyword).toArray(new FileItem[0]);
    }
    
    public List<FileItem> getFileItemListByKeyword(String fieldNameKeyword){
    	return getFileItemListByKeyword(fieldNameKeyword,true);
    }

    public List<FileItem> getFileItemListByKeyword(String fieldNameKeyword, boolean isFile){
        List<FileItem> fileItemList=new ArrayList<FileItem>();
        for (FileItem fileItem : oriFileItems) {
            if (fileItem.getFieldName().toLowerCase().contains(fieldNameKeyword.toLowerCase())){
                if (isFile){
                    if (!fileItem.isFormField() && fileItem.getSize()>0){
                        fileItemList.add(fileItem);
                    }
                }else{
                    fileItemList.add(fileItem);
                }
            }
        }

        return fileItemList;
    }
    

    public String[] getStringArrByKeyword(String fieldNameKeyword){
        return getStringListByKeyword(fieldNameKeyword).toArray(new String[0]);
    }
    
    public List<String> getStringListByKeyword(String fieldNameKeyword){
    	 List<String> strItemList=new ArrayList<String>();
         for (FileItem fileItem : oriFileItems) {
             if (fileItem.getFieldName().toLowerCase().contains(fieldNameKeyword.toLowerCase())){
                 try {
                     strItemList.add(fileItem.getString("UTF-8"));
                 } catch (UnsupportedEncodingException e) {
                     log.error(e);
                 }
             }
         }
         
         return strItemList;
    }
    

    public long getFileByteSize(String fieldName) {
        FileItem fileItem = (FileItem) fields.get(fieldName);
        return fileItem.getSize();
    }

    /**
     * 取得文件大小,单位KB
     * @param fieldName
     * @return
     */
    public float getFileKBSize(String fieldName) {
        return getFileByteSize(fieldName) / 1024.0f;
    }

    public double getFileMBSize(String fieldName) {
        return getFileByteSize(fieldName) / 1024.0 / 1024;
    }

    public boolean exist(String fieldName) {
        return fields.containsKey(fieldName);
    }

}

 

    用到的文件包装器,可以返回上传文件的原始名字,url编码后的名字等等,便于下载用到:

import com.liferay.portal.kernel.log.Log;
import com.liferay.portal.kernel.log.LogFactoryUtil;
import com.liferay.portal.kernel.util.FileUtil;

import java.io.File;
import java.io.UnsupportedEncodingException;

/**
 * 文件的实用类,含有一些实用的方法
 */
public class FileWrapper {
    private static Log log = LogFactoryUtil.getLog(FileWrapper.class);
    private File file;
    private String oldName;

    public FileWrapper(File file) {
        this.file = file;
    }

    public String getFileName(){
        return file.getName();
    }

    /**
     * 获得文件被保存的路径,不含文件名
     * @return
     */
    public String getFolderPath(){
        return FileUtil.getPath(file.getAbsolutePath());
    }

    /**
     * 将文件名转码成url中用的编码
     * @return
     */
    public String getUrlEncodingName(){
        try {
            return java.net.URLEncoder.encode(oldName, "UTF-8");
        } catch (UnsupportedEncodingException e) {
            log.error(e);
            return "";
        }
    }

    /**
     * 获得文件原始名
     * @return
     */
    public String getOldName() {
        return oldName;
    }

    public void setOldName(String oldName) {
        if (oldName.contains("\\") || oldName.contains("/")){
            oldName = oldName.replaceAll("\\\\","/");
            oldName = oldName.substring(oldName.lastIndexOf("/"));
            this.oldName = oldName;
        }else{
            this.oldName = oldName;
        }
    }

    public String getExtName(){
        return FileUtil.getExtension(file.getAbsolutePath());
    }
    
    public String getFullPath(){
    	return file.getAbsolutePath();
    }
}

 

    调用示例:

 UploadForm uploadForm=new UploadForm(request);
 
  String zip_code = uploadForm.getStringField("zip_code");
    List<String> provinces = uploadForm.getStringListByKeyword("province");//省份字段是在页面动态添加的
    List<FileWrapper> certFileList = uploadForm.saveFilesWithUUID(uploadForm.getFileItemListByKeyword("certFile"), "d:/upload");//上传文件的保存

 

    通过这种封装,以后使用commons-fileupload就不再是一件头疼的事了。不过,代码中用到了一少部分liferay的一些实用类,可以根据需要很容易地自己写或其它开源类库替换

你可能感兴趣的:(liferay)