Building RESTful web services for storing images

Let's build a REST API to store the image sent by the client. We will start with the client and then move on to the server-side implementation.

This example uses an HTML client to upload images to the REST API. When you make a POST request to the server, you have to encode the data that forms the body of the request. You can use the multipart/form-data encoding to deal with a large binary object uploaded via <input type="file">. The client-side HTML code may look like the following:

<html> 
  <head> 
   <title>File upload</title> 
   <meta charset="UTF-8"> 
  </head> 
  <body> 
   <form action="employees/100/image"  
     method="post" enctype="multipart/form-data"> 
     Choose photo for employee# 100 :  
     <input type="file" name="empImgFile" /> 
     <br> 
     <input type="submit" value="Upload Image" /> 
   </form> 
  </body> 
</html> 

This HTML client uploads images for an employee identified by id=100. The RESTful web API for storing images is located at the employees/100/image URI. The client code for uploading an image to the RESTful web API is in place now.

As the next step, we will build a RESTful web API that accepts an uploaded image and stores it in a database. Jersey makes it simple by offering many binding annotations for method parameters to extract the desired value from the request body. For instance, it offers the @org.glassfish.jersey.media.multipart.FormDataParam annotation, which can be used for binding the named body parts of a multipart/form-data request body to a method parameter or a class member variable, as appropriate. We will use this annotation in conjunction with the request content encoded with multipart/form-data for consuming forms that contain files, non-ASCII data, and binary data. Jersey allows you to inject @FormDataParam onto the following parameter types:

  • Any type of parameter for which a message body reader is available: The following example binds an input stream present in the first named body part, empImageFile, with an inputStream object: @FormDataParam("empImgFile") InputStream inputStream.
  • org.glassfish.jersey.media.multipart.FormDataBodyPart: This object can be used for reading the value of a parameter that represents the first named body part present in the request body. You can also use List or Collection of FormDataBodyPart to read the values of multiple body parts with the same name. An example is @FormDataParam("p1") List<FormDataBodyPart> values.
  • org.glassfish.jersey.media.multipart.FormDataContentDisposition: This represents the form-data content disposition header in the incoming payload. You can use it for retrieving details about the uploaded file, such as its name and size.

When you use @FormDataParam on a field, the entity provider will inject content from the incoming message body to the annotated fields, as appropriate.

The following code snippet demonstrates how you can use @FormDataParam for building a REST API that reads an image uploaded by a client. Note that the name parameter set for @FormDataParam(...) must match with the file input component present in the request payload. In this example, we name the input file component empImgFile in the HTML, <input type="file" name="empImgFile" />. You must use the same name as the parameter for @FormDataParam("empImgFile") to read the uploaded file content present in the payload posted to the server. This example uses JPA to persist the data:

//Other imports are not shown for brevity 
import org.glassfish.jersey.media.multipart. 
           FormDataContentDisposition; 
import org.glassfish.jersey.media.multipart.FormDataParam; 
  
@Stateless 
@Path("employees") 
public class EmployeeResource { 
   //Name of the persistence unit from persistence.xml  
   @PersistenceContext(unitName = "EMP_PU") 
   private EntityManager entityManager; 
 
   @POST 
   @Path("{empId}/image") 
   @Consumes(MediaType.MULTIPART_FORM_DATA) 
   public void uploadImage(@Context HttpServletRequest request,  
       @FormDataParam("empImgFile") InputStream in, 
      @FormDataParam("empImgFile") FormDataContentDisposition 
       fileDetail,  
      @PathParam("empId") Integer empId) throws Exception { 
 
      try(ByteArrayOutputStream bos = new ByteArrayOutputStream()) 
{ int size = request.getContentLength(); byte[] buffer = new byte[size]; int len=0; while ((len = in.read(buffer, 0, 10240)) != -1) { bos.write(buffer, 0, len); } byte[] imgBytes = bos.toByteArray(); //Pass the image to underlying entity //to persist the content EmployeeImage empImg = findEmployeeImageEntity(empId); empImg.setImage(imgBytes); entityManager.merge(empImg);
} } //Other methods are not shown for brevity }

Before ending this section on REST support for handling binary files, let's take a quick look at the code snippet for reading binary files (or images) as well.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.191.235.62