Skip to content

Qigsaw 1.4.0 更新详情

kissonchen edited this page Jun 18, 2020 · 2 revisions

1.4.0 重大更新说明

  1. 随着国内越来越多应用商店需要上传64位APK,Qigsaw在1.4.0版本支持Base APk和Split APKs基于ABI维度拆分ABI。Qigsaw会依据当前应用运行的CPU架构环境选择对应Split APKs下载。
  2. 支持Base APK中Activity使用Split APKs中Fragment或Resources。
  3. 不再强制要求启动编译命令中包含qigsawAssemble${variantName.capitalize()}

基于ABI维度拆分APK

Split APKs 拆分

1.4.0版本开始,如果您的Split APK包含ABI,如下图。

Qigsaw会将Split APK基于ABI维度拆分成多个APK,如下图。

以debug为例,中间产物在app/build/intermediates/qigsaw/split-outputs/apks/debug路径下

通过上图可以看到,名为native的Split APK被拆分成三个APK。

  1. native-master.apk,包含除lib目录下的所有文件。
  2. native-arm64-v8a.apk,仅包含lib/arm64-v8a下所有*.so*文件。
  3. native-x86.apk,仅包含lib/x86下所有*.so*文件

Qigsaw如此做的目的是为了与Android App Bundle行为保持一致,拆分出的Split APKs通过Android Multiple-APKs安装机制也能正常安装。

因为一个dynamic-feature可能由多个Split APKs组成,因此记录Split APKs信息的JSON文件数据结构也有相应调整。

{
  "qigsawId": "1.0.0_9e81a29",
  "appVersionName": "1.0.0",
  "splits": [
    {
      "splitName": "native",
      "builtIn": true,
      "onDemand": true,
      "version": "1.0@1",
      "minSdkVersion": 14,
      "dexNumber": 2,
      "workProcesses": [
        ""
      ],
      "apkData": [ //增加apkData记录所有Split APKs信息
        {
          "abi": "x86",//仅包含x86架构的.so文件
          "url": "assets://qigsaw/native-x86.zip",
          "md5": "ffd381956867211187d20d5719f6b1e7",
          "size": 8539
        },
        {
          "abi": "arm64-v8a",//仅包含arm64-v8a架构的.so文件
          "url": "assets://qigsaw/native-arm64-v8a.zip",
          "md5": "89f92ff123c2f048f34ff9b29125f46f",
          "size": 8545
        },
        {
          "abi": "master",//包含除了lib目录下的所有文件
          "url": "assets://qigsaw/native-master.zip",
          "md5": "46746bddb14e1fdd546115a57f114865",
          "size": 12824
        }
      ],
      "libData": [
        {
          "abi": "x86",
          "jniLibs": [
            {
              "name": "libhello-jni.so",
              "md5": "33e3ad5634e7034b946533e9d670439e",
              "size": 5536
            }
          ]
        },
        {
          "abi": "arm64-v8a",
          "jniLibs": [
            {
              "name": "libhello-jni.so",
              "md5": "50bf7cdb8edb8af9c36bfe07bf661cee",
              "size": 5824
            }
          ]
        }
      ]
    }
  ]
}

1.4.0不支持内置dynamic-feature的APKs拷贝至Base APK的lib目录下,内置dynamic-feature所有APKs全部拷贝至Base APK的assets/qigsaw目录,如下图。

上图中,Base APK没有lib文件夹,因此native所有abi维度的APKs都会拷贝Base APK。此外,Qigsaw会生成assets/base.app.cpu.abilist.properties文件记录Base APK支持的所有ABI,该值为空表示Base APK所支持的ABI由当前运行设备来决定。

Base APK 拆分

目前国内大部分应用商店支持32和64位APK单独上传,因此Qigsaw也提供拆分Base APK。如下配置,将multipleApkForABIs值设为true即可开启。为方便开发者对Base APK进行7z格式压缩,Qigsaw也提供use7z配置。

qigsawSplit {

    ......
    
    /**
     * Whether repack base apk with 7z format.
     * default value is {@code false}
     */
    use7z = false

    /**
     * Whether build multiple APKs for ABIs
     */
    multipleApkForABIs = true
}

当Base APK包含包含两个及以上维度的ABI时,Qigsaw才会对Base APK进行拆分,如下图。

未使用7z压缩。

使用7z压缩。

Base APK加载Split APKs中Fragment或Resources

开启如下配置。

qigsawSplit {

    ......

    /**
     * Split fragments which would be loaded by activities of base apk.(Not all fragments in split apk)
     */
    splitEntryFragments = ['com.iqiyi.qigsaw.sample.java.JavaSampleFragment']

    /**
     * Activities of base apk which would load split's fragments or resources.
     */
    baseContainerActivities = ["com.iqiyi.qigsaw.sample.MainActivity"]
}

当java Split APK中com.iqiyi.qigsaw.sample.java.JavaSampleFragment需要被Base APK中com.iqiyi.qigsaw.sample.MainActivity加载,需要您分别填写对应Class文件的全类名。

不再强制要求启动编译命令中包含qigsawAssemble${variantName.capitalize()}

为方便开发者自定义并拓展您应用编译命令,1.4.0版本开始不再强制要求启动编译命令中包含qigsawAssemble开头的命令。

public static final String QIGSAW_BUILD = "QIGSAW_BUILD"

public static final String QIGSAW = "qigsaw"

public static final String ASSEMBLE = "Assemble"

public static final String INSTALL = "Install"

public static final String QIGSAW_ASSEMBLE_TASK_PREFIX = QIGSAW + ASSEMBLE

public static final String QIGSAW_INSTALL_TASK_PREFIX = QIGSAW + INSTALL

static boolean isQigsawBuild(Project project) {
        List<String> startTaskNames = project.gradle.startParameter.taskNames
        for (String taskName : startTaskNames) {
            if (taskName.contains(QIGSAW_ASSEMBLE_TASK_PREFIX) || taskName.contains(QIGSAW_INSTALL_TASK_PREFIX)) {
                return true
            }
        }
        if (project.hasProperty(QIGSAW_BUILD) || System.getenv().containsKey(QIGSAW_BUILD)
                || System.properties.containsKey(QIGSAW_BUILD)) {
            return true
        }
        return false
    }

通过上述代码片段可知,判断是否需要Qigsaw参与编译条件有四个,满足其中一个即可。

  1. 启动命令中包含qigsawAssemble开头的命令
  2. app project的properties包含"QIGSAW_BUILD"的Key
  3. 系统环境变量是否包含"QIGSAW_BUILD"的Key,Jenkins编译时可注入。
  4. 系统properties是否包含"QIGSAW_BUILD"的Key,Jenkins编译时可注入。
Clone this wiki locally