自動更新

今天做了自動更新功能,現在把趟過的坑介紹一下:
自動更新步驟:獲取當前版本號,然後去和服務器版本號對比,如果不一樣就說明有升級,提示用戶升級,用戶點擊確定後自動後臺下載新APK並且安裝。聽起來是不是很簡單?做起來也很簡單,只是有一些坑而已。

我是在LoginActivity()中寫的自動更新功能,在用戶準備登陸時判斷一下是否有新版本,如果有的話就自動更新(我做的是強制性更新),沒有不做處理,當然可以有更人性化的處理,給用戶選擇是否升級的權利

  private int versionCode;//當前版本號
private String version_info;//版本信息
private Context mContext;
private int version_netcode;//服務端當前版本號
 @Override   protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_login);
    initView();
    mContext = this;
    Log.e("tag", "11111111111111111111111");
    // 獲取當前版本號
    try {
        getVersonCode();//
    } catch (Exception e) {
        e.printStackTrace();
    }
    //獲取服務端的版本號
    getNetVersonCode();//

 }   /**
 * 獲取當前程序版本號//
 *
 * @return
 * @throws Exception
 */
private int getVersonCode() throws Exception {
    PackageManager packageManager = getPackageManager();
    //getPackageName()是你當前類的包名,0代表是獲取版本信息
    PackageInfo packageInfo = packageManager.getPackageInfo(getPackageName(), 0);
    versionCode = packageInfo.versionCode;

Log.e(“TTTTTTT”, versionCode + “”);
return versionCode;

}

/**
 * 獲取服務端的版本號
 */
private void getNetVersonCode() {
    String url = "http://crm.taxchina.com/wcm/inside/gkk/interface/AndroidUpdate.aspx ";//各自公司後臺提供,裏面存儲APK基本信息
    OkHttpUtils
            .get()
            .url(url)
            .build()
            .execute(new StringCallback() {
                @Override
                public void onError(Call call, Exception e) {
                }
                @Override
                public void onResponse(String response) {
                    //請求網絡成功解析數據
                    Log.e("888888888888888888888", "聯網成功");
                    processData(response);


                }
            });


}

private void processData(String response) {


    VersonModel versonModel = new Gson().fromJson(response, VersonModel.class);
    version_netcode = Integer.parseInt(String.valueOf(versonModel.getVersion_code()));

    version_info = versonModel.getVersion_info();

    Log.e("tttttt", version_netcode + "");
    //比較兩個版本是否一致
    CheckVersionTask();

}

private void CheckVersionTask() {


    if (versionCode == version_netcode) {
        Log.e("tagggggg", "版本號相同無需升級");

    } else {

        //提示用戶升級
        Message msg = Message.obtain();
        msg.what = UPDATA_CLIENT;
        handler.sendMessage(msg);
    }

}

Handler handler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
        super.handleMessage(msg);
        switch (msg.what) {
            case UPDATA_CLIENT:
                //提示用戶升級的對話框
                showUpdataDialog();
                break;
        }
    }
};

private void showUpdataDialog() {

    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setTitle("版本升級");
    builder.setMessage(version_info);
    //用戶點擊確定按鈕下載新的apk
    builder.setPositiveButton("確定", new DialogInterface.OnClickListener() {
        @Override
        public void onClick(DialogInterface dialog, int which) {
            Log.e("tag000000000", "下載apk,更新");
            downLoadApk();
        }
    });
    builder.show();
}

/**
 * 從服務器中下載apk
 */
private void downLoadApk() {

    final String path = "http://crm.taxchina.com/wcm/resource/UploadApk/taxSign.apk";//下載APK的路徑也是公司後臺服務端給接口
    final ProgressDialog pd;
    pd = new ProgressDialog(this);
    pd.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
    pd.setMessage("正在下載更新");
    pd.show();
    new Thread() {

        @Override
        public void run() {
            super.run();

            //下載安裝apk

            try {
                Utils.getFileFromServer(mContext,path,pd);*強調內容*重點內容**

            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }.start();


}

//下面放上utils工具包代碼,也是核心代碼

/**
 * 從服務器下載apk:
 *
 * @param context
 * @param path
 * @param pd
 * @throws Exception
 */
public static void getFileFromServer(Context context, String path,
                                     ProgressDialog pd) throws Exception {  
    String downloadPath = Environment.getExternalStorageDirectory()
            .getPath() + "/download_cache";
    File file = new File(downloadPath);
    if (!file.exists())
        file.mkdir();

    URL url = new URL(path);
    HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
    urlConnection.setConnectTimeout(5 * 1000);
    urlConnection.setRequestMethod("GET");
    urlConnection.connect();
    try {
        if (urlConnection.getResponseCode() == 200) {
            InputStream is = urlConnection.getInputStream();
            // 開始下載apk文件
            FileOutputStream fos = new FileOutputStream(downloadPath
                    + "/action.apk");
            BufferedInputStream bis = new BufferedInputStream(is);
            byte[] buffer = new byte[5120];
            int total = 0;
            int count = 0;
            while ((count = bis.read(buffer)) != -1) {
                fos.write(buffer, 0, count);
                total += count;
                // 獲取當前下載量
                pd.setProgress(total);
            }
            fos.close();
            bis.close();
            is.close();
            urlConnection.disconnect();
            pd.dismiss();
            // 安裝 apk 文件
            installApk(context, downloadPath + "/action.apk");
        }
    } catch (Exception e) {
        pd.dismiss();
    }
}

/**
 * 安裝apk
 *
 * @param context
 * @param filename
 */
protected static void installApk(Context context, String filename) {

    File file = new File(filename);
    Intent intent = new Intent();

    intent.setAction(Intent.ACTION_VIEW); // 瀏覽網頁的Action(動作)
   intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
 String type = "application/vnd.android.package-archive";
intent.setDataAndType(Uri.fromFile(file), type); // 設置數據類型

context.startActivity(intent);

}

好了,到此爲止自動更新功能就添加完成了,就會自動下載安裝了。

此處有兩個坑:1、 String type = “application/vnd.android.package-archive”; android必須都是小寫
2、 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);加上此句纔會有安裝運行新應用窗口提示

最後一個大坑是用真機測試的時候,卻提示“未安裝應用程序”。

說明:這裏的要升級的文件已經正常下載到手機上了,權限也都加好了。

產生這種現象的原因就是:手機上已經安裝好的apk和正在安裝的apk包名都是一樣的,可是簽名不一樣,所以它會提示你安裝不成功。在服務器上的升級包是做好籤名的,而我在測試的時候是用真機測試的,也就是說電腦上的android程序直接運行在了手機上,而沒有經過打包簽名,最後導致的結果就是文件正常下載到手機上,可是安裝不成功。

其實解決方法也很簡單了:把簽名的安裝包安裝到手機上,再測試升級的功能,這樣就沒有問題了。

這是我的一些個人理解,由於水平有限,如果有問題我會及時改正,歡迎大家指正錯誤。

發佈了22 篇原創文章 · 獲贊 8 · 訪問量 1萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章