/* 下载中 */ private static final int DOWNLOAD = 1; /* 下载结束 */ private static final int DOWNLOAD_FINISH = 2; // 安装 private String cmd_install = "pm install -r "; // 卸载 private String cmd_uninstall = "pm uninstall "; // 静默安装在根目录 String apkLocation = Environment.getExternalStorageDirectory().toString() + "/"; String fileName; int length = 0; private int progress; private ProgressBar progressBar; private TextView downTV; private LinearLayout downlayout, barlayout; private Handler mHandler = new Handler() { public void handleMessage(Message msg) { switch (msg.what) { // 正在下载 case DOWNLOAD: // 设置进度条位置 progressBar.setProgress(progress); break; case DOWNLOAD_FINISH: progressBar.setProgress(length); barlayout.removeView(progressBar); ProgressBar large = new ProgressBar(DownloadUpdate.this); barlayout.addView(large); downTV.setText("下载完成,正在安装最新版本,请稍后!"); break; default: break; } }; };
安卓中基本的下载方法:
// 文件下载 protected File downLoadFile(String httpUrl) { //自定义的文件名称 fileName = "updata1.apk"; //文件保存在SDCARD下的根目录。如果有需要可以新建一个文件夹 final File file = new File("/sdcard/" + fileName); try { //下载的地址 URL url = new URL(httpUrl); try { HttpURLConnection conn = (HttpURLConnection) url .openConnection(); InputStream is = conn.getInputStream(); FileOutputStream fos = new FileOutputStream(file); byte[] buf = new byte[1024]; conn.connect(); length = conn.getContentLength(); int count = 0; if (conn.getResponseCode() >= 400) { Toast.makeText(DownloadUpdate.this, "连接超时", Toast.LENGTH_SHORT).show(); } else { while (1 == 1) { int numread = is.read(buf); count += numread; // 计算进度条位置 progress = (int) (((float) count / length) * 100); // 更新进度 mHandler.sendEmptyMessage(DOWNLOAD); if (numread <= 0) { // 下载完成 mHandler.sendEmptyMessage(DOWNLOAD_FINISH); break; } // 写入文件 fos.write(buf, 0, numread); } } conn.disconnect(); fos.close(); is.close(); } catch (IOException e) { e.printStackTrace(); } } catch (MalformedURLException e) { e.printStackTrace(); } return file; }
以上是下载的方法,后面是安装的方法
// 一般打开APK程序 private void openFile(File file) { Log.e("OpenFile", file.getName()); Intent intent = new Intent(); intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); intent.setAction(android.content.Intent.ACTION_VIEW); intent.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive"); startActivity(intent); }
有时候根据客户的要求,要用到静默安装,这里找到一个静默安装的方法,前提条件是要有ROOT环境
//静默安装和卸载 protected int excuteSuCMD(String cmd) { try { Process process = Runtime.getRuntime().exec("su"); DataOutputStream dos = new DataOutputStream( (OutputStream) process.getOutputStream()); dos.writeBytes((String) "export LD_LIBRARY_PATH=/vendor/lib:/system/lib\n"); cmd = String.valueOf(cmd); dos.writeBytes((String) (cmd + "\n")); dos.flush(); dos.writeBytes("exit\n"); dos.flush(); process.waitFor(); int result = process.exitValue(); return (Integer) result; } catch (Exception localException) { localException.printStackTrace(); return -1; } }
最后是主线程里面调用这些方法
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.downloadupdate); downTV = (TextView) findViewById(R.id.downloadTV); progressBar = (ProgressBar) findViewById(R.id.progressBar1); downlayout = (LinearLayout) findViewById(R.id.downLayout); barlayout = (LinearLayout) findViewById(R.id.downBarLayout); final Thread thread = new Thread(new Runnable() { @Override public void run() { Log.d("TAG", "进更新线程"); // 下载文件的地址 //------------------------------------------------------------------------// File file = downLoadFile("http://dd-20141030eoux:8080/Tese/GetMacAndIP.apk"); //------------------------------------------------------------------------// if (file.exists()) { Log.d("TAG", "下载成功"); } else { Log.d("TAG", "下载失败"); } //------------------------------------------------------------------------// // 静默卸载原来程序(根据包名) String ucmd = cmd_uninstall + "com.example.getmacandip"; //------------------------------------------------------------------------// excuteSuCMD(ucmd); // 一般的安装 // openFile(file); // 需要静默安装的文件,文件名自己定义为下载的文件名 String cmd = cmd_install + apkLocation + "updata1.apk"; excuteSuCMD(cmd); // 根据包名打开应用 PackageManager packageManager = DownloadUpdate.this .getPackageManager(); Intent intent = new Intent(); //------------------------------------------------------------------------// // 包名打开 intent = packageManager .getLaunchIntentForPackage("com.example.getmacandip"); //------------------------------------------------------------------------// startActivity(intent); } }); thread.start(); }
xml文件里面需要用到的权限:
<uses-permission android:name="android.permission.INTERNET" /> <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> <uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS" /> <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
以上可以实现下载目标地址的APK,根据包名静默卸载原有APK,静默安装新下载的APK,最后直接打开APK。中间完全不询问