android 状态栏显示
ackers-zhang opened this issue · 5 comments
ackers-zhang commented
我这边使用你的方式 通知栏中并没有显示下载的进度
Jiiiiiin commented
- 我这边也遇到了,测试手机是mate9 8.0系统;
- 另外还有一个问题是,使用模拟器会报下面的问题:
- 第三个问题是,我下载源代码示例工程,可以提示我安装,但是换成我自己的工程在下载完毕就直接闪了一下,还有就是,因为我们有自己的后台返回的数据格式,我已经通过下面进转换了,只是没有使用您说的appkey,因为我们后台接口就不需要嘛,难道还和这个有关系?
下面是我【自定义接口协议的代码】:
AppUpdateUtil.update(activity, BaseConfig.TRANSCODE_UPDATE_URL, null, true, new UpdateCallback() {
/**
* 解析json,自定义协议
*
* @param resp 服务器返回的json
* @return UpdateAppBean
*/
@Override
protected UpdateAppBean parseJson(String resp) {
UpdateAppBean updateAppBean = new UpdateAppBean();
JSONObject data = JSONObject.parseObject(resp);
final boolean appHasNewVer = appHasNewVer(activity, data);
final boolean h5HasNewVer = h5HasNewVer(data);
// final String apkFileUrl = getApkFileUrl(data);
final String apkFileUrl = "https://raw.githubusercontent.com/WVector/AppUpdateDemo/master/apk/app-debug.apk";
final String update = (appHasNewVer || h5HasNewVer) && !TextUtils.isEmpty(apkFileUrl) ? "Yes" : "No";
LoggerProxy.d("update %s", update);
updateAppBean
//(必须)是否更新Yes,No
// .setUpdate(update)
.setUpdate(update)
//(必须)新版本号,
.setNewVersion(String.valueOf(getNewVersion(data)))
//(必须)下载地址
.setApkFileUrl(apkFileUrl)
//(必须)更新内容
.setUpdateLog(getUpdateLogFull(data))
//大小,不设置不显示大小,可以不设置
// 如果是1标识app存在更新
// .setTargetSize(appHasNewVer ? "1" : HACK_FALG_IS_ONLEY_H5_UPDATE)
//设置md5,可以不设置
//.setNewMd5();
//是否强制更新,可以不设置
.setConstraint(appMustBeForceUpdateToNewVer(data));
return updateAppBean;
}
@Override
public void onBefore() {
LoggerProxy.d("更新请求网络请求之前");
// CProgressDialogUtils.showProgressDialog(JavaActivity.this);
}
@Override
protected void hasNewApp(UpdateAppBean updateApp, UpdateAppManager updateAppManager) {
LoggerProxy.d("hasNewApp %s", updateApp);
updateAppManager.showDialogFragment();
}
@Override
public void onAfter() {
LoggerProxy.d("更新请求网络请求之后");
// CProgressDialogUtils.cancelProgressDialog(JavaActivity.this);
}
/**
* 没有新版本
*/
@Override
public void noNewApp() {
// ToastUtils.showLong("没有新版本", Toast.LENGTH_SHORT).show();
}
});
public class AppUpdateUtil {
public static void update(Activity activity, String updateUrl, Map<String, String> params, boolean isPost, UpdateCallback updateCallback) {
if(params == null){
params = new WeakHashMap<>();
params.put("appKey", "ab55ce55Ac4bcP408cPb8c1Aaeac179c5f6f");
params.put("appVersion", "1.0");
}
new UpdateAppManager
.Builder()
//必须设置,当前Activity
.setActivity(activity)
//必须设置,实现httpManager接口的对象
.setHttpManager(new UpdateAppHttpUtil(activity))
//必须设置,更新地址
.setUpdateUrl(updateUrl)
//以下设置,都是可选
//设置请求方式,默认get
.setPost(isPost)
//添加自定义参数,默认version=1.0.0(app的versionName);apkKey=唯一表示(在AndroidManifest.xml配置)
.setParams(params)
//设置点击升级后,消失对话框,默认点击升级后,对话框显示下载进度
.hideDialogOnDownloading(false)
//设置头部,不设置显示默认的图片,设置图片后自动识别主色调,然后为按钮,进度条设置颜色
// .setTopPic(R.mipmap.top_8)
//为按钮,进度条设置颜色,默认从顶部图片自动识别。
//.setThemeColor(ColorUtil.getRandomColor())
//设置apk下砸路径,默认是在下载到sd卡下/Download/1.0.0/test.apk
// .setTargetPath(path)
//设置appKey,默认从AndroidManifest.xml获取,如果,使用自定义参数,则此项无效
//.setAppKey("ab55ce55Ac4bcP408cPb8c1Aaeac179c5f6f")
//不显示通知栏进度条
//.dismissNotificationProgress()
//是否忽略版本
//.showIgnoreVersion()
.build()
//检测是否有新版本
.checkNewApp(updateCallback);
}
}
package cn.jiiiiiin.vplus.core.update;
import android.app.Activity;
import android.support.annotation.NonNull;
import com.vector.update_app.HttpManager;
import com.zhy.http.okhttp.callback.FileCallBack;
import java.io.File;
import java.util.Map;
import java.util.WeakHashMap;
import cn.jiiiiiin.vplus.core.net.RestClientBuilder;
import cn.jiiiiiin.vplus.core.net.RestOkHttpUtilsClient;
import cn.jiiiiiin.vplus.core.util.log.LoggerProxy;
import okhttp3.Call;
import okhttp3.Request;
/**
* Created by Vector
* on 2017/6/19 0019.
*/
public class UpdateAppHttpUtil implements HttpManager {
private final Activity ACTIVITY;
public UpdateAppHttpUtil(Activity activity) {
this.ACTIVITY = activity;
}
/**
* 异步get
*
* @param url get请求地址
* @param params get参数
* @param callBack 回调
*/
@Override
public void asyncGet(@NonNull String url, @NonNull Map<String, String> params, @NonNull final Callback callBack) {
RestClientBuilder restClientBuilder = RestOkHttpUtilsClient.builder(ACTIVITY)
.ignoreCommonCheck()
// loader 由前端控制
//.loader()
.url(url);
restClientBuilder.params(new WeakHashMap<>(params));
// 业务判断由前端完成
restClientBuilder.ignoreCommonCheck()
.success(response -> {
callBack.onResponse(response.toJSONString());
})
.failure(() -> callBack.onError("请求失败,请稍后尝试"))
.error(errRes -> callBack.onError(String.format("请求失败,请稍后尝试[%s]", errRes)))
.build()
.get();
}
/**
* 异步post
*
* @param url post请求地址
* @param params post请求参数
* @param callBack 回调
*/
@Override
public void asyncPost(@NonNull String url, @NonNull Map<String, String> params, @NonNull final Callback callBack) {
RestClientBuilder restClientBuilder = RestOkHttpUtilsClient.builder(ACTIVITY)
.ignoreCommonCheck()
// loader 由前端控制
//.loader()
.url(url);
restClientBuilder.params(new WeakHashMap<>(params));
// 业务判断由前端完成
restClientBuilder.ignoreCommonCheck()
.success(response -> {
callBack.onResponse(response.toJSONString());
})
.failure(() -> callBack.onError("请求失败,请稍后尝试"))
.error(errRes -> callBack.onError(String.format("请求失败,请稍后尝试[%s]", errRes)))
.build()
.post();
}
/**
* 下载
*
* @param url 下载地址
* @param path 文件保存路径
* @param fileName 文件名称
* @param callback 回调
*/
@Override
public void download(@NonNull String url, @NonNull String path, @NonNull String fileName, @NonNull final FileCallback callback) {
LoggerProxy.e("fileCallBack %s %s %s ", url, path, fileName);
RestOkHttpUtilsClient.builder(ACTIVITY)
.ignoreCommonCheck()
// loader 由前端控制
//.loader()
.url(url)
.fileCallBack(new FileCallBack(path, fileName) {
@Override
public void inProgress(float progress, long total, int id) {
LoggerProxy.e("inProgress %s", progress);
callback.onProgress(progress, total);
}
@Override
public void onError(Call call, Exception e, int id) {
LoggerProxy.e(e, "onError");
}
@Override
public void onResponse(File response, int id) {
LoggerProxy.e("onResponse %s", response.exists());
callback.onResponse(response);
}
@Override
public void onBefore(Request request, int id) {
LoggerProxy.e("onBefore %s", request);
super.onBefore(request, id);
callback.onBefore();
}
})
.build()
.download();
}
}
download方法已经执行到了onResponse
,而且 LoggerProxy.e("onResponse %s", response.exists());
这一行打出来的为true,为啥还不能安装呢?
@WVector 麻烦您帮忙看看。
Jiiiiiin commented
刚才我用华为mate8 7.0系统可以使用。
但是8.0的系统还是不支持,安装,而且会出现状态栏通知不出来问题:
03-29 20:44:53.785 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-29 20:45:04.684 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-29 20:45:16.283 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-29 20:45:16.473 8925-8932/com.csii.mobilebank I/zygote64: Compiler allocated 6MB to compile void android.view.ViewRootImpl.performTraversals()
03-29 20:45:29.406 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-29 20:45:32.300 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-29 20:45:37.086 8925-8925/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
但是我奇怪的是,为什么官方demo是ok的呢?
WVector commented
android8.0 通知的问题已经适配
Jiiiiiin commented
@WVector 我更新之后测试:
static void appUpdate(final Activity activity, boolean needShowProgress) {
DeviceUtil.generateWriteExternalStorage(activity, (granted) -> {
if (granted) {
_update(activity, needShowProgress);
} else {
ToastUtils.showLong("未授权SD卡写权限,应用更新无法正常进行,存在某些应用不能得到及时更新的风险");
}
});
}
private static void _update(Activity activity, boolean needShowProgress) {
// 官方测试
new UpdateAppManager
.Builder()
//当前Activity
.setActivity(activity)
//更新地址
.setUpdateUrl("https://raw.githubusercontent.com/WVector/AppUpdateDemo/master/json/json.txt")
//实现httpManager接口的对象
.setHttpManager(new UpdateAppHttpUtil(activity))
.build()
.update();
}
发现3个问题:
- 通知栏每每前进百分之1就【报警】一声
- 切换到任务栏之后,更新就会断掉,必须重新开始
- 下载成功不安装,之后还需要从零开始下载
控制台在更新的时候还是会报:
03-30 16:09:01.758 29447-29447/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-30 16:09:02.479 29447-29447/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-30 16:09:03.858 29447-29447/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-30 16:09:05.987 29447-29447/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
03-30 16:09:07.324 29447-29447/com.csii.mobilebank E/NotificationManager: notifyAsUser: tag=null, id=0, user=UserHandle{0}
Jiiiiiin commented
另外一个,其实appkey和appVersion是框架所需的后台交易需要的参数,针对一般的应用来说都会存在自身的交易和返回值,所以这个应该不是必须的:
// if(params == null){
// params = new WeakHashMap<>();
// params.put("appKey", "ab55ce55Ac4bcP408cPb8c1Aaeac179c5f6f");
// params.put("appVersion", "1.0");
// }
避免误导有些同学,觉得是不是非得用,其实这个插件好的地方出了UI还有就是.checkNewApp(updateCallback)
提供了我们这个回调自己去适配的功能,这就够了。因为需求其实是千变万化的,比如我这边的需求就是"https://www.easy-mock.com/mock/5abc903ff5c35b191f472d79/example/QryMobileClientVerNew.do" 请求这样一个后台地址(POST),返回的不仅仅是app的更新信息还有h5的离线缓存包更新信息。