程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> JAVA編程 >> 關於JAVA >> java文件上傳技巧深刻分析

java文件上傳技巧深刻分析

編輯:關於JAVA

java文件上傳技巧深刻分析。本站提示廣大學習愛好者:(java文件上傳技巧深刻分析)文章只能為提供參考,不一定能成為您想要的結果。以下是java文件上傳技巧深刻分析正文


本文實例為年夜家分享了java文件上傳技巧,供年夜家參考,詳細內容以下

表單:
客戶端發送HTTP必需應用multipart/form-data數據類型,表現復合數據類型。即:
在表單中應用html標簽。

須要的包:
        Commons-fileupload.jar,焦點上傳文件對象都在這個包中。
        commons-io.jar – 上傳文件所須要的包

上傳文件類詳解:
DiskFileItemFactory-創立監時文件目次,指是緩存區年夜小
ServletFileUpload用於解析HttpServletRequest。前往一組文件對象。
FileItem – 表現用戶上傳的每個文件對像。

<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
 <head>

  <title>文件上傳演示</title>
 </head>

 <body>
  <font color="red" size="6">過渡板--懂得底層</font>
  <!-- multipart/form-data:多部門(不只有文件,也有部門) -->
  <form action="<%=request.getContextPath()%>/upload0" method="post" enctype="multipart/form-data">
    文件:<input type="file" name="file"/>
    <input type="submit" value="上傳"/> 
    <!-- 上傳的文件名不克不及為中文,不然獲得的文件名是亂碼,不外上面的例子可以處理這個成績 -->  
  </form>
  <br/>


  <font color="red" size="6">應用apache文件上傳對象完成文件上傳</font>
  <!-- application/x-www-form-urlencoded -->
  <form action="<%=request.getContextPath()%>/upload" method="post" enctype="multipart/form-data">
    文件:<input type="file" name="file"/>
    <input type="submit" value="上傳"/>  
  </form>


  <font color="red" size="6">應用apache文件上傳對象完成文件上傳2(處理文件名亂碼)</font>
  <p>
  POST1(通俗表單):enctype=application/x-www-form-urlencoded(默許值)
  </p>
  <p>
  POST2(上傳文件表單):enctype=multipart/form-data:多部門(不只有文件,也有部門)
  </p>
  <form action="<%=request.getContextPath()%>/upload2" method="post" enctype="multipart/form-data">
    文件:<input type="file" name="file"/><!-- POST2(上傳文件表單) --><br/>
    文件解釋:<input type="text" name="desc"/><!-- POST1(通俗表單) --><br/><br/>
    文件2:<input type="file" name="file"/><br/>
    文件解釋2:<input type="text" name="desc"/>
    <input type="submit" value="上傳"/>  
  </form>
  <font color="red" size="6">應用apache文件上傳對象完成文件上傳3(文件打散)</font>
  <!-- POST1(通俗表單):enctype=application/x-www-form-urlencoded(默許值) -->
  <!-- POST2(上傳文件表單):enctype=multipart/form-data:多部門(不只有文件,也有部門) -->
  <form action="<%=request.getContextPath()%>/upload3" method="post" enctype="multipart/form-data">
    文件:<input type="file" name="file"/><!-- POST2(上傳文件表單) --><br/>
    文件解釋:<input type="text" name="desc"/><!-- POST1(通俗表單) --><br/><br/>
    文件2:<input type="file" name="file"/><br/>
    文件解釋2:<input type="text" name="desc"/>
    <input type="submit" value="上傳"/>  
  </form>
 </body>
</html>

過渡板–懂得底層

package cn.hncu.servlet;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class Upload0Servlet extends HttpServlet {


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

    InputStream in=request.getInputStream();
    BufferedReader br=new BufferedReader(new InputStreamReader(in));
    String line;
    while((line=br.readLine())!=null){
      System.out.println(line);
    }
  }

}

應用apache文件上傳對象完成文件上傳

package cn.hncu.servlet;

import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
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.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.io.FileUtils;

public class UploadServlet extends HttpServlet {

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

    response.setContentType("text/html");
    PrintWriter out = response.getWriter();
    out.println("<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\">");
    out.println("<HTML>");
    out.println(" <HEAD><TITLE>A Servlet</TITLE></HEAD>");
    out.println(" <BODY>");
    out.print("不支撐Get方法上傳。。。。。。");
    out.println(" </BODY>");
    out.println("</HTML>");
    out.flush();
    out.close();
  }

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

        //在辦事器上,為一切上傳文件指定一個寄存目次
    String path=getServletContext().getRealPath("/upload");
    System.out.println("path:"+path);
    File dir=new File(path);
    if(!dir.exists()){
      dir.mkdirs();
    }

    //創立一個基於硬盤的工場
    //DiskFileItemFactory disk = new DiskFileItemFactory();
    //設置暫時目次(建議設計暫時目次,不然會應用體系暫時目次。)
    //disk.setRepository(new File(“d:/a”));
    //3、 設置向硬盤寫數據的緩沖區年夜小
disk.setSizeThreshold(1024*4);//當文件年夜於此設置時,將會在暫時目次下構成暫時文件


    //設置暫時文件緩沖區年夜小--8K緩沖,暫時文件地址
    DiskFileItemFactory f=new DiskFileItemFactory(1024*8, new File("d:/a"));
    //上傳對象--創立用於解析的對像
    ServletFileUpload upload=new ServletFileUpload(f);
    upload.setFileSizeMax(1024*1024*5);//設置上傳的單個文件最年夜為5M
    //設置上傳文件的最年夜年夜小,假如是多個文件,則為多個文件的和最年夜8M
    upload.setSizeMax(1024*1024*8);//設置一切上傳的文件年夜小之和最年夜為8M
    //應用解析對象解析
    try {
      List<FileItem> list=upload.parseRequest(request);
      for(FileItem fI:list){
        System.out.println("文件內容類型:"+fI.getContentType());//文件內容類型:text/plain
        System.out.println("文件名:"+fI.getName());//文件名:C:\Users\adl1\Desktop\a.txt
        String ext=fI.getName().substring(fI.getName().lastIndexOf("."));//.txt
        String uuid=UUID.randomUUID().toString().replace("-", "");
        String fileName=uuid+ext;
//       FileUtils.copyInputStreamToFile(fI.getInputStream(), new File("d:/a/d/a.txt"));//寫逝世了
        //fI.getInputStream()是真注釋件信息
        FileUtils.copyInputStreamToFile(fI.getInputStream(), new File(path+"/"+fileName));//寫活了
      }
    } catch (FileUploadException e) {
      e.printStackTrace();
    }


  }

}

在這個處所存儲上傳的文件


上傳信息:


上傳成果:

應用apache文件上傳對象完成文件上傳2(處理文件名亂碼)

package cn.hncu.servlet;

import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
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.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.io.FileUtils;

public class Upload2Servlet extends HttpServlet {

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


    response.setContentType("text/html");
    //假如是含上傳文件的表單(POST2),該劇只能設置所上傳文件的文件名中的編碼(處理他的中文亂碼)
    //但不克不及處理在POST2方法下的通俗表單組件的中文亂碼
    PrintWriter out = response.getWriter();
    out.println("<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\">");
    out.println("<HTML>");
    out.println(" <HEAD><TITLE>A Servlet</TITLE></HEAD>");
    out.println(" <BODY>");
    out.print("不支撐Get方法上傳。。。。。。");
    out.println(" </BODY>");
    out.println("</HTML>");
    out.flush();
    out.close();
  }

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

    //第一步
    //通俗的form表單(POST1),上面這句可以設置通俗表單組件內容的編碼(可以或許處理它們的中文亂碼成績)
    request.setCharacterEncoding("utf-8");
    //假如是含上傳文件的表單(POST2),該句只能設置所上傳文件的文件名中的編碼(處理它的中文亂碼)。但不克不及處理通俗表單組件的亂碼(不克不及設它編碼)


    //在辦事器上,為一切上傳文件指定一個寄存目次
    String path=getServletContext().getRealPath("/upload");
    System.out.println("path:"+path);
    File dir=new File(path);
    if(!dir.exists()){
      dir.mkdirs();
    }


    //設置暫時文件緩沖區年夜小--8K緩沖,暫時文件地址
    DiskFileItemFactory f=new DiskFileItemFactory(1024*8, new File("d:/a"));
    //上傳對象
    ServletFileUpload upload=new ServletFileUpload(f);
    upload.setFileSizeMax(1024*1024*5);//設置上傳的單個文件最年夜為5M
    upload.setSizeMax(1024*1024*8);//設置一切上傳的文件年夜小之和最年夜為8M
    //應用解析對象解析
    try {
      List<FileItem> list=upload.parseRequest(request);
      for(FileItem fI:list){
        if((fI.isFormField())){//假如是通俗表單組件:checkbox,radio,password...
//         String desc=fI.getString();
          System.out.println("fI.getString():"+fI.getString());
          //第二步
          String desc=fI.getString("utf-8");
          //該句設置通俗表單組件內容編碼
          System.out.println("編碼後:"+desc);
        }else{
          String ext=fI.getName().substring(fI.getName().lastIndexOf("."));//.txt
          String uuid=UUID.randomUUID().toString().replace("-", "");
          String fileName=uuid+ext;
          //fI.getInputStream()是真注釋件信息
          FileUtils.copyInputStreamToFile(fI.getInputStream(), new File(path+"/"+fileName));//寫活了
        }
      }
    } catch (FileUploadException e) {
      e.printStackTrace();
    }
  }
}

上傳信息:

上傳成果:
 

應用apache文件上傳對象完成文件上傳3(文件打散)

用Hash目次優化文件存儲:
Hash目次是一種優化文件存儲機能的辦法。不管是Windows照樣Linux,不管是NTFS照樣ext3,每一個目次下所能包容的項目數是無限的。
其實不是不克不及保留,而是當項目數目過年夜的時刻,會下降文件索引速度,
所以衡量一個目次下應當保留若干文件是很需要的。保留很多了會影響機能,保留得少了會形成目次太多和空間糟蹋。所以當保留年夜批文件的時刻,
須要有一種算法能將文件比擬平均地“打散”在分歧的子目次下以進步每級的索引速度,這類算法就是 Hash。平日用的MD5、sha1等都可以用來做Hash目次,我的Session裡也異樣應用了MD5,獲得sessionID的第一名和第九位,這就組成了兩級Hash途徑,也就是說,體系把一切的Session文件疏散到了16×16=256個子目次下。假定Linux每一個目次下保留1000個文件可以取得最好的空間機能比,那末體系在幻想情形下可以同時有256000個session文件在被應用。

package cn.hncu.servlet;

import java.io.File;
import java.io.IOException;
import java.io.PrintWriter;
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.FileUploadException;
import org.apache.commons.fileupload.ProgressListener;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.commons.io.FileUtils;

public class Upload3Servlet extends HttpServlet {

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


    response.setContentType("text/html");
    //假如是含上傳文件的表單(POST2),該劇只能設置所上傳文件的文件名中的編碼(處理他的中文亂碼)
    //但不克不及處理在POST2方法下的通俗表單組件的中文亂碼
    PrintWriter out = response.getWriter();
    out.println("<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\">");
    out.println("<HTML>");
    out.println(" <HEAD><TITLE>A Servlet</TITLE></HEAD>");
    out.println(" <BODY>");
    //獲得GET方法的url中“?”號前面的部門
    //http://localhost:8080/servletDemo3/upload?name=Jack&sex=male
    String qStr = request.getQueryString();
    System.out.println("qStr: "+qStr);//qStr: name=Jack&sex=male
    out.print("不支撐Get方法上傳。。。。。。");
    out.println(" </BODY>");
    out.println("</HTML>");
    out.flush();
    out.close();
  }

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

    response.setContentType("text/html;charset=utf-8");
    PrintWriter out = response.getWriter();
    //1防黑: 防護前端采取POST1方法提交
    //法1
    /*
    String type=request.getContentType();
    if(!type.contains("multipart/form-data")){
      out.println("不支撐通俗表單提交");
      return;
    }*/
    //法2
    boolean boo = ServletFileUpload.isMultipartContent(request);
    if(!boo){
      out.println("不支撐通俗表單提交");
      return;
    }

    //第一步
    //通俗的form表單(POST1),上面這句可以設置通俗表單組件內容的編碼(可以或許處理它們的中文亂碼成績)
    request.setCharacterEncoding("utf-8");
    //假如是含上傳文件的表單(POST2),該句只能設置所上傳文件的文件名中的編碼(處理它的中文亂碼)。但不克不及處理通俗表單組件的亂碼(不克不及設它編碼)


    //在辦事器上,為一切上傳文件指定一個寄存目次
    String path=getServletContext().getRealPath("/upload");
    System.out.println("path:"+path);
    File dir=new File(path);
    if(!dir.exists()){
      dir.mkdirs();
    }


    //設置暫時文件緩沖區年夜小--8K緩沖,暫時文件地址
    DiskFileItemFactory f=new DiskFileItemFactory(1024*8, new File("d:/a"));
    //上傳對象
    ServletFileUpload upload=new ServletFileUpload(f);
    upload.setFileSizeMax(1024*1024*5);//設置上傳的單個文件最年夜為5M
    upload.setSizeMax(1024*1024*8);//設置一切上傳的文件年夜小之和最年夜為8M

    //▲4上傳進度監聽
    upload.setProgressListener(new ProgressListener(){
      private double pre=0D;
      @Override//參數1:已上傳若干字節 參數2:一共若干字節  參數3:第幾個文件(序號從1開端)
      public void update(long pByteRead, long pContentLength, int pItems) {
        double d = 1.0*pByteRead/pContentLength*100;
        System.out.println(d+"%");
            if(pre!=d){
              System.out.println(d+"%");
              pre=d;
            }
      }
    });


    //應用解析對象解析
    try {
      List<FileItem> list=upload.parseRequest(request);
      for(FileItem fI:list){
        if((fI.isFormField())){//假如是通俗表單組件:checkbox,radio,password...
//         String desc=fI.getString();
          System.out.println("fI.getString():"+fI.getString());
          //第二步
          String desc=fI.getString("utf-8");
          //該句設置通俗表單組件內容編碼
          System.out.println("編碼後:"+desc);
        }else{
          //防護:過濾失落沒選擇文件的空文件組件
          if(fI.getSize()<=0){
            continue;//讀下一個文件
          }

          System.out.println("文件內容類型:"+fI.getContentType());//文件內容類型:text/plain
          System.out.println("文件名:"+fI.getName());//文件名:C:\Users\adl1\Desktop\a.txt

          String ext=fI.getName().substring(fI.getName().lastIndexOf("."));//.txt
          String uuid=UUID.randomUUID().toString().replace("-", "");
          String fileName=uuid+ext;

          //文件目次打散技巧
          String dir1=Integer.toHexString(uuid.hashCode()&0x0f);
          String dir2=Integer.toHexString((uuid.hashCode()&0xf0)>>4);


          //fI.getInputStream()是真注釋件信息
          FileUtils.copyInputStreamToFile(fI.getInputStream(), new File(path+"/"+dir1+"/"+dir2+"/"+fileName));//寫活了
        }
      }
    } catch (FileUploadException e) {
      e.printStackTrace();
    }
  }
}

打散信息:


打散成果:

文件1:

 

文件2:

演示上傳進度道理

以上就是本文的全體內容,願望對年夜家的進修有所贊助,也願望年夜家多多支撐。

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved