commons-lang3-3.12.0.jar
commons-io-2.11.0.jar
slf4j-api-1.7.36.jar
slf4j-log4j12-1.7.7.jar
log4j-1.2.17.jar
package com.chenwc.util;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.Map.Entry;
import com.chenwc.enums.RequestMethodEnum;
import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.net.ssl.HttpsURLConnection;
public class RestMock {
/**
* 连接超时时间,30秒
*/
private static final int CONNECT_TIME_OUT = 30 * 1000;
/**
* 读取超时时间,30秒
*/
private static final int READ_TIME_OUT = 30 * 1000;
private static final Logger log = LoggerFactory.getLogger(RestMock.class);
/**
* 发送post请求,默认超时时间30秒
*
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @param body 请求体,如json、xml、text、html等
* @return 响应信息
*/
public static String sendPost(String url,
Map<String, String> hearderParams, String body) {
return getResultByHttp(RequestMethodEnum.POST, url, hearderParams, body, READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送post请求,默认超时时间30秒
*
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @return 响应信息
*/
public static String sendPost(String url,
Map<String, String> hearderParams) {
return getResultByHttp(RequestMethodEnum.POST, url, hearderParams, "", READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送post请求,默认超时时间30秒
*
* @param url 请求路径
* @return 响应信息
*/
public static String sendPost(String url) {
return getResultByHttp(RequestMethodEnum.POST, url, new HashMap<>(), "", READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送get请求,默认超时时间30秒
*
* @param url 请求路径
* @return 响应信息
*/
public static String sendGet(String url) {
return getResultByHttp(RequestMethodEnum.GET, url, new HashMap<>(), "", READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送get请求,默认超时时间30秒
*
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @return 响应信息
*/
public static String sendGet(String url,
Map<String, String> hearderParams) {
return getResultByHttp(RequestMethodEnum.GET, url, hearderParams, "", READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送get请求,默认超时时间30秒
*
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @param parameterMap 请求参数
* @return 响应信息
*/
public static String sendGet(String url,
Map<String, String> hearderParams, Map<String, String> parameterMap) {
String paramerterString = generateGetParameter(parameterMap);
if (StringUtils.isNotEmpty(paramerterString)) {
if (url.endsWith("?")) {
url = url + paramerterString;
} else {
url = url + "?" + paramerterString;
}
}
return getResultByHttp(RequestMethodEnum.GET, url, hearderParams, "", READ_TIME_OUT, CONNECT_TIME_OUT);
}
/**
* 发送请求
*
* @param requestMethod 请求方式
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @param body 请求体,如json、xml、text、html等
* @param connectTimeOut 连接超时时间
* @param readTimeOut 读取响应超时时间
* @return 响应信息
*/
public static String getResultByHttp(RequestMethodEnum requestMethod, String url,
Map<String, String> hearderParams, String body, int connectTimeOut, int readTimeOut) {
log.info("请求url------------->: {}", url);
log.info("请求方法------------>: {}", requestMethod.getRequestMethod());
if (null != hearderParams && !hearderParams.isEmpty()) {
for (String key : hearderParams.keySet()) {
log.info("添加的请求头信息---------->: {}:{}", key, hearderParams.get(key));
}
}
if (StringUtils.isNotEmpty(body)) {
log.info("请求体-------------->: {}", body);
}
log.info("连接超时时间-------->: {} ms", connectTimeOut);
log.info("读取响应超时时间----->: {} ms", readTimeOut);
HttpURLConnection conn = null;
OutputStream output = null;
InputStream inputStream = null;
// 定义返回结果
String result = "";
try {
long start = System.currentTimeMillis();
// Java的URL网络类可以让你通过URL去连接网络服务器并获取资源
URL u = new URL(url);
log.info("开始建立连接............");
// HttpURLConnection是Java的标准类,它继承自URLConnection,可用于向指定网站发送GET请求、POST请求
// 得到网络访问对象java.net.HttpURLConnection
conn = (HttpURLConnection) u.openConnection();
//跳过所有https证书认证
boolean useHttps = url.startsWith("https");
if (useHttps) {
TrustAllHosts.trustAllHosts((HttpsURLConnection) conn);
((HttpsURLConnection) conn).setHostnameVerifier(TrustAllHosts.DO_NOT_VERIFY);
}
// 设置是否向HttpURLConnection输出
conn.setDoInput(true);
// 设置是否从httpUrlConnection读入
conn.setDoOutput(true);
// 连接超时时间
conn.setConnectTimeout(connectTimeOut);
// 读取超时时间
conn.setReadTimeout(readTimeOut);
// 请求方式
conn.setRequestMethod(requestMethod.getRequestMethod());
// 放入需要添加的请求头参数
if (null != hearderParams) {
for (Entry<String, String> entry : hearderParams.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
conn.setRequestProperty(key, value);
}
}
// 建立连接
conn.connect();
log.info("建立连接成功............");
if (StringUtils.isNotEmpty(body)) {
// 定义输出流,加入请求报文
output = conn.getOutputStream();
log.info("开始写入请求体............");
output.write(body.getBytes(StandardCharsets.UTF_8));
output.flush();
log.info("写入请求体成功............");
}
Map<String, List<String>> responseHeader = conn.getHeaderFields();
if (null != responseHeader && !responseHeader.isEmpty()) {
for (String key : responseHeader.keySet()) {
if (null != key) {
log.info("响应头信息---------->: {}:{}", key, responseHeader.get(key).get(0));
} else {
log.info("响应头信息---------->: {}", responseHeader.get(null).get(0));
}
}
}
int statusCode = conn.getResponseCode();
log.info("请求响应码:{}", statusCode);
if (200 == statusCode) {
log.info("开始读取响应............");
inputStream = conn.getInputStream();
result = IOUtils.toString(inputStream, StandardCharsets.UTF_8);
log.info("读取响应成功............");
long end = System.currentTimeMillis();
log.info("请求耗时----------->: {} ms", (end - start));
} else {
log.error("请求失败,HTTP 请求响应码不等于 200!!!");
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (null != conn) {
conn.disconnect();
}
if (null != output) {
output.close();
}
if (null != inputStream) {
inputStream.close();
}
} catch (Exception e2) {
// TODO: handle exception
e2.printStackTrace();
}
}
return result;
}
/**
* 使用GET方法下载文件
*
* @param url 请求路径
* @param filePath 文件保存路径
*/
public static void downloadFileByGet(String url, String filePath) {
downloadFileByGet(url, new HashMap<>(), new HashMap<>(), filePath);
}
/**
* 使用GET方法下载文件
*
* @param url 请求路径
* @param hearderParams 请求头,如Content-type、Content-Length等
* @param parameterMap 表单参数
* @param filePath 文件保存路径
*/
public static void downloadFileByGet(String url, Map<String, String> hearderParams,
Map<String, String> parameterMap, String filePath) {
String paramerterString = generateGetParameter(parameterMap);
if (StringUtils.isNotEmpty(paramerterString)) {
if (url.endsWith("?")) {
url = url + paramerterString;
} else {
url = url + "?" + paramerterString;
}
}
log.info("请求url------------->: {}", url);
log.info("请求方法------------>: {}", RequestMethodEnum.GET.getRequestMethod());
if (null != hearderParams && !hearderParams.isEmpty()) {
for (String key : hearderParams.keySet()) {
log.info("添加的请求头信息---------->: {}:{}", key, hearderParams.get(key));
}
}
log.info("连接超时时间-------->: {} ms", CONNECT_TIME_OUT);
log.info("读取响应超时时间----->: {} ms", READ_TIME_OUT);
HttpURLConnection conn = null;
InputStream inputStream = null;
FileOutputStream fos = null;
ByteArrayOutputStream bos = null;
File fileExists = new File(filePath);
try {
long start = System.currentTimeMillis();
if (!fileExists.exists()) {
if (!mkdirParents(fileExists)) {
log.info("创建父级目录失败!");
return;
}
if (!fileExists.createNewFile()) {
log.info("创建文件: {} 失败!", filePath);
return;
}
}
// Java的URL网络类可以让你通过URL去连接网络服务器并获取资源
URL u = new URL(url);
log.info("开始建立连接............");
// HttpURLConnection是Java的标准类,它继承自URLConnection,可用于向指定网站发送GET请求、POST请求
// 得到网络访问对象java.net.HttpURLConnection
conn = (HttpURLConnection) u.openConnection();
//跳过所有https证书认证
boolean useHttps = url.startsWith("https");
if (useHttps) {
TrustAllHosts.trustAllHosts((HttpsURLConnection) conn);
((HttpsURLConnection) conn).setHostnameVerifier(TrustAllHosts.DO_NOT_VERIFY);
}
// 设置是否向HttpURLConnection输出
conn.setDoInput(true);
// 设置是否从httpUrlConnection读入
conn.setDoOutput(true);
// 连接超时时间
conn.setConnectTimeout(CONNECT_TIME_OUT);
// 读取超时时间
conn.setReadTimeout(READ_TIME_OUT);
// 请求方式
conn.setRequestMethod(RequestMethodEnum.GET.getRequestMethod());
// 放入需要添加的请求头参数
if (null != hearderParams) {
for (Entry<String, String> entry : hearderParams.entrySet()) {
String key = entry.getKey();
String value = entry.getValue();
conn.setRequestProperty(key, value);
}
}
// 建立连接
conn.connect();
log.info("建立连接成功............");
Map<String, List<String>> responseHeader = conn.getHeaderFields();
if (null != responseHeader && !responseHeader.isEmpty()) {
for (String key : responseHeader.keySet()) {
if (null != key) {
log.info("响应头信息---------->: {}:{}", key, responseHeader.get(key).get(0));
} else {
log.info("响应头信息---------->: {}", responseHeader.get(null).get(0));
}
}
}
int statusCode = conn.getResponseCode();
log.info("请求响应码:{}", statusCode);
if (200 == statusCode) {
log.info("开始读取响应............");
inputStream = conn.getInputStream();
byte[] buffer = new byte[1024];
int len = 0;
bos = new ByteArrayOutputStream();
while ((len = inputStream.read(buffer)) != -1) {
bos.write(buffer, 0, len);
}
byte[] getData = bos.toByteArray();
fos = new FileOutputStream(fileExists);
fos.write(getData);
log.info("下载文件成功!");
log.info("文件保存到:{}", filePath);
log.info("读取响应成功............");
long end = System.currentTimeMillis();
log.info("请求耗时----------->: {} ms", (end - start));
} else {
log.error("请求失败,HTTP 请求响应码不等于 200!!!");
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
if (null != conn) {
conn.disconnect();
}
if (null != inputStream) {
inputStream.close();
}
if (null != fos) {
fos.close();
}
if (null != bos) {
bos.close();
}
} catch (Exception e2) {
// TODO: handle exception
e2.printStackTrace();
}
}
}
/**
* 根据map生成get请求参数,格式 A=a&B=b
*
* @param parameterMap 请求参数map
* @return get请求参数url
*/
private static String generateGetParameter(Map<String, String> parameterMap) {
StringBuilder sb = new StringBuilder();
if (null != parameterMap) {
Set<String> keySet = parameterMap.keySet();
int index = 1;
for (String key : keySet) {
String value = parameterMap.get(key);
try {
value = URLEncoder.encode(value, String.valueOf(StandardCharsets.UTF_8));
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
if (index == keySet.size()) {
sb.append(key).append("=").append(value);
} else {
sb.append(key).append("=").append(value).append("&");
}
index++;
}
}
return sb.toString();
}
/**
* 判断文件的父级目录是否存在,不存在则创建
*
* @param file 文件
* @return true 父级目录存在或创建父级目录成功, false创建父级目录失败
*/
public static boolean mkdirParents(File file) {
if (!file.getParentFile().exists()) {
return file.getParentFile().mkdirs();
} else {
return true;
}
}
}
package com.chenwc.enums;
/**
* 一些常用http请求方法枚举
* @author CalvinChan
*
*/
public enum RequestMethodEnum {
POST("POST"),
GET("GET"),
DELETE("DELETE"),
PUT("PUT"),
HEAD("HEAD"),
PATCH("PATCH"),
OPTIONS("OPTIONS"),
TRACE("TRACE");
private String requestMethod;
private RequestMethodEnum(String requestMethod) {
this.requestMethod = requestMethod;
}
public String getRequestMethod() {
return requestMethod;
}
public void setRequestMethod(String requestMethod) {
this.requestMethod = requestMethod;
}
}
log4j.rootLogger=info,stdout log4j.appender.stdout=org.apache.log4j.ConsoleAppender log4j.appender.stdout.Target=System.out log4j.appender.stdout.layout=org.apache.log4j.PatternLayout log4j.appender.stdout.layout.ConversionPattern=%d %-5p %-5L --- [%-5t] %-10c : %m %n
package com.chenwc;
import com.chenwc.enums.AlgorithmEnum;
import com.chenwc.enums.RequestMethodEnum;
import com.chenwc.util.RestMock;
import com.chenwc.util.ShaUtilsByJavaApi;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
public class Main {
private static final Logger log = LoggerFactory.getLogger(Main.class);
public static void main(String[] args){
String result = "";
String body = "{\"UUID\":\"3128a4de-2e29-49cd-b293-02af6c827d72\",\"title\":\"title\",\"Date\":\"2023-01-15 11:44:06.625\",\"content\":\"content\"}";
//POST提交表单
Map<String, String> header = new HashMap<>();
header.put("Authorization", ShaUtilsByJavaApi.getShaHash(UUID.randomUUID().toString(), AlgorithmEnum.SHA_256));
header.put("Cookie", String.valueOf(System.nanoTime()));
header.put("Content-Type", "application/x-www-form-urlencoded;charset=UTF-8");
result = RestMock.sendPost("http://localhost:9090/post_form?content=content&title=title", header);
log.info("POST提交表单 Result: {}", result);
//POST提交请求体
header.put("Content-Type", "application/json;charset=UTF-8");
result = RestMock.sendPost("http://localhost:9090/post_body", header, body);
log.info("POST提交请求体 Result: {}", result);
//GET提交表单
Map<String, String> parameter = new HashMap<>();
parameter.put("content", "content");
parameter.put("title", "title");
header.put("Content-Type", "application/x-www-form-urlencoded;charset=UTF-8");
result = RestMock.sendGet("http://localhost:9090/get_form", header, parameter);
log.info("GET提交表单 Result: {}", result);
//OPTIONS提交请求
result = RestMock.getResultByHttp(RequestMethodEnum.OPTIONS, "http://localhost:9090/put_body", new HashMap<>(), "", 3000, 3000);
log.info("OPTIONS提交请求 Result: {}", result);
//PUT提交请求体
header.put("Content-Type", "application/json;charset=UTF-8");
result = RestMock.getResultByHttp(RequestMethodEnum.PUT, "http://localhost:9090/put_body", header, body, 3000, 3000);
log.info("PUT提交请求体 Result: {}", result);
//自签证书
result = RestMock.sendGet("https://192.168.100.129:9443/carbon/admin/login.jsp");
log.info(result);
//公网证书
result = RestMock.sendGet("https://www.jianshu.com/p/a928b6c34f06");
log.info(result);
}
}
package com.chenwc.util;
import com.chenwc.enums.HttpsAlgorithmEnum;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.net.ssl.*;
import java.security.SecureRandom;
import java.security.cert.X509Certificate;
/**
* HttpURLConnection绕过HTTPS的SSL验证
* @author chenwc
*/
public class TrustAllHosts {
private static final Logger log = LoggerFactory.getLogger(TrustAllHosts.class);
/**
* 覆盖java默认的证书验证
*/
private static final TrustManager[] trustAllCerts = new TrustManager[]{new X509TrustManager() {
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[]{};
}
public void checkClientTrusted(X509Certificate[] chain, String authType) {
}
public void checkServerTrusted(X509Certificate[] chain, String authType) {
}
}};
/**
* 设置不验证主机
*/
public static final HostnameVerifier DO_NOT_VERIFY = (hostname, session) -> true;
/**
* 信任所有
*
* @param connection https连接
* @return SSLSocketFactory
*/
public static SSLSocketFactory trustAllHosts(HttpsURLConnection connection) {
SSLSocketFactory oldFactory = connection.getSSLSocketFactory();
try {
//设置HTTPS的加密算法名称
SSLContext sc = SSLContext.getInstance(HttpsAlgorithmEnum.TLSV_1_2.getAlgorithm());
sc.init(null, trustAllCerts, new SecureRandom());
SSLSocketFactory newFactory = sc.getSocketFactory();
log.info("SSLContext Version: {}", sc.getProtocol());
connection.setSSLSocketFactory(newFactory);
} catch (Exception e) {
e.printStackTrace();
}
return oldFactory;
}
}
package com.chenwc.enums;
/**
* TLS/SSL 协议枚举
* @author chenwc
*/
public enum HttpsAlgorithmEnum {
SSL("SSL"),
TLS("TLS"),
TLSV_1_1("TLSv1.1"),
TLSV_1_2("TLSv1.2");
//JDK8不支持TLSv1.3
//TLSV_1_3("TLSv1.3");
private String algorithm;
HttpsAlgorithmEnum(String algorithm) {
this.algorithm = algorithm;
}
public String getAlgorithm() {
return algorithm;
}
public void setAlgorithm(String algorithm) {
this.algorithm = algorithm;
}
/**
* 根据算法名称获取 HttpsAlgorithmEnum
* @param algo 算法名称
* @return HttpsAlgorithmEnum
*/
public HttpsAlgorithmEnum getAlgorithmEnum(String algo) {
for (HttpsAlgorithmEnum algorithmEnum : HttpsAlgorithmEnum.values()) {
if (algo.equals(algorithmEnum.getAlgorithm())) {
return algorithmEnum;
}
}
return null;
}
}