ofbiz——上传工具类HttpRequestFileUpload修改优化

来源:互联网 发布:22周排畸b超数据看男女 编辑:程序博客网 时间:2024/06/14 01:50

在使用HttpRequestFileUpload类实现文件上传功能时,发现单用户没有选择上传文件时,执行uploadObject.doUpload(request);方法时会报错,所以进行了优化。

主要添加了一个Map<String, File> fileMap;成员。当用户没有上传文件时,其uploadObject.getFile("file控件name")对于获取的值为null。

当用户上传多个文件,也会解析保存到fileMap中,之前的实现上传多个文件则无法判断上传了几个文件。

org.apache.ofbiz.base.util.HttpRequestFileUpload类

原来的实现代码:

package org.apache.ofbiz.base.util;import java.io.File;import java.io.FileOutputStream;import java.io.IOException;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.servlet.ServletInputStream;import javax.servlet.http.HttpServletRequest;/** * HttpRequestFileUpload - Receive a file upload through an HttpServletRequest * */public class HttpRequestFileUpload {    private int BUFFER_SIZE = 4096;    private int WAIT_INTERVAL = 200; // in milliseconds    private int MAX_WAITS = 20;    private int waitCount = 0;    private String savePath;    private String filepath;    private String filename;    private String contentType;    private String overrideFilename = null;    private Map<String, String> fields;    public String getOverrideFilename() {        return overrideFilename;    }    public void setOverrideFilename(String ofName) {        overrideFilename = ofName;    }    public String getFilename() {        return filename;    }    public String getFilepath() {        return filepath;    }    public void setSavePath(String savePath) {        this.savePath = savePath;    }    public String getContentType() {        return contentType;    }    public String getFieldValue(String fieldName) {        if (fields == null || fieldName == null)            return null;        return fields.get(fieldName);    }    private void setFilename(String s) {        if (s == null)            return;        int pos = s.indexOf("filename=\"");        if (pos != -1) {            filepath = s.substring(pos + 10, s.length() - 1);            // Windows browsers include the full path on the client            // But Linux/Unix and Mac browsers only send the filename            // test if this is from a Windows browser            pos = filepath.lastIndexOf("\\");            if (pos != -1)                filename = filepath.substring(pos + 1);            else                filename = filepath;        }    }    private void setContentType(String s) {        if (s == null)            return;        int pos = s.indexOf(": ");        if (pos != -1)            contentType = s.substring(pos + 2, s.length());    }    public void doUpload(HttpServletRequest request) throws IOException {        ServletInputStream in = request.getInputStream();        String reqLengthString = request.getHeader("content-length");        System.out.println("expect " + reqLengthString + " bytes.");        int requestLength = 0;        try {            requestLength = Integer.valueOf(reqLengthString).intValue();        } catch (Exception e2) {            e2.printStackTrace();            return;        }        byte[] line = new byte[BUFFER_SIZE];        int i = -1;        i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);        requestLength -= i;        if (i < 3)            return;        int boundaryLength = i - 2;        String boundary = new String(line, 0, boundaryLength); // -2 discards the newline character        System.out.println("boundary=[" + boundary + "] length is " + boundaryLength);        fields = new HashMap<String, String>();        while (requestLength > 0/* i != -1*/) {            String newLine = "";            if (i > -1) {                newLine = new String(line, 0, i);            }            if (newLine.startsWith("Content-Disposition: form-data; name=\"")) {                if (newLine.indexOf("filename=\"") != -1) {                    setFilename(new String(line, 0, i - 2));                    if (filename == null)                        return;                    // this is the file content                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    setContentType(new String(line, 0, i - 2));                    // blank line                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    newLine = new String(line, 0, i);                    String filenameToUse = filename;                    if (overrideFilename != null) {                        filenameToUse = overrideFilename;                    }                    // first line of actual file                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    newLine = new String(line, 0, i);                    byte[] lastTwoBytes = new byte[2];                    if (i > 1) {                        lastTwoBytes[0] = line[i - 2];                        lastTwoBytes[1] = line[i - 1];                    }                    System.out.println("about to create a file:" + (savePath == null ? "" : savePath) + filenameToUse);                    // before creating the file make sure directory exists                    File savePathFile = new File(savePath);                    if (!savePathFile.exists()) {                        savePathFile.mkdirs();                    }                    FileOutputStream fos = new FileOutputStream((savePath == null ? "" : savePath) + filenameToUse);                    boolean bail = (new String(line, 0, i).startsWith(boundary));                    boolean oneByteLine = (i == 1); // handle one-byte lines                    while ((requestLength > 0/* i != -1*/) && !bail) {                        // write the current buffer, except the last 2 bytes;                        if (i > 1) {                            fos.write(line, 0, i - 2);                        }                        oneByteLine = (i == 1); // we need to track on-byte lines differently                        i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                        requestLength -= i;                        // the problem is the last line of the file content                        // contains the new line character.                        // if the line just read was the last line, we're done.                        // if not, we must write the last 2 bytes of the previous buffer                        // just assume that a one-byte line isn't the last line                        if (requestLength < 1) {                            bail = true;                        } else if (oneByteLine) {                            fos.write(lastTwoBytes, 0, 1); // we only saved one byte                        } else {                            fos.write(lastTwoBytes, 0, 2);                        }                        if (i > 1) {                            // save the last 2 bytes of the buffer                            lastTwoBytes[0] = line[i - 2];                            lastTwoBytes[1] = line[i - 1];                        } else {                            lastTwoBytes[0] = line[0]; // only save one byte                        }                    }                    fos.flush();                    fos.close();                } else {                    // this is a field                    // get the field name                    int pos = newLine.indexOf("name=\"");                    String fieldName = newLine.substring(pos + 6, newLine.length() - 3);                    // blank line                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    newLine = new String(line, 0, i);                    StringBuilder fieldValue = new StringBuilder(BUFFER_SIZE);                    while (requestLength > 0/* i != -1*/ && !newLine.startsWith(boundary)) {                        // The last line of the field                        // contains the new line character.                        // So, we need to check if the current line is                        // the last line.                        i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                        requestLength -= i;                        if ((i == boundaryLength + 2 || i == boundaryLength + 4) // + 4 is eof                            && (new String(line, 0, i).startsWith(boundary)))                            fieldValue.append(newLine.substring(0, newLine.length() - 2));                        else                            fieldValue.append(newLine);                        newLine = new String(line, 0, i);                    }                    fields.put(fieldName, fieldValue.toString());                }            }            i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);            if (i > -1) {                requestLength -= i;            }        } // end while    }    // reads a line, waiting if there is nothing available and reqLen > 0    private int waitingReadLine(ServletInputStream in, byte[] buf, int off, int len, int reqLen) throws IOException {        int i = -1;        while (((i = in.readLine(buf, off, len)) == -1) && (reqLen > 0)) {            System.out.print("waiting");            if (waitCount > MAX_WAITS) {                System.out.println("waited " + waitCount + " times, bailing out while still expecting " +                    reqLen + " bytes.");                throw new IOException("waited " + waitCount + " times, bailing out while still expecting " +                        reqLen + " bytes.");            }            waitCount++;            long endMS = new Date().getTime() + WAIT_INTERVAL;            while (endMS > (new Date().getTime())) {                try {                    wait(WAIT_INTERVAL);                } catch (Exception e3) {                    System.out.print(".");                }            }            System.out.println((new Date().getTime() - endMS) + " ms");        }        return i;    }}

修改后实现代码:

package org.apache.ofbiz.base.util;import java.io.File;import java.io.FileOutputStream;import java.io.IOException;import java.util.Date;import java.util.HashMap;import java.util.Map;import javax.servlet.ServletInputStream;import javax.servlet.http.HttpServletRequest;/** * HttpRequestFileUpload - Receive a file upload through an HttpServletRequest * */public class HttpRequestFileUpload {    private int BUFFER_SIZE = 4096;    private int WAIT_INTERVAL = 200; // in milliseconds    private int MAX_WAITS = 20;    private int waitCount = 0;    private String savePath;    private String filepath;    private String filename;    private String contentType;    private String overrideFilename = null;    private Map<String, String> fields;private Map<String, File> fileMap;    public String getOverrideFilename() {        return overrideFilename;    }    public void setOverrideFilename(String ofName) {        overrideFilename = ofName;    }    public String getFilename() {        return filename;    }    public String getFilepath() {        return filepath;    }    public void setSavePath(String savePath) {        this.savePath = savePath;    }    public String getContentType() {        return contentType;    }    public String getFieldValue(String fieldName) {        if (fields == null || fieldName == null)            return null;        return fields.get(fieldName);    }public File getFile(String fieldName) {if (fileMap == null || fieldName == null)            return null;        return fileMap.get(fieldName);    }    private void setFilename(String s) {        if (s == null)            return;        int pos = s.indexOf("filename=\"");        if (pos != -1) {            filepath = s.substring(pos + 10, s.length() - 1);            // Windows browsers include the full path on the client            // But Linux/Unix and Mac browsers only send the filename            // test if this is from a Windows browser            pos = filepath.lastIndexOf("\\");            if (pos != -1)                filename = filepath.substring(pos + 1);            else                filename = filepath;        }    }    private void setContentType(String s) {        if (s == null)            return;        int pos = s.indexOf(": ");        if (pos != -1)            contentType = s.substring(pos + 2, s.length());    }    public void doUpload(HttpServletRequest request) throws IOException {        ServletInputStream in = request.getInputStream();        String reqLengthString = request.getHeader("content-length");        System.out.println("expect " + reqLengthString + " bytes.");        int requestLength = 0;        try {            requestLength = Integer.valueOf(reqLengthString).intValue();        } catch (Exception e2) {            e2.printStackTrace();            return;        }        byte[] line = new byte[BUFFER_SIZE];        int i = -1;        i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);        requestLength -= i;        if (i < 3)            return;        int boundaryLength = i - 2;        String boundary = new String(line, 0, boundaryLength); // -2 discards the newline character        System.out.println("boundary=[" + boundary + "] length is " + boundaryLength);        fields = new HashMap<String, String>();fileMap = new HashMap<String, File>();        while (requestLength > 0/* i != -1*/) {            String newLine = "";            if (i > -1) {                newLine = new String(line, 0, i);            }            if (newLine.startsWith("Content-Disposition: form-data; name=\"")) {                if (newLine.indexOf("filename=\"") != -1) {int pos = newLine.indexOf("name=\"");String fieldName = newLine.substring(pos + 6, newLine.indexOf("\"", pos + 6 ));setFilename(new String(line, 0, i - 2));if("".equals(filename) || filename == null){fileMap.put(fieldName, null);}else{// this is the file contenti = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);requestLength -= i;setContentType(new String(line, 0, i - 2));// blank linei = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);requestLength -= i;newLine = new String(line, 0, i);String filenameToUse = filename;if (overrideFilename != null) {filenameToUse = overrideFilename;}// first line of actual filei = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);requestLength -= i;newLine = new String(line, 0, i);byte[] lastTwoBytes = new byte[2];if (i > 1) {lastTwoBytes[0] = line[i - 2];lastTwoBytes[1] = line[i - 1];}System.out.println("about to create a file:" + (savePath == null ? "" : savePath) + filenameToUse);// before creating the file make sure directory existsFile savePathFile = new File(savePath);if (!savePathFile.exists()) {savePathFile.mkdirs();}FileOutputStream fos = new FileOutputStream((savePath == null ? "" : savePath) + filenameToUse);boolean bail = (new String(line, 0, i).startsWith(boundary));boolean oneByteLine = (i == 1); // handle one-byte lineswhile ((requestLength > 0/* i != -1*/) && !bail) {// write the current buffer, except the last 2 bytes;if (i > 1) {fos.write(line, 0, i - 2);}oneByteLine = (i == 1); // we need to track on-byte lines differentlyi = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);requestLength -= i;// the problem is the last line of the file content// contains the new line character.// if the line just read was the last line, we're done.// if not, we must write the last 2 bytes of the previous buffer// just assume that a one-byte line isn't the last lineif (requestLength < 1) {bail = true;} else if (oneByteLine) {fos.write(lastTwoBytes, 0, 1); // we only saved one byte} else {fos.write(lastTwoBytes, 0, 2);}if (i > 1) {// save the last 2 bytes of the bufferlastTwoBytes[0] = line[i - 2];lastTwoBytes[1] = line[i - 1];} else {lastTwoBytes[0] = line[0]; // only save one byte}}fos.flush();fos.close();fileMap.put(fieldName, new File((savePath == null ? "" : savePath) + filenameToUse));}                } else {                    // this is a field                    // get the field name                    int pos = newLine.indexOf("name=\"");                    String fieldName = newLine.substring(pos + 6, newLine.length() - 3);                    // blank line                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                    requestLength -= i;                    newLine = new String(line, 0, i);                    StringBuilder fieldValue = new StringBuilder(BUFFER_SIZE);                    while (requestLength > 0/* i != -1*/ && !newLine.startsWith(boundary)) {                        // The last line of the field                        // contains the new line character.                        // So, we need to check if the current line is                        // the last line.                        i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);                        requestLength -= i;                        if ((i == boundaryLength + 2 || i == boundaryLength + 4) // + 4 is eof                            && (new String(line, 0, i).startsWith(boundary)))                            fieldValue.append(newLine.substring(0, newLine.length() - 2));                        else                            fieldValue.append(newLine);                        newLine = new String(line, 0, i);                    }                    fields.put(fieldName, fieldValue.toString());                }            }            i = waitingReadLine(in, line, 0, BUFFER_SIZE, requestLength);            if (i > -1) {                requestLength -= i;            }        } // end while    }    // reads a line, waiting if there is nothing available and reqLen > 0    private int waitingReadLine(ServletInputStream in, byte[] buf, int off, int len, int reqLen) throws IOException {        int i = -1;        while (((i = in.readLine(buf, off, len)) == -1) && (reqLen > 0)) {            System.out.print("waiting");            if (waitCount > MAX_WAITS) {                System.out.println("waited " + waitCount + " times, bailing out while still expecting " +                    reqLen + " bytes.");                throw new IOException("waited " + waitCount + " times, bailing out while still expecting " +                        reqLen + " bytes.");            }            waitCount++;            long endMS = new Date().getTime() + WAIT_INTERVAL;            while (endMS > (new Date().getTime())) {                try {                    wait(WAIT_INTERVAL);                } catch (Exception e3) {                    System.out.print(".");                }            }            System.out.println((new Date().getTime() - endMS) + " ms");        }        return i;    }}


原创粉丝点击