How would you design a REST based web service that receives an image file in the form of an InputStream
? If the InputStream
is posted to a REST end point, how does that end point receive it so that it can create an image file?
Receiving an InputStream is possible in JAX-RS. You just put the InputStream parameter without annotations:
@POST
public void uploadImage(InputStream stream) {
// store image
}
Pay attention that it will work for any content type.
Although it will work, I would suggest a more "JAX-RS way":
1 Create provider that will create an image class (e.g. java.awt.Image) from the InputStream:
@Provider
@Consumes("image/jpeg")
class ImageProvider implements MessageBodyReader<Image> {
public Image readFrom(Class<Image> type,
Type genericType,
Annotation[] annotations,
MediaType mediaType,
MultivaluedMap<String, String> httpHeaders,
InputStream entityStream) throws IOException,
WebApplicationException {
// create Image from stream
}
}
2 Register the provider the same way you register a resource.
3 Make your resource class to receive Image instead of InputStream.
Why is this approach better?
You separate the deserialization logic from your resource class. So if in the future you would like to support more image formats, you just need to add additional providers, while the resource will stay the same.
import java.io.ByteArrayInputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import javax.ws.rs.Consumes;
import javax.ws.rs.FormParam;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.Produces;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import javax.ws.rs.core.UriInfo;
import com.sun.jersey.core.header.FormDataContentDisposition;
import com.sun.jersey.multipart.FormDataParam;
import com.sun.org.apache.xml.internal.security.exceptions.Base64DecodingException;
import com.sun.org.apache.xml.internal.security.utils.Base64;
@Path("/upload")
public class Upload_Documents {
private static final String UPLOAD_FOLDER = "c:/uploadedFiles/";
@Context
private UriInfo context;
/**
* Returns text response to caller containing uploaded file location
*
* @return error response in case of missing parameters an internal
* exception or success response if file has been stored
* successfully
*/
@POST
@Path("/pic")
@Consumes(MediaType.MULTIPART_FORM_DATA)
public Response uploadFile(
@FormDataParam("file") InputStream uploadedInputStream,
@FormDataParam("file") FormDataContentDisposition fileDetail) {
System.out.println("Called Upload Image");
// check if all form parameters are provided
if (uploadedInputStream == null || fileDetail == null)
return Response.status(400).entity("Invalid form data").build();
// create our destination folder, if it not exists
try {
createFolderIfNotExists(UPLOAD_FOLDER);
} catch (SecurityException se) {
return Response.status(500)
.entity("Can not create destination folder on server")
.build();
}
String uploadedFileLocation = UPLOAD_FOLDER + fileDetail.getFileName();
try {
saveToFile(uploadedInputStream, uploadedFileLocation);
} catch (IOException e) {
return Response.status(500).entity("Can not save file").build();
}
return Response.status(200)
.entity("File saved to " + uploadedFileLocation).build();
}
/**
* Utility method to save InputStream data to target location/file
*
* @param inStream
* - InputStream to be saved
* @param target
* - full path to destination file
*/
private void saveToFile(InputStream inStream, String target)
throws IOException {
OutputStream out = null;
int read = 0;
byte[] bytes = new byte[1024];
out = new FileOutputStream(new File(target));
while ((read = inStream.read(bytes)) != -1) {
out.write(bytes, 0, read);
}
out.flush();
out.close();
}
/**
* Creates a folder to desired location if it not already exists
*
* @param dirName
* - full path to the folder
* @throws SecurityException
* - in case you don't have permission to create the folder
*/
private void createFolderIfNotExists(String dirName)
throws SecurityException {
File theDir = new File(dirName);
if (!theDir.exists()) {
theDir.mkdir();
}
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With