Okhttp简介
okhttp是现代化应用程序的网络通信的方式。它用来帮助程序交换数据和媒体信息,使用okhttp可以让你的程序加载物料(翻译为服务器数据更合适在)更加高效、更节省网络带宽。
okhttp通过以下措施让你的网络更加高效
1. HTTP/2支持对同一个host的所有网络请求 共享socket。
2. 在不启用HTTP/2的情况,连接池能减少潜在的网络请求。
3. 透明GZIP技术压缩了下载数据的大小。
4. 结果缓存技术避免重复的网络请求。
OkHttp在网络出现问题时,仍然能支持良好的运行。它能解决常见的网络连接问题。如果你的服务端有多个ip地址,okhttp会在第一个地址连接失败时,自动尝试备用地址。 这种技术在你的服务器有多地备份时,是必须要用到的。OkHttp支持现代TLS特性(TLS 1.3、ALPN、证书固定)。可以将其配置为回滚以实现广播连接。
Okhttp优点
1. 支持HTTP2/SPDY(SPDY是Google开发的基于TCP的传输层协议,用以最小化网络延迟,提升网络速度,优化用户的网络使用体验)。
2. socket自动选择最好路线,并支持自动重连,拥有自动维护的socket连接池,减少握手次数,减少了请求延迟,共享Socket,减少对服务器的请求次数。
3. 基于Headers的缓存策略减少重复的网络请求。
4. 拥有Interceptors轻松处理请求与响应(自动处理GZip压缩)。
Okhttp的应用
用于替代HttpUrlConnection和Apache HttpClient
Android4.4开始,google已经开始将源码中的HttpURLConnection替换为OkHttp
Android6.0里已移除HttpClient。
OKhttp的功能
- PUT,DELETE,POST,GET等请求
- 文件的上传下载
- 加载图片(内部会图片大小自动压缩)
- 支持请求回调,直接返回对象、对象集合
- 支持session的保持
使用方式
以下代码在项目里,项目地址:https://gitee.com/urasaki/RxJava2AndRetrofit2
1.首先添加访问网络权限在manifest里。
<!-- 允许访问网络的权限 -->
<uses-permission android:name="android.permission.INTERNET" />
2.添加依赖(如果同步失败,可能是因为公司的网络有好多情况下连不到Google的仓库,所以就要连接自己的手机热点进行同步,手机热点一般会同步成功的,但是注意流量消耗)。
//okhttp3网络框架导入(我用的Android Studio 3.0.1)
implementation 'com.squareup.okhttp3:okhttp:3.12.0'
//fastjson(阿里云json解析框架导入)
implementation 'com.alibaba:fastjson:1.2.61'
3.初始化Okhttp3。
(1)Okhttp3的初始化。
private static final String TAG = Okhttp3Manager.class.getSimpleName();
private OkHttpClient client;
private static Okhttp3Manager manager;
public static final int UPDATA = 666;
/**
* 单例模式,所以构造函数私有化
*/
private Okhttp3Manager() {
//创建OkHttpClient对象
client = new OkHttpClient.Builder()
.connectTimeout(5000, TimeUnit.MILLISECONDS) //连接超时
.readTimeout(5000, TimeUnit.MILLISECONDS) //读取超时
.writeTimeout(5000, TimeUnit.MILLISECONDS) //写入超时
.addInterceptor(new AddAccessTokenInterceptor(BaseApplication.getInstance())) //拦截器用于设置header
.addInterceptor(new ReceivedAccessTokenInterceptor(BaseApplication.getInstance())) //拦截器用于接收并持久化cookie
.sslSocketFactory(SSLSocketManager.getSSLSocketFactory())//配置(只有https请求需要配置)
.hostnameVerifier(SSLSocketManager.getHostnameVerifier())//配置(只有https请求需要配置)
// .proxy(Proxy.NO_PROXY)
.build();
}
/**
* 线程安全的单例模式,整个项目中只有一个okhttp3实例
*
* @return
*/
public static Okhttp3Manager getInstance() {
if (manager == null) {
synchronized (Okhttp3Manager.class) {
if (manager == null) {
manager = new Okhttp3Manager();
}
}
}
return manager;
}
(2)添加token拦截器(关于accessToken的详细说明,请看还傻傻分不清 Cookie、Session、Token、JWT?_UrasakiNakajima的博客-CSDN博客_jwt和token区别。)
public class AddTokenInterceptor implements Interceptor {
private static final String TAG = "AddCookiesInterceptor";
private BaseApplication baseApplication;
public AddTokenInterceptor(BaseApplication baseApplication) {
super();
this.baseApplication = baseApplication;
}
@NonNull
@Override
public Response intercept(@NonNull Chain chain) throws IOException {
Request.Builder builder = chain.request().newBuilder();
//添加accessToken
String accessToken = baseApplication.getAccessToken();
if (!TextUtils.isEmpty(accessToken)) {
builder.addHeader("accessToken", accessToken);
LogManager.i(TAG, "accessToken*****" + accessToken);
}
// //添加cookie
// String cookie = baseApplication.getCookie();
// if (cookie != null && !"".equals(cookie)) {
// builder.addHeader("cookie", cookie);
// LogManager.i(TAG, "cookie*****" + cookie);
// }
// //添加用户代理
// builder.removeHeader("User-Agent")
// .addHeader("User-Agent",
// SystemManager.getUserAgent(baseApplication.getApplicationContext())).build();
// builder.removeHeader("User-Agent")//移除旧的
// .addHeader("User-Agent", WebSettings.getDefaultUserAgent(baseApplication));//添加真正的头部
return chain.proceed(builder.build());
}
}
public class ReceivedTokenInterceptor implements Interceptor {
private static final String TAG = "ReceivedCookiesInterceptor";
private BaseApplication baseApplication;
public ReceivedTokenInterceptor(Context context) {
super();
baseApplication = (BaseApplication) context.getApplicationContext();
}
@NonNull
@Override
public Response intercept(@NonNull Chain chain) throws IOException {
Response originalResponse = chain.proceed(chain.request());
//这里获取请求返回的accessToken
String accessToken = originalResponse.header("accessToken");
LogManager.i(TAG, "originalResponse appToken*****" + accessToken);
if (!TextUtils.isEmpty(accessToken)) {
baseApplication.setAccessToken(accessToken);
LogManager.i(TAG, "accessToken*****" + accessToken);
}
// //这里获取请求返回的cookie
// if (!originalResponse.headers("set-cookie").isEmpty()) {
// String cookie = originalResponse.header("set-cookie").split(";")[0];
// mineApplication.setCookie(cookie);
// LogManager.i(TAG, "cookie*****" + cookie);
// }
Response.Builder builder = originalResponse.newBuilder();
return builder.build();
}
}
(3)Application中的Shared存储(用于存储accessToken)。
//声明 初始化
protected SharedPreferences sp;
protected SharedPreferences.Editor editor;
protected static final int MODE = Context.MODE_PRIVATE;
//初始化(在Appcation中的onCreate函数里)
//文件为mySp 存放在/data/data/<packagename>/shared_prefs/目录下的
sp = getSharedPreferences("app", MODE);
editor = sp.edit();
//在Application里添加函数
public void setAccessToken(String accessToken) {
LogManager.i(TAG, "setAccessToken***" + accessToken);
editor.putString("accessToken", accessToken);
editor.commit();
}
public void setLogout() {
LogManager.i(TAG, "setLogout***");
// editor.clear();
editor.remove("accessToken");
editor.remove("isLogin");
editor.commit();
}
(4)添加SSLSocketManager类。(https请求才需要写并配置,http请求不用配置)。
package com.phone.common_library.manager;
import java.security.SecureRandom;
import java.security.cert.X509Certificate;
import javax.net.ssl.HostnameVerifier;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSession;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;
import javax.net.ssl.X509TrustManager;
/**
* okhttp3忽略https证书
*/
public class SSLSocketManager {
/**
* 获取这个SSLSocketFactory
*
* @return
*/
public static SSLSocketFactory getSSLSocketFactory() {
try {
SSLContext sslContext = SSLContext.getInstance("SSL");
sslContext.init(null, getTrustManager(), new SecureRandom());
return sslContext.getSocketFactory();
} catch (Exception e) {
throw new RuntimeException(e);
}
}
/**
* 获取trustManager
*
* @return
*/
public static TrustManager[] getTrustManager() {
TrustManager[] trustManager = new TrustManager[]{
new X509TrustManager() {
@Override
public void checkClientTrusted(X509Certificate[] chain, String authType) {
}
@Override
public void checkServerTrusted(X509Certificate[] chain, String authType) {
}
@Override
public X509Certificate[] getAcceptedIssuers() {
return new X509Certificate[]{};
}
}
};
return trustManager;
}
/**
* 获取hostnameVerifier
*
* @return
*/
public static HostnameVerifier getHostnameVerifier() {
HostnameVerifier hostnameVerifier = new HostnameVerifier() {
@Override
public boolean verify(String s, SSLSession sslSession) {
return true;
}
};
return hostnameVerifier;
}
}
4.自定义接口。
public interface OnCommonSingleParamCallback<T> {
void onSuccess(T success);
void onError(String error);
}
5.自定义子线程切换主线程管理类MainThreadManager。
public class MainThreadManager {
private Handler mainThreadHandler;
private OnSubThreadToMainThreadCallback onSubThreadToMainThreadCallback;
public MainThreadManager() {
}
public MainThreadManager(OnSubThreadToMainThreadCallback onSubThreadToMainThreadCallback) {
this.onSubThreadToMainThreadCallback = onSubThreadToMainThreadCallback;
if (Looper.myLooper() != Looper.getMainLooper()) {
// If we finish marking off of the main thread, we need to
// actually do it on the main thread to ensure correct ordering.
mainThreadHandler = new Handler(Looper.getMainLooper());
mainThreadHandler.post(new Runnable() {
@Override
public void run() {
onSubThreadToMainThreadCallback.onSuccess();
mainThreadHandler.removeCallbacksAndMessages(null);
mainThreadHandler = null;
}
});
} else {
onSubThreadToMainThreadCallback.onSuccess();
}
}
public void setOnSubThreadToMainThreadCallback(OnSubThreadToMainThreadCallback onSubThreadToMainThreadCallback) {
this.onSubThreadToMainThreadCallback = onSubThreadToMainThreadCallback;
}
/**
* 子线程到主线程
*/
public void subThreadToUIThread() {
if (Looper.myLooper() != Looper.getMainLooper()) {
// If we finish marking off of the main thread, we need to
// actually do it on the main thread to ensure correct ordering.
mainThreadHandler = new Handler(Looper.getMainLooper());
mainThreadHandler.post(new Runnable() {
@Override
public void run() {
onSubThreadToMainThreadCallback.onSuccess();
mainThreadHandler.removeCallbacksAndMessages(null);
mainThreadHandler = null;
}
});
} else {
onSubThreadToMainThreadCallback.onSuccess();
}
}
}
6.get请求,异步方式。
/**
* get请求,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param onCommonSingleParamCallback
*/
public void getAsync(String url,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
//2.创建Request对象,设置一个url地址(百度地址),设置请求方式。
Request request = new Request.Builder().url(url).method("GET", null).build();
// Request request = new Request.Builder()
// .url(url)
// .get()//默认就是GET请求,可以不写(最好写上,要清晰表达出来)
// .build();
//3.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "getAsync onFailure e*******" + e.toString());
LogManager.i(TAG, "getAsync onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "getAsync onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
7.get请求,携带请求参数,异步方式。
/**
* get请求,添加请求参数,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param bodyParams
* @param onCommonSingleParamCallback
*/
public void getAsync(String url,
Map<String, String> bodyParams,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
String urlNew = url;
// 设置HTTP请求参数
urlNew += getBodyParams(bodyParams);
//2.创建Request对象,设置一个url地址,设置请求方式。
Request request = new Request.Builder().url(urlNew).get().build();
// Request request = new Request.Builder()
// .url(url)
// .get()//默认就是GET请求,可以不写(最好写上,要清晰表达出来)
// .build();
//3.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "getAsync onFailure e*******" + e.toString());
LogManager.i(TAG, "getAsync onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "getAsync onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
/**
* 添加参数
*
* @param bodyParams
* @return
*/
private String getBodyParams(Map<String, String> bodyParams) {
//1.添加请求参数
//遍历map中所有参数到builder
if (bodyParams != null && bodyParams.size() > 0) {
StringBuffer stringBuffer = new StringBuffer("?");
for (String key : bodyParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
//如果参数不是null并且不是"",就拼接起来
stringBuffer.append("&");
stringBuffer.append(key);
stringBuffer.append("=");
stringBuffer.append(bodyParams.get(key));
}
}
return stringBuffer.toString();
} else {
return "";
}
}
/**
* 添加headers
*
* @param headerParams
* @return
*/
private Headers setHeaderParams(Map<String, String> headerParams) {
Headers headers = null;
Headers.Builder headersbuilder = new Headers.Builder();
if (headerParams != null && headerParams.size() > 0) {
for (String key : headerParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
//如果参数不是null并且不是"",就拼接起来
headersbuilder.add(key, headerParams.get(key));
}
}
}
headers = headersbuilder.build();
return headers;
}
8.get请求,添加请求参数和header参数,异步方式。
/**
* get请求,添加请求参数和header参数,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param headerParams
* @param bodyParams
* @param onCommonSingleParamCallback
*/
public void getAsync(String url,
Map<String, String> headerParams,
Map<String, String> bodyParams,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
String urlNew = url;
// 设置HTTP请求参数
urlNew += getBodyParams(bodyParams);
Headers headers = setHeaderParams(headerParams);
//2.创建Request对象,设置一个url地址,设置请求方式。
Request request = new Request.Builder().url(urlNew).get().headers(headers).build();
// Request request = new Request.Builder()
// .url(url)
// .get()//默认就是GET请求,可以不写(最好写上,要清晰表达出来)
// .build();
//3.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "getAsync onFailure e*******" + e.toString());
LogManager.i(TAG, "getAsync onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "getAsync onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
9.post请求提交字符串,异步方式。
/**
* post请求提交字符串,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param bodyParams
* @param onCommonSingleParamCallback
*/
public void postAsyncString(String url,
Map<String, String> bodyParams,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
JSONObject jsonObject = new JSONObject(bodyParams);
String requestData = jsonObject.toString();
LogManager.i(TAG, "postAsyncString requestData*****" + requestData);
MediaType mediaType = MediaType.parse("application/json; charset=utf-8");//"类型,字节码"
//2.通过RequestBody.create 创建requestBody对象
RequestBody requestBody = RequestBody.create(mediaType, requestData);
//3.创建Request对象,设置URL地址,将RequestBody作为post方法的参数传入
Request request = new Request.Builder().url(url).post(requestBody).build();
//4.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncString onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncString onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsyncString onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
10.post请求不传递参数,异步方式。
/**
* post请求不携带参数,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param onCommonSingleParamCallback
*/
public void postAsync(String url,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
//这句话是重点Request
//3.创建Request对象,设置URL地址,将RequestBody作为post方法的参数传入
Request request = new Request.Builder().post(RequestBody.create(null, "")).url(url).build();
//4.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsync onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsync onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
// MainThreadManager mainThreadManager2 =
// new MainThreadManager(new OnSubThreadToMainThreadCallback() {
// @Override
// public void onSuccess() {
// onCommonSingleParamCallback.onError(context.getResources().getString(R.string.network_sneak_off));
// }
// });
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsync onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
11.post请求提交流,异步方式。
/**
* post请求提交流,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param requestData
* @param onCommonSingleParamCallback
*/
public void postAsyncStream(String url,
String requestData,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
LogManager.i(TAG, "requestData*****" + requestData);
//2.通过new RequestBody 创建requestBody对象
RequestBody requestBody = new RequestBody() {
@Nullable
@Override
public MediaType contentType() {
return MediaType.parse("text/x-markdown; charset=utf-8");
}
@Override
public void writeTo(@NonNull BufferedSink sink) throws IOException {
sink.writeUtf8(requestData);
}
};
//3.创建Request对象,设置URL地址,将RequestBody作为post方法的参数传入
Request request = new Request.Builder().url(url).post(requestBody).build();
//4.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncStream onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncStream onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsyncStream onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
12.post请求提交键值对,异步方式。
/**
* post请求提交键值对,异步方式,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param bodyParams
* @param onCommonSingleParamCallback
*/
public void postAsyncKeyValuePairs(String url,
Map<String, String> bodyParams,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
if (bodyParams != null && bodyParams.size() > 0) {
LogManager.i(TAG, "postAsyncKeyValuePairs bodyParams*****" + bodyParams.toString());
LogManager.i(TAG, "postAsyncKeyValuePairs bodyParams json*****" + MapManager.mapToJsonStr(bodyParams));
}
//2.通过new FormBody()调用build方法,创建一个RequestBody,可以用add添加键值对
FormBody.Builder formEncodingBuilder = new FormBody.Builder();
//1.添加请求参数
//遍历map中所有参数到builder
if (bodyParams != null && bodyParams.size() > 0) {
for (String key : bodyParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
formEncodingBuilder.add(key, bodyParams.get(key));
}
}
}
//构建请求体
RequestBody requestBody = formEncodingBuilder.build();
//3.创建Request对象,设置URL地址,将RequestBody作为post方法的参数传入
Request request = new Request.Builder().url(url).post(requestBody).build();
//4.创建一个call对象,参数就是Request请求对象
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncKeyValuePairs onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncKeyValuePairs onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
// MainThreadManager mainThreadManager2 =
// new MainThreadManager(new OnSubThreadToMainThreadCallback() {
// @Override
// public void onSuccess() {
// onCommonSingleParamCallback.onError(context.getResources().getString(R.string.network_sneak_off));
// }
// });
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsyncKeyValuePairs onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
13.post请求上传Form表单,异步方式。
/**
* post请求上传Form表单,异步方式,提交表单,是在子线程中执行的,需要切换到主线程才能更新UI
* 这个函数可以把服务器返回的数据统一处理
*
* @param url
* @param bodyParams
* @param onCommonSingleParamCallback
*/
public void postAsyncForm(String url,
Map<String, String> bodyParams,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
if (bodyParams != null && bodyParams.size() > 0) {
LogManager.i(TAG, "postAsyncForm bodyParams String*******" + bodyParams.toString());
LogManager.i(TAG, "postAsyncForm bodyParams json*****" + MapManager.mapToJsonStr(bodyParams));
}
// form 表单形式上传
MultipartBody.Builder multipartBodyBuilder = new MultipartBody.Builder().setType(MultipartBody.FORM);
//1.添加请求参数
//遍历map中所有参数到builder
if (bodyParams != null && bodyParams.size() > 0) {
for (String key : bodyParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
multipartBodyBuilder.addFormDataPart(key, bodyParams.get(key));
}
}
}
//构建请求体
RequestBody requestBody = multipartBodyBuilder.build();
Request request = new Request.Builder().post(requestBody).url(url).build();
//3 将Request封装为Call
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncForm onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncForm onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
// //服务器返回的是加密字符串,要解密
// String dataEncrypt = response.body().string();
// LogManager.i(TAG, "login onResponse dataEncrypt*****" + dataEncrypt);
String responseString = response.body().string();
// try {
// responseString = AESManager.aesDecrypt(dataEncrypt);
LogManager.i(TAG, "postAsyncForm onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
// } catch (Exception e) {
// e.printStackTrace();
// }
}
});
}
14.post请求上传Form表单和图片文件(上传java服务器),异步方式。
/**
* post请求上传Form表单和图片文件(上传java服务器),异步方式,提交表单,是在子线程中执行的,需要切换到主线程才能更新UI
* 这个函数可以把服务器返回的数据统一处理
*
* @param url
* @param bodyParams
* @param fileList
* @param onCommonSingleParamCallback
*/
public void postAsyncFormAndFiles(String url,
Map<String, String> bodyParams,
List<File> fileList,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
if (bodyParams != null && bodyParams.size() > 0) {
LogManager.i(TAG, "postAsyncFormAndFiles bodyParams String*******" + bodyParams.toString());
LogManager.i(TAG, "postAsyncFormAndFiles bodyParams json*****" + MapManager.mapToJsonStr(bodyParams));
}
// MediaType MEDIA_TYPE = MediaType.parse("image/png");
MediaType MEDIA_TYPE = MediaType.parse("image/*");
// form 表单形式上传
MultipartBody.Builder multipartBodyBuilder = new MultipartBody.Builder().setType(MultipartBody.FORM);
//1.添加请求参数
//遍历map中所有参数到builder
if (bodyParams != null && bodyParams.size() > 0) {
for (String key : bodyParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
multipartBodyBuilder.addFormDataPart(key, bodyParams.get(key));
}
}
}
//遍历fileList中所有图片绝对路径到builder,并约定key如"upload"作为上传php服务器接受多张图片的key
if (fileList != null && fileList.size() > 0) {
for (int i = 0; i < fileList.size(); i++) {
if (fileList.get(i).exists()) {
multipartBodyBuilder.addFormDataPart("upload", fileList.get(i).getName(), RequestBody.create(MEDIA_TYPE, fileList.get(i)));
}
}
} else {
LogManager.i(TAG, "postAsyncFormAndFiles fileList.size() = 0");
}
//构建请求体
RequestBody requestBody = multipartBodyBuilder.build();
Request request = new Request.Builder().post(requestBody).url(url).build();
//3 将Request封装为Call
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncFormAndFiles onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncFormAndFiles onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsyncFormAndFiles onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
15.post请求上传Form表单和文件(上传php服务器),异步方式。
/**
* post请求上传Form表单和文件(上传php服务器),异步方式,提交表单,是在子线程中执行的,需要切换到主线程才能更新UI
*
* @param url
* @param bodyParams
* @param fileList
* @param onCommonSingleParamCallback
*/
public void postAsyncPhpFormAndFiles(String url,
Map<String, String> bodyParams,
List<File> fileList,
OnCommonSingleParamCallback<String> onCommonSingleParamCallback) {
if (bodyParams != null && bodyParams.size() > 0) {
LogManager.i(TAG, "postAsyncPhpFormAndFiles bodyParams String*******" + bodyParams.toString());
LogManager.i(TAG, "postAsyncPhpFormAndFiles bodyParams json*****" + MapManager.mapToJsonStr(bodyParams));
}
MediaType MEDIA_TYPE = MediaType.parse("image/png");
// form 表单形式上传
MultipartBody.Builder multipartBodyBuilder = new MultipartBody.Builder().setType(MultipartBody.FORM);
//1.添加请求参数
//遍历map中所有参数到builder
if (bodyParams != null && bodyParams.size() > 0) {
for (String key : bodyParams.keySet()) {
if (!TextUtils.isEmpty(key) && !TextUtils.isEmpty(bodyParams.get(key))) {
multipartBodyBuilder.addFormDataPart(key, bodyParams.get(key));
}
}
}
//遍历fileList中所有图片绝对路径到builder,并约定key如"upload[]"作为php服务器接受多张图片的key
if (fileList != null && fileList.size() > 0) {
for (int i = 0; i < fileList.size(); i++) {
if (fileList.get(i).exists()) {
multipartBodyBuilder.addFormDataPart("upload[]", fileList.get(i).getName(), RequestBody.create(MEDIA_TYPE, fileList.get(i)));
}
}
}
//构建请求体
RequestBody requestBody = multipartBodyBuilder.build();
Request request = new Request.Builder().post(requestBody).url(url).build();
//3 将Request封装为Call
Call call = client.newCall(request);
//4 执行Call
call.enqueue(new Callback() {
@Override
public void onFailure(@NonNull Call call, @NonNull IOException e) {
LogManager.i(TAG, "postAsyncPhpFormAndFiles onFailure e*******" + e.toString());
LogManager.i(TAG, "postAsyncPhpFormAndFiles onFailure e detailMessage*******" + e.getMessage());
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.network_sneak_off));
}
});
mainThreadManager.subThreadToUIThread();
}
@Override
public void onResponse(@NonNull Call call, @NonNull Response response) throws IOException {
String responseString = response.body().string();
LogManager.i(TAG, "postAsyncPhpFormAndFiles onResponse responseString*****" + responseString);
MainThreadManager mainThreadManager = new MainThreadManager();
mainThreadManager.setOnSubThreadToMainThreadCallback(new OnSubThreadToMainThreadCallback() {
@Override
public void onSuccess() {
if (!TextUtils.isEmpty(responseString)) {
BaseResponse baseResponse;
try {
baseResponse = JSON.parseObject(responseString, BaseResponse.class);
} catch (Exception e) {
//如果不是标准json字符串,就返回错误提示
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
return;
}
onCommonSingleParamCallback.onSuccess(responseString);
} else {
onCommonSingleParamCallback.onError(BaseApplication.getInstance().getResources().getString(R.string.server_sneak_off));
}
}
});
mainThreadManager.subThreadToUIThread();
}
});
}
16.判断网络是否可用。
/**
* 判断网络是否可用
*
* @param context
* @return
*/
public static boolean isNetworkAvailable(Context context) {
ConnectivityManager connectivityManager = (ConnectivityManager) context.getApplicationContext()
.getSystemService(Context.CONNECTIVITY_SERVICE);
if (connectivityManager != null) {
//如果仅仅是用来判断网络连接
//connectivityManager.getActiveNetworkInfo().isAvailable();
NetworkInfo[] info = connectivityManager.getAllNetworkInfo();
// LogManager.i(TAG, "isNetworkAvailable*****" + info.toString());
if (info != null) {
for (int i = 0; i < info.length; i++) {
if (info[i].getState() == NetworkInfo.State.CONNECTED) {
return true;
}
}
}
}
return false;
}
17.代码中定义的字符串的string值。
<string name="network_sneak_off">網絡開小差了</string>
<string name="server_sneak_off">服務器開小差了</string>
如对此有疑问,请联系qq1164688204。
推荐Android开源项目
项目功能介绍:RxJava2和Retrofit2项目,添加自动管理token功能,添加RxJava2生命周期管理,使用App架构设计是MVP模式和MVVM模式,同时使用组件化,部分代码使用Kotlin,此项目持续维护中。
项目地址:https://gitee.com/urasaki/RxJava2AndRetrofit2