【第一節】android增量升級之生成so文件

該篇文章從eoeAndroid搬遷過來的,原文地址:【第一節】android增量升級之生成so文件

前言

對於android項目,我們常常會遇到這樣一種情況,比如某一版本的線上應用,突然發現了一個BUG,修改後發現不值當爲這個BUG進行一次版本升級,那麼怎麼去解決在同一版本上修改線上應用的BUG呢,Google給了我們一種解決方案 Smart App update,也就是應用增量升級。

那麼,何謂增量升級呢?簡單的來說,也就是把同一版本的新舊兩個apk進行差分,得到一個差異包,然後在舊的應用中下載該差異包和舊的apk進行合併成新的apk,然後去安裝新的apk,該合成的apk和差分前新apk是一樣的,這樣就可以做到應用的增量升級。一般來說,獲取到的差異包較之新的apk來說小了很多,這樣就可以減少用戶的下載流量。

增量升級需要用到jni開發,所以我們需要去生成合並差異包的so文件,這裏我們需要準備的工具有:eclipse,NDK環境(這裏用的是ndk9以上的版本),bsdiff文件,bzip2文件(這兩個文件在下面附件中給出)。

第一步

創建一個android項目,比如SmartAppUpdateSo,設定好包名(此處爲以後引用so文件的方法做準備),例如com.smartapp.update。右鍵點擊項目 -> Android tools -> Add Native Support…,在彈出窗裏填寫你要生成的so文件名稱,如SmartAppUpdate,這樣我們就能在項目中看到jni和obj兩個文件夾了,刪除jni文件夾下的SmartAppUpdate.cpp文件。

第二步

新建BatchUtils工具類,在類中增加方法

private native static int patchApk(String oldApkPath, String newApkPath, String patchPath);

打開cmd界面,進入到項目的bin\classes路徑下,執行javah com.smartapp.update.BatchUtils命令,我們就能在bin\classes路徑下發現一個命名爲com_smartapp_update_BatchUtils.h的文件,打開該文件,裏面的內容爲

/* DO NOT EDIT THIS FILE - it is machine generated */
#include <jni.h>
/* Header for class com_smartapp_update_BatchUtils */

#ifndef _Included_com_smartapp_update_BatchUtils
#define _Included_com_smartapp_update_BatchUtils
#ifdef __cplusplus
extern "C" {
#endif
/*
 * Class:     com_smartapp_update_BatchUtils
 * Method:    patchApk
 * Signature: (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)I
 */
JNIEXPORT jint JNICALL Java_com_smartapp_update_BatchUtils_patchApk
  (JNIEnv *, jclass, jstring, jstring, jstring);

#ifdef __cplusplus
}
#endif
#endif

第三步

將com_smartapp_update_BatchUtils.h文件拷貝到項目的jni文件夾下,然後將bzip2文件中的相關文件也拷貝到項目的jni文件夾下,需要拷貝的文件有:

blocksort.c
bzip2.c
bzip2recover.c
bzlib_private.h
bzlib.c
bzlib.h
compress.c
crctable.c
decompress.c
dlltest.c
huffman.c
mk251.c
randtable.c
spewG.c
unzcrash.c

第四步

將bsdiff中的bspatch.c文件拷貝到項目的jni文件夾中,並將其重命名爲com_smartapp_update_BatchUtils.c,打開該文件,修改其中的內容:

1.將頭文件替換掉,原內容爲:

#if 0
__FBSDID("$FreeBSD: src/usr.bin/bsdiff/bspatch/bspatch.c,v 1.1 2005/08/06 01:59:06 cperciva Exp [        DISCUZ_CODE_3        ]quot;);
#endif

#include <bzlib.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <err.h>
#include <unistd.h>
#include <fcntl.h>

替換後的內容爲:

#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <err.h>
#include <unistd.h>
#include <fcntl.h>
#include <android/log.h>
#include <jni.h>

#include "bzlib.c"
#include "crctable.c"
#include "compress.c"
#include "decompress.c"
#include "randtable.c"
#include "blocksort.c"
#include "huffman.c"

#include "com_smartapp_update_BatchUtils.h"

2.將main方法名稱替換成applypatch

3.在文件內添加方法

JNIEXPORT jint JNICALL Java_com_smartapp_update_BatchUtils_patchApk(JNIEnv *env,
                jobject obj, jstring old, jstring new, jstring patch) {

        char * ch[4];
        ch[0] = "bspatch";
        ch[1] = (char*) ((*env)->GetStringUTFChars(env, old, 0));
        ch[2] = (char*) ((*env)->GetStringUTFChars(env, new, 0));
        ch[3] = (char*) ((*env)->GetStringUTFChars(env, patch, 0));

        __android_log_print(ANDROID_LOG_INFO, "ApkPatchLibrary", "old = %s ", ch[1]);
        __android_log_print(ANDROID_LOG_INFO, "ApkPatchLibrary", "new = %s ", ch[2]);
        __android_log_print(ANDROID_LOG_INFO, "ApkPatchLibrary", "patch = %s ", ch[3]);

        int ret = applypatch(4, ch);

        __android_log_print(ANDROID_LOG_INFO, "ApkPatchLibrary", "applypatch result = %d ", ret);

        (*env)->ReleaseStringUTFChars(env, old, ch[1]);
        (*env)->ReleaseStringUTFChars(env, new, ch[2]);
        (*env)->ReleaseStringUTFChars(env, patch, ch[3]);

        return ret;
}

第五步

修改Android.mk文件內容

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)

LOCAL_MODULE    := SmartAppUpdate
LOCAL_SRC_FILES := com_smartapp_update_BatchUtils.c

LOCAL_LDLIBS     := -lz -llog

include $(BUILD_SHARED_LIBRARY)

第六步

右鍵點擊項目 -> properties,在彈出窗中點擊Buiders,選擇New…,在新彈出窗中選擇Program,點擊OK,此時彈出一個Edit Configuration彈窗。

1.Name中填寫SmartAppUpdateBuilder

2.選擇Main標籤,在Location一欄中點擊Browse File System,選擇你NDK安裝路徑下的ndk-build.cmd文件,Working Directory一欄中點擊Browse Workspace,選擇該項目的jni文件夾

3.選擇Refresh標籤,勾選Refresh resources upon completion,選擇The entire workspace,勾選上Recursively include sub-folders

4.選擇BuildOptions,勾選Allocte Console,After a “Clean”,During manual builds,During auto builds,Specify working set of relevant resources ,點擊Specify Resources,在彈出窗中勾選該項目jni文件夾,點擊Apply,點擊OK,這樣我們就能在Buiders列表中看見新建的SmartAppUpdateBuilder,點擊OK

第七步

等待片刻,我們會發現在obj文件夾下自動編譯出一些文件,而其中obj\local\armeabi下的libSmartAppUpdate.so文件就是我們需要的so文件,那麼生成增量升級的so文件的教程到此爲止。

如何去使用該so文件進行增量升級,請看 【第二節】android增量升級之使用so文件進行增量升級

下載地址:項目文件及工具(bsdiff-4.3,bzip2-1.0.6,SmartAppUpdateSo)

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章