Reputation: 8583
I'm using Oreilly MultipartRequest servlet to parse a forms multipart/form-data request as so:
String path = getServletContext().getRealPath("/tmp");
List uploadFiles = new ArrayList();
MultipartRequest multi = new MultipartRequest(request, path, 50 * 1024 * 1024, "UTF-8");
Enumeration<String> params = multi.getParameterNames();
Enumeration<String> files = multi.getFileNames();
//retrieve text parameters
String param;
while(params .hasMoreElements()){
param = params .nextElement();
for(String occurence : multi.getParameterValues(param)){
pageContext.setAttribute(param, occurence);
}
}
//get files
String fileParam;
while(files.hasMoreElements()){
fileParam = files.nextElement();
uploadFiles.add(multi.getFile(fileParam));
}
I'm able to get all the data, but in regards of files, I want to send them as an attachment, typically this is done as such (by parsing the request
)
ServletFileUpload servletFileUpload = new ServletFileUpload(new DiskFileItemFactory());
try {
List fileItemsList = servletFileUpload.parseRequest(request);
Iterator it = fileItemsList.iterator();
while (it.hasNext()){
FileItem fileItem = (FileItem)it.next();
if (fileItem.isFormField()){
messageBodyPart = new MimeBodyPart();
DataSource source = new FileDataSource(fileItem.getString());
messageBodyPart.setDataHandler(new DataHandler(source));
messageBodyPart.setFileName(fileItem.getFieldName());
multipart.addBodyPart(messageBodyPart);
}
}
} catch(Exception e) {
out.println(e.toString());
}
Instead, I am creating a list of all files uploadFiles
to upload. The problem is the attachment uses FileItem interface which allows me to get the contents of the file item as a String using getString()
, whereas Oreilly MultipartRequest
only returns the file as a File
object. How can I use the content of the File
Object similarly, or cast it into a FileItem
object perhaps.
Upvotes: 1
Views: 133
Reputation: 5606
According to the documentation, FileItem.getString() returns "the contents of the file item as a String". But FileDataSource(String) "creates a FileDataSource from the specified path name". So in your second code fragment you are passing a file contents as a String (which who knows what will do for binary files) instead of a file name. And getFieldName() will return the name of the form field and not the name of the upload file (which is what you want).
If you processed the upload with MultipartRequest then it's trivial to instantiate the FileDataSource required by DataHandler from the File objects returned by MultipartRequest.
If you processed the upload with ServletFileUpload then probably the best is to create your own custom implementation of DataSource interface which allows a FileItem in the constructor
public class FileItemDataSource implements DataSource {
private FileItem item;
public FileItemDataSource(FileItem item) {
this.item = item;
}
@Override
public String getContentType() {
return item.getContentType() ;
}
@Override
public InputStream getInputStream() throws IOException {
return item.getInputStream();
}
@Override
public String getName() {
return item.getName();
}
@Override
public OutputStream getOutputStream() throws IOException {
return item.getOutputStream();
}
}
with such class you could do
DataSource source = new FileItemDataSource(fileItem);
messageBodyPart.setDataHandler(new DataHandler(source));
messageBodyPart.setFileName(fileItem.getName());
multipart.addBodyPart(messageBodyPart);
Upvotes: 1
Reputation: 8583
Apparently the class FileDataSource
accepts a File
or String
at it's constructor. So passing the File object directly simply solves the problem. As such:
File fileItem = (File)it.next();
DataSource source = new FileDataSource(fileItem);
Upvotes: 0