3

提速Android Gradle 构建

 2 years ago
source link: http://www.androidchina.net/7944.html
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

提速法则一览

手段 全量构建 Java增量构建 资源增量构建 升级 android gradle tools 到3.0 -15s(-25%) -10(-38%) -2.5(-16%) 避免使用遗留的Multidex -5.5s(-12%) -8(53%) same debug 环境关闭multi-APK -4.8s(-12%) -0.5s(-6%) -3s(-26%) 设置包含最少的资源 -6s(-17%) -1.5s(-24%) -2s(21%) 关闭 png crunching -9s(-33%) same same 使用Instance Run +7s(+37%) -3s(-54%) -3s(-42%) 避免不注意的改变 - - - 不要使用动态版本号 - - - 注意分配 gradle 内存 - - - 开启 Gradle Caching -7s(-25%) same +0.5s(+12%) 使用implementation 或者 api 代替 compile - - -

以上优化方案基于android gradle tools 3.0-alpha

关于Santa Tracker Project

  • 9 个模块,包括Wear
  • 500 多个Java文件
  • 1700 个XML 文件,3500张PNG
  • Multi-dex
  • 没有 annotation processors
  • APK大小接近60MB

这个项目可以在Google Github 帐号中找到

优化方案详解

避免使用遗留的MultiDex

  • 遗留的multidex是指使用了MultiDex 并且minSDkVersion < 21
  • 遗留的multidex会导致构建的时候签名速度变慢
  • 使用Android Studio 2.3+ IDE构建的时候,会自动避免这样的状况

也就是说,使用点击AS运行的按钮,这个不需要配置。

关闭 multi-APK

multi-apk 是为了根据配置生成不同的APK,以达到减少APK体积大小的问题。但是这个配置没有必要在开发的时候开启。

  1. 设置监测到flag 就关闭代码
    android{
        if(project.hasProperty('devBuild')){
            splits.abi.enable = false
            splits.density.enable = false
        }
    }
    
  2. 在AS设定中加入flag

  3. 或者使用gradlew 构建
    ./gradlew app:assembleDebug -PdevBuild
    

包含最少的资源

如果你的app是包含多资源的,比如多语言的和多分辨率。但是在开发的时候,大部分时间都是只用一种资源,所以其他资源就会无用,导致拖慢构建速度。

以下是固定使用某种资源的办法

productFlavors{
    development{
        minSdkVersion 21
        resConfigs ("en","xxhdpi")
        ...
    }
} 

关闭 png 压缩

png 在 android build tools 里面是默认开启的。这个功能可以使你构建更小的apk,但是在debug构建中,我们并不需要这个功能,所以,应该在debug构建的时候禁止。

禁止方法就是使用关闭multi-APK 一样的标记

 android{
        if(project.hasProperty('devBuild')){
            splits.abi.enable = false
            splits.density.enable = false
            aaptOptions.cruncherEnabled = false
        }
    }

添加标记的方法同关闭 multi-APK 的一样

当然你可以把图片转换到webp , 如果你的PNG已经压缩过的也可以完全关闭这个功能

使用 Instant Run

Instant Run 已经要求最低API 为21 ,各方面的兼容性都好了很多,推荐使用。
当然完整编译是需要更长的时间的

避免不注意的改变

栗子

def buildDateTime = new Date().format('yyMMddHHmm').toInteger()
android{
    defaultConfig{
        versionCode buildDateTime
        ...
    }
}

这个操作看起来很合理,每次构建的时候都可以获得唯一的versionCode,这样每次测试就能根据versionCode 来告诉你问题所在。但是,对于debug构建来说,这不是一个好的设置。这个设置会导致 AndroidManifest 改变 , AndroidManifest 改变会导致增量编译的时间增加。

Manifest 改变对于编译的影响
Manifest 改变对于编译的影响
Crashlytics

Crashlytics 是个很好的开发工具,如果你使用得正确的话。Crashlytics 每次构建的时候都会生成唯一的ID,关掉这个ID可以加快构建速度。

apply plugin: 'io.fabric'
...

android{
    buildTypes{
        debug{
            ext.alwaysUpdateBuildId = false
        }
    }
}
不要使用动态版本号
android{
    dependencies{
        compile 'com.android.suport:appcompat-v7:+'        
    }
}

以上的依赖使用了动态版本号来设置使用最新的版本号。但是这样会导致gradle每24小时就要联网检查最新的版本,增加了构建的时间。同时,这样使用会导致你的构建不稳定,可能今天还能构建成功,但是明天就失败了

注意分配 Gradle 内存

在新建一个项目的时候,默认在 gradle.properties 中设置了 gradle 使用的内存为1.5G,这可能是个好的值,也可能不是,取决你项目的大小,越大的项目需要越大的内存

开启 Gradle 缓存

这是 Gradle 3.5的新特性 ,和 2.3 build chache 是不一样的,可以接受任何系之前的构建,任何的地点的构建。
开启代码如下:

org.gradle.caching = true

使用implementation 或者 api 代替 compile

假设你有如图这几个项目

1240

app 依赖与lib1,lib1依赖于 lib2,但是,app只使用了lib1提供的公共api。如果使用compile 关键字,当你更改lib2的时候,app,lib1 都要重新编译。但是,如果app 是使用implementtation依赖lib1的时候,lib2 就算发生更改,app也不需要重新编译。

所以我们在编写库的时候,如果库依赖的库不想曝光给使用者,建议使用implementation,如果你想把自己使用的库曝光给使用者,请使用 api 关键字

模块化好处

  • Gradle 可以平行的构建模块
  • 缺乏增量任务的一个变通方法
  • 多模块代表着多任务,多任务代表着可以平行执行
  • Some parallelism within a task is provided but limited(自己看吧,我也看不懂)

如何调试缓慢构建

Gradle 提供了工具去帮助知道哪里花了大部分时间

  • –dry-run
  • –info
  • –profile
  • Gradle profile
–dry-run

可以让你知道花费了多少时间在 configuration 上,10s以内是最好的,如果配置的时间过长,你的方法gradle 已经出了问题了。

使用方法:gradle yourtask --dry-run

–info

这个参数可以告诉你,当前任务执行的详细信息,包括在执行什么,还有为什么执行。

使用方法:gradle yourtask --info

–profile

这个参数会在 you-project/build/reports/profile、 中生成一个html文件,详细告诉你哪个任务花了多少时间,是个非常有用的debug工具

使用方法:gradle build --profile

Gradle Profiler

Gradle Profiler 是 Gradle 官方用于自动收集Gradle构建的分析和基准测试信息的工具。具体的使用办法在 github 上有,以后有必要再出个专题吧。这个工具是当上面的办法都无效的时候才推荐使用的。


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK