AGP 升级7.2.0之后 图片压缩失败? 踩坑实录

2,063 阅读4分钟

发生了啥?

在升级agp7.2.2 之后(之前是7.0.4),我们发现之前 在编译期 执行 png 自动压缩成webp的 task执行失败了,导致包体积减少的计划失败, 遂逐个排查之后 发现是agp从7.2.0 版本开始 这个png 压缩成 webp的task就失败了,那么到底是为啥失败,又要怎么改呢?

主流图片转换压缩的原理

目前主流在编译期间 图片压缩的方案 主要是在 编译期间 png 转换 成webp格式,主要利用的是在编译期间的flat 文件,这个flat 文件包含了 原始的 资源文件位置,形如:

image.png

我们拿到这个资源文件的原始位置之后 就可以对这个图片进行压缩, 那为什么升级到7.2.2 之后就不行了呢?

我们用7.2.2 编译项目以后 再次观察下 这个flat文件

image.png

你会发现 这个flat文件中的 path信息 发生了变化,似乎是从 绝对路径 变成了相对路径?

这样自然是无法压缩图片了,因为你路径都找不到了

问题原因找到了 就得想想办法 怎么解决了

怎么解决 该问题?

现在的问题就是怎么从flat 文件中的相对路径信息 还原成绝对路径的信息

经过一番搜索 我发现 在编译的产物中 新增了这么一组文件:

image.png

这个文件包含了 所有的 flat 文件中 相对路径和 绝对路径的信息, 有了这个文件 我们就可以做进一步的操作了

我们可以将 这个文件中的信息提取出来, 在解析flat文件的时候 判断一下,如果agp的版本>=7.0 则将相对路径

替换成绝对路径即可

这个文件的路径 在agp7.2.0 中 就可以 找到 信息

image.png

有了这个关键的文件路径就可以了吗?其实还没完,因为你要保证你的图片压缩任务 在这个 文件生成之后才行 否则 如果在这之前 你读取这个文件是读不到的

利用--dry-run 看一下 task的执行顺序:

image.png

猜一下就能猜到 mapDefaultOldSignDebugSourceSetPaths 这个任务 应该就是生成那个 路径信息文件的task了

我们只要设定我们压缩图片的任务 在这个 任务之后执行,即可保证 我们的图片压缩任务在执行的时候 一定能到对应键值对的信息

剩下的就是完善你的代码 就可以了

最后看下具体的信息配置吧,

agp 7.2.0 以后 flat 文件解析出来的 路径信息如下:

com.xxx.yyy.app-jetified-zzz_coment-6.2.0.0-SNAPSHOT-58:/drawable-xxhdpi-v4/space_component_address_select_icon.png

可以明显看出来 : 作为分隔符

而配置文件信息中

com.xxx.yyy.app-jetified-zzz_coment-6.2.0.0-SNAPSHOT-58 /Users/njvivo/.gradle/caches/transforms-3/85f6d8be7a5f41646330c938b4265d02/transformed/jetified-vivospace_component-6.2.0.0-SNAPSHOT/res

注意这里是配置文件中的 分隔符是 空格符

瑕疵

经过上面的分析,目前的图片压缩任务 基本可以正常运行,但还是有一些瑕疵,譬如我们在 读取那个 路径信息 文件的时候 发现 这个信息有时候会不全, 目前我发现 部分app module下的图片 信息 在路径信息文件中 会找到不到,目前还不清楚这个 问题的产生原因, 举个例子,

在我的项目中,有些flat文件解析出来,他的相对路径信息 是

com.xxx.yyy.app-main-111 开头的

然而这个 开头的信息 在路径文件中 并找不到,能找到的 只有 com.xxx.yyy.app-main-110

这个问题 目前我是用的硬编码的方式去解决的, 也就是说如果找不到 对应的相对路径 我们就直接用默认的app module下的路径 去覆盖, 这样虽然能解决问题 但看起来并不是很优雅,

有知道具体原因的大佬可以指点下

后来想了想 也许是最后这个110 111 并没有 什么特殊的信息 在做key匹配的时候 去除掉这个 尾号 也一样可以解决问题 这种方法比硬编码 优雅多了,经过测试 也没发现啥bug,目前暂时先用这个方案吧