HttpClient4模擬帶檔案上傳的表單提交
阿新 • • 發佈:2019-01-05
這裡用apache的HttpClient4.3模擬檔案上傳,上傳到一個java servlet,然後用servlet解析,把上傳檔案放到伺服器目錄下
下面這個java應用,往一個java servlet中提交了一個檔案,和幾個普通表單屬性
package com.test.httpClient; import java.io.File; import java.io.IOException; import java.nio.charset.Charset; import org.apache.http.Consts; import org.apache.http.HttpEntity; import org.apache.http.client.methods.CloseableHttpResponse; import org.apache.http.client.methods.HttpPost; import org.apache.http.entity.ContentType; import org.apache.http.entity.mime.MultipartEntityBuilder; import org.apache.http.entity.mime.content.FileBody; import org.apache.http.entity.mime.content.StringBody; import org.apache.http.impl.client.CloseableHttpClient; import org.apache.http.impl.client.HttpClients; import org.apache.http.util.EntityUtils; public class ClientMultipartFormPost { /** * 這個例子展示瞭如何執行請求包含一個多部分編碼的實體 * 模擬表單提交 * @throws IOException */ public static void main(String[] args) throws IOException { CloseableHttpClient httpClient = HttpClients.createDefault(); try{ //要上傳的檔案的路徑 String filePath = "D:\\my_shutdown.log"; //把一個普通引數和檔案上傳給下面這個地址 是一個servlet HttpPost httpPost = new HttpPost("http://localhost:80/testjs/servlet/UploadServlet"); //把檔案轉換成流物件FileBody FileBody bin = new FileBody(new File(filePath)); //普通欄位 重新設定了編碼方式 StringBody comment = new StringBody("這裡是一個評論", ContentType.create("text/plain", Consts.UTF_8)); //StringBody comment = new StringBody("這裡是一個評論", ContentType.TEXT_PLAIN); StringBody name = new StringBody("王五", ContentType.create("text/plain", Consts.UTF_8)); StringBody password = new StringBody("123456", ContentType.create("text/plain", Consts.UTF_8)); HttpEntity reqEntity = MultipartEntityBuilder.create() .addPart("media", bin)//相當於<input type="file" name="media"/> .addPart("comment", comment) .addPart("name", name)//相當於<input type="text" name="name" value=name> .addPart("password", password) .build(); httpPost.setEntity(reqEntity); System.out.println("發起請求的頁面地址 " + httpPost.getRequestLine()); //發起請求 並返回請求的響應 CloseableHttpResponse response = httpClient.execute(httpPost); try { System.out.println("----------------------------------------"); //列印響應狀態 System.out.println(response.getStatusLine()); //獲取響應物件 HttpEntity resEntity = response.getEntity(); if (resEntity != null) { //列印響應長度 System.out.println("Response content length: " + resEntity.getContentLength()); //列印響應內容 System.out.println(EntityUtils.toString(resEntity,Charset.forName("UTF-8"))); } //銷燬 EntityUtils.consume(resEntity); } finally { response.close(); } }finally{ httpClient.close(); } } }
用於接收的java servlet 用到了apache的common-fileupload來解析請求main中提交的引數
package com.vincente.test.servlet; import java.io.BufferedReader; import java.io.DataInputStream; import java.io.DataOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStream; import java.io.PrintWriter; import java.net.HttpURLConnection; import java.net.URL; import java.util.Iterator; import java.util.List; 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.FileItemFactory; import org.apache.commons.fileupload.FileUploadException; import org.apache.commons.fileupload.disk.DiskFileItemFactory; import org.apache.commons.fileupload.servlet.ServletFileUpload; public class UploadServlet extends HttpServlet { public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { request.setCharacterEncoding("utf-8"); response.setCharacterEncoding("utf-8"); //利用apache的common-upload上傳元件來進行 來解析獲取到的流檔案 //把上傳來的檔案放在這裡 String uploadPath = getServletContext().getRealPath("/upload");//獲取檔案路徑 //檢測是不是存在上傳檔案 // Check that we have a file upload request boolean isMultipart = ServletFileUpload.isMultipartContent(request); if(isMultipart){ DiskFileItemFactory factory = new DiskFileItemFactory(); //指定在記憶體中快取資料大小,單位為byte,這裡設為1Mb factory.setSizeThreshold(1024*1024); //設定一旦檔案大小超過getSizeThreshold()的值時資料存放在硬碟的目錄 factory.setRepository(new File("D://temp")); // Create a new file upload handler ServletFileUpload upload = new ServletFileUpload(factory); // 指定單個上傳檔案的最大尺寸,單位:位元組,這裡設為5Mb upload.setFileSizeMax(5 * 1024 * 1024); //指定一次上傳多個檔案的總尺寸,單位:位元組,這裡設為10Mb upload.setSizeMax(10 * 1024 * 1024); upload.setHeaderEncoding("UTF-8"); //設定編碼,因為我的jsp頁面的編碼是utf-8的 List<FileItem> items = null; try { // 解析request請求 items = upload.parseRequest(request); } catch (FileUploadException e) { e.printStackTrace(); } if(items!=null){ //把上傳檔案放到伺服器的這個目錄下 if (!new File(uploadPath).isDirectory()){ new File(uploadPath).mkdirs(); //選定上傳的目錄此處為當前目錄,沒有則建立 } //解析表單專案 // Process the uploaded items Iterator<FileItem> iter = items.iterator(); while (iter.hasNext()) { FileItem item = iter.next(); //如果是普通表單屬性 if (item.isFormField()) { //<input type="text" name="content"> String name = item.getFieldName();//相當於input的name屬性 String value = item.getString();//input的value屬性 System.out.println("屬性:"+name+" 屬性值:"+value); } //如果是上傳檔案 else { //屬性名 String fieldName = item.getFieldName(); //上傳檔案路徑 String fileName = item.getName(); fileName = fileName.substring(fileName.lastIndexOf("/")+1);// 獲得上傳檔案的檔名 try { item.write(new File(uploadPath,fileName)); } catch (Exception e) { e.printStackTrace(); } //給請求頁面返回響應 response.getWriter().println("檔案上傳成功! 檔名是:"+fileName); } } } } }
main中的執行結果:
發起請求的頁面地址 POST http://localhost:80/testjs/servlet/UploadServlet HTTP/1.1
----------------------------------------
HTTP/1.1 200 OK
Response content length: 50
檔案上傳成功! 檔名是:my_shutdown.log
tomcat中的執行結果:
屬性:comment 屬性值:這裡是一個評論
屬性:name 屬性值:王五
屬性:password 屬性值:123456