第一种是一次自动更新

1.在服务器需要一个json或html文件,json最好

  1. {
  2. "state":"yes",//是否自动更新
  3. "mark":"1.0.6",//版本号
  4. "url":"http:\/\/xx\/appproject\/mm.apk"//更新的应用下载地址
  5. }

2.自动更新函数
t是你当前正在运行的app的版本号

  1. //检查自动更新
  2. function svnt){
  3. var xhr=new plus.net.XMLHttpRequest();
  4. xhr.onreadystatechange=function(){
  5. if(xhr.readyState==4) {
  6. if(xhr.status==200){
  7. var res=JSON.parse(xhr.responseText);
  8. if(res.state=='yes'){
  9. if(res.mark!=t){
  10. var upr;
  11. plus.nativeUI.confirm('有新版本发布了,是否更新?',function(e){
  12. upr=(e.index==0)?'Y':'N';
  13. if(upr=='Y'){
  14. var wt=plus.nativeUI.showWaiting('下载更新中,请勿关闭');
  15. var url=res.url;//下载地址
  16. var dtask=plus.downloader.createDownload(url,{},function(d,status){
  17. if(status==200){
  18. var path=d.filename;
  19. plus.runtime.install(path);
  20. }else{//下载失败
  21. alert('Download failed:'+status);
  22. }
  23. });
  24. dtask.start();
  25. }else {}
  26. },'xx系统',['确认','取消']);
  27. }else {
  28. console.log('最新');
  29. }
  30. }
  31. }else {
  32. plus.nativeUI.toast('网络连接错误!');
  33. }
  34. }
  35. }
  36. xhr.open('GET','http://xx/appproject/imes/update.json');//这里的地址是上面的json地址
  37. xhr.send();
  38. }

3.调用方法:在每次系统打开运行的时候执行上面的函数就行了

第二种是增量更新

对于移动app,尤其是webapp,如何更新一直是比较重要的话题。以前的大部分APP都是从应用商店进行版本更新,但是对于webapp来说,使用增量更新可以节省流量;更重要的是,它免去了新版本在应用商店的审核,使上架时间可以更加提前。
一、前提
1.环境:使用H5+作为webview与手机平台交互的中间件;关于H5+,请自行参考http://www.html5plus.org/#home
2.需求:点击“检查更新”,app在线检查版本是否有更新,如果有,下载并更新:
3.更新包后缀名为:.wgt,制作方式:使用zip打包所有项目根目录下的html/js/css/images/manifest.json;其中:manifest.json不能有注释,否则在ios下将会更新失败;
二、实现
1.检查更新按钮:

  1. <ul class="mui-table-view">
  2. <li class="mui-table-view-cell">
  3. <a class="mui-navigate-right" onclick="CheckUpdate(false);">检查更新</a>
  4. <button class="mui-btn mui-btn-link mui-btn-block" id=Progress_burron" style="display:none;"></button>
  5. </li>
  6. </ul>

2.update.js:

  1. function CheckUpdate(auto){
  2. //API的get请求
  3. var checkUrl="http://app.com?appkey="+appkey+"&clientversion="+plus.runtime.version;
  4. var RequestResponse=new Object();
  5. RequestResponse.Success=function(Result){
  6. Unloading();
  7. var ResulteObject=JSON.parse(Result);
  8. if(ResultObject.apicode==0){//当api返回code为0表示成功
  9. if(ResultObject.needUpdate){
  10. //MessageBox("需要更新",function(){
  11. //MessageBox("下载包地址:"+ResultObject.url,function(){
  12. ConfirmBox("有新版本,是否更新?",function(){
  13. document.getElementById("Progress_Button").style.cssText="display:block;";
  14. UpdateKey=ResultObject.updatekey;
  15. DownloadFile(ResultObject.url);
  16. DownloadFile(serverHost+"/app/update.wgt");
  17. },function(){
  18. return;
  19. });
  20. //});
  21. //});
  22. }else {
  23. if(!auto){
  24. MessageBox("不需要更新",function(){});
  25. }
  26. }
  27. }else {
  28. if(!auto){
  29. showError();
  30. }
  31. }
  32. }
  33. RequestResponse.Error=function(Result){
  34. Unloading();
  35. showError();
  36. }
  37. console.log(CheckUrl);
  38. //发送请求
  39. SendData(Checkrl,RequestResponse);//发送Post
  40. }
  41. //完成更新
  42. function FinishUpdate(){
  43. //API的get请求地址
  44. var UpdateUrl="http://app.zimayan.com/Rest/finishUpdate?updatekey="+UpdateKey;
  45. UpdateUrl+="&model="+encodeURIComponent(GetDeviceInfo().Model);
  46. UpdateUrl+="&vendor="+encodeURIComponent(GetDeviceInfor().Vendor);
  47. Update+="&uuid=" + encodeURIComponent(GetDeviceInfo().UUID);
  48. UpdateUrl+="&screen=" + encodeURIComponent(GetDeviceInfo().Screen);
  49. UpdateUrl+="&dpi=" + encodeURIComponent(GetDeviceInfo().DPI);
  50. UpdateUrl+="&networkinfo=" + encodeURIComponent(GetDeviceInfo().NetworkInfo);
  51. UpdateUr+="&oslanguage=" + encodeURIComponent(GetDeviceInfo().OS.Language);
  52. UpdateUrl+="&osversion=" + encodeURIComponent(GetDeviceInfo().OS.Version);
  53. UpdateUrl+="&osname=" + encodeURIComponent(GetDeviceInfo().OS.Name);
  54. UpdateUrl+="&osvendor=" + encodeURIComponent(GetDeviceInfo().OS.Vendor);
  55. var RequestResponse=new Object();
  56. RequestResponse.Success=function(Result){
  57. var ResultObject=JSON.parse(Result);
  58. if(ResultObject.apicode==0){//当api返回code为0表示成功
  59. }else {
  60. //showError();
  61. }
  62. }
  63. RequestResponse.Error=function(Result){}
  64. //发送请求
  65. SendDate(UpdateUrl,RequestResponse);//发送Post
  66. }
  67. //下载
  68. function DownloadFile(url){
  69. var d = plus.downloader.createDownload(url, {}, function(f, s) {
  70. document.getElementById("Progress_Button").style.cssText = "display: none;";
  71. ConfirmBox("下载完成,是否立即更新", function() {
  72. // console.log(f.filename)
  73. /*
  74. * unzip the folder..
  75. */
  76. // plus.zip.decompress( f.filename, "_doc/", function(){alert("decompress success!")}, function(err){
  77. // alert(JSON.stringify(err));
  78. // });
  79. plus.runtime.install(f.filename, {force:true}, function() {
  80. //完成更新向服务器进行通知
  81. alert("更新完毕,将重启应用!");
  82. FinishUpdate();
  83. plus.runtime.restart();
  84. },function(err){
  85. alert(JSON.stringify(err));
  86. mui.toast("安装升级失败");
  87. });
  88. }, function() {
  89. return;
  90. });
  91. }, function() {
  92. MessageBox("下载失败", function() {});
  93. });
  94. d.addEventListener('statechanged', function(download, status) {
  95. // console.log(JSON.stringify(download));
  96. if (download.state == 3 && status == 200) {
  97. var percent = Math.round((download.downloadedSize / download.totalSize) * 100);
  98. document.getElementById("Progress_Button").innerHTML = (percent + "%");
  99. } else if (download.state == 4) {}
  100. }, false);
  101. d.start();
  102. }
  103. //确认消息
  104. function ConfirmBox(MSG, OKFN, CancelFN) {
  105. plus.nativeUI.confirm(MSG, function(e) {
  106. if (e.index == 0) {
  107. OKFN();
  108. } else {
  109. CancelFN();
  110. }
  111. }, "提示", ["确定", "取消"]);
  112. }
  113. //发送数据
  114. function SendData(URL, ResponseObject) {
  115. var MyXMLHttpRequest = new plus.net.XMLHttpRequest();
  116. MyXMLHttpRequest.onreadystatechange = function() {
  117. switch (MyXMLHttpRequest.readyState) {
  118. case 0:
  119. break;
  120. case 1:
  121. break;
  122. case 2:
  123. break;
  124. case 3:
  125. break;
  126. case 4:
  127. if (MyXMLHttpRequest.status == 200) {
  128. ResponseObject.Success(MyXMLHttpRequest.responseText);
  129. } else {
  130. plus.nativeUI.toast("检查更新出错");
  131. }
  132. break;
  133. }
  134. }
  135. MyXMLHttpRequest.open("GET", URL);
  136. MyXMLHttpRequest.send();
  137. }
  138. //获得系统信息
  139. function GetDeviceInfo() {
  140. var device = {
  141. IMEI: plus.device.imei,
  142. IMSI: "",
  143. Model: plus.device.model,
  144. Vendor: plus.device.vendor,
  145. UUID: plus.device.uuid,
  146. Screen: plus.screen.resolutionWidth * plus.screen.scale + " x " + plus.screen.resolutionHeight * plus.screen.scale + "",
  147. DPI: plus.screen.dpiX + " x " + plus.screen.dpiY,
  148. OS: new Object()
  149. };
  150. for (var i = 0; i < plus.device.imsi.length; i++) {
  151. device.IMSI += plus.device.imsi[i];
  152. }
  153. var types = {};
  154. types[plus.networkinfo.CONNECTION_UNKNOW] = "未知";
  155. types[plus.networkinfo.CONNECTION_NONE] = "未连接网络";
  156. types[plus.networkinfo.CONNECTION_ETHERNET] = "有线网络";
  157. types[plus.networkinfo.CONNECTION_WIFI] = "WiFi网络";
  158. types[plus.networkinfo.CONNECTION_CELL2G] = "2G蜂窝网络";
  159. types[plus.networkinfo.CONNECTION_CELL3G] = "3G蜂窝网络";
  160. types[plus.networkinfo.CONNECTION_CELL4G] = "4G蜂窝网络";
  161. device.NetworkInfo = types[plus.networkinfo.getCurrentType()];
  162. device.OS = {
  163. Language: plus.os.language,
  164. Version: plus.os.version,
  165. Name: plus.os.name,
  166. Vendor: plus.os.vendor
  167. };
  168. return device;
  169. }

其中,

  1. plus.runtime.install(f.filename,{force:true},function(){}

这一行,{force:true}这个参数必不可少。这是由于在安卓下目前还有一些bug,必须加上。
实现效果:当用户点击检查更新,先检查是否更新;如果需要更新,则下载.wgt文件,调用plus.runtime.install进行安装,安装成功后弹出成功,然后自动重启应用。