Article From:https://www.cnblogs.com/huangdabing/p/9219450.html

  For file uploading, in the process of uploading, the browser submits the file to the server in the form of stream. If you use Servlet directly to get the input stream of the uploaded file and then parse the request parameters in the inside, it is generally chosen to use the open source tool commo of Apache.N-fileupload this file upload component. This common-fileupload upload component’s jar package can be downloaded on the Apache website or under the Lib folder of struts. The function of struts uploads isBased on this implementation.common-fileuploadIs dependent oncommon-ioThis package, so you also need to download this package.

1. The construction of the development environment

  Create a FileUploadAndDownLoad project, add the relevant Jar package of the Apache commons-fileupload file upload component, as shown in the following figure:

  

Two. File uploading

  There are many small details to note in the file upload function. The following points need special attention.

  1、To ensure server security, uploaded files should be placed in directories that can not be directly accessed by the outside world, such as in the WEB-INF directory.

  2、To prevent the occurrence of file coverage, a unique filename is generated for uploading files.

  3、To prevent too many files below a directory, use the hash algorithm to scatter storage.

  4、Limit the maximum value of uploaded files.

  5、wantlimitThe type of uploaded file determines whether the suffix name is legal when the file name is uploaded.

2.1、File upload page and message prompt page

  upload.jspThe code of the page is as follows:

<%@ page language="java" pageEncoding="UTF-8"%>
<!DOCTYPE HTML>
<html>
  <head>
    <title>File upload</title>
  </head>
  
  <body>
    <form action="${pageContext.request.contextPath}/servlet/UploadHandleServlet" enctype="multipart/form-data" method="post">
        Uploading users:<input type="text" name="username"><br/>
        Upload file 1:<input type="file" name="file1"><br/>
        Upload file 2:<input type="file" name="file2"><br/>
        <input type="submit" value="Submission ">
    </form>
  </body>
</html>

message.jspThe code is as follows:

<%@ page language="java" pageEncoding="UTF-8"%>
<!DOCTYPE HTML>
<html>
  <head>
    <title>Message hints</title>
  </head>
  
  <body>
        ${message}
  </body>
</html>

2.2、Processing file uploaded Servlet

  UploadHandleServletThe code is as follows:

package com.web.controller;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.List;
import java.util.UUID;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadBase;
import org.apache.commons.fileupload.ProgressListener;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;

/**
* @ClassName: UploadHandleServlet
* @Description: TODO(Here is a word to describe the role of this class.*@author: hdb
* @date: 2017-11-13 14:35:50
*
*/ 
public class UploadHandleServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
                //Get the saved directory of uploaded files, store the uploaded files in the WEB-INF directory, do not allow direct access to the outside world, and ensure the security of uploaded files.
                String savePath = this.getServletContext().getRealPath("/WEB-INF/upload");
                //Temporary file save directory generated when Uploaded
                String tempPath = this.getServletContext().getRealPath("/WEB-INF/temp");
                File tmpFile = new File(tempPath);
                if (!tmpFile.exists()) {
                    //Create a temporary directory
                    tmpFile.mkdir();
                }
                
                //Message hints
                String message = "";
                try{
                    //Using Apache file upload component to process file upload steps://1、Create a DiskFileItemFactory factory
                    DiskFileItemFactory factory = new DiskFileItemFactory();
                    //Setting the size of the factory's buffer, when the size of the uploaded file exceeds the size of the buffer, a temporary file is generated in the specified temporary directory.
                    factory.setSizeThreshold(1024*100);//The size of the buffer is set to 100KB. If not specified, the size of the buffer is 10KB by default.//Set the save directory for temporary files generated when uploading.
                    factory.setRepository(tmpFile);
                    //2、Create a file upload parser
                    ServletFileUpload upload = new ServletFileUpload(factory);
                    //Monitor file upload progress
                    upload.setProgressListener(new ProgressListener(){
                        public void update(long pBytesRead, long pContentLength, int arg2) {
                            System.out.println("The file size is: + pContentLength +, which is currently processed: + pBytesRead);
                            /**
                             * The file size is: 14608, currently processed: 4096The file size is: 14608, currently processed: 7367The file size is: 14608, currently processed: 11419The file size is: 14608, currently processed: 14608                   */
                        }
                    });
                     //Chinese messy code to upload file names
                    upload.setHeaderEncoding("UTF-8"); 
                    //3、Determine whether the data submitted is uploaded form data.
                    if(!ServletFileUpload.isMultipartContent(request)){
                        //Getting data in a traditional way
                        return;
                    }
                    
                    //Set the maximum size for uploading a single file, which is currently set to 1024*1024 bytes, that is, 1MB.
                    upload.setFileSizeMax(1024*1024);
                    //The maximum value of the total upload file is set. The maximum value is the sum of the maximum size of multiple files uploaded at the same time, and is currently set to 10MB.
                    upload.setSizeMax(1024*1024*10);
                    //4、Using the ServletFileUpload parser to parse the uploaded data, the parse result is a List< FileItem> the collection, each FileItem corresponds to the input item of a Form form
                    List<FileItem> list = upload.parseRequest(request);
                    for(FileItem item : list){
                        //If fileitem encapsulates data from ordinary input items
                        if(item.isFormField()){
                            String name = item.getFieldName();
                            //Chinese garbled problem for data of ordinary input items
                            String value = item.getString("UTF-8");
                            //value = new String(value.getBytes("iso8859-1"),"UTF-8");
                            System.out.println(name + "=" + value);
                        }else{//If the file is encapsulated in fileitem, the file is uploaded.//Get the name of the uploaded file,
                            String filename = item.getName();
                            System.out.println(filename);
                            if(filename==null || filename.trim().equals("")){
                                continue;
                            }
                            //Note: the file names submitted by different browsers are different, and some browsers submit their filenames with paths, such as c:\a\b\1.txt, and some are simply filenames, such as 1.txt      //The path part of the file name of the uploaded file is processed, leaving only the file name part.
                            filename = filename.substring(filename.lastIndexOf("\\")+1);
                            //Get the extension name of the uploaded file
                            String fileExtName = filename.substring(filename.lastIndexOf(".")+1);
                            //If you need to restrict the type of uploaded file, you can decide whether the type of uploaded file is legal by extending the name of the file.
                            System.out.println("The extension of the uploaded file is: "+fileExtName);
                            //Get the input stream of the uploaded file in item
                            InputStream in = item.getInputStream();
                            //Get the name of the file saved
                            String saveFilename = makeFileName(filename);
                            //Get the saved directory of the file
                            String realSavePath = makePath(saveFilename, savePath);
                            //Create a file output stream
                            FileOutputStream out = new FileOutputStream(realSavePath + "\\" + saveFilename);
                            //Create a buffer
                            byte buffer[] = new byte[1024];
                            //Identifies whether the data in the input stream has been read out.
                            int len = 0;
                            //The loop reads the input stream into the buffer, (len=in.read (buffer)) > 0 means that there is data in in.
                            while((len=in.read(buffer))>0){
                                //Use the FileOutputStream output stream to write the buffer data to the specified directory (savePath + \ \ + + filename).
                                out.write(buffer, 0, len);
                            }
                            //Closing the input stream
                            in.close();
                            //Closing the output stream
                            out.close();
                            //Delete the temporary file generated when the processing file is uploaded//item.delete();
                            message = "File upload success! ";
                        }
                    }
                }catch (FileUploadBase.FileSizeLimitExceededException e) {
                    e.printStackTrace();
                    request.setAttribute("message", "A single file is beyond the maximum!!! ");
                    request.getRequestDispatcher("/message.jsp").forward(request, response);
                    return;
                }catch (FileUploadBase.SizeLimitExceededException e) {
                    e.printStackTrace();
                    request.setAttribute("message", "The total size of uploaded files exceeds the maximum limit!!! ");
                    request.getRequestDispatcher("/message.jsp").forward(request, response);
                    return;
                }catch (Exception e) {
                    message= "File upload failed! ";
                    e.printStackTrace();
                }
                request.setAttribute("message",message);
                request.getRequestDispatcher("/message.jsp").forward(request, response);
    }
    
    /**
    * @Method: makeFileName
    * @Description: The file name of the uploaded file is generated. The file name is: uuid+ "+" + the original name of the file.
    * @Anthor:hdb
    * @param filename The original name of the file*@return uuid+"_"+The original name of the file*/ 
    private String makeFileName(String filename){  //2.jpg
        //To prevent the occurrence of file coverage, a unique filename is generated for uploading files.
        return UUID.randomUUID().toString() + "_" + filename;
    }
    
    /**
     * To prevent too many files below a directory, use the hash algorithm to scatter storage.* @Method: makePath* @Description:* @Anthor:hdb**@param filename File name, to generate the storage directory based on the file name*@param savePath File storage path*@return New storage directory*/ 
    private String makePath(String filename,String savePath){
        //Gets the value of the hashCode of the file name, and gets the address of the filename string object in memory.
        int hashcode = filename.hashCode();
        int dir1 = hashcode&0xf;  //0--15
        int dir2 = (hashcode&0xf0)>>4;  //0-15
        //Constructing a new storage directory
        String dir = savePath + "\\" + dir1 + "\\" + dir2;  //upload\2\3  upload\3\5
        //FileIt can either represent a file or a directory
        File file = new File(dir);
        //If the directory does not exist
        if(!file.exists()){
            //Create a directory
            file.mkdirs();
        }
        return dir;
    }

    public void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {

        doGet(request, response);
    }
}

Register UploadHandleServlet in the Web.xml file:

<servlet>
    <servlet-name>UploadHandleServlet</servlet-name>
    <servlet-class>com.web.controller.UploadHandleServlet</servlet-class>
</servlet>

<servlet-mapping>
    <servlet-name>UploadHandleServlet</servlet-name>
    <url-pattern>/servlet/UploadHandleServlet</url-pattern>
</servlet-mapping>

The operation results are as follows:

   

  After the file upload is successful, the uploaded file is saved in the upload directory under the WEB-INF directory, as shown in the following figure:

  

Three, file downloading

3.1、List the file resources to provide Downloads

  We want to provide the file resources in the Web application system to the user for downloading. First, we have a page to list all the files under the file directory. When the user clicks the file to download the hyperlink, we do the downloading operation and write a ListFileServlet to list the WebAll downloaded files in the application system.

  ListFileServletThe code is as follows:

package com.web.controller;

import java.io.File;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
* @ClassName: ListFileServlet
* @Description: List all downloaded files in the Web system*@author: hdb
* @date: 2017-11-14 19:54:40
*
*/ 
public class ListFileServlet extends HttpServlet {

    public void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        //Get the directory of the uploaded file
        String uploadFilePath = this.getServletContext().getRealPath("/WEB-INF/upload");
        //File name to be downloaded
        Map<String,String> fileNameMap = new HashMap<String,String>();
        //Recursively traverses all files and directories in the filepath directory and stores the file name of the file in the map collection.
        listfile(new File(uploadFilePath),fileNameMap);//FileIt can represent a file or a directory.//Send the Map collection to the listfile.jsp page for display.
        request.setAttribute("fileNameMap", fileNameMap);
        request.getRequestDispatcher("/listfile.jsp").forward(request, response);
    }
    
    /**
    * @Method: listfile
    * @Description: Recursively traverse all files under the specified directory* @Anthor:hdb*@param file It represents a file and represents a file directory.*@param map Map collection for storing file names*/ 
    public void listfile(File file,Map<String,String> map){
        //If file is not a file, it is a directory.
        if(!file.isFile()){
            //List all the files and directories under this directory
            File files[] = file.listFiles();
            //Traversing the files[] array
            for(File f : files){
                //recursion
                listfile(f,map);
            }
        }else{
            /**
             * The name of the file is processed, and the uploaded file is renamed in the form of the uuid_ file name, removing the uuid_ part of the file name.File.getName ().IndexOf ("") retrieves the first occurrence of the string.The location of the "character" character, if the file name is similar to: 9349249849-88343-8344_,.AviThen file.getName ().Substring (file.geAfter processing tName ().IndexOf ("+1") +1, we can get the.Avi part of ah fan van da.*/
            String realName = file.getName().substring(file.getName().indexOf("_")+1);
            //file.getName()The original name of the file is obtained. This name is unique, so it can be used as key. RealName is the name after processing. It may be duplicated.
            map.put(file.getName(), realName);
        }
    }
    
    public void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        doGet(request, response);
    }
}

Here’s a brief description of the LISTFILE method in ListFileServlet. The LISTFILE method is used to list all the files under the directory, and the LISTFILE method uses recursion. In the actual development, we are sure to create a table in the database.It will store the uploaded file name and the specific storage directory of the file. We can know the specific storage directory of the file through the query table. It does not need to use the recursive operation. This example is because the file name and the file store location are not used in the database storage, and the storage location of the file is uploaded.It also uses the hash algorithm to scatter storage, so it is necessary to use recursion. When recursion, the obtained file name is stored from the outside to the Map set in the LISTFILE method, so that all the files can be kept in the same Map set.

  Configure ListFileServlet in the Web.xml file:

<servlet>
     <servlet-name>ListFileServlet</servlet-name>
     <servlet-class>com.web.controller.ListFileServlet</servlet-class>
</servlet>
 
<servlet-mapping>
     <servlet-name>ListFileServlet</servlet-name>
    <url-pattern>/servlet/ListFileServlet</url-pattern>
</servlet-mapping>

The listfile.jsp page that displays the download file is as follows:

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE HTML>
<html>
  <head>
    <title>Download the file display page</title>
  </head>
  
  <body>
      <!-- Traversing the Map set-->
    <c:forEach var="me" items="${fileNameMap}">
        <c:url value="/servlet/DownLoadServlet" var="downurl">
            <c:param name="filename" value="${me.key}"></c:param>
        </c:url>
        ${me.value}<a href="${downurl}">download</a>
        <br/>
    </c:forEach>
  </body>
</html>

When you visit ListFileServlet, you can display the file resources provided to the user in the listfile.jsp page, as shown in the following figure:

  

3.2、Implement file download

  Write a Servlet file for downloading files. The code for DownLoadServlet is as follows:

package com.web.controller;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.URLEncoder;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class DownLoadServlet extends HttpServlet {

    
    public void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        //Get the file name to be downloadedStringfileName = request.getParameter("filename");  //23239283-92489-Avatar.AvifileName = new String(fileName.getBytes("iso8859-1"),"UTF-8");
        //The uploaded files are saved in the subdirectory under the /WEB-INF/upload directory.StringfileSaveRootPath=this.getServletContext().getRealPath("/WEB-INF/upload");
        //Find the directory of the file by the name of the fileStringpath = findFileSavePathByFileName(fileName,fileSaveRootPath);
        //Get the files to be downloadedFile file = new File (path + "\ \" + fileName);/ / if the file does not existIf (! File.ex)Ists ()) {Request.setAttribute ("message", "the resources you want to download have been deleted!! ");Request.getRequesTDispatcher ("/message.jsp").Forward (request, response);Return;}/ / processing filenameString realName = fileName.substring (fileName.indexOf ("+1"));/ / / set the response header, the browser downloads the file        response.setHeader("content-disposition", "attachment;filename=" + URLEncoder.encode(realname, "UTF-8"));
        //Read the file that you want to download and save it to the file input stream.FileInputStream in = new FileInputStream (path + \ "+ fileName);/ / create output streamOutputStream out = response.getOutputStream ();/ / create a bufferByte buffer[]= new byte[1024];Int len = 0;/ / loop reads the contents of the input stream into the buffer.While ((len=in.read (buff)Er)) > 0) {/ / output the contents of the buffer to the browser, and download the files.Out.write (buffer, 0, len);}/ / close the file input streamIn.close ();/ / close out the output streamOut.close ();}/ * * * * ** @MethOd: findFileSavePathByFileName* @Description:Find the location of the file to download by storing the file name and storing the root directory of the uploaded file.
    * @Anthor:hdb
    * @param filename File name to be downloaded* @param saveRootPath saves the root directory of the uploaded file, that is, the /WEB-INF/upload directory.* the storage directory of the file to be downloaded by @return* * /Public StringfindFileSavePathByFileName(String filename,String saveRootPath){
        int hashcode = filename.hashCode();
        int dir1 = hashcode&0xf;  //0--15
        int dir2 = (hashcode&0xf0)>>4;  //0-15
        String dir = saveRootPath + "\\" + dir1 + "\\" + dir2;  //upload\2\3  upload\3\5
        File file = new File(dir);
        if(!file.exists()){
            //Create a directoryFile.mkdirs ();}Return dir;}Public void doPost (HttpServletRequest request, HttpServletResponse response)Throws ServletException, IOExceptiOn {DoGet (request, response);}}

Configure DownLoadServlet in the Web.xml file:

<servlet>
      <servlet-name>DownLoadServlet</servlet-name>
      <servlet-class>com.web.controller.DownLoadServlet</servlet-class>
</servlet>
 
<servlet-mapping>
      <servlet-name>DownLoadServlet</servlet-name>
      <url-pattern>/servlet/DownLoadServlet</url-pattern>
</servlet-mapping>

Click on the hyperlink, submit the request to DownLoadServlet, and then download the file.

  

  From the running result, we can see that our file download function has been able to download the files normally.

Leave a Reply

Your email address will not be published. Required fields are marked *