目录
1.实现思路
①将安装包存储在后台服务器。
创建版本信息表,存储安装包的相关信息。保存安装包的名称,版本号,网络地址,是否强制升级,发布时间信息及升级内容等。表结构如下:
开发前端画面,设置版本的发布时间,版本号,是否强制及升级内容,并上传安装包。
后端将安装包的信息存储到数据库的版本表中,并将安装包上传到服务器上。
②获取后端的版本信息
获取发布时间小于等于系统时间的按照版本号或者创建时间进行降序排列的第一条数据,即最新的版本信息。
如果app的版本号和最新的版本号差了不只一个版本,则设置为强制升级;否则则按照最新app的强制升级区分进行处理。
3.app端处理
将app的版本号作为参数,获取后端的版本信息。
将app的版本号和后端最新的版本号进行比较。
相等则不做任何处理。
当小于最新的版本号时,再判断强制类型。强制时,弹出强制升级框,只有更新按钮,没有取消按钮,安卓的原生返回按钮失效。也就是说必须点击更新按钮,无法进行其他操作。非强制升级时,弹出升级框,有更新按钮和取消按钮,按照需要进行升级。
2.app代码示例
①升级判断方法
import { getUpdateInfo } from '@/api/appUpdate'
import { ref } from 'vue';
export default function AppUpdate() {
// 获取运行平台
let platform = uni.getSystemInfoSync().platform
// 获取appid
const appId : any = plus.runtime.appid
// 获取当前app的版本信息
const version = ref();
plus.runtime.getProperty(appId, (inf) => {
version.value = inf.versionCode
/*
2, 用当前版本号提交给服务端,判断是否需要更新,接口返回信息如下
versionCode 版本号 string
appPath apk地址 string
forceType 是否强制更新 string
content 升级内容 string
*/
getUpdateInfo({ versionCode: version.value }).then((res) => {
if (res.data.resHdr && res.data.resHdr.resCode != "0000") {
return
}
if (!res.data.resBody) {
return
}
const {
versionCode,
appPath,
forceType,
content
} = res.data.resBody;
// 后台返回的版本号大于现有的版本号
if (Number(versionCode) > Number(inf.versionCode)) {
//modify 1 强制更新 0 自然更新
if (forceType) {
uni.showModal({
title: '紧急升级通知',
content: '尊敬的用户,为了您更好的使用体验,请进行系统升级,否则将无法正常使用。感谢您的配合与支持!\r\n升级内容:' + content,
confirmText: '立即更新',
showCancel: false,
success: function (res) {
if (res.confirm) {
// uni.showToast({
// icon: 'none',
// title: '有新的版本发布,程序已启动自动更新。',
// duration: 2000
// });
//设置 最新版本apk的下载链接 这是固定的
let downloadApkUrl = appPath
console.log(downloadApkUrl);
uni.downloadFile({
url: downloadApkUrl, //仅为示例,并非真实的资源
success: (res) => {
if (res.statusCode === 200) {
console.log('下载成功');
plus.runtime.install(res.tempFilePath, {
force: false
}, () => {
console.log("更新成功")
// uni.hideToast();
plus.runtime.restart();
return;
}, err => {
console.log("更新失败")
uni.showToast({
icon: "none",
title: "更新失败" + JSON.stringify(err),
duration: 2000
})
})
}
}
});
// plus.runtime.openURL(downloadApkUrl);
} else {
AppUpdate()
}
}
})
} else {
uni.showModal({
title: '升级通知',
content: '尊敬的用户,我们为您准备了最新的版本,点击立即升级,享受更多精彩和便利。\r\n升级内容:' + content,
confirmText: '立即更新',
cancelText: '取消',
success: function (res) {
if (res.confirm) {
// uni.showToast({
// icon: 'none',
// title: '有新的版本发布,程序已启动自动更新。',
// duration: 5000
// });
//设置 最新版本apk的下载链接 这是固定的 每次把包放在这个链接里里面即可 由后端制作
let downloadApkUrl = appPath
uni.downloadFile({
url: downloadApkUrl, //仅为示例,并非真实的资源
success: (res) => {
if (res.statusCode === 200) {
console.log('下载成功');
plus.runtime.install(res.tempFilePath, {
force: false
}, () => {
plus.runtime.restart();
console.log("重启成功")
return;
}, err => {
console.log("更新失败")
uni.showToast({
icon: "none",
title: "更新失败" + JSON.stringify(err),
duration: 2000
})
})
}
}
});
} else if (res.cancel) {
console.log('下次一定');
}
}
});
}
} else {
console.log("版本号已经是最新不用升级")
}
}
).catch((res) => {
uni.showToast({
title: '获取版本号失败',
icon: 'error'
})
})
});
}
通过plus命令获取当前app的相关信息,如下:
获取后端的版本信息后,进行版本号的比较,如果存在最新的版本号,则进行强制区分的判断,强制时则弹出强制升级框,否则弹出非强制升级模态框。
升级框通过uni.showModal实现。
强制升级时,设置标题,升级内容,按钮的名字,并设置取消按钮不显示。在打开模态框成功的方法中,通过res.confirm判断点击了升级按钮,点击了升级按钮后,进行安装包的下载,下载成功后进行安装,安装成功后进行重启。如果没有点击升级按钮,则再次执行此方法。
非强制升级时,设置了取消按钮显示,点击了取消按钮,不进行升级操作。点击升级按钮,进行升级操作。
②在首页的setup函数中执行此方法
3.说明
①强制升级安装过程中避免取消操作
安装包安装时,用户可以在安装过程中进行取消,如何避免这个问题?
执行plus.runtime.install方法时,即使用户取消操作,还是会执行成功方法,在成功的方法中添加restart方法,则会避免这个问题,如果用户取消了,则app会重新启动,登录之后再次弹出升级框。
②规避安卓手机原生的返回按钮
弹出强制升级框后,点击原生的返回按钮,可以关闭强制升级框,如何避免这个问题?
(1)通过判断是否点击的升级按钮,如果res.confirm返回true,则代表点击了升级按钮,如果为false,则代表没有点击升级按钮,则再次调用此升级方法进行升级
(2)不使用模态框方式,如果需要强制升级,跳转到强制升级画面,设置画面不能进行返回。
参照:
uniapp实现app版本更新弹窗,处理自主更新以及强制更新_uni-app检测app版本更新-CSDN博客
uniapp APP端在线升级功能实现讲解------强制或可选升级,下载进度显示_plus.runtime.install-CSDN博客