diff --git a/HelpDoc.md b/HelpDoc.md index 535e748..02baecd 100644 --- a/HelpDoc.md +++ b/HelpDoc.md @@ -293,7 +293,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(activity) { @Override - public void onHttpSuccess(HttpData data) { + public void onHttpSuccess(@NonNull HttpData data) { toast("登录成功"); } }); @@ -339,7 +339,7 @@ EasyHttp.post(this) .request(new OnUpdateListener() { @Override - public void onUpdateStart(Call call) { + public void onUpdateStart(@NonNull IRequestApi api) { mProgressBar.setVisibility(View.VISIBLE); } @@ -349,17 +349,17 @@ EasyHttp.post(this) } @Override - public void onUpdateSuccess(Void result) { + public void onUpdateSuccess(@NonNull Void result) { toast("上传成功"); } @Override - public void onUpdateFail(Throwable throwable) { + public void onUpdateFail(@NonNull Throwable throwable) { toast("上传失败"); } @Override - public void onUpdateEnd(Call call) { + public void onUpdateEnd(@NonNull IRequestApi api) { mProgressBar.setVisibility(View.GONE); } }); @@ -385,29 +385,29 @@ EasyHttp.download(this) .listener(new OnDownloadListener() { @Override - public void onDownloadStart(File file) { + public void onDownloadStart(@NonNull File file) { mProgressBar.setVisibility(View.VISIBLE); } @Override - public void onDownloadProgressChange(File file, int progress) { + public void onDownloadProgressChange(@NonNull File file, int progress) { mProgressBar.setProgress(progress); } @Override - public void onDownloadSuccess(File file) { + public void onDownloadSuccess(@NonNull File file) { toast("下载完成:" + file.getPath()); installApk(XxxActivity.this, file); } @Override - public void onDownloadFail(File file, Throwable throwable) { + public void onDownloadFail(@NonNull File file, @NonNull Throwable throwable) { toast("下载失败:" + throwable.getMessage()); file.delete(); } @Override - public void onDownloadEnd(File file) { + public void onDownloadEnd(@NonNull File file) { mProgressBar.setVisibility(View.GONE); } @@ -437,7 +437,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(Xxx data) { + public void onHttpSuccess(@NonNull Xxx data) { } }); @@ -469,28 +469,25 @@ try { ```java public final class RequestHandler implements IRequestHandler { - private final Application mApplication; - private final MMKV mMmkv; - - public RequestHandler(Application application) { - mApplication = application; - mMmkv = MMKV.mmkvWithID("http_cache_id"); - } - - .................. - @Nullable @Override public Object readCache(@NonNull HttpRequest httpRequest, @NonNull Type type, long cacheTime) { String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); - String cacheValue = HttpCacheManager.getMmkv().getString(cacheKey, null); - if (cacheValue == null || "".equals(cacheValue) || "{}".equals(cacheValue)) { + String cacheValue = HttpCacheManager.readHttpCache(cacheKey); + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { return null; } - EasyLog.printLog(httpRequest, "----- readCache cacheKey -----"); + EasyLog.printLog(httpRequest, "----- read cache key -----"); EasyLog.printJson(httpRequest, cacheKey); - EasyLog.printLog(httpRequest, "----- readCache cacheValue -----"); + EasyLog.printLog(httpRequest, "----- read cache value -----"); EasyLog.printJson(httpRequest, cacheValue); + EasyLog.printLog(httpRequest, "cacheTime = " + cacheTime); + boolean cacheInvalidate = HttpCacheManager.isCacheInvalidate(cacheKey, cacheTime); + EasyLog.printLog(httpRequest, "cacheInvalidate = " + cacheInvalidate); + if (cacheInvalidate) { + // 表示缓存已经过期了,直接返回 null 给外层,表示缓存不可用 + return null; + } return GsonFactory.getSingletonGson().fromJson(cacheValue, type); } @@ -498,50 +495,131 @@ public final class RequestHandler implements IRequestHandler { public boolean writeCache(@NonNull HttpRequest httpRequest, @NonNull Response response, @NonNull Object result) { String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); String cacheValue = GsonFactory.getSingletonGson().toJson(result); - if (cacheValue == null || "".equals(cacheValue) || "{}".equals(cacheValue)) { + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { return false; } - EasyLog.printLog(httpRequest, "----- writeCache cacheKey -----"); + EasyLog.printLog(httpRequest, "----- write cache key -----"); EasyLog.printJson(httpRequest, cacheKey); - EasyLog.printLog(httpRequest, "----- writeCache cacheValue -----"); + EasyLog.printLog(httpRequest, "----- write cache value -----"); EasyLog.printJson(httpRequest, cacheValue); - return HttpCacheManager.getMmkv().putString(cacheKey, cacheValue).commit(); + boolean writeHttpCacheResult = HttpCacheManager.writeHttpCache(cacheKey, cacheValue); + EasyLog.printLog(httpRequest, "writeHttpCacheResult = " + writeHttpCacheResult); + boolean refreshHttpCacheTimeResult = HttpCacheManager.setHttpCacheTime(cacheKey, System.currentTimeMillis()); + EasyLog.printLog(httpRequest, "refreshHttpCacheTimeResult = " + refreshHttpCacheTimeResult); + return writeHttpCacheResult && refreshHttpCacheTimeResult; + } + + @Override + public boolean deleteCache(@NonNull HttpRequest httpRequest) { + String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); + EasyLog.printLog(httpRequest, "----- delete cache key -----"); + EasyLog.printJson(httpRequest, cacheKey); + boolean deleteHttpCacheResult = HttpCacheManager.deleteHttpCache(cacheKey); + EasyLog.printLog(httpRequest, "deleteHttpCacheResult = " + deleteHttpCacheResult); + return deleteHttpCacheResult; } @Override public void clearCache() { - HttpCacheManager.getMmkv().clearMemoryCache(); - HttpCacheManager.getMmkv().clearAll(); + HttpCacheManager.clearCache(); } -} ``` ```java -public class HttpCacheManager { +public final class HttpCacheManager { - private volatile static MMKV sMmkv; + private static final MMKV HTTP_CACHE_CONTENT = MMKV.mmkvWithID("http_cache_content");; - /** - * 获取单例的 MMKV 实例 - */ - public static MMKV getMmkv() { - if(sMmkv == null) { - synchronized (RequestHandler.class) { - if (sMmkv == null) { - sMmkv = MMKV.mmkvWithID("http_cache_id"); - } - } - } - return sMmkv; - } + private static final MMKV HTTP_CACHE_TIME = MMKV.mmkvWithID("http_cache_time"); - /** - * 生成缓存的 key - */ - public static String generateCacheKey(@NonNull HttpRequest httpRequest) { - IRequestApi requestApi = httpRequest.getRequestApi(); - return "用户 id" + "\n" + requestApi.getApi() + "\n" + GsonFactory.getSingletonGson().toJson(requestApi); - } + /** + * 生成缓存的 key + */ + @NonNull + public static String generateCacheKey(@NonNull HttpRequest httpRequest) { + IRequestApi requestApi = httpRequest.getRequestApi(); + return "请替换成当前的用户 id" + "\n" + requestApi.getApi() + "\n" + GsonFactory.getSingletonGson().toJson(requestApi); + } + + /** + * 读取缓存 + */ + public static String readHttpCache(@NonNull String cacheKey) { + String cacheValue = HTTP_CACHE_CONTENT.getString(cacheKey, null); + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { + return null; + } + return cacheValue; + } + + /** + * 写入缓存 + */ + public static boolean writeHttpCache(String cacheKey, String cacheValue) { + return HTTP_CACHE_CONTENT.putString(cacheKey, cacheValue).commit(); + } + + /** + * 删除缓存 + */ + public static boolean deleteHttpCache(String cacheKey) { + return HTTP_CACHE_CONTENT.remove(cacheKey).commit(); + } + + /** + * 清理缓存 + */ + public static void clearCache() { + HTTP_CACHE_CONTENT.clearMemoryCache(); + HTTP_CACHE_CONTENT.clearAll(); + + HTTP_CACHE_TIME.clearMemoryCache(); + HTTP_CACHE_TIME.clearAll(); + } + + /** + * 获取 Http 写入缓存的时间 + */ + public static long getHttpCacheTime(String cacheKey) { + return HTTP_CACHE_TIME.getLong(cacheKey, 0); + } + + /** + * 设置 Http 写入缓存的时间 + */ + public static boolean setHttpCacheTime(String cacheKey, long cacheTime) { + return HTTP_CACHE_TIME.putLong(cacheKey, cacheTime).commit(); + } + + /** + * 判断缓存是否过期 + */ + public static boolean isCacheInvalidate(String cacheKey, long maxCacheTime) { + if (maxCacheTime == Long.MAX_VALUE) { + // 表示缓存长期有效,永远不会过期 + return false; + } + long httpCacheTime = getHttpCacheTime(cacheKey); + if (httpCacheTime == 0) { + // 表示不知道缓存的时间,这里默认当做已经过期了 + return true; + } + return httpCacheTime + maxCacheTime < System.currentTimeMillis(); + } +} +``` + +* 最后记得在应用启动的时候初始化 MMKV + +```java +public final class AppApplication extends Application { + + @Override + public void onCreate() { + super.onCreate(); + + MMKV.initialize(this); + } } ``` @@ -1169,10 +1247,10 @@ EasyHttp.post(MainActivity.this) .api(new XxxApi()) // 延迟 5 秒后请求 .delay(5000) - .request(new HttpCallbackProxy>(MainActivity.this) { + .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1207,7 +1285,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy(this) { @Override - public void onHttpSuccess(Xxx result) { + public void onHttpSuccess(@NonNull Xxx result) { } }); @@ -1248,7 +1326,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1270,7 +1348,7 @@ EasyHttp.post(new ActivityLifecycle(this)) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1289,12 +1367,12 @@ EasyHttp.post(ApplicationLifecycle.getInstance()) .request(new OnHttpListener>() { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { } }); @@ -1347,12 +1425,12 @@ public class XxxViewModel extends BaseViewModel { .request(new OnHttpListener>() { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { } }); @@ -1372,13 +1450,13 @@ EasyHttp.post(this) .request(new HttpCallbackProxy(this) { @Override - public void onHttpStart(Call call) { + public void onHttpStart(@NonNull IRequestApi api) { // 重写方法并注释父类调用 //super.onHttpStart(call); } @Override - public void onHttpEnd(Call call) { + public void onHttpEnd(@NonNull IRequestApi api) { // 重写方法并注释父类调用 //super.onHttpEnd(call); } @@ -1394,12 +1472,12 @@ EasyHttp.post(this) .request(new OnHttpListener() { @Override - public void onHttpSuccess(Xxx result) { + public void onHttpSuccess(@NonNull Xxx result) { } @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { } }); @@ -1421,7 +1499,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1456,7 +1534,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1476,7 +1554,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1493,7 +1571,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1590,7 +1668,7 @@ EasyHttp.get(this) .request(new HttpCallbackProxy(this) { @Override - public void onHttpSuccess(Xxx result) { + public void onHttpSuccess(@NonNull Xxx result) { } }); @@ -1719,7 +1797,7 @@ Observable.intervalRange(1, 3, 5000, 1000, TimeUnit.MILLISECONDS) .request(new HttpCallbackProxy>(MainActivity.this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); @@ -1740,13 +1818,13 @@ Observable.create(new ObservableOnSubscribe>() { .request(new HttpCallbackProxy>(MainActivity.this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { emitter.onNext(result); emitter.onComplete(); } @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { super.onHttpFail(throwable); emitter.onError(throwable); } @@ -1927,7 +2005,7 @@ EasyHttp.post(this) .request(new HttpCallbackProxy>(this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { } }); diff --git a/README.md b/README.md index 3090c7e..14f4fb6 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,7 @@ * 博客地址:[网络请求,如斯优雅](https://www.jianshu.com/p/93cd59dec002) -* 可以扫码下载 Demo 进行演示或者测试,如果扫码下载不了的,[点击此处下载Demo](https://github.com/getActivity/EasyHttp/releases/download/12.8/EasyHttp.apk) +* 可以扫码下载 Demo 进行演示或者测试,如果扫码下载不了的,[点击此处下载Demo](https://github.com/getActivity/EasyHttp/releases/download/13.0/EasyHttp.apk) ![](picture/demo_code.png) @@ -63,7 +63,7 @@ android { dependencies { // 网络请求框架:https://github.com/getActivity/EasyHttp - implementation 'com.github.getActivity:EasyHttp:12.8' + implementation 'com.github.getActivity:EasyHttp:13.0' // OkHttp 框架:https://github.com/square/okhttp // noinspection GradleDependency implementation 'com.squareup.okhttp3:okhttp:3.12.13' @@ -100,6 +100,10 @@ dependencies { -keep public class * implements com.hjq.http.listener.OnHttpListener { *; } + +-keep public class * extends com.hjq.http.model.ResponseClass { + *; +} ``` * 不混淆某个包下的 Bean 类 @@ -119,9 +123,9 @@ dependencies { | 功能或细节 | [EasyHttp](https://github.com/getActivity/EasyHttp) | [Retrofit](https://github.com/square/retrofit) | [OkGo](https://github.com/jeasonlzy/okhttp-OkGo) | | :----: | :------: | :-----: | :-----: | -| 对应版本 | 12.8 | 2.9.0 | 3.0.4 | +| 对应版本 | 13.0 | 2.9.0 | 3.0.4 | | issues 数 | [![](https://img.shields.io/github/issues/getActivity/EasyHttp.svg)](https://github.com/getActivity/EasyHttp/issues) | [![](https://img.shields.io/github/issues/square/retrofit.svg)](https://github.com/square/retrofit/issues) | [![](https://img.shields.io/github/issues/jeasonlzy/okhttp-OkGo.svg)](https://github.com/jeasonlzy/okhttp-OkGo/issues) | -| **aar 包大小** | 95 KB | 123 KB | 131 KB | +| **aar 包大小** | 96 KB | 123 KB | 131 KB | | minSdk 要求 | API 14+ | API 21+ | API 14+ | | 配置多域名 | ✅ | ❌ | ✅ | | **动态 Host** | ✅ | ❌ | ❌ | diff --git a/app/build.gradle b/app/build.gradle index 24672dc..9ffa903 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -14,8 +14,8 @@ android { applicationId 'com.hjq.easy.demo' minSdkVersion 21 targetSdkVersion 31 - versionCode 1208 - versionName '12.8' + versionCode 1300 + versionName '13.0' } // 支持 JDK 1.8 @@ -76,13 +76,13 @@ dependencies { implementation 'com.github.getActivity:Toaster:12.6' // 权限请求框架:https://github.com/getActivity/XXPermissions - implementation 'com.github.getActivity:XXPermissions:18.6' + implementation 'com.github.getActivity:XXPermissions:20.0' // 标题栏框架:https://github.com/getActivity/TitleBar implementation 'com.github.getActivity:TitleBar:10.5' // Gson 解析容错:https://github.com/getActivity/GsonFactory - implementation 'com.github.getActivity:GsonFactory:9.5' + implementation 'com.github.getActivity:GsonFactory:9.6' // Json 解析框架:https://github.com/google/gson implementation 'com.google.code.gson:gson:2.10.1' // Kotlin 反射库:用于反射 Kotlin data class 类对象 diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index f891761..ad7ab93 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -23,6 +23,7 @@ android:networkSecurityConfig="@xml/network_security_config" android:requestLegacyExternalStorage="true" android:roundIcon="@mipmap/ic_launcher_round" + android:supportsRtl="true" android:theme="@style/AppTheme" tools:ignore="LockedOrientationActivity,UnusedAttribute" tools:targetApi="n"> diff --git a/app/src/main/java/com/hjq/easy/demo/BaseActivity.java b/app/src/main/java/com/hjq/easy/demo/BaseActivity.java index 34f7e3e..14eed89 100644 --- a/app/src/main/java/com/hjq/easy/demo/BaseActivity.java +++ b/app/src/main/java/com/hjq/easy/demo/BaseActivity.java @@ -1,10 +1,11 @@ package com.hjq.easy.demo; import android.app.ProgressDialog; +import androidx.annotation.NonNull; import androidx.appcompat.app.AppCompatActivity; +import com.hjq.http.config.IRequestApi; import com.hjq.http.listener.OnHttpListener; import com.hjq.toast.Toaster; -import okhttp3.Call; /** * author : Android 轮子哥 @@ -57,20 +58,20 @@ public void hideDialog() { } @Override - public void onHttpStart(Call call) { + public void onHttpStart(@NonNull IRequestApi api) { showDialog(); } @Override - public void onHttpSuccess(Object result) {} + public void onHttpSuccess(@NonNull Object result) {} @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { Toaster.show(throwable.getMessage()); } @Override - public void onHttpEnd(Call call) { + public void onHttpEnd(@NonNull IRequestApi api) { hideDialog(); } } \ No newline at end of file diff --git a/app/src/main/java/com/hjq/easy/demo/MainActivity.java b/app/src/main/java/com/hjq/easy/demo/MainActivity.java index 46225ef..d14ab0a 100644 --- a/app/src/main/java/com/hjq/easy/demo/MainActivity.java +++ b/app/src/main/java/com/hjq/easy/demo/MainActivity.java @@ -23,6 +23,7 @@ import com.hjq.easy.demo.http.model.HttpData; import com.hjq.http.EasyHttp; import com.hjq.http.EasyUtils; +import com.hjq.http.config.IRequestApi; import com.hjq.http.listener.HttpCallbackProxy; import com.hjq.http.listener.OnDownloadListener; import com.hjq.http.listener.OnUpdateListener; @@ -38,7 +39,6 @@ import java.io.OutputStream; import java.util.ArrayList; import java.util.List; -import okhttp3.Call; /** * author : Android 轮子哥 @@ -121,7 +121,7 @@ public void onClick(View view) { .request(new HttpCallbackProxy>>(this) { @Override - public void onHttpSuccess(HttpData> result) { + public void onHttpSuccess(@NonNull HttpData> result) { Toaster.show("Get 请求成功,请看日志"); } }); @@ -129,12 +129,12 @@ public void onHttpSuccess(HttpData> result) { } else if (viewId == R.id.btn_main_post) { EasyHttp.post(this) - .api(new SearchBlogsApi() - .setKeyword("搬砖不再有")) + .api(new SearchBlogsApi() + .setKeyword("搬砖不再有")) .request(new HttpCallbackProxy>(MainActivity.this) { @Override - public void onHttpSuccess(HttpData result) { + public void onHttpSuccess(@NonNull HttpData result) { Toaster.show("Post 请求成功,请看日志"); } }); @@ -204,7 +204,7 @@ public void onHttpSuccess(HttpData result) { .request(new OnUpdateListener() { @Override - public void onUpdateStart(Call call) { + public void onUpdateStart(@NonNull IRequestApi api) { mProgressBar.setProgress(0); mProgressBar.setVisibility(View.VISIBLE); } @@ -215,17 +215,17 @@ public void onUpdateProgressChange(int progress) { } @Override - public void onUpdateSuccess(Void result) { + public void onUpdateSuccess(@NonNull Void result) { Toaster.show("上传成功"); } @Override - public void onUpdateFail(Throwable throwable) { + public void onUpdateFail(@NonNull Throwable throwable) { Toaster.show("上传失败"); } @Override - public void onUpdateEnd(Call call) { + public void onUpdateEnd(@NonNull IRequestApi api) { mProgressBar.setVisibility(View.GONE); } }); @@ -273,30 +273,30 @@ public void onUpdateEnd(Call call) { .listener(new OnDownloadListener() { @Override - public void onDownloadStart(File file) { + public void onDownloadStart(@NonNull File file) { mProgressBar.setProgress(0); mProgressBar.setVisibility(View.VISIBLE); } @Override - public void onDownloadProgressChange(File file, int progress) { + public void onDownloadProgressChange(@NonNull File file, int progress) { mProgressBar.setProgress(progress); } @Override - public void onDownloadSuccess(File file) { + public void onDownloadSuccess(@NonNull File file) { Toaster.show("下载成功:" + file.getPath()); installApk(MainActivity.this, file); } @Override - public void onDownloadFail(File file, Throwable throwable) { + public void onDownloadFail(@NonNull File file, @NonNull Throwable throwable) { Toaster.show("下载失败:" + throwable.getMessage()); file.delete(); } @Override - public void onDownloadEnd(File file) { + public void onDownloadEnd(@NonNull File file) { mProgressBar.setVisibility(View.GONE); } }) diff --git a/app/src/main/java/com/hjq/easy/demo/http/api/SearchAuthorApi.java b/app/src/main/java/com/hjq/easy/demo/http/api/SearchAuthorApi.java index 6bccf55..11bf72f 100644 --- a/app/src/main/java/com/hjq/easy/demo/http/api/SearchAuthorApi.java +++ b/app/src/main/java/com/hjq/easy/demo/http/api/SearchAuthorApi.java @@ -26,7 +26,7 @@ public SearchAuthorApi setId(int id) { return this; } - public final static class Bean { + public static final class Bean { private int courseId; private int id; diff --git a/app/src/main/java/com/hjq/easy/demo/http/model/HttpCacheManager.java b/app/src/main/java/com/hjq/easy/demo/http/model/HttpCacheManager.java index 5851297..6502493 100644 --- a/app/src/main/java/com/hjq/easy/demo/http/model/HttpCacheManager.java +++ b/app/src/main/java/com/hjq/easy/demo/http/model/HttpCacheManager.java @@ -1,7 +1,6 @@ package com.hjq.easy.demo.http.model; import androidx.annotation.NonNull; - import com.hjq.gson.factory.GsonFactory; import com.hjq.http.config.IRequestApi; import com.hjq.http.request.HttpRequest; @@ -22,6 +21,7 @@ public final class HttpCacheManager { /** * 生成缓存的 key */ + @NonNull public static String generateCacheKey(@NonNull HttpRequest httpRequest) { IRequestApi requestApi = httpRequest.getRequestApi(); return "请替换成当前的用户 id" + "\n" + requestApi.getApi() + "\n" + GsonFactory.getSingletonGson().toJson(requestApi); @@ -30,9 +30,9 @@ public static String generateCacheKey(@NonNull HttpRequest httpRequest) { /** * 读取缓存 */ - public static String readHttpCache(String cacheKey) { + public static String readHttpCache(@NonNull String cacheKey) { String cacheValue = HTTP_CACHE_CONTENT.getString(cacheKey, null); - if ("".equals(cacheValue) || "{}".equals(cacheValue)) { + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { return null; } return cacheValue; @@ -45,6 +45,13 @@ public static boolean writeHttpCache(String cacheKey, String cacheValue) { return HTTP_CACHE_CONTENT.putString(cacheKey, cacheValue).commit(); } + /** + * 删除缓存 + */ + public static boolean deleteHttpCache(String cacheKey) { + return HTTP_CACHE_CONTENT.remove(cacheKey).commit(); + } + /** * 清理缓存 */ diff --git a/app/src/main/java/com/hjq/easy/demo/http/model/RequestHandler.java b/app/src/main/java/com/hjq/easy/demo/http/model/RequestHandler.java index a058086..3a4bf43 100644 --- a/app/src/main/java/com/hjq/easy/demo/http/model/RequestHandler.java +++ b/app/src/main/java/com/hjq/easy/demo/http/model/RequestHandler.java @@ -205,7 +205,7 @@ public Throwable downloadFail(@NonNull HttpRequest httpRequest, @NonNull Thro public Object readCache(@NonNull HttpRequest httpRequest, @NonNull Type type, long cacheTime) { String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); String cacheValue = HttpCacheManager.readHttpCache(cacheKey); - if (cacheValue == null || "".equals(cacheValue) || "{}".equals(cacheValue)) { + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { return null; } EasyLog.printLog(httpRequest, "----- read cache key -----"); @@ -226,7 +226,7 @@ public Object readCache(@NonNull HttpRequest httpRequest, @NonNull Type type, public boolean writeCache(@NonNull HttpRequest httpRequest, @NonNull Response response, @NonNull Object result) { String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); String cacheValue = GsonFactory.getSingletonGson().toJson(result); - if (cacheValue == null || "".equals(cacheValue) || "{}".equals(cacheValue)) { + if (cacheValue == null || cacheValue.isEmpty() || "{}".equals(cacheValue)) { return false; } EasyLog.printLog(httpRequest, "----- write cache key -----"); @@ -240,6 +240,16 @@ public boolean writeCache(@NonNull HttpRequest httpRequest, @NonNull Response return writeHttpCacheResult && refreshHttpCacheTimeResult; } + @Override + public boolean deleteCache(@NonNull HttpRequest httpRequest) { + String cacheKey = HttpCacheManager.generateCacheKey(httpRequest); + EasyLog.printLog(httpRequest, "----- delete cache key -----"); + EasyLog.printJson(httpRequest, cacheKey); + boolean deleteHttpCacheResult = HttpCacheManager.deleteHttpCache(cacheKey); + EasyLog.printLog(httpRequest, "deleteHttpCacheResult = " + deleteHttpCacheResult); + return deleteHttpCacheResult; + } + @Override public void clearCache() { HttpCacheManager.clearCache(); diff --git a/app/src/main/java/com/hjq/easy/demo/other/ContentResolverUriStore.java b/app/src/main/java/com/hjq/easy/demo/other/ContentResolverUriStore.java index b2d8ea6..5c2a275 100644 --- a/app/src/main/java/com/hjq/easy/demo/other/ContentResolverUriStore.java +++ b/app/src/main/java/com/hjq/easy/demo/other/ContentResolverUriStore.java @@ -27,7 +27,7 @@ public class ContentResolverUriStore { // 使用字符串作为缓存键 String cacheKey = "ContentResolver insert: " + "Uri = " + url + ", ContentValues = " + convertContentValuesToString(values); String oldUriString = sharedPreferences.getString(cacheKey, ""); - if (oldUriString != null && !"".equals(oldUriString)) { + if (oldUriString != null && !oldUriString.isEmpty()) { Cursor cursor = null; try { Uri oldUri = Uri.parse(oldUriString); diff --git a/library/build.gradle b/library/build.gradle index 02aad34..3655107 100644 --- a/library/build.gradle +++ b/library/build.gradle @@ -5,8 +5,8 @@ android { defaultConfig { minSdkVersion 16 - versionCode 1208 - versionName "12.8" + versionCode 1300 + versionName "13.0" } // 使用 JDK 1.8 diff --git a/library/src/main/java/com/hjq/http/callback/BaseCallback.java b/library/src/main/java/com/hjq/http/callback/BaseCallback.java index 8a1c7c1..e585b8b 100644 --- a/library/src/main/java/com/hjq/http/callback/BaseCallback.java +++ b/library/src/main/java/com/hjq/http/callback/BaseCallback.java @@ -41,11 +41,6 @@ public BaseCallback(@NonNull HttpRequest request) { () -> HttpLifecycleManager.register(mHttpRequest.getLifecycleOwner())); } - public BaseCallback setCallProxy(CallProxy callProxy) { - mCallProxy = callProxy; - return this; - } - public BaseCallback setCallProxyFactory(CallProxy.Factory factory) { mCallProxyFactory = factory; return this; diff --git a/library/src/main/java/com/hjq/http/callback/DownloadCallback.java b/library/src/main/java/com/hjq/http/callback/DownloadCallback.java index 8a948b4..7157f7d 100644 --- a/library/src/main/java/com/hjq/http/callback/DownloadCallback.java +++ b/library/src/main/java/com/hjq/http/callback/DownloadCallback.java @@ -38,7 +38,8 @@ public final class DownloadCallback extends BaseCallback { private static final String FILE_MD5_REGEX = "^[\\w]{32}$"; /** 保存的文件 */ - private File mFile; + @NonNull + private final File mFile; /** 校验的 MD5 */ private String mMd5; @@ -58,14 +59,10 @@ public final class DownloadCallback extends BaseCallback { /** 断点续传开关 */ private boolean mResumableTransfer; - public DownloadCallback(@NonNull HttpRequest request) { + public DownloadCallback(@NonNull HttpRequest request, @NonNull File file) { super(request); mHttpRequest = request; - } - - public DownloadCallback setFile(File file) { mFile = file; - return this; } public DownloadCallback setMd5(String md5) { @@ -151,10 +148,10 @@ protected void onHttpResponse(Response response) throws Throwable { String contentRange = response.header("Content-Range"); // 若能够找到 Content-Range,则表明服务器支持断点续传 // 有些服务器还会返回 Accept-Ranges,输出结果 Accept-Ranges: bytes,说明服务器支持按字节下载 - if (acceptRanges != null && !"".equals(acceptRanges)) { + if (acceptRanges != null && !acceptRanges.isEmpty()) { // Accept-Ranges:bytes supportResumableTransfer = "bytes".equalsIgnoreCase(acceptRanges); - } else if (contentRange != null && !"".equals(contentRange)) { + } else if (contentRange != null && !contentRange.isEmpty()) { // Content-Range: bytes 7897088-221048888/221048889 supportResumableTransfer = contentRange.matches("bytes\\s+\\d+-\\d+/\\d+"); } @@ -203,7 +200,7 @@ protected void onHttpResponse(Response response) throws Throwable { EasyUtils.closeStream(response); String md5 = EasyUtils.getFileMd5(EasyUtils.openFileInputStream(mFile)); - if (mMd5 != null && !"".equals(mMd5) && !mMd5.equalsIgnoreCase(md5)) { + if (mMd5 != null && !mMd5.isEmpty() && !mMd5.equalsIgnoreCase(md5)) { // 文件 MD5 值校验失败 throw new FileMd5Exception("File md5 hash verify failure", md5); } @@ -224,7 +221,7 @@ protected void onHttpFailure(final Throwable throwable) { public boolean verifyFileMd5() { try { - return mFile.isFile() && mMd5 != null && !"".equals(mMd5) && + return mFile.isFile() && mMd5 != null && !mMd5.isEmpty() && mMd5.equalsIgnoreCase(EasyUtils.getFileMd5(EasyUtils.openFileInputStream(mFile))); } catch (FileNotFoundException e) { e.printStackTrace(); diff --git a/library/src/main/java/com/hjq/http/callback/NormalCallback.java b/library/src/main/java/com/hjq/http/callback/NormalCallback.java index 9c0de19..c964b9a 100644 --- a/library/src/main/java/com/hjq/http/callback/NormalCallback.java +++ b/library/src/main/java/com/hjq/http/callback/NormalCallback.java @@ -41,6 +41,11 @@ public NormalCallback setListener(OnHttpListener listener) { return this; } + public NormalCallback setReflectType(Type reflectType) { + mReflectType = reflectType; + return this; + } + @Override public void start() { CacheMode cacheMode = mHttpRequest.getRequestCache().getCacheMode(); @@ -152,15 +157,15 @@ protected void onHttpFailure(Throwable throwable) { private void dispatchHttpStartCallback() { if (mListener != null && HttpLifecycleManager.isLifecycleActive(mHttpRequest.getLifecycleOwner())) { - mListener.onHttpStart(getCallProxy()); + mListener.onHttpStart(mHttpRequest.getRequestApi()); } EasyLog.printLog(mHttpRequest, "Http request start"); } - private void dispatchHttpSuccessCallback(Object result, boolean cache) { + private void dispatchHttpSuccessCallback(@NonNull Object result, boolean cache) { if (mListener != null && HttpLifecycleManager.isLifecycleActive(mHttpRequest.getLifecycleOwner())) { mListener.onHttpSuccess(result, cache); - mListener.onHttpEnd(getCallProxy()); + mListener.onHttpEnd(mHttpRequest.getRequestApi()); } EasyLog.printLog(mHttpRequest, "Http request success"); } @@ -168,7 +173,7 @@ private void dispatchHttpSuccessCallback(Object result, boolean cache) { private void dispatchHttpFailCallback(Throwable throwable) { if (mListener != null && HttpLifecycleManager.isLifecycleActive(mHttpRequest.getLifecycleOwner())) { mListener.onHttpFail(throwable); - mListener.onHttpEnd(getCallProxy()); + mListener.onHttpEnd(mHttpRequest.getRequestApi()); } EasyLog.printLog(mHttpRequest, "Http request fail"); } diff --git a/library/src/main/java/com/hjq/http/config/IRequestHandler.java b/library/src/main/java/com/hjq/http/config/IRequestHandler.java index ffdfc50..d80d64a 100644 --- a/library/src/main/java/com/hjq/http/config/IRequestHandler.java +++ b/library/src/main/java/com/hjq/http/config/IRequestHandler.java @@ -73,6 +73,16 @@ default boolean writeCache(@NonNull HttpRequest httpRequest, @NonNull Respons return false; } + /** + * 删除缓存 + * + * @param httpRequest 请求接口对象 + * @return 删除缓存的结果 + */ + default boolean deleteCache(@NonNull HttpRequest httpRequest) { + return false; + } + /** * 清空缓存 */ diff --git a/library/src/main/java/com/hjq/http/listener/HttpCallbackProxy.java b/library/src/main/java/com/hjq/http/listener/HttpCallbackProxy.java index 80d29bf..70811bc 100644 --- a/library/src/main/java/com/hjq/http/listener/HttpCallbackProxy.java +++ b/library/src/main/java/com/hjq/http/listener/HttpCallbackProxy.java @@ -1,6 +1,7 @@ package com.hjq.http.listener; -import okhttp3.Call; +import androidx.annotation.NonNull; +import com.hjq.http.config.IRequestApi; /** * author : Android 轮子哥 @@ -18,15 +19,15 @@ public HttpCallbackProxy(OnHttpListener listener) { } @Override - public void onHttpStart(Call call) { + public void onHttpStart(@NonNull IRequestApi api) { if (mSourceListener == null) { return; } - mSourceListener.onHttpStart(call); + mSourceListener.onHttpStart(api); } @Override - public void onHttpSuccess(T result, boolean cache) { + public void onHttpSuccess(@NonNull T result, boolean cache) { // 这里解释一下,为什么不那么写 // 这是因为回调原有的监听器的 onHttpSuccess(T result, boolean cache) 方法, // 最终它只会回调原有监听器的 onHttpSuccess(T result) 方法 @@ -39,7 +40,7 @@ public void onHttpSuccess(T result, boolean cache) { } @Override - public void onHttpSuccess(T result) { + public void onHttpSuccess(@NonNull T result) { if (mSourceListener == null) { return; } @@ -47,7 +48,7 @@ public void onHttpSuccess(T result) { } @Override - public void onHttpFail(Throwable throwable) { + public void onHttpFail(@NonNull Throwable throwable) { if (mSourceListener == null) { return; } @@ -55,10 +56,10 @@ public void onHttpFail(Throwable throwable) { } @Override - public void onHttpEnd(Call call) { + public void onHttpEnd(@NonNull IRequestApi api) { if (mSourceListener == null) { return; } - mSourceListener.onHttpEnd(call); + mSourceListener.onHttpEnd(api); } } \ No newline at end of file diff --git a/library/src/main/java/com/hjq/http/listener/OnDownloadListener.java b/library/src/main/java/com/hjq/http/listener/OnDownloadListener.java index 3e36a88..16365e8 100644 --- a/library/src/main/java/com/hjq/http/listener/OnDownloadListener.java +++ b/library/src/main/java/com/hjq/http/listener/OnDownloadListener.java @@ -1,5 +1,6 @@ package com.hjq.http.listener; +import androidx.annotation.NonNull; import java.io.File; /** @@ -13,7 +14,7 @@ public interface OnDownloadListener { /** * 下载开始 */ - default void onDownloadStart(File file) {} + default void onDownloadStart(@NonNull File file) {} /** * 下载字节改变 @@ -21,36 +22,36 @@ default void onDownloadStart(File file) {} * @param totalByte 总字节数 * @param downloadByte 已下载字节数 */ - default void onDownloadByteChange(File file, long totalByte, long downloadByte) {} + default void onDownloadByteChange(@NonNull File file, long totalByte, long downloadByte) {} /** * 下载进度改变 * * @param progress 下载进度值(0-100) */ - void onDownloadProgressChange(File file, int progress); + void onDownloadProgressChange(@NonNull File file, int progress); /** * 下载成功 * * @param cache 是否是通过缓存下载成功的 */ - default void onDownloadSuccess(File file, boolean cache) { + default void onDownloadSuccess(@NonNull File file, boolean cache) { onDownloadSuccess(file); } /** * 下载成功 */ - void onDownloadSuccess(File file); + void onDownloadSuccess(@NonNull File file); /** * 下载失败 */ - void onDownloadFail(File file, Throwable throwable); + void onDownloadFail(@NonNull File file, @NonNull Throwable throwable); /** * 下载结束 */ - default void onDownloadEnd(File file) {} + default void onDownloadEnd(@NonNull File file) {} } \ No newline at end of file diff --git a/library/src/main/java/com/hjq/http/listener/OnHttpListener.java b/library/src/main/java/com/hjq/http/listener/OnHttpListener.java index 603bc41..0449fe8 100644 --- a/library/src/main/java/com/hjq/http/listener/OnHttpListener.java +++ b/library/src/main/java/com/hjq/http/listener/OnHttpListener.java @@ -1,6 +1,7 @@ package com.hjq.http.listener; -import okhttp3.Call; +import androidx.annotation.NonNull; +import com.hjq.http.config.IRequestApi; /** * author : Android 轮子哥 @@ -13,29 +14,29 @@ public interface OnHttpListener { /** * 请求开始 */ - default void onHttpStart(Call call) {} + default void onHttpStart(@NonNull IRequestApi api) {} /** * 请求成功 * * @param cache 是否是通过缓存请求成功的 */ - default void onHttpSuccess(T result, boolean cache) { + default void onHttpSuccess(@NonNull T result, boolean cache) { onHttpSuccess(result); } /** * 请求成功 */ - void onHttpSuccess(T result); + void onHttpSuccess(@NonNull T result); /** * 请求出错 */ - void onHttpFail(Throwable throwable); + void onHttpFail(@NonNull Throwable throwable); /** * 请求结束 */ - default void onHttpEnd(Call call) {} + default void onHttpEnd(@NonNull IRequestApi api) {} } \ No newline at end of file diff --git a/library/src/main/java/com/hjq/http/listener/OnUpdateListener.java b/library/src/main/java/com/hjq/http/listener/OnUpdateListener.java index 3f094a1..28c1cc3 100644 --- a/library/src/main/java/com/hjq/http/listener/OnUpdateListener.java +++ b/library/src/main/java/com/hjq/http/listener/OnUpdateListener.java @@ -1,6 +1,7 @@ package com.hjq.http.listener; -import okhttp3.Call; +import androidx.annotation.NonNull; +import com.hjq.http.config.IRequestApi; /** * author : Android 轮子哥 @@ -14,15 +15,15 @@ public interface OnUpdateListener extends OnHttpListener { * 请求开始 */ @Override - default void onHttpStart(Call call) { - onUpdateStart(call); + default void onHttpStart(@NonNull IRequestApi api) { + onUpdateStart(api); } /** * 请求成功 */ @Override - default void onHttpSuccess(T result) { + default void onHttpSuccess(@NonNull T result) { onUpdateSuccess(result); } @@ -30,7 +31,7 @@ default void onHttpSuccess(T result) { * 请求出错 */ @Override - default void onHttpFail(Throwable throwable) { + default void onHttpFail(@NonNull Throwable throwable) { onUpdateFail(throwable); } @@ -38,8 +39,8 @@ default void onHttpFail(Throwable throwable) { * 请求结束 */ @Override - default void onHttpEnd(Call call) { - onUpdateEnd(call); + default void onHttpEnd(@NonNull IRequestApi api) { + onUpdateEnd(api); } /* --------------------------------------------------------------- */ @@ -47,7 +48,7 @@ default void onHttpEnd(Call call) { /** * 上传开始 */ - default void onUpdateStart(Call call) {} + default void onUpdateStart(@NonNull IRequestApi api) {} /** * 上传字节改变 @@ -67,15 +68,15 @@ default void onUpdateByteChange(long totalByte, long updateByte) {} /** * 上传成功 */ - void onUpdateSuccess(T result); + void onUpdateSuccess(@NonNull T result); /** * 上传出错 */ - void onUpdateFail(Throwable throwable); + void onUpdateFail(@NonNull Throwable throwable); /** * 上传结束 */ - default void onUpdateEnd(Call call) {} + default void onUpdateEnd(@NonNull IRequestApi api) {} } \ No newline at end of file diff --git a/library/src/main/java/com/hjq/http/request/BodyRequest.java b/library/src/main/java/com/hjq/http/request/BodyRequest.java index 6edb6e0..e53420b 100644 --- a/library/src/main/java/com/hjq/http/request/BodyRequest.java +++ b/library/src/main/java/com/hjq/http/request/BodyRequest.java @@ -188,7 +188,7 @@ private RequestBody createRequestBody(HttpParams params, @Nullable String conten RequestBody requestBody = requestBodyStrategy.createRequestBody(this, params); // 如果外层需要自定义 Content-Type 这个字段,那么就使用装饰设计模式,对原有的 RequestBody 对象进行扩展 - if (contentType != null && !"".equals(contentType)) { + if (contentType != null && !contentType.isEmpty()) { MediaType mediaType = MediaType.parse(contentType); if (mediaType != null) { CustomTypeRequestBody customTypeRequestBody = new CustomTypeRequestBody(requestBody); diff --git a/library/src/main/java/com/hjq/http/request/DownloadRequest.java b/library/src/main/java/com/hjq/http/request/DownloadRequest.java index 2fb6d49..f6a98d8 100644 --- a/library/src/main/java/com/hjq/http/request/DownloadRequest.java +++ b/library/src/main/java/com/hjq/http/request/DownloadRequest.java @@ -152,9 +152,8 @@ public DownloadRequest start() { } EasyLog.printStackTrace(this, stackTrace); - DownloadCallback downloadCallback = new DownloadCallback(this); - downloadCallback.setFile(mFile) - .setMd5(mMd5) + DownloadCallback downloadCallback = new DownloadCallback(this, mFile); + downloadCallback.setMd5(mMd5) .setResumableTransfer(mResumableTransfer) .setListener(mListener) .setCallProxyFactory(() -> mCallProxy = new CallProxy(createCall())); diff --git a/library/src/main/java/com/hjq/http/request/HttpRequest.java b/library/src/main/java/com/hjq/http/request/HttpRequest.java index c8704c6..c00ffbf 100644 --- a/library/src/main/java/com/hjq/http/request/HttpRequest.java +++ b/library/src/main/java/com/hjq/http/request/HttpRequest.java @@ -365,6 +365,7 @@ public Bean execute(ResponseClass responseClass) throws Throwable { if (cacheMode == CacheMode.USE_CACHE_FIRST) { // 使用异步请求来刷新缓存 new NormalCallback(this) + .setReflectType(reflectType) .setCallProxyFactory(() -> { // 如果存在缓存的情况下,则后面的逻辑不会继续请求,可以直接使用 CallProxy 对象字段 // 如果不存在缓存的话,则重新 new 一个 CallProxy 对象,这是因为后面的逻辑会请重新发起网络请求 @@ -386,6 +387,10 @@ public Bean execute(ResponseClass responseClass) throws Throwable { try { Response response = mCallProxy.execute(); + IRequestInterceptor interceptor = mRequestInterceptor; + if (interceptor != null) { + response = interceptor.interceptResponse(this, response); + } Object result = mRequestHandler.requestSuccess(this, response, reflectType); if (cacheMode == CacheMode.USE_CACHE_ONLY || cacheMode == CacheMode.USE_CACHE_AFTER_FAILURE) {