Uploading a file into a database with JSP
Posted on April 11th, 2008 in Uncategorized | No Comments »
These days I’ve came uppon the problem of uploading an image to a web server and save it into a database as a Blob field with JSP. After some research and some experiencing on my own the solution that worked for my case looked like this:
<form method=post action="includes/upload.jsp?imgId=<%=iNumPhoto%>" name="upform" enctype="multipart/form-data"> onchange="LimitAttach(this.form, this.form.uploadfile.value)">
Where “iNumPhoto” is a parameter that i use when i need to overwrite an image (it’s set to -1 when the image is new), and “LimitAttach” is a JavaScript function that limits the types of file that can be submited trough my upload form.
<%@ page import="java.io.DataInputStream" %>
<%@ page import="java.io.FileOutputStream" %>
<%@ page import="java.util.Hashtable" %>
<%
String iNumPhoto = request.getParameter("imgId");
String contentType = request.getContentType();
if ((contentType != null) && (contentType.indexOf("multipart/form-data") >= 0)) {
DataInputStream in = new DataInputStream(request.getInputStream());
int formDataLength = request.getContentLength();
byte dataBytes[] = new byte[formDataLength];
int byteRead = 0;
int totalBytesRead = 0;
while (totalBytesRead < formDataLength) {
byteRead = in.read(dataBytes, totalBytesRead, formDataLength);
totalBytesRead += byteRead;
}
String file = new String(dataBytes);
String saveFile = file.substring(file.indexOf("filename=\"") + 10);
saveFile = saveFile.substring(0, saveFile.indexOf("\n"));
saveFile = saveFile.substring(saveFile.lastIndexOf("\\") + 1, saveFile.indexOf("\""));
int lastIndex = contentType.lastIndexOf("=");
String boundary = contentType.substring(lastIndex + 1, contentType.length());
int pos;
pos = file.indexOf("filename=\"");
pos = file.indexOf("\n", pos) + 1;
int boundaryLocation = file.indexOf(boundary, pos) - 4;
int startPos = ((file.substring(0, pos)).getBytes()).length;
int endPos = ((file.substring(0, boundaryLocation)).getBytes()).length;
FileOutputStream fileOut = new FileOutputStream(saveFile);
int imageSize = endPos - startPos;
byte[] imgBuffer = new byte[imageSize];
byte[] width = new byte[4];
// Calculate width from byte position 17 to 20 of PNG header
System.arraycopy(dataBytes, startPos + 16, width, 0, 4);
Integer myWidth = (width[0] * 16 * 3) + (width[1] * 16 * 2) + (width[2] * 16) + width[3];
System.arraycopy(dataBytes, startPos, imgBuffer, 0, imgBuffer.length);
Hashtable< Integer, Object> messageImages = message.getMessageImages();
if (!iNumPhoto.equals("-1")) {
Integer idPhoto = Integer.parseInt(iNumPhoto);
MessageImage messageImage = (MessageImage) messageImages.get(idPhoto);
if (!myWidth.equals(messageImage.getWidth())) {
out.print(" The selected image has an invalid width! Please select a valid one! (width = "+myWidth+")");
out.print("");
//todo send error
} else {
messageImages.remove(idPhoto);
messageImage.setWidth(myWidth);
messageImage.setData(imgBuffer);
messageImages.put(idPhoto, messageImage);
message.setMessageImages(messageImages);
out.print(" Image replaced! (width = "+myWidth+")");
out.print("");
}
} else {
MessageImage newImage = new MessageImage();
newImage.changeMandatoryValues(new String[]{"id", "messageId"}, new String[]{"-1", message.getId()});
newImage.setWidth(myWidth);
newImage.setData(imgBuffer);
messageImages.put(-1, newImage);
message.setMessageImages(messageImages);
%>
The tricky part was getting separated the byte-array containing the image, from all the data sent by the upload form (yes the form doesn’t send only the file). After that all easy, even figured out how to get the image width. I’m using a bean called “message”, and the “saving into the database” part is done by passing the byte-array to the bean where all the data-base related operations take place.
.






