Create File Upload Functionalty Using Jersey in Mule

Posted on the 03 May 2013 by Abhishek Somani @somaniabhi
Creating Rest services in Mule is very easy as Jersey is shipped with mule runtime[Read more]. Now , if you want to create a Multipart Rest service using Mule , you have to add following dependencies in your mule Runtime. Make sure the versions of jersey-multipart.jar , mimepull.jar matches with the existing jersey version in mule runtime. For example , Mule Server 3.3.1 CE comes with Jersey version 1.6 , so i have downloaded jersey-multipart 1.6.
<dependency>
   <groupId>com.sun.jersey.contribs</groupId>
   <artifactId>jersey-multipart</artifactId>
   <version>1.6</version>
  </dependency>

<groupId>org.jvnet</groupId>
  <artifactId>mimepull</artifactId>
  <version>1.6</version>

This is the Rest Jersey Component :
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import javax.servlet.http.HttpServletRequest;
import javax.ws.rs.Consumes;
import javax.ws.rs.POST;
import javax.ws.rs.Path;
import javax.ws.rs.core.Context;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;

import com.sun.jersey.core.header.FormDataContentDisposition;
import com.sun.jersey.multipart.FormDataParam;

@Path("/application")
public class FileUploadService {

 
 @POST
 @Path("/upload")
 @Consumes(MediaType.MULTIPART_FORM_DATA)
 public Response uploadFile(
  @FormDataParam("file") InputStream uploadedInputStream,
  @FormDataParam("file") FormDataContentDisposition fileDetail) {
 
  String uploadedFileLocation = "D://" + fileDetail.getFileName();
 
  // save it
  writeToFile(uploadedInputStream, uploadedFileLocation);
 
  String output = "File uploaded to : " + uploadedFileLocation;
 
  return Response.status(200).entity(output).build();
 }
 
 // save uploaded file to new location
 private void writeToFile(InputStream uploadedInputStream,
  String uploadedFileLocation) {
  OutputStream out=null;
  File f = new File(uploadedFileLocation);
  try {
   
   out = new FileOutputStream(f);
   int read = 0;
   byte[] bytes = new byte[1024];
 
   out = new FileOutputStream(new File(uploadedFileLocation));
   while ((read = uploadedInputStream.read(bytes)) != -1) {
    out.write(bytes, 0, read);
   }
   out.flush();
  } catch (IOException e) {
 
   e.printStackTrace();
  }
  finally{
   if(out !=null)
    try {
     uploadedInputStream.close();
     out.close();
    } catch (IOException e) {
     // TODO Auto-generated catch block
     e.printStackTrace();
    }
  }
 
 }

 
}


This is the mule xml configuration :
<?xml version="1.0" encoding="UTF-8"?>

<mule xmlns:jetty="http://www.mulesoft.org/schema/mule/jetty" xmlns:jersey="http://www.mulesoft.org/schema/mule/jersey"
 xmlns:http="http://www.mulesoft.org/schema/mule/http"
 xmlns="http://www.mulesoft.org/schema/mule/core" xmlns:doc="http://www.mulesoft.org/schema/mule/documentation" xmlns:spring="http://www.springframework.org/schema/beans" version="EE-3.3.2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="
http://www.mulesoft.org/schema/mule/http http://www.mulesoft.org/schema/mule/http/current/mule-http.xsd 
http://www.mulesoft.org/schema/mule/jersey http://www.mulesoft.org/schema/mule/jersey/current/mule-jersey.xsd 
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-current.xsd 
http://www.mulesoft.org/schema/mule/core http://www.mulesoft.org/schema/mule/core/current/mule.xsd 
http://www.mulesoft.org/schema/mule/jetty http://www.mulesoft.org/schema/mule/jetty/current/mule-jetty.xsd ">

<flow name="fileUploadExampleFlow1" doc:name="fileUploadExampleFlow1">
        <http:inbound-endpoint exchange-pattern="request-response" host="localhost" port="8082" doc:name="HTTP"/>
        <jersey:resources doc:name="REST">
            <component class="FileUploadService"/>
        </jersey:resources>
    </flow>


</mule>

And this is the test class to test Multipart Rest service using Jersey client :
import java.io.File;
import java.io.FileInputStream;

import javax.ws.rs.core.MediaType;

import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.WebResource;
import com.sun.jersey.core.header.FormDataContentDisposition;
import com.sun.jersey.multipart.FormDataBodyPart;
import com.sun.jersey.multipart.FormDataMultiPart;
import com.sun.jersey.multipart.file.FileDataBodyPart;

public class TestFileUploadService {

 public static void main(String[] args) {

  try {

   Client client = Client.create();

   WebResource webResource = client
     .resource("http://localhost:8082/application/upload");

   File f = new File("D://soft//depp.JPG");
   FileDataBodyPart fdp = new FileDataBodyPart("file", f,
     MediaType.APPLICATION_OCTET_STREAM_TYPE);

   FormDataMultiPart formDataMultiPart = new FormDataMultiPart();

   formDataMultiPart.bodyPart(fdp);

   String reString = webResource.type(MediaType.MULTIPART_FORM_DATA)
     .accept(MediaType.TEXT_HTML)
     .post(String.class, formDataMultiPart);
   System.out.println(reString);

   System.out.println("Output from Server .... \n");

  } catch (Exception e) {

   e.printStackTrace();

  }

 }

}

If you forgot to include jersey-mutipart.jar or mimepull.jar , you may get error warnings like this on server side :
SEVERE: A message body reader for Java class com.sun.jersey.multipart.FormDataMultiPart, and Java type class com.sun.jersey.multipart.FormDataMultiPart, and MIME media type multipart/form-data; boundary=Boundary_1_1409104443_1367490786430 was not found
May 02, 2013 4:03:06 PM com.sun.jersey.spi.container.ContainerRequest getEntity
SEVERE: The registered message body readers compatible with the MIME media type are:
*/* ->
  com.sun.jersey.core.impl.provider.entity.FormProvider
  com.sun.jersey.core.impl.provider.entity.MimeMultipartProvider
  com.sun.jersey.core.impl.provider.entity.StringProvider
  com.sun.jersey.core.impl.provider.entity.ByteArrayProvider
  com.sun.jersey.core.impl.provider.entity.FileProvider
  com.sun.jersey.core.impl.provider.entity.InputStreamProvider
  com.sun.jersey.core.impl.provider.entity.DataSourceProvider
  com.sun.jersey.core.impl.provider.entity.XMLJAXBElementProvider$General
  com.sun.jersey.core.impl.provider.entity.ReaderProvider
  com.sun.jersey.core.impl.provider.entity.DocumentProvider
  com.sun.jersey.core.impl.provider.entity.SourceProvider$StreamSourceReader
  com.sun.jersey.core.impl.provider.entity.SourceProvider$SAXSourceReader
  com.sun.jersey.core.impl.provider.entity.SourceProvider$DOMSourceReader
  com.sun.jersey.json.impl.provider.entity.JSONJAXBElementProvider$General
  com.sun.jersey.core.impl.provider.entity.XMLRootElementProvider$General
  com.sun.jersey.core.impl.provider.entity.XMLListElementProvider$General
  com.sun.jersey.core.impl.provider.entity.XMLRootObjectProvider$General
  com.sun.jersey.core.impl.provider.entity.EntityHolderReader
  com.sun.jersey.json.impl.provider.entity.JSONRootElementProvider$General
  com.sun.jersey.json.impl.provider.entity.JSONListElementProvider$General
  com.sun.jersey.json.impl.provider.entity.JacksonProviderProxy
And at the client side you may get 415 status code :
com.sun.jersey.api.client.UniformInterfaceException: POST http://localhost:8082/application/upload returned a response status of 415


Post Comments And Suggestions !!