package com.iailab.framework.common.util.http;
|
|
import cn.hutool.core.codec.Base64;
|
import cn.hutool.core.map.TableMap;
|
import cn.hutool.core.net.url.UrlBuilder;
|
import cn.hutool.core.util.ReflectUtil;
|
import cn.hutool.core.util.StrUtil;
|
import org.springframework.util.CollectionUtils;
|
import org.springframework.util.StringUtils;
|
import org.springframework.web.util.UriComponents;
|
import org.springframework.web.util.UriComponentsBuilder;
|
|
import javax.servlet.http.HttpServletRequest;
|
import java.io.BufferedReader;
|
import java.io.IOException;
|
import java.io.InputStreamReader;
|
import java.io.PrintWriter;
|
import java.net.URI;
|
import java.net.URL;
|
import java.net.URLConnection;
|
import java.nio.charset.Charset;
|
import java.util.List;
|
import java.util.Map;
|
|
/**
|
* HTTP 工具类
|
*
|
* @author iailab
|
*/
|
public class HttpUtils {
|
|
@SuppressWarnings("unchecked")
|
public static String replaceUrlQuery(String url, String key, String value) {
|
UrlBuilder builder = UrlBuilder.of(url, Charset.defaultCharset());
|
// 先移除
|
TableMap<CharSequence, CharSequence> query = (TableMap<CharSequence, CharSequence>)
|
ReflectUtil.getFieldValue(builder.getQuery(), "query");
|
query.remove(key);
|
// 后添加
|
builder.addQuery(key, value);
|
return builder.build();
|
}
|
|
private String append(String base, Map<String, ?> query, boolean fragment) {
|
return append(base, query, null, fragment);
|
}
|
|
/**
|
* 拼接 URL
|
*
|
* copy from Spring Security OAuth2 的 AuthorizationEndpoint 类的 append 方法
|
*
|
* @param base 基础 URL
|
* @param query 查询参数
|
* @param keys query 的 key,对应的原本的 key 的映射。例如说 query 里有个 key 是 xx,实际它的 key 是 extra_xx,则通过 keys 里添加这个映射
|
* @param fragment URL 的 fragment,即拼接到 # 中
|
* @return 拼接后的 URL
|
*/
|
public static String append(String base, Map<String, ?> query, Map<String, String> keys, boolean fragment) {
|
UriComponentsBuilder template = UriComponentsBuilder.newInstance();
|
UriComponentsBuilder builder = UriComponentsBuilder.fromUriString(base);
|
URI redirectUri;
|
try {
|
// assume it's encoded to start with (if it came in over the wire)
|
redirectUri = builder.build(true).toUri();
|
} catch (Exception e) {
|
// ... but allow client registrations to contain hard-coded non-encoded values
|
redirectUri = builder.build().toUri();
|
builder = UriComponentsBuilder.fromUri(redirectUri);
|
}
|
template.scheme(redirectUri.getScheme()).port(redirectUri.getPort()).host(redirectUri.getHost())
|
.userInfo(redirectUri.getUserInfo()).path(redirectUri.getPath());
|
|
if (fragment) {
|
StringBuilder values = new StringBuilder();
|
if (redirectUri.getFragment() != null) {
|
String append = redirectUri.getFragment();
|
values.append(append);
|
}
|
for (String key : query.keySet()) {
|
if (values.length() > 0) {
|
values.append("&");
|
}
|
String name = key;
|
if (keys != null && keys.containsKey(key)) {
|
name = keys.get(key);
|
}
|
values.append(name).append("={").append(key).append("}");
|
}
|
if (values.length() > 0) {
|
template.fragment(values.toString());
|
}
|
UriComponents encoded = template.build().expand(query).encode();
|
builder.fragment(encoded.getFragment());
|
} else {
|
for (String key : query.keySet()) {
|
String name = key;
|
if (keys != null && keys.containsKey(key)) {
|
name = keys.get(key);
|
}
|
template.queryParam(name, "{" + key + "}");
|
}
|
template.fragment(redirectUri.getFragment());
|
UriComponents encoded = template.build().expand(query).encode();
|
builder.query(encoded.getQuery());
|
}
|
return builder.build().toUriString();
|
}
|
|
public static String[] obtainBasicAuthorization(HttpServletRequest request) {
|
String clientId;
|
String clientSecret;
|
// 先从 Header 中获取
|
String authorization = request.getHeader("Authorization");
|
authorization = StrUtil.subAfter(authorization, "Basic ", true);
|
if (StringUtils.hasText(authorization)) {
|
authorization = Base64.decodeStr(authorization);
|
clientId = StrUtil.subBefore(authorization, ":", false);
|
clientSecret = StrUtil.subAfter(authorization, ":", false);
|
// 再从 Param 中获取
|
} else {
|
clientId = request.getParameter("client_id");
|
clientSecret = request.getParameter("client_secret");
|
}
|
|
// 如果两者非空,则返回
|
if (StrUtil.isNotEmpty(clientId) && StrUtil.isNotEmpty(clientSecret)) {
|
return new String[]{clientId, clientSecret};
|
}
|
return null;
|
}
|
|
/**
|
* 向指定URL发送GET方法的请求
|
*
|
* @param url 发送请求的URL
|
* @param param 请求参数,请求参数应该是 name1=value1&name2=value2 的形式。
|
* @return URL 所代表远程资源的响应结果
|
*/
|
public static String sendGet(String url, String param) {
|
String result = "";
|
BufferedReader in = null;
|
try {
|
String urlNameString = url + "?" + param;
|
URL realUrl = new URL(urlNameString);
|
// 打开和URL之间的连接
|
URLConnection connection = realUrl.openConnection();
|
// 设置通用的请求属性
|
connection.setRequestProperty("accept", "*/*");
|
connection.setRequestProperty("connection", "Keep-Alive");
|
connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
|
|
// 建立实际的连接
|
connection.connect();
|
// 获取所有响应头字段
|
Map<String, List<String>> map = connection.getHeaderFields();
|
// 遍历所有的响应头字段
|
for (String key : map.keySet()) {
|
System.out.println(key + "--->" + map.get(key));
|
}
|
// 定义 BufferedReader输入流来读取URL的响应
|
in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
|
String line;
|
while ((line = in.readLine()) != null) {
|
result += line;
|
}
|
} catch (Exception e) {
|
System.out.println("发送GET请求出现异常!" + e);
|
e.printStackTrace();
|
}
|
// 使用finally块来关闭输入流
|
finally {
|
try {
|
if (in != null) {
|
in.close();
|
}
|
} catch (Exception e2) {
|
e2.printStackTrace();
|
}
|
}
|
return result;
|
}
|
|
public static String sendGet(String url, Map<String, String> params, String authorization) {
|
String result = "";
|
BufferedReader in = null;
|
try {
|
StringBuilder sb = new StringBuilder();
|
sb.append(url);
|
if (!CollectionUtils.isEmpty(params)) {
|
sb.append("?");
|
params.forEach((k, v) -> {
|
sb.append(k + "=" + v + "&");
|
});
|
sb.append("t=" + System.currentTimeMillis());
|
}
|
String urlNameString = sb.toString();
|
URL realUrl = new URL(urlNameString);
|
// 打开和URL之间的连接
|
URLConnection connection = realUrl.openConnection();
|
// 设置通用的请求属性
|
connection.setRequestProperty("Authorization", authorization);
|
connection.setRequestProperty("accept", "*/*");
|
connection.setRequestProperty("connection", "Keep-Alive");
|
connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
|
|
// 建立实际的连接
|
connection.connect();
|
// 获取所有响应头字段
|
Map<String, List<String>> map = connection.getHeaderFields();
|
// 遍历所有的响应头字段
|
for (String key : map.keySet()) {
|
System.out.println(key + "--->" + map.get(key));
|
}
|
// 定义 BufferedReader输入流来读取URL的响应
|
in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
|
String line;
|
while ((line = in.readLine()) != null) {
|
result += line;
|
}
|
} catch (Exception e) {
|
System.out.println("发送GET请求出现异常!" + e);
|
e.printStackTrace();
|
}
|
// 使用finally块来关闭输入流
|
finally {
|
try {
|
if (in != null) {
|
in.close();
|
}
|
} catch (Exception e2) {
|
e2.printStackTrace();
|
}
|
}
|
return result;
|
}
|
|
/**
|
* 向指定 URL 发送POST方法的请求
|
*
|
* @param url
|
* @param json
|
* @return
|
*/
|
public static String sendPost(String url, String json) {
|
PrintWriter out = null;
|
BufferedReader in = null;
|
String result = "";
|
try {
|
URL realUrl = new URL(url);
|
// 打开和URL之间的连接
|
URLConnection conn = realUrl.openConnection();
|
// 设置通用的请求属性
|
conn.setRequestProperty("content-type", "application/json");
|
conn.setRequestProperty("accept", "*/*");
|
conn.setRequestProperty("connection", "Keep-Alive");
|
conn.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
|
|
// 发送POST请求必须设置如下两行
|
conn.setDoOutput(true);
|
conn.setDoInput(true);
|
// 获取URLConnection对象对应的输出流
|
out = new PrintWriter(conn.getOutputStream());
|
// 发送请求参数
|
out.print(json);
|
// flush输出流的缓冲
|
out.flush();
|
// 定义BufferedReader输入流来读取URL的响应
|
in = new BufferedReader(new InputStreamReader(conn.getInputStream()));
|
String line;
|
while ((line = in.readLine()) != null) {
|
result += line;
|
}
|
} catch (Exception e) {
|
System.out.println("发送 POST 请求出现异常!" + e);
|
e.printStackTrace();
|
}
|
//使用finally块来关闭输出流、输入流
|
finally {
|
try {
|
if (out != null) {
|
out.close();
|
}
|
if (in != null) {
|
in.close();
|
}
|
} catch (IOException ex) {
|
ex.printStackTrace();
|
}
|
}
|
return result;
|
}
|
|
/**
|
* 向指定 URL 发送POST方法的请求
|
*
|
* @param url
|
* @param json
|
* @param authorization
|
* @return
|
*/
|
public static String sendPost(String url, String json, String authorization) {
|
PrintWriter out = null;
|
BufferedReader in = null;
|
String result = "";
|
try {
|
URL realUrl = new URL(url);
|
// 打开和URL之间的连接
|
URLConnection conn = realUrl.openConnection();
|
// 设置通用的请求属性
|
conn.setRequestProperty("Authorization", authorization);
|
conn.setRequestProperty("accept", "*/*");
|
conn.setRequestProperty("connection", "Keep-Alive");
|
conn.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
|
|
// 发送POST请求必须设置如下两行
|
conn.setDoOutput(true);
|
conn.setDoInput(true);
|
// 获取URLConnection对象对应的输出流
|
out = new PrintWriter(conn.getOutputStream());
|
// 发送请求参数
|
out.print(json);
|
// flush输出流的缓冲
|
out.flush();
|
// 定义BufferedReader输入流来读取URL的响应
|
in = new BufferedReader(new InputStreamReader(conn.getInputStream()));
|
String line;
|
while ((line = in.readLine()) != null) {
|
result += line;
|
}
|
} catch (Exception e) {
|
System.out.println("发送 POST 请求出现异常!" + e);
|
e.printStackTrace();
|
}
|
//使用finally块来关闭输出流、输入流
|
finally {
|
try {
|
if (out != null) {
|
out.close();
|
}
|
if (in != null) {
|
in.close();
|
}
|
} catch (IOException ex) {
|
ex.printStackTrace();
|
}
|
}
|
return result;
|
}
|
|
|
}
|