• springmvc http请求,支持get,post,附件传输和参数传输


    主要解决http请求支持get,post,put,delete等常规方法,支持@RequestParam,@RequestBody,@PathVariable等参数格式传输,支持传输附件同时传递参数等,主体代码如下:

    1. package mes.client.action;
    2. import cn.hutool.crypto.digest.DigestUtil;
    3. import com.alibaba.fastjson.JSON;
    4. import mes.client.pojo.po.CommonEntityPo;
    5. import mes.client.pojo.vo.ResponseInfo;
    6. import org.slf4j.Logger;
    7. import org.slf4j.LoggerFactory;
    8. import java.io.*;
    9. import java.net.HttpURLConnection;
    10. import java.net.URL;
    11. import java.util.List;
    12. import java.util.Map;
    13. public class MesMomConnectAction {
    14. private static Logger logger = LoggerFactory.getLogger(MesMomConnectAction.class);
    15. /**
    16. * 无请求体body,向指定URL发送方法的请求
    17. *
    18. * @param url 发送请求的URL
    19. * @return URL 所代表远程资源的响应结果
    20. */
    21. public static ResponseInfo getHttpParamReq(String url,String requestMethodType) {
    22. StringBuilder result = new StringBuilder();
    23. BufferedReader in = null;
    24. HttpURLConnection connection = null;
    25. try {
    26. URL getUrl = new URL(url);
    27. // 打开和URL之间的连接
    28. connection = (HttpURLConnection) getUrl.openConnection();
    29. // 在connect之前,设置通用的请求属性
    30. connection.setRequestProperty("accept", "*/*");
    31. connection.setRequestProperty("connection", "Keep-Alive");
    32. connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
    33. connection.setRequestProperty("Charsert", "UTF-8");
    34. //添加必须的头部信息
    35. addHeader(connection);
    36. // 配置本次连接的Content-type,form表单是"application/x-www-form-urlencoded",json是"application/json"
    37. // 根据需求自己调整Content-type
    38. connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
    39. // 设置连接主机服务器的超时时间:15000毫秒
    40. connection.setConnectTimeout(15000);
    41. // 设置读取远程返回的数据时间:60000毫秒
    42. connection.setReadTimeout(60000);
    43. // 设置连接方式:get
    44. connection.setRequestMethod(requestMethodType);
    45. // 建立实际的连接,可不写,注意connection.getOutputStream会隐含的进行connect。
    46. connection.connect();
    47. // 定义BufferedReader输入流来读取URL的响应
    48. in = new BufferedReader(new InputStreamReader(connection.getInputStream(), "UTF-8"));
    49. String line;
    50. while ((line = in.readLine()) != null) {
    51. result.append(line);
    52. }
    53. ResponseInfo responseInfo = JSON.parseObject(result.toString(), ResponseInfo.class);
    54. if(responseInfo.getStatusCode() == null){
    55. return getFailResponse(result.toString());
    56. }
    57. return responseInfo;
    58. } catch (Exception e) {
    59. logger.error("调用MES4.0接口异常",e);
    60. return getExceptionResponse(e);
    61. }
    62. // 使用finally块来关闭输入流
    63. finally {
    64. try {
    65. if (in != null) {
    66. in.close();
    67. }
    68. if (connection != null) {
    69. //关闭连接
    70. connection.disconnect();
    71. }
    72. } catch (Exception e2) {
    73. e2.printStackTrace();
    74. }
    75. }
    76. }
    77. /**
    78. * @description: get请求
    79. * @date: 2023-10-16 16:58:30
    80. * @param url
    81. * @return ResponseInfo
    82. */
    83. public static ResponseInfo sendGet(String url){
    84. return getHttpParamReq(url,"GET");
    85. }
    86. /**
    87. * @description:方法说明
    88. * @date: 2023-10-16 15:42:33
    89. * @param url
    90. * @return ResponseInfo
    91. */
    92. public static ResponseInfo sendDelete(String url) {
    93. return getHttpParamReq(url,"DELETE");
    94. }
    95. /**
    96. * @description: post请求
    97. * @date: 2023-10-16 17:04:07
    98. * @param url
    99. * @param param
    100. * @return ResponseInfo
    101. */
    102. public static ResponseInfo sendPost(String url, CommonEntityPo param){
    103. return getHttpBodyReq(url,param,"POST");
    104. }
    105. /**
    106. * @description: put请求
    107. * @date: 2023-10-16 17:05:05
    108. * @param url
    109. * @param param
    110. * @return ResponseInfo
    111. */
    112. public static ResponseInfo sendPut(String url, CommonEntityPo param){
    113. return getHttpBodyReq(url,param,"PUT");
    114. }
    115. /**
    116. * 有请求体body,向指定 URL 发送方法的请求
    117. *
    118. * @param url 发送请求的 URL
    119. * @param param 请求参数。
    120. * @return 所代表远程资源的响应结果
    121. */
    122. public static ResponseInfo getHttpBodyReq(String url, CommonEntityPo param, String requestMethodType) {
    123. BufferedReader in = null;
    124. InputStream inputStream = null;
    125. HttpURLConnection connection = null;
    126. StringBuilder result = new StringBuilder();
    127. try {
    128. URL postUrl = new URL(url);
    129. // 打开和URL之间的连接
    130. connection = (HttpURLConnection) postUrl.openConnection();
    131. // 在connect之前,设置通用的请求属性
    132. connection.setRequestProperty("accept", "*/*");
    133. connection.setRequestProperty("connection", "Keep-Alive");
    134. connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
    135. connection.setRequestProperty("Charsert", "UTF-8");
    136. //添加一些必要的请求头信息
    137. addHeader(connection);
    138. //connection.setRequestProperty("Authorization","Bearer eyJhbGciOiJSUzI1NiIsInR5cCIgOiAiSldUIiwia2lkIiA6ICJiUlR5WGJ0Q05aaS1fUkVKSGUwNHNEd2RYaTNVSHRLOWZoWndXdGdPdWdNIn0.eyJleHAiOjE2OTc0MzM5NDksImlhdCI6MTY5NzAwMTk0OSwiYXV0aF90aW1lIjoxNjk2NzYwOTcxLCJqdGkiOiJiMjcyYzM2My1kMDQ1LTRhMTAtOTc5Ni0xZGE0ZmYwNDkxYTkiLCJpc3MiOiJodHRwOi8vaWRtLWRldi5zdW53b2RhLWV2Yi5jb20vYXV0aC9yZWFsbXMvc3RhbmRhcmQiLCJhdWQiOiJhY2NvdW50Iiwic3ViIjoiNmIxOTE4NWYtODcxZi00NTk1LWIxZTUtYTIwZTQ1MzcyZjQ3IiwidHlwIjoiQmVhcmVyIiwiYXpwIjoibnRzLWZyb250LXRlc3QiLCJub25jZSI6Ijc3MjBkM2QyLTg3NDQtNDI3Yy1iMzBhLTE5YWU2ZDM5NzY3NiIsInNlc3Npb25fc3RhdGUiOiJhNDJlNzU0ZC04MmRjLTQxNTgtOWQyYi1iZWZkNzNmMGI4NzUiLCJhY3IiOiIwIiwiYWxsb3dlZC1vcmlnaW5zIjpbIioiXSwicmVhbG1fYWNjZXNzIjp7InJvbGVzIjpbIm9mZmxpbmVfYWNjZXNzIiwidW1hX2F1dGhvcml6YXRpb24iXX0sInJlc291cmNlX2FjY2VzcyI6eyJhY2NvdW50Ijp7InJvbGVzIjpbIm1hbmFnZS1hY2NvdW50IiwibWFuYWdlLWFjY291bnQtbGlua3MiLCJ2aWV3LXByb2ZpbGUiXX19LCJzY29wZSI6Im9wZW5pZCBlbWFpbCBwcm9maWxlIiwiZW1haWxfdmVyaWZpZWQiOmZhbHNlLCJuYW1lIjoi6IuP5pWPIiwicHJlZmVycmVkX3VzZXJuYW1lIjoieHdkMTYiLCJnaXZlbl9uYW1lIjoi6IuP5pWPIiwibG9jYWxlIjoiemgtQ04ifQ.AUnf5meZWqYNYbfbzyqY3C9WoiL-ISCoVebvtJV-1EF8iQe2FXVEE22CLKnTvHBEoY-W62F8LtG3eW3B5LP54WBXq0JyxnMSLTjqZWMfvYmxNLfjO3rcviK9jAqqxrvLy1IR4ZVFz8ez4ThfCr3TrbammQvZgxF1jie_hx_-3RTiLTra1qyTUj8CrFRaVDBvWTt8nDu6FsRBAkqImPgZ3Jdhf-WDeVlwOkDCGPd5cUQ9KAQs2JUMY4H_jC9cgcSpQuUjNOQOnu1lnYjnsREswR7iBNSkaW6DlRry-HhD8FRs1QLOwKGcgFCBU7O9O-NCH8EyrZOriSpiPaElE2-i2Q");
    139. connection.setConnectTimeout(15000);
    140. connection.setReadTimeout(60000);
    141. // 发送POST请求必须设置如下两行,参数要放在http正文内
    142. connection.setDoOutput(true);
    143. connection.setDoInput(true);
    144. // 默认是 GET方式
    145. connection.setRequestMethod(requestMethodType);
    146. // Post 请求不使用缓存
    147. connection.setUseCaches(false);
    148. // 配置连接的Content-type,form表单是"application/x-www-form-urlencoded",json是"application/json"
    149. connection.setRequestProperty("Content-Type", "application/json");
    150. connection.connect();
    151. //参数处理
    152. if(param != null){
    153. //打印接口入参
    154. logger.info("post请求接口入参:{}",JSON.toJSONString(param.getData()));
    155. BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(connection.getOutputStream(), "UTF-8"));
    156. writer.write(JSON.toJSONString(param.getData()));
    157. writer.close();
    158. }
    159. // 定义BufferedReader输入流来读取URL的响应
    160. in = new BufferedReader(new InputStreamReader(connection.getInputStream(), "UTF-8"));
    161. String line;
    162. while ((line = in.readLine()) != null) {
    163. result.append(line);
    164. }
    165. ResponseInfo responseInfo = JSON.parseObject(result.toString(), ResponseInfo.class);
    166. if(responseInfo.getStatusCode() == null){
    167. return getFailResponse(result.toString());
    168. }
    169. return responseInfo;
    170. } catch (Exception e) {
    171. logger.error("调用MES4.0接口异常",e);
    172. return getExceptionResponse(e);
    173. } finally {
    174. try {
    175. if (in != null) {
    176. in.close();
    177. }
    178. if(inputStream != null){
    179. inputStream.close();
    180. }
    181. if (connection != null) {
    182. //关闭连接
    183. connection.disconnect();
    184. }
    185. } catch (IOException ex) {
    186. ex.printStackTrace();
    187. }
    188. }
    189. }
    190. /*public static void main(String[] args) throws IOException {
    191. //=========================================邮箱==================================================
    192. List<Map<String, Object>> files = new ArrayList<>();
    193. Map<String, Object> map = new HashMap();
    194. File file = new File("C:\\Users\\86188\\Desktop\\t1.png");
    195. map.put("name", "t1.png");
    196. map.put("file", file);
    197. files.add(map);
    198. Map<String, Object> param = new HashMap();
    199. param.put("data", "data");
    200. sendFileUrl("http://127.0.0.1:8080/sendReport", files, param);
    201. }*/
    202. /**
    203. * @description: 有附件和参数的发送方法的请求(调用方式参考实例如上方法)
    204. * @date: 2023-10-23 10:41:40
    205. * @param actionUrl :请求链接url
    206. * @param files : 附件
    207. * @param param :请求参数
    208. * @return ResponseInfo
    209. */
    210. public static void sendFileUrl(String actionUrl, List<Map<String, Object>> files, Map param){
    211. HttpURLConnection conn = null;
    212. DataOutputStream outStream = null;
    213. try {
    214. final String NEWLINE = "\r\n";
    215. String BOUNDARY = java.util.UUID.randomUUID().toString();
    216. String PREFIX = "--", LINEND = "\r\n";
    217. String MULTIPART_FROM_DATA = "multipart/form-data";
    218. String CHARSET = "UTF-8";
    219. URL uri = new URL(actionUrl);
    220. conn = (HttpURLConnection) uri.openConnection();
    221. conn.setConnectTimeout(15000);
    222. conn.setReadTimeout(60000);
    223. conn.setDoInput(true);// 允许输入
    224. conn.setDoOutput(true);// 允许输出
    225. conn.setUseCaches(false);
    226. conn.setRequestMethod("POST"); // Post方式
    227. conn.setRequestProperty("connection", "keep-alive");
    228. conn.setRequestProperty("Charsert", "UTF-8");
    229. conn.setRequestProperty("Accept", "application/json;charset=UTF-8");
    230. conn.setRequestProperty("Content-Type", MULTIPART_FROM_DATA
    231. + ";boundary=" + BOUNDARY);
    232. outStream = new DataOutputStream(
    233. conn.getOutputStream());
    234. // 获取表单中上传控件之外的控件数据,写入到输出流对象(根据上面分析的抓包的内容格式拼凑字符串);
    235. if (param != null && !param.isEmpty()) { // 这时请求中的普通参数,键值对类型的,相当于上面分析的请求中的username,可能有多个
    236. for (Map.Entry<String, Object> entry : param.entrySet()) {
    237. String key = entry.getKey(); // 键,相当于上面分析的请求中的username
    238. Object value = param.get(key); // 值,相当于上面分析的请求中的sdafdsa
    239. outStream.writeBytes(PREFIX + BOUNDARY + NEWLINE); // 像请求体中写分割线,就是前缀+分界线+换行
    240. outStream.writeBytes("Content-Disposition: form-data; "
    241. + "name=\"" + key + "\"" + NEWLINE); // 拼接参数名,格式就是Content-Disposition: form-data; name="key" 其中key就是当前循环的键值对的键,别忘了最后的换行
    242. outStream.writeBytes(NEWLINE); // 空行,一定不能少,键和值之间有一个固定的空行
    243. outStream.write(value.toString().getBytes("UTF-8")); // 将值写入,用字节流防止乱码
    244. // 或者写成:dos.write(value.toString().getBytes(charset));
    245. outStream.writeBytes(NEWLINE); // 换行
    246. }
    247. }
    248. // 发送文件数据
    249. if (files != null)
    250. for (Map<String, Object> file : files) {
    251. StringBuilder sb1 = new StringBuilder();
    252. sb1.append(PREFIX);
    253. sb1.append(BOUNDARY);
    254. sb1.append(LINEND);
    255. sb1.append("Content-Disposition: form-data; name=\"file\"; filename=\""
    256. + file.get("name") + "\"" + LINEND);
    257. sb1.append("Content-Type: application/octet-stream; charset="
    258. + CHARSET + LINEND);
    259. sb1.append(LINEND);
    260. outStream.write(sb1.toString().getBytes("utf-8")); //getBytes()不加utf-8 传输中文名附件时,接收附件的地方解析文件名会乱码
    261. InputStream is = new FileInputStream((File) file.get("file"));
    262. byte[] buffer = new byte[1024];
    263. int len = 0;
    264. while ((len = is.read(buffer)) != -1) {
    265. outStream.write(buffer, 0, len);
    266. }
    267. is.close();
    268. outStream.write(LINEND.getBytes());
    269. }
    270. // 请求结束标志
    271. byte[] end_data = (PREFIX + BOUNDARY + PREFIX + LINEND).getBytes();
    272. outStream.write(end_data);
    273. outStream.flush();
    274. // 得到响应码
    275. int res = conn.getResponseCode();
    276. //if (res == 200) {
    277. InputStream in = conn.getInputStream();
    278. InputStreamReader isReader = new InputStreamReader(in,"UTF-8");
    279. BufferedReader bufReader = new BufferedReader(isReader);
    280. String line = "";
    281. String data = "";
    282. while ((line = bufReader.readLine()) != null) {
    283. data += line;
    284. }
    285. logger.info("读取后最后结果:" + data);
    286. //}
    287. } catch (Exception e) {
    288. e.printStackTrace();
    289. } finally {
    290. try {
    291. //关闭流
    292. if(outStream != null){
    293. outStream.close();
    294. }
    295. //关闭连接
    296. if(conn != null){
    297. conn.disconnect();
    298. }
    299. } catch (IOException e) {
    300. e.printStackTrace();
    301. }
    302. }
    303. }
    304. //multipartFile格式文件发送
    305. public static void sendMultipartFileUrl(String actionUrl, MultipartFile file, Map<String, Object> param){
    306. HttpURLConnection conn = null;
    307. DataOutputStream outStream = null;
    308. try {
    309. final String NEWLINE = "\r\n";
    310. String BOUNDARY = java.util.UUID.randomUUID().toString();
    311. String PREFIX = "--", LINEND = "\r\n";
    312. String MULTIPART_FROM_DATA = "multipart/form-data";
    313. String CHARSET = "UTF-8";
    314. URL uri = new URL(actionUrl);
    315. conn = (HttpURLConnection) uri.openConnection();
    316. conn.setConnectTimeout(15000);
    317. conn.setReadTimeout(60000);
    318. conn.setDoInput(true);// 允许输入
    319. conn.setDoOutput(true);// 允许输出
    320. conn.setUseCaches(false);
    321. conn.setRequestMethod("POST"); // Post方式
    322. conn.setRequestProperty("connection", "keep-alive");
    323. conn.setRequestProperty("Charsert", "UTF-8");
    324. conn.setRequestProperty("Accept", "application/json;charset=UTF-8");
    325. conn.setRequestProperty("Content-Type", MULTIPART_FROM_DATA
    326. + ";boundary=" + BOUNDARY);
    327. outStream = new DataOutputStream(
    328. conn.getOutputStream());
    329. // 获取表单中上传控件之外的控件数据,写入到输出流对象(根据上面分析的抓包的内容格式拼凑字符串);
    330. if (param != null && !param.isEmpty()) { // 这时请求中的普通参数,键值对类型的,相当于上面分析的请求中的username,可能有多个
    331. for (Map.Entry<String, Object> entry : param.entrySet()) {
    332. String key = entry.getKey(); // 键,相当于上面分析的请求中的username
    333. Object value = param.get(key); // 值,相当于上面分析的请求中的sdafdsa
    334. outStream.writeBytes(PREFIX + BOUNDARY + NEWLINE); // 像请求体中写分割线,就是前缀+分界线+换行
    335. outStream.writeBytes("Content-Disposition: form-data; "
    336. + "name=\"" + key + "\"" + NEWLINE); // 拼接参数名,格式就是Content-Disposition: form-data; name="key" 其中key就是当前循环的键值对的键,别忘了最后的换行
    337. outStream.writeBytes(NEWLINE); // 空行,一定不能少,键和值之间有一个固定的空行
    338. outStream.write(value.toString().getBytes("UTF-8")); // 将值写入,用字节流防止乱码
    339. // 或者写成:dos.write(value.toString().getBytes(charset));
    340. outStream.writeBytes(NEWLINE); // 换行
    341. }
    342. }
    343. // 发送文件数据
    344. if (file != null){
    345. StringBuilder sb1 = new StringBuilder();
    346. sb1.append(PREFIX);
    347. sb1.append(BOUNDARY);
    348. sb1.append(LINEND);
    349. sb1.append("Content-Disposition: form-data; name=\"file\"; filename=\""
    350. + file.getOriginalFilename() + "\"" + LINEND);
    351. sb1.append("Content-Type: application/octet-stream; charset="
    352. + CHARSET + LINEND);
    353. sb1.append(LINEND);
    354. outStream.write(sb1.toString().getBytes("utf-8")); //getBytes()不加utf-8 传输中文名附件时,接收附件的地方解析文件名会乱码
    355. InputStream is = file.getInputStream();
    356. byte[] buffer = new byte[1024];
    357. int len = 0;
    358. while ((len = is.read(buffer)) != -1) {
    359. outStream.write(buffer, 0, len);
    360. }
    361. is.close();
    362. outStream.write(LINEND.getBytes());
    363. }
    364. // 请求结束标志
    365. byte[] end_data = (PREFIX + BOUNDARY + PREFIX + LINEND).getBytes();
    366. outStream.write(end_data);
    367. outStream.flush();
    368. // 得到响应码
    369. int res = conn.getResponseCode();
    370. //if (res == 200) {
    371. InputStream in = conn.getInputStream();
    372. InputStreamReader isReader = new InputStreamReader(in,"UTF-8");
    373. BufferedReader bufReader = new BufferedReader(isReader);
    374. String line = "";
    375. String data = "";
    376. while ((line = bufReader.readLine()) != null) {
    377. data += line;
    378. }
    379. logger.info("读取后最后结果:" + data);
    380. //}
    381. } catch (Exception e) {
    382. e.printStackTrace();
    383. } finally {
    384. try {
    385. //关闭流
    386. if(outStream != null){
    387. outStream.close();
    388. }
    389. //关闭连接
    390. if(conn != null){
    391. conn.disconnect();
    392. }
    393. } catch (IOException e) {
    394. e.printStackTrace();
    395. }
    396. }
    397. }
    398. /**
    399. * @description: 需要额外添加一些请求头信息
    400. * @date: 2023-10-11 14:42:07
    401. */
    402. private static void addHeader(HttpURLConnection connection){
    403. //针对一些第三方系统加密header
    404. }
    405. /**
    406. * @description: 返回请求异常信息
    407. * @date: 2023-10-15 17:43:36
    408. * @param e
    409. * @return ResponseInfo
    410. */
    411. private static ResponseInfo getExceptionResponse(Exception e){
    412. ByteArrayOutputStream baos = new ByteArrayOutputStream();
    413. e.printStackTrace(new PrintStream(baos));
    414. String failMsg = baos.toString();
    415. return getFailResponse(failMsg);
    416. }
    417. /**
    418. * @description: 封装返回信息结果
    419. * @date: 2023-10-19 19:44:23
    420. * @param failMsg
    421. * @return ResponseInfo
    422. */
    423. private static ResponseInfo getFailResponse(String failMsg){
    424. ResponseInfo responseInfo = new ResponseInfo();
    425. responseInfo.setStatusCode(400);
    426. responseInfo.setMessage(failMsg);
    427. return responseInfo;
    428. }
    429. }

  • 相关阅读:
    Java核心知识体系4:AOP原理和切面应用
    如何彻底搞懂组合(Composite)设计模式?
    Linux实现原理 — I/O 处理流程与优化手段
    Piramiko实现root权限登录
    Metabase学习教程:权限-1
    新闻文化建设杂志新闻文化建设杂志社新闻文化建设编辑部2022年第14期目录
    (附源码)计算机毕业设计ssmJAVA高校田径运动会管理
    Codeforces 802I - Fake News(hard) 后缀数组+单调栈
    Pytest-xdist并行执行用例时的“坑”
    算法竞赛入门【码蹄集进阶塔335题】(MT2281-2285)
  • 原文地址:https://blog.csdn.net/qq_25313187/article/details/133989948