Android Studio打包APK后动态库so文件被改动

本人项目中遇到一个非常奇葩的问题,百思不得其解。

问题是这样的:

由于项目是将C/C++层的代码与java代码分开管理的,所以C/C++代码没有放进AS里,编译时将在linux下编译好的动态库直接放进AS工程的jniLibs下再打包生成APK。问题来了。

AS 打包APK后,打开APK检查里面的so动态库,与工程目录下jniLibs存放的so对比MD5签名,发现不一致。

Android Studio打包APK后动态库so文件被改动_第1张图片

Android Studio打包APK后动态库so文件被改动_第2张图片

取其中一个动态库进行校验,MD5不一致,看文件大小是一样大的(都是426460字节),错误库文件的修改时间正是APK编译的时间。

以前用着好好的,并没有出现这个问题,直到后来项目中踩到坑了,才发现so不对,最终定位到是AS打包APK时so被改动了。最开始以为是AS和Gradle版本问题,遂升级到最新版本,问题依然存在。没办法了,只能静下心来研究一番。

查看打包APK之后Module级别的build目录,在 build/intermediates/transforms/stripDebugSymbol/release/0/lib/armeabi 目录下发现了所有的动态库文件,检查库文件的MD5,与jniLibs下的so 不一致。

进一步查看gradle编译信息,发现在packageRelease之前有执行名为“transformNativeLibsWithStripDebugSymbolForRelease”的任务。如图:

Android Studio打包APK后动态库so文件被改动_第3张图片

对比一下名字,不难发现这个任务就是生成stripDebugSymbol目录内文件的过程。

修改module的build.gradle文件,尝试删除stripDebugSymbol目录下的库文件,看看编译出的APK会有什么变化。代码如下:

project.afterEvaluate {
    packageRelease.doFirst {
        delete{
            delete 'build/intermediates/transforms/stripDebugSymbol/release/0/lib/armeabi'
        }
    }
}

rebuild一下工程,发现编译出来的APK没有动态库了!这证明了最终打包APK的so文件就是使用的 stripDebugSymbol目录下的动态库。

现在可以针对这个目录进行修改了,在执行了transformNativeLibsWithStripDebugSymbolForRelease任务之后,packageRelease之前,我们将stripDebugSymbol目录清空,再把jniLibs目录下的库文件拷贝过去。代码如下:

packageRelease.doFirst {
        delete{
            delete 'build/intermediates/transforms/stripDebugSymbol/release/0/lib/armeabi'
        }
        copy{
            from 'src/main/jniLibs/armeabi'
            into 'build/intermediates/transforms/stripDebugSymbol/release/0/lib/armeabi/'
            include '*.so'
        }
    }
rebuild一下,检验APK,这下APK里的动态库文件正确了。

至于为什么执行了 transformNativeLibsWithStripDebugSymbolForRelease之后,动态库文件会被改动,这个实在是查不出原因。


后续在实际使用过程中,又发现目录不固定,目前发现有两种目录:

build/intermediates/transforms/stripDebugSymbol/release/0/lib/armeabi 

build/intermediates/transforms/mergeJniLibs/release/folders/2000/1f/main/lib/armeabi/

红字对应的是编译类型,如果是debug类型,则需要改成debug,对应的脚本也要改成 packageDebug.doFirst


你可能感兴趣的:(Android Studio打包APK后动态库so文件被改动)