September 1, 2014
Hot Topics:
RSS RSS feed Download our iPhone app

5 Leading Java File Upload Solutions, Page 2

  • April 25, 2012
  • By Constantin Marian Alin
  • Send Email »
  • More Articles »

Java Upload with GWTUpload

Another way to upload files is using the GWTUpload upload library. GWTUpload is a library for uploading files to Web servers; it can display a progress bar that displays the upload status. In addition, you can get the size of the uploaded file, the original filename in the client's filesystem, the content type passed by the browser, the bytes transferred, and so on.

Java Upload

GWTUpload has two components:

  1. the server side, written in Java with servlet and utility classes
  2. the client side, written in JavaScript using GWT

The following bullets characterize this upload mechanism:

  • the server side could be implemented in any language
  • the client side can be used from GWT applications, or from JavaScript without knowing GWT
  • ability to upload single and multiple files
  • ability to customize the progress bar or implement another one
  • ability to customize the choose button
  • easy to use

This upload uses JDK 6 and can be easily tested under the Tomcat 6 container. The libraries used include:

In this section, you will develop an application using GWTUpload based on the simplest scenario. A user selects a file from his computer, uploads the file and gets basic feedback about the uploaded file.

First, on the client side, I have a basic HTML upload form in the index.html page, which you have probably seen many times:


...
  <form enctype="multipart/form-data" action="./gwt_upload"   
    method="POST"> 
    File to be uploaded : 
    <input type="file" name="userfile">
    <br>
    <input type="submit" value="Upload">
  </form>
...

The next step is to configure the application descriptor file (web.xml):


<!DOCTYPE web-app PUBLIC "-//Sun Microsystems, Inc.//DTD Web Application 2.2//EN" "http://java.sun.com/j2ee/dtds/web-app_2_2.dtd">

<web-app>

    <display-name>Numele aplicatiei</display-name>

    <context-param>
     <param-name>maxSize</param-name>
     <param-value>3145728</param-value>
    </context-param>
    <context-param>
     <param-name>slowUploads</param-name>
     <param-value>200</param-value>
    </context-param>

  <servlet>
    <servlet-name>uploadServlet</servlet-name>    
    <servlet-class>com.extensions.GWTUploadServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>uploadServlet</servlet-name>
    <url-pattern>/gwt_upload</url-pattern>
  </servlet-mapping>

</web-app>

As you can see, I have configured the maximum size of the upload request:


...    
    <context-param>
     <param-name>maxSize</param-name>
     <param-value>3145728</param-value>
    </context-param>
...

If you are working in development mode, it is useful to slow down the uploads in fast networks by putting the number of milliseconds to sleep in each block received in the server, or you can use false or 0 if you don't want to use slow uploads:


...    
    <context-param>
     <param-name>slowUploads</param-name>
     <param-value>200</param-value>
    </context-param>
...

On the client side, when a user clicks on the upload button, the action attribute of the form field calls a Java servlet that is able to deal with HTTP requests. On the server side, in the GWTUploadServlet.java servlet, the first thing I have to do is to maintain a list with the received files and their content types. We can do this with just a few lines:


...
public class GWTUploadServlet extends UploadAction {

  private static final long serialVersionUID = 1L;
  Hashtable<String, String> receivedContentTypes = new Hashtable<String, String>();
  Hashtable<String, File> receivedFiles = new Hashtable<String, File>();
...

The next step is to override the executeAction method to save the received files in a custom place and then delete these items from the session. Each item type is determined by calling the isFormField boolean method. Once you know the item type, you can choose how you process it forward:


...
  @Override
  public String executeAction(HttpServletRequest request, List<FileItem> sessionFiles) throws UploadActionException {
    String response = "";
    int cont = 0;
    for (FileItem item : sessionFiles) {
      if (false == item.isFormField()) {
        cont ++;
        try {
          /// Create a new file based on the remote file name in the client
          // String saveName = item.getName().replaceAll("[\\\\/><\\|\\s\"'{}()\\[\\]]+", "_");
          File file =new File(request.getRealPath("//WEB-INF//files") + "//" + item.getName());
          
          /// Create a temporary file placed in /tmp (only works in unix)
          // File file = File.createTempFile("upload-", ".bin", new File("/tmp"));
          
          /// Create a temporary file placed in the default system temp folder
          //File file = File.createTempFile("upload-", ".bin");
          item.write(file);
          
          /// Save a list with the received files
          receivedFiles.put(item.getFieldName(), file);
          receivedContentTypes.put(item.getFieldName(), item.getContentType());
          
          /// Compose a xml message with the full file information which can be parsed in client side
          response += "<file-" + cont + "-field>" + item.getFieldName() + "</file-" + cont + "-field>\n";
          response += "<file-" + cont + "-name>" + item.getName() + "</file-" + cont + "-name>\n";
          response += "<file-" + cont + "-size>" + item.getSize() + "</file-" + cont + "-size>\n";
          response += "<file-" + cont + "-type>" + item.getContentType()+ "</file-" + cont + "type>\n";
        } catch (Exception e) {
          throw new UploadActionException(e);
        }
      }
    }
    
    /// Remove files from session because I have a copy of them
    removeSessionFileItems(request);
    
    /// Send information of the received files to the client.
    return "<response>\n" + response + "</response>\n";
  }
...

Now, if I want to get the content of an uploaded file, I need to override the getUploadedFile method:


...
  @Override
  public void getUploadedFile(HttpServletRequest request, HttpServletResponse response) throws IOException {
    String fieldName = request.getParameter(PARAM_SHOW);
    File f = receivedFiles.get(fieldName);
    if (f != null) {
      response.setContentType(receivedContentTypes.get(fieldName));
      FileInputStream is = new FileInputStream(f);
      copyFromInputStreamToOutputStream(is, response.getOutputStream());
    } else {
      renderXmlResponse(request, response, ERROR_ITEM_NOT_FOUND);
   }
  }
...  

Finally, remove a file when the user sends a delete request:


...
  @Override
  public void removeItem(HttpServletRequest request, String fieldName)  throws UploadActionException {
    File file = receivedFiles.get(fieldName);
    receivedFiles.remove(fieldName);
    receivedContentTypes.remove(fieldName);
    if (file != null) {
      file.delete();
    }
  }
}

The result of this application is shown below:

Java Upload

Java Upload with JUpload Applet

JUpload is a Java applet used for uploading files to Web servers using the standard HTTP POST command, or in FTP mode JUpload can directly write the file on the target server. It supports multiple-file uploading using a nice, easy-to-use design, and it has a lot of configuration parameters that allow for easy adaptation to your specific needs.

JUpload provides seven main features:

  • File progress bar
  • Error checking
  • Easy selection and upload of multiple files
  • FTP and HTTP (POST) capabilities
  • Multilingual: more than 20 languages
  • Control of allowed file extension
  • Picture management (resizing, rotation, format change)

To start, you must download the JUpload stable release from the project page. In the download section, you will find a link to the project download page. (At the time of writing, the JUpload stable version was jupload-5.0.7-src-5.0.7.zip.) The applet is mapped under wjhk.jupload.jar. This can be found under the /site directory. You need to copy this archive under your project root.

The applet is customizable through a set of parameters. Here are just some of these parameters:

  • afterUploadTarget: allows you to select a specific target frame when redirecting to afterUploadURL
  • afterUploadURL: allows the applet to change the current page to another one after a successful upload
  • allowedFileExtensions: allows the caller to specify a list of file extensions
  • debugLevel: The normal production output is 0. The higher the number is, the more information is displayed in the log window.
  • fileChooserIconSize: allows you to control the size of icons, in pixels, in the file chooser
  • fileChooserImagePreview: allows you to control whether a preview is available for the picture in the file chooser
  • ftpCreateDirectoryStructure: allows you to control whether the directory structure on the client side must be created on the server side
  • ftpTransfertBinary: allows you to control whether the upload should be done in binary or ASCII mode
  • ftpTransfertPassive: allows you to control whether the upload should be done in FTP passive mode, or in active mode (where the FTP server opens a connection to the client, to do the upload)
  • maxChunkSize: defines the maximum size of an upload
  • maxFileSize: identifies the maximum size that an uploaded file may have
  • postURL: specifies the target URL toward which the files should be uploaded
  • showStatusBar: controls if the status bar is shown in the applet. If shown, the status bar provides information about the current transfer speed and estimated time of completion.
  • uploadPolicy: contains the class name for the UploadPolicy that should be used

The JUpload applet has many parameters. For more details, visit this page.

Depending on the list of parameters added, the JUpload applet can be configurated in two modes: a basic mode and a picture mode. Below, you can see a possible basic mode applet configuration:


. . .
  <applet
        code="wjhk.jupload2.JUploadApplet"
        name="JUpload"
        archive="./applet/wjhk.jupload.jar"
        width="640"
        height="300"
        mayscript="true"
        alt="The java pugin must be installed.">           
        <param name="postURL" value="./oreilly_upload" />            
        <param name="showLogWindow" value="false" />            
  </applet>
. . .

The picture mode adds some nice and useful capabilities using another existing UploadPolicy, the PictureUploadPolicy:

  • browse files with picture preview, in the file chooser.
  • rotate pictures, quarter by quarter.
  • resize picture, according to a maximum allowed height and/or width
  • change the file format (for instance .gif to .png)
  • send (or not) the picture metadata
  • preview pictures, from the 'file to upload' list

Below, you can see a possible picture mode applet configuration:


. . .
  <applet code="wjhk.jupload2.JUploadApplet"
          archive="./applet/wjhk.jupload.jar" width="640" height="400" alt="The java pugin must be installed."
          mayscript="true">
          <param name="postURL" value="./oreilly_upload" />
          <param name="maxChunkSize" value="500000" />
          <param name="uploadPolicy" value="PictureUploadPolicy" />
          <param name="nbFilesPerRequest" value="1" />
          <param name="maxPicHeight" value="900" />
          <param name="maxPicWidth" value="700" />
          <param name="debugLevel" value="0" />
          <param name="showLogWindow" value="false" />
          Java 1.5 or higher plugin required. 
   </applet>
. . .

By providing the <uploadPolicy> parameter within the APPLET tag, you can select another class that implements the UploadPolicy interface found at the UploadPolicy page.

On the official JUpload project site, you can find more details about how to customize the JUpload applet, choose the best UploadPolicy for you, or if those customizations are not enough, create a new Java Upload Policy.

For this application (on the server side) you can use the COS described in COS and SWFUpload for End-to-end Java File Upload. The COS implementation for JUpload is:


protected void processRequest(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {        
     
   final int permitedSize = 314572800;  //~ 300 MB in bytes
                
   PrintWriter out = response.getWriter();
   response.setContentType("text/html;charset=UTF-8");
   response.setHeader("Cache-Control", "no-cache");
   response.setHeader("Pragma", "No-cache");
   response.setDateHeader("Expires",0);                       
    
    try{               
       String type = "";
       String name = "";
       String originalFilename = "";
       String extension1 = "";
       String extension2 = "";
       String filename = "";

       String strDirectory = "files";
       String uploadPath = request.getRealPath("//WEB-INF//"+strDirectory+"//");

       //the path can also be specified in the web.xml and from there it can be extracted like this
       String uploadPath_2 = request.getRealPath(getServletConfig().getInitParameter("uploadPath"));

       //constructs a new MultipartRequest to handle the specified request
       MultipartRequest multipartRequest = new MultipartRequest(request, uploadPath, permitedSize, "ISO-8859-1", new DefaultFileRenamePolicy()); 
          
       //extract the uploaded files as an Enumeration
       Enumeration files = multipartRequest.getFileNames();               
          
          //getting a few details about each uploaded file    
          while (files.hasMoreElements()) 
              { 
                 name = (String)files.nextElement();
                 type = multipartRequest.getContentType(name); 
                 filename = multipartRequest.getFilesystemName(name); 
                 originalFilename = multipartRequest.getOriginalFileName(name);                 
                 
                 //extract the file extension - this can be use to reject a undesired file extension                      

                 extension1 = filename.substring(filename.length() - 4, filename.length());
                 extension2 = originalFilename.substring(originalFilename.length() - 4, originalFilename.length());

                 //return a File object for the specified uploaded file                   
                 File currentFile = multipartRequest.getFile(name);
                 //InputStream inputStream = new BufferedInputStream(new FileInputStream(currentFile));
                 if(currentFile == null) {
                      out.println("ERROR: There is no file selected!\n");
                      return;
                    }

                 //checking the file extensions according to the MIME types
                 if((type.equals("text/plain") || type.equals("image/gif") || type.equals("image/pjpeg")
                   || type.equals("image/x-png") || type.equals("image/jpeg"))) {       
                     //show a few details about the uploaded file                                           
                   } else {
                          //the file has a different extension, reject it!
                          //you have to write a code snippet to delete this file!!!
                          out.println("ERROR: Wrong file type!\n");
                          }

                 out.println("SUCCESS\n");         
                 }                        

       }catch (Exception exception)
          {                         
       response.sendError(response.SC_METHOD_NOT_ALLOWED);
       } finally { if(out != null) {out.close();} }         
}  

The JUpload applet can test if the server has detected an error in the upload progress. In other words, the applet will find an error if at least one line returned in the server response begins with "ERROR: " as shown below:


out.println("ERROR: Wrong file type!\n");

The applet will display this message to the user using an alert box:

Java Upload

If everything goes well and the server accepts the upload, the applet will receive a "success" message:

out.println("SUCCESS\n");

The result of this application is shown below:

  1. Basic mode applet

    Java Upload

  2. Picture mode applet

    Java Upload

Conclusion

In this article, you have seen a set of five upload solutions for Java Web applications:

  • YUI Uploader
  • GWTUpload
  • Postlet Applet
  • JUpload Applet
  • PrimeFaces upload

All these upload components bring very useful facilities for Java Web developers.


Tags: Java, upload files

Originally published on http://www.developer.com.

Page 2 of 2



Comment and Contribute

 


(Maximum characters: 1200). You have characters left.

 

 


Sitemap | Contact Us

Rocket Fuel