package com.hotent.im.network; import org.springframework.web.multipart.MultipartFile; import java.io.*; import java.net.HttpURLConnection; import java.net.URL; import java.util.HashMap; import java.util.List; import java.util.Map; /** * HttpURLConnection发送Post请求工具类 * * @author yanhongliang */ public abstract class AbstractHttpPost { /** * 网络请求回调 * 抽象方法 * @param response */ public abstract void complete(Response response); /** * post 网络请求 * @param actionUrl 网络请求地址 * @param params 常规参数 * @param files 文件参数 */ public void post( final String actionUrl, final Map params, final HashMap files) { sendRequest(actionUrl, params, files); } /** * 通过拼接的方式构造请求内容,实现参数传输以及文件传输 * * @param actionUrl * 访问的服务器URL * @param params * 普通参数 * @param files * 文件参数 */ private void sendRequest( String actionUrl, Map params, HashMap files) { if (actionUrl == null || actionUrl.isEmpty()) { return; } Response response = new Response(0); HttpURLConnection conn = null; InputStreamReader in = null; try { String boundary = java.util.UUID.randomUUID().toString(); String prefix = "--", linend = "\r\n"; String multipartFromData = "multipart/form-data"; String charset = "UTF-8"; URL uri = new URL(actionUrl); conn = (HttpURLConnection) uri.openConnection(); // 缓存的最长时间 conn.setReadTimeout(30 * 1000); // 允许输入 conn.setDoInput(true); // 允许输出 conn.setDoOutput(true); // 不允许使用缓存 conn.setUseCaches(false); conn.setRequestMethod("POST"); conn.setRequestProperty("connection", "keep-alive"); conn.setRequestProperty("Charsert", "UTF-8"); conn.setRequestProperty("Content-Type", multipartFromData + ";boundary=" + boundary); DataOutputStream outStream = new DataOutputStream(conn.getOutputStream()); // 首先组拼文本类型的参数------start------ if (params != null){ StringBuilder text = new StringBuilder(); for (Map.Entry entry : params.entrySet()) { text.append(prefix); text.append(boundary); text.append(linend); text.append("Content-Disposition: form-data; name=\"") .append(entry.getKey()) .append("\"") .append(linend); text.append("Content-Type: text/plain; charset=") .append(charset) .append(linend); text.append("Content-Transfer-Encoding: 8bit") .append(linend); text.append(linend); text.append(entry.getValue()); text.append(linend); } outStream.write(text.toString().getBytes()); } // 首先组拼文本类型的参数------end------ // 发送文件数据--------------start----- if (files != null) { for (HashMap.Entry file : files.entrySet()) { StringBuilder fileBuilder = new StringBuilder(); fileBuilder.append(prefix); fileBuilder.append(boundary); fileBuilder.append(linend); // name是post中传参的键 filename是文件的名称 fileBuilder.append("Content-Disposition: form-data; name=\"file\"; filename=\"") .append(file.getKey()) .append("\"") .append(linend); fileBuilder.append("Content-Type: application/octet-stream; charset=") .append(charset) .append(linend); fileBuilder.append(linend); outStream.write(fileBuilder.toString().getBytes()); InputStream is = file.getValue().getInputStream(); byte[] buffer = new byte[1024]; int len = 0; while ((len = is.read(buffer)) != -1) { outStream.write(buffer, 0, len); } is.close(); outStream.write(linend.getBytes()); } } // 发送文件数据--------------start----- // 请求结束标志 byte[] endData = (prefix + boundary + prefix + linend).getBytes(); outStream.write(endData); outStream.flush(); outStream.close(); long timestamp = System.currentTimeMillis(); response.timestamp = conn.getHeaderFieldDate("Date", 0); if (response.timestamp != 0) { response.timestamp += System.currentTimeMillis() - timestamp; } // 得到响应码 response.state = conn.getResponseCode(); if (response.state == 200) { in = new InputStreamReader(conn.getInputStream(), "UTF-8"); // 读取返回数据 BufferedReader reader = new BufferedReader(in); StringBuilder strBuilder = new StringBuilder(); String line = null; while ((line = reader.readLine()) != null && !cancel) { //$NON-NLS-1$ strBuilder.append(line).append("\n"); } reader.close(); response.content = strBuilder.toString(); } }catch (Exception e){ response.content = e.getLocalizedMessage(); error(e); }finally { if (in != null) { try { in.close(); } catch (IOException e) { e.printStackTrace(); } } if (conn != null){ conn.disconnect(); } response.cancel = cancel; cancel = false; complete(response); } } /** * 取消网络请求 */ private boolean cancel = false; public void cancel() { cancel = true; } /** * 异常输出 * @param e 异常 */ private void error(Exception e){ e.printStackTrace(); } }