cn.xishan.oftenporter.bridge.http.HttpUtil Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of Porter-Bridge-Http Show documentation
Show all versions of Porter-Bridge-Http Show documentation
转接远程的http接口,服务器响应正确的数据格式必须是JResponse定义的格式。
客户端websocket使用"org.java-websocket:Java-WebSocket:1.5.2",项目地址https://github.com/TooTallNate/Java-WebSocket;
对Java-WebSocket做了适当修改。
The newest version!
package cn.xishan.oftenporter.bridge.http;
import cn.xishan.oftenporter.porter.core.JResponse;
import cn.xishan.oftenporter.porter.core.ResultCode;
import cn.xishan.oftenporter.porter.core.annotation.MayNull;
import cn.xishan.oftenporter.porter.core.annotation.NotNull;
import cn.xishan.oftenporter.porter.core.base.*;
import cn.xishan.oftenporter.porter.core.exception.OftenCallException;
import cn.xishan.oftenporter.porter.core.util.OftenTool;
import cn.xishan.oftenporter.porter.core.util.ResourceUtil;
import cn.xishan.oftenporter.servlet.ContentType;
import com.alibaba.fastjson.JSONObject;
import okhttp3.*;
import okio.BufferedSink;
import javax.net.ssl.*;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.UnsupportedEncodingException;
import java.net.URLEncoder;
import java.nio.charset.Charset;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.TimeUnit;
/**
* Created by 宇宙之灵 on 2015/9/12.
*/
public class HttpUtil {
public interface OnBuilding {
void onBuild(OkHttpClient.Builder builder);
}
public static class TimeoutKey implements Cloneable {
private long connTimeout = -1;
private long writeTimeout = -1;
private long readTimeout = -1;
private long callTimeout = -1;
public TimeoutKey() {
}
public TimeoutKey(long connTimeout, long writeTimeout, long readTimeout) {
this.connTimeout = connTimeout;
this.writeTimeout = writeTimeout;
this.readTimeout = readTimeout;
}
@Override
public TimeoutKey clone() {
try {
TimeoutKey timeoutKey = (TimeoutKey) super.clone();
return timeoutKey;
} catch (CloneNotSupportedException e) {
throw new RuntimeException(e);
}
}
@Override
public int hashCode() {
return (int) (connTimeout + writeTimeout + readTimeout + callTimeout);
}
@Override
public boolean equals(Object obj) {
if (obj instanceof TimeoutKey) {
TimeoutKey timeoutKey = (TimeoutKey) obj;
return this.connTimeout == timeoutKey.connTimeout && this.writeTimeout == timeoutKey.writeTimeout &&
this.readTimeout == timeoutKey.readTimeout && this.callTimeout == timeoutKey.callTimeout;
} else {
return false;
}
}
public long getConnTimeout() {
return connTimeout;
}
public void setConnTimeout(long connTimeout) {
this.connTimeout = connTimeout;
}
public void setConnTimeout(long connTimeout, TimeUnit timeUnit) {
this.setConnTimeout(timeUnit.toMillis(connTimeout));
}
public long getWriteTimeout() {
return writeTimeout;
}
public void setWriteTimeout(long writeTimeout) {
this.writeTimeout = writeTimeout;
}
public void setWriteTimeout(long writeTimeout, TimeUnit timeUnit) {
this.setWriteTimeout(timeUnit.toMillis(writeTimeout));
}
public long getReadTimeout() {
return readTimeout;
}
public void setReadTimeout(long readTimeout) {
this.readTimeout = readTimeout;
}
public void setReadTimeout(long readTimeout, TimeUnit timeUnit) {
this.setReadTimeout(timeUnit.toMillis(readTimeout));
}
public long getCallTimeout() {
return callTimeout;
}
public void setCallTimeout(long callTimeout) {
this.callTimeout = callTimeout;
}
public void setCallTimeout(long callTimeout, TimeUnit timeUnit) {
this.setCallTimeout(timeUnit.toMillis(callTimeout));
}
}
private static final TimeoutKey DEFAULT_TIMEOUT_KEY = new TimeoutKey(30 * 1000, 60 * 1000, 60 * 1000);
private static final X509TrustManager X509_TRUST_MANAGER = new X509TrustManager() {
@Override
public void checkClientTrusted(X509Certificate[] x509Certificates,
String s) throws CertificateException {
}
@Override
public void checkServerTrusted(X509Certificate[] x509Certificates,
String s) throws CertificateException {
}
@Override
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[0];
}
};
static class StreamBody extends RequestBody {
private MediaType mediaType;
private InputStream inputStream;
public StreamBody(MediaType mediaType, InputStream inputStream) {
this.mediaType = mediaType;
this.inputStream = inputStream;
}
@Override
public MediaType contentType() {
return mediaType;
}
@Override
public void writeTo(BufferedSink sink) throws IOException {
try (InputStream in = this.inputStream) {
byte[] buf = new byte[2048];
int n;
while ((n = in.read(buf)) != -1) {
sink.write(buf, 0, n);
}
} finally {
this.inputStream = null;
}
}
}
private static OkHttpClient _getClient(SSLSocketFactory sslSocketFactory, X509TrustManager x509TrustManager,
boolean hasCookie, TimeoutKey timeoutKey, OnBuilding building) {
try {
OkHttpClient.Builder builder = new OkHttpClient.Builder();
if (x509TrustManager == null) {
x509TrustManager = X509_TRUST_MANAGER;
}
if (sslSocketFactory == null) {
SSLContext sslContext = SSLContext.getInstance("TLS");
sslContext.init(null, new TrustManager[]{x509TrustManager}, new SecureRandom());
sslSocketFactory = sslContext.getSocketFactory();
}
builder.sslSocketFactory(sslSocketFactory, x509TrustManager);
if (timeoutKey.connTimeout != -1) {
builder.connectTimeout(timeoutKey.connTimeout, TimeUnit.MILLISECONDS);
}
if (timeoutKey.readTimeout != -1) {
builder.readTimeout(timeoutKey.readTimeout, TimeUnit.MILLISECONDS);
}
if (timeoutKey.writeTimeout != -1) {
builder.writeTimeout(timeoutKey.writeTimeout, TimeUnit.MILLISECONDS);
}
if (timeoutKey.callTimeout != -1) {
builder.callTimeout(timeoutKey.callTimeout, TimeUnit.MILLISECONDS);
}
if (hasCookie) {
builder.cookieJar(new CookieJar() {
private final Map> cookieStore = new ConcurrentHashMap<>();
@Override
public void saveFromResponse(HttpUrl url, List cookies) {
cookieStore.put(url, cookies);
}
@Override
public List loadForRequest(HttpUrl url) {
List cookies = cookieStore.get(url);
return cookies != null ? cookies : Collections.emptyList();
}
});
} else {
builder.cookieJar(CookieJar.NO_COOKIES);
}
if (x509TrustManager == X509_TRUST_MANAGER) {
builder.hostnameVerifier((s, sslSession) -> true);
}
if (building != null) {
building.onBuild(builder);
}
OkHttpClient okHttpClient = builder.build();
return okHttpClient;
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 忽略证书验证。
*
* @return
*/
public static synchronized OkHttpClient getClient() {
return getClient(null, null, false);
}
/**
* 忽略证书验证。
*
* @return
*/
public static synchronized OkHttpClient getClient(TimeoutKey timeoutKey) {
return getClient(null, null, false, timeoutKey);
}
/**
* 可以设置双向认证。
*
* @return
*/
public static synchronized OkHttpClient getClient(SSLSocketFactory sslSocketFactory,
X509TrustManager x509TrustManager, boolean hasCookie) {
return getClient(sslSocketFactory, x509TrustManager, hasCookie, DEFAULT_TIMEOUT_KEY);
}
/**
* 可以设置双向认证。
*
* @return
*/
public static synchronized OkHttpClient getClient(SSLSocketFactory sslSocketFactory,
X509TrustManager x509TrustManager, boolean hasCookie, TimeoutKey timeoutKey) {
return getClient(sslSocketFactory, x509TrustManager, hasCookie, timeoutKey, null);
}
/**
* 可以设置双向认证。
*
* @return
*/
public static synchronized OkHttpClient getClient(SSLSocketFactory sslSocketFactory,
X509TrustManager x509TrustManager, boolean hasCookie, TimeoutKey timeoutKey, OnBuilding building) {
return _getClient(sslSocketFactory, x509TrustManager, hasCookie, timeoutKey, building);
}
/**
* 移除末尾指定的字符(若存在的话)。
*
* @param sb
* @param c 要移除的字符
*/
private static void removeEndChar(StringBuilder sb, char c) {
if (sb.length() > 0 && sb.charAt(sb.length() - 1) == c) {
sb.deleteCharAt(sb.length() - 1);
}
}
/**
* 添加地址参数
*
* @param url 地址
* @param nameValues 如name=123&age=12
* @param afterSharp 是否放在#后面
*/
public static String addUrlParam(String url, String nameValues, boolean afterSharp) {
int index = url.lastIndexOf(afterSharp ? "#" : "?");
if (index == -1) {
return url + (afterSharp ? "#" : "?") + nameValues;
} else {
return url + "&" + nameValues;
}
}
private static void addUrlParams(StringBuilder stringBuilder, InNames.Name[] names,
Object[] values, String encoding) throws UnsupportedEncodingException {
if (names == null || values == null) {
return;
}
for (int i = 0; i < names.length; i++) {
if (values[i] != null) {
stringBuilder.append(URLEncoder.encode(names[i].varName, encoding)).append("=")
.append(URLEncoder.encode(values[i] + "", encoding)).append('&');
}
}
}
private static String dealUrlParams(OftenObject oftenObject, String url) throws UnsupportedEncodingException {
if (oftenObject == null || (oftenObject._fInNames == null && oftenObject._cInNames == null)) {
return url;
}
StringBuilder stringBuilder = new StringBuilder();
String encoding = "utf-8";
if (oftenObject._fInNames != null) {
addUrlParams(stringBuilder, oftenObject._fInNames.nece, oftenObject._fn, encoding);
addUrlParams(stringBuilder, oftenObject._fInNames.unece, oftenObject._fu, encoding);
}
if (oftenObject._cInNames != null) {
addUrlParams(stringBuilder, oftenObject._cInNames.nece, oftenObject._cn, encoding);
addUrlParams(stringBuilder, oftenObject._cInNames.unece, oftenObject._cu, encoding);
}
if (stringBuilder.length() > 0) {
removeEndChar(stringBuilder, '&');
if (url.indexOf('?') == -1) {
url += "?" + stringBuilder;
} else {
url += "&" + stringBuilder;
}
}
return url;
}
private static void addFormParams(FormBody.Builder builder, InNames.Name[] names, Object[] values) {
if (names == null || values == null) {
return;
}
for (int i = 0; i < names.length; i++) {
if (values[i] != null) {
builder.add(names[i].varName, String.valueOf(values[i]));
}
}
}
private static RequestBody dealBodyParams(OftenObject oftenObject, RequestData requestData) {
RequestBody body;
if (requestData != null) {
MediaType mediaType = null;
if (requestData.getContentType() != null) {
if (requestData.getEncoding() != null) {
mediaType = MediaType.parse(requestData.getContentType().getType() + ";charset=" + requestData
.getEncoding());
} else {
mediaType = MediaType.parse(requestData.getContentType().getType());
}
}
if (requestData.getBodyContent() != null) {
Object content = requestData.getBodyContent();
if (content instanceof byte[]) {
byte[] bs = (byte[]) content;
body = RequestBody.create(mediaType, bs);
} else if (content instanceof InputStream) {
body = new StreamBody(mediaType, (InputStream) content);
} else if (content instanceof File) {
File file = (File) content;
body = RequestBody.create(mediaType, file);
} else {
String strContent = String.valueOf(content);
body = RequestBody.create(mediaType, strContent);
}
} else if (requestData.getContentType() == ContentType.MULTIPART_FORM) {
MultipartBody.Builder builder = new MultipartBody.Builder();
builder.setType(mediaType);
Map params = requestData.getParams();
if (params != null) {
for (Map.Entry entry : params.entrySet()) {
String name = entry.getKey();
Object value = entry.getValue();
if (value == null) {
continue;
}
if (value instanceof File) {
File file = (File) value;
RequestBody fileBody = RequestBody
.create(MediaType.parse(ResourceUtil.getMimeType(file.getName())), file);
builder.addFormDataPart(name, file.getName(), fileBody);
} else {
builder.addFormDataPart(name, String.valueOf(value));
}
}
}
body = builder.build();
} else if (requestData.getContentType() == ContentType.APP_FORM_URLENCODED) {
FormBody.Builder builder = new FormBody.Builder(mediaType.charset());
Map params = requestData.getParams();
if (params != null) {
for (Map.Entry entry : params.entrySet()) {
String name = entry.getKey();
Object value = entry.getValue();
if (value == null) {
continue;
} else {
builder.add(name, String.valueOf(value));
}
}
}
body = builder.build();
} else {
JSONObject jsonObject = new JSONObject();
Map params = requestData.getParams();
if (params != null) {
jsonObject.putAll(params);
}
body = RequestBody.create(mediaType, jsonObject.toString());
}
} else {
FormBody.Builder builder = new FormBody.Builder(Charset.forName("utf-8"));
if (oftenObject != null) {
if (oftenObject._fInNames != null) {
addFormParams(builder, oftenObject._fInNames.nece, oftenObject._fn);
addFormParams(builder, oftenObject._fInNames.unece, oftenObject._fu);
}
if (oftenObject._cInNames != null) {
addFormParams(builder, oftenObject._cInNames.nece, oftenObject._cn);
addFormParams(builder, oftenObject._cInNames.unece, oftenObject._cu);
}
}
body = builder.build();
}
return body;
}
/**
* 把请求进行转发。
*
* @param requestData
* @param method
* @param okHttpClient
* @param url
* @param callback 为null表示同步,则返回response;否则表示异步,返回的response为null。
* @return
* @throws IOException
*/
public static Response request(@NotNull RequestData requestData, PortMethod method,
@MayNull OkHttpClient okHttpClient,
String url, Callback callback) throws IOException {
return request(requestData == null ? null : new OftenObjectImpl(method, requestData), method, okHttpClient, url,
callback);
}
/**
* 把请求进行转发。
*
* @param oftenObject 可以为null
* @param method
* @param okHttpClient
* @param url
* @param callback 为null表示同步,则返回response;否则表示异步,返回的response为null。
* @return
* @throws IOException
*/
public static Response request(@MayNull OftenObject oftenObject, PortMethod method,
@MayNull OkHttpClient okHttpClient, String url, Callback callback) throws IOException {
if (okHttpClient == null) {
okHttpClient = getClient(null, null, false);
}
Response response = null;
try {
RequestData requestData = null;
Request.Builder builder = new Request.Builder();
if (oftenObject instanceof OftenObjectImpl) {
requestData = ((OftenObjectImpl) oftenObject).getRequestData();
Map headers = requestData.getHeaders();
if (OftenTool.notEmptyOf(headers)) {
for (Map.Entry entry : headers.entrySet()) {
builder.addHeader(entry.getKey(), entry.getValue());
}
}
}
Request request;
if (method == null) {
method = PortMethod.GET;
}
switch (method) {
case PUT: {
RequestBody requestBody = dealBodyParams(oftenObject, requestData);
request = builder.url(url).put(requestBody).build();
}
break;
case POST: {
RequestBody requestBody = dealBodyParams(oftenObject, requestData);
request = builder.url(url).post(requestBody).build();
}
break;
case GET: {
url = dealUrlParams(oftenObject, url);
request = builder.url(url).get().build();
}
break;
case DELETE: {
url = dealUrlParams(oftenObject, url);
request = builder.url(url).delete().build();
}
break;
default:
throw new RuntimeException("not support:" + method);
}
if (callback == null) {
response = okHttpClient.newCall(request).execute();
} else {
okHttpClient.newCall(request).enqueue(callback);
}
} catch (IOException e) {
throw e;
}
return response;
}
public static JResponse requestJResponse(@MayNull RequestData requestData, PortMethod method,
@MayNull OkHttpClient okHttpClient, String url, JRCallback jrCallback) {
return requestJResponse(requestData == null ? null : new OftenObjectImpl(method, requestData), method,
okHttpClient,
url,
jrCallback);
}
public static String requestString(@MayNull RequestData requestData, PortMethod method,
@MayNull OkHttpClient okHttpClient, String url) {
ResponseBody responseBody = null;
Response response = null;
try {
response = request(requestData, method, okHttpClient, url, null);
int code = response.code();
if (code == 200 || code == 201) {
responseBody = response.body();
return responseBody.string();
} else if (code == 204) {
return null;
} else {
throw new OftenCallException("errcode=" + code + ",msg=" + response.message());
}
} catch (OftenCallException e) {
throw e;
} catch (Throwable e) {
throw new OftenCallException(e);
} finally {
OftenTool.close(responseBody);
OftenTool.close(response);
}
}
public static byte[] requestBytes(@MayNull RequestData requestData, PortMethod method,
@MayNull OkHttpClient okHttpClient, String url) {
ResponseBody responseBody = null;
Response response = null;
try {
response = request(requestData, method, okHttpClient, url, null);
int code = response.code();
if (code == 200 || code == 201) {
responseBody = response.body();
return responseBody.bytes();
} else if (code == 204) {
return null;
} else {
throw new OftenCallException("errcode=" + code + ",msg=" + response.message());
}
} catch (OftenCallException e) {
throw e;
} catch (Throwable e) {
throw new OftenCallException(e);
} finally {
OftenTool.close(responseBody);
OftenTool.close(response);
}
}
private static JResponse toJResponse(Response response) {
JResponse jResponse;
ResponseBody responseBody = null;
try {
int code = response.code();
if (code == 200 || code == 201) {
responseBody = response.body();
String json = responseBody.string();
jResponse = JResponse.fromJSON(json);
} else if (code == 204) {
jResponse = new JResponse(ResultCode.SUCCESS);
} else {
jResponse = new JResponse(code);
jResponse.setDescription(response.message());
}
} catch (IOException e) {
jResponse = onIOException(e);
} catch (JResponse.JResponseFormatException e) {
jResponse = new JResponse();
jResponse.setCode(ResultCode.PARAM_DEAL_EXCEPTION);
jResponse.setDescription(e.toString());
jResponse.setExCause(e);
} finally {
OftenTool.close(responseBody);
OftenTool.close(response);
}
return jResponse;
}
/**
* 把数据发向服务器,并接受响应结果。(同步的)
*
* @param oftenObject 可以为null
* @param method 像服务器发起的请求方法
* @param okHttpClient
* @param url url地址
* @param jrCallback
* @return
*/
public static JResponse requestJResponse(@MayNull OftenObject oftenObject, PortMethod method,
@MayNull OkHttpClient okHttpClient, String url, final JRCallback jrCallback) {
JResponse jResponse = null;
try {
if (jrCallback == null) {
Response response = request(oftenObject, method, okHttpClient, url, null);
jResponse = toJResponse(response);
} else {
request(oftenObject, method, okHttpClient, url, new Callback() {
@Override
public void onFailure(Call call, IOException e) {
jrCallback.onResult(onIOException(e));
}
@Override
public void onResponse(Call call, Response response) throws IOException {
jrCallback.onResult(toJResponse(response));
}
});
}
} catch (IOException e) {
jResponse = onIOException(e);
if (jrCallback != null) {
jrCallback.onResult(jResponse);
}
}
return jResponse;
}
private static JResponse onIOException(IOException e) {
JResponse jResponse = new JResponse();
jResponse.setCode(ResultCode.NET_EXCEPTION);
jResponse.setDescription(e.toString());
jResponse.setExCause(e);
return jResponse;
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy