我正在使用wicket将大型(~2Gb +)zip文件提交给Web应用程序,处理我正在使用java.util.zip。*类的zip文件,我需要能够随机读取来自zip文件的条目。所以我的代码是这样的:
class MyForm extends Form {
private FileUploadField fileField;
MyForm(String id) {
super(id);
fileField = new FileUploadField("upload");
add(fileField);
}
@Override
protected void onSubmit() {
FileUpload fileUpload = fileField.getFileUpload();
File file = fileUpload.writeToTempFile();
ZipFile zipFile = new ZipFile(file);
// Do more stuff
}
}
由于上传很大,wicket在解析请求时会将其放入临时文件中,但是writeToTempFile()会将其复制到另一个临时文件中,所以我现在在磁盘上有两个文件副本。这会浪费磁盘空间,磁盘IO并增加请求处理时间。
我无法使用ZipFileInputStream,因为我需要以随机顺序访问文件。有没有办法阻止wicket复制磁盘上的文件?
答案 0 :(得分:2)
基于@biziclop的回答,我写了这个类:
public class RawFileUploadField extends FileUploadField {
private static final long serialVersionUID = 1L;
public RawFileUploadField(String id) {
super(id);
}
/**
* Attempts to get the file that is on disk if it exists and if it doesn't
* then just write the file to a temp location.
* @return The file or <code>null</code> if no file.
* @throws IOException
*/
public File getFile() throws IOException {
// Get request
final Request request = getRequest();
// If we successfully installed a multipart request
if (request instanceof IMultipartWebRequest)
{
// Get the item for the path
FileItem item = ((IMultipartWebRequest)request).getFile(getInputName());
if (item instanceof DiskFileItem) {
File location = ((DiskFileItem)item).getStoreLocation();
if (location != null) {
return location;
}
}
}
// Fallback
FileUpload upload = getFileUpload();
return (upload != null)?upload.writeToTempFile():null;
}
}
答案 1 :(得分:1)
是的,但这不是一个好方法。
您可以创建FileUploadField
的子类,并使用公开基础getFileUpload()
的副本覆盖FileItem
方法。
或者,另一种方法是在FileUploadField
子类中创建一个新方法,只是为了返回FileItem
:
public FileItem getFileItem() {
return ((IMultipartWebRequest)getRequest()).getFile(getInputName());
}