Android/ target=_blank class=infotextkey>安卓更新方式,网上五花八门,但是真正实现apk自动更新无痕迹的方式,少之又少,毕竟不要钱的方式,稳定的方式才能让开发者在困难中脱颖而出 。
安卓程序如何做到自动更新?安卓程序如何实现无弹框更新?
1,安卓apk自动更新方式?
a,第三方平台更新apk,灰度发布,用友等
b,系统更新方式有弹窗contenx,通过窗体上下文方式实现更新 。
c,通过安卓程序系统服务实现命令更新,自启等 。
d,通过安卓反编译修改安卓源码包实现自动更新 。
我们采用安卓系统apk方式实现apk重启更新上图:
文章插图
文章插图
整体流程:1,我们Tomcat服务器挂载或者ftp服务器提供apkurl地址 。
2,安卓程序定时拉取获取监听下载url地址,下载apk到本地获取新的版本,对比当前的apk版本进行更新 。
3,如果当前版本大于运行的apk程序版本进行apk更新 。
4,通过我们JAVA程序执行cmd命令 adb 方式去读取命令行执行方式返回信息进行程序更新 。
5,通过adb命令把apk推送到系统程序里面,获取apk包名实现程序重启,即可完成安卓程序自动更新 。
实现弹框的方式:
public boolean installApk(Context context) throws Exception {try {Intent intent = new Intent();intent.setAction(Intent.ACTION_VIEW);intent.setDataAndType(Uri.fromFile(new File(configPath + "App-release.apk")), "application/vnd.android.package-archive");intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);//打开安装应用界面context.startActivity(intent);} catch (Exception e) {e.printStackTrace();return false;}return true;}
文章插图
文章插图
?
这种方式不能实现自动发包,但是可以完成自动更新 。
通过cmd命令操作实现apk覆盖自动重启:1,连接到adb
adb connect 127.0.0.1:7555
文章插图
2,查看连接状态
adb devices
文章插图
?
3,通过adb root 命令权限 。
adb root
文章插图
?
4,获取系统app权限
adb remount
文章插图
5,把app上传到系统里面
adb push D:app-release.apk /system/app/
文章插图
6,查找包名重启apk
adb shell pm list package -f
文章插图
?
查看启动Activity类名
adb shell dumpsys package com.instwall.launch(进行系统shell里面去查看包名)
文章插图
?
7,重启程序(复制系统app下面的应用包名)
adb shell am start -n <应用包名>/<应用启动Activity绝对名称>adb shell am start -ncom.instwall.launch/.MainActivity
文章插图
【Android APK 程序实现自动更新,java服务处理无弹窗,终极解决方案】
?
我们可以看到当前的程序已经启动 。但是命令行的方式还是需要手动去打命令自然不满足我们自动更新的操作处理,至于这里为什么不用第三方平台的问题,原因是因为我们的apk程序要支持离线更新,apk程序本身在专网里面,所以有很多限制 。这里我们可以通过java 程序去代替我们执行adb 脚本命令从而实现apk自动更新,只不过步骤要写很多 。
贴几个代码执行脚本的代码:
版本更新的核心处理类 。
package com.instwall.launch.task;import static com.instwall.launch.contans.Contans.configPath;import static com.instwall.launch.utils.FileDirectoryUtils.dropVedio;import static com.instwall.launch.utils.FileDirectoryUtils.getDownApkVersion;import static com.instwall.launch.utils.FileDirectoryUtils.readAppInfo;import static com.instwall.launch.utils.FileDirectoryUtils.writeAppInfo;import static com.instwall.launch.utils.FileDirectoryUtils.writeLog;import android.content.Context;import android.content.Intent;import android.net.Uri;import android.os.Build;import android.util.Log;import androidx.annotation.RequiresApi;import com.instwall.launch.contans.Contans;import com.instwall.launch.utils.CmdTerminalUtils;import com.instwall.launch.utils.FileDirectoryUtils;import java.io.File;import java.io.FileNotFoundException;import java.io.FileOutputStream;import java.io.IOException;import java.io.InputStream;import java.net.MalformedURLException;import java.net.URL;import java.net.URLConnection;/** * 版本更新 */public class UpdateVersionTask implements Runnable {private final Context context;public UpdateVersionTask(Context context) {this.context = context;}private static void download(String mUrl, String mPath) throws MalformedURLException {// 下载网络文件int byteread = 0;int mDownloadSize = 0;URL url = new URL(mUrl);URLConnection conn = null;InputStream is = null;FileOutputStream os = null;try {conn = url.openConnection();is = conn.getInputStream();os = new FileOutputStream(mPath);byte[] buffer = new byte[1204];int length;while ((byteread = is.read(buffer)) != -1) {mDownloadSize += byteread;os.write(buffer, 0, byteread);}Log.i("文件下载成功-------", mPath);writeLog("apk downfilesuccess .......... " + mPath);} catch (FileNotFoundException e) {e.printStackTrace();//dropFile(mPath);writeLog("apk downfileerror .......... " + e.getMessage());Log.e("文件下载失败-------", e.getMessage());} catch (IOException e) {e.printStackTrace();// dropFile(mPath);Log.e("文件下载失败---删除当前下载文件----", e.getMessage());writeLog("apk downfileerror .......... " + e.getMessage());} catch (Exception e) {e.printStackTrace();//dropFile(mPath);Log.e("文件下载失败---删除当前下载文件----", e.getMessage());writeLog("apk downfileerror .......... " + e.getMessage());} finally {// 关闭输出流if (os != null) {try {os.close();} catch (IOException e) {e.printStackTrace();}}// 关闭输入流if (is != null) {try {is.close();} catch (IOException e) {e.printStackTrace();}}}}@Overridepublic void run() {try {download(Contans.getApiDownUrl(), configPath + "app-release.apk");//获取下载的版本包int verson = getDownApkVersion(context, configPath + "app-release.apk");// writeLog("down apkversion .......... " + verson);int installVersion = readAppInfo();if (installVersion == 0) {installVersion = FileDirectoryUtils.getVersionCode(context);}writeLog("down nowversion .......... " + installVersion);//如果下载的版本大于当前运行的apk版本直接安装最新并且写入文件if (verson > installVersion) {writeLog("down nowversion .......... " + installVersion);//安装apkCmdTerminalUtils.startApk();//写入当前版本到文件夹writeAppInfo(verson);//删除没有下载完成的视频dropVedio();}} catch (Exception e) {writeLog("ReportHear apipulisherror .......... " + e.getMessage());}}public boolean installApk(Context context) throws Exception {try {Intent intent = new Intent();intent.setAction(Intent.ACTION_VIEW);intent.setDataAndType(Uri.fromFile(new File(configPath + "app-release.apk")), "application/vnd.android.package-archive");intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);//打开安装应用界面context.startActivity(intent);} catch (Exception e) {e.printStackTrace();return false;}return true;}@RequiresApi(api = Build.VERSION_CODES.O)private boolean isHasInstallPermissionWithO(Context context) {if (context == null) {return false;}return context.getPackageManager().canRequestPackageInstalls();}@RequiresApi(api = Build.VERSION_CODES.O)private void startInstallPermissionSettingActivity(Context context) {if (context == null) {return;}Intent intent = new Intent();//获取当前apk包URI,并设置到intent中(这一步设置,可让“未知应用权限设置界面”只显示当前应用的设置项)Uri packageURI = Uri.parse("package:" + context.getPackageName());intent.setData(packageURI);//设置不同版本跳转未知应用的动作if (Build.VERSION.SDK_INT >= 26) {//intent = new Intent(android.provider.Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES,packageURI);intent.setAction(android.provider.Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES);} else {intent.setAction(android.provider.Settings.ACTION_SECURITY_SETTINGS);}context.startActivity(intent);}}
推荐阅读
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- “顶级”java程序猿手把手教你快速启动Django项目 Django 应用程序
- 系统维护必备技巧:禁用非必要的启动程序,加快电脑启动速度
- 手把手教你进行安卓逆向之篡改apk名称和图标
- Android获取屏幕宽高的四种方式
- AspNet 应用程序热更新升级工具
- 程序员之间神奇的鄙视链,你在其中哪一层?
- 程序员与体面的公务员,到底怎么选?现在有结果了
- 小程序消息推送,订阅消息的实现,定时推送订阅消息功能
- 实战总结的7个C程序,好东西不私藏
- 2022必须拥有Chrome扩展程序 - 浏览器插件,让你上网效率翻倍