Gradle在transformClassesWithDexForDebug上的构建缓慢


70

构建我的Android应用大约需要90秒(“快速”),每次更新我的代码最多需要3分钟。确实,这完全是在浪费时间,我认为必须找到解决方案。我尝试调查此问题,并找到了不同的博客帖子和带有建议的SO答案,其中大多数我都尝试过。

  • 我有org.gradle.deamon = true的gradle.properties文件
  • 我在具有Gradle Prefence的Android Studio上运行脱机工作(虽然有所改进,但仍然很慢)
  • 我在命令行上运行(虽然更快,但仍然很慢)
  • 在build.gradle,defaultConfig中,我将multiDexEnabled设置为false
  • 在build.gradle,dexOptions中,我将preDexLibraries设置为false
  • 在gradle-wrapper.properties中,我获取了最新的gradle版本(2.8)(速​​度的重大变化发生在2.4上)

该过程似乎耗时较长,约占总构建时间的85%::app:transformClassesWithDexForDebug

该过程实际上在做什么?我可以找到遇到崩溃的人,但是对我来说很好,除了需要花费很多时间。我是否需要它,因为此时我真的不需要Dex?

另外,我有13个依赖项和3个testCompile依赖项。我已经指向了特定的播放程序包,因此我不会编译不需要的东西。如果我理解正确,gradle还将构建每个项目构建的所有那些库。如果正确的话,有没有办法跳过呢?我可以自己将它们构建为打包库并包含它们,而无需每次都对其进行处理吗?这可能会使我失去对将来更改依赖项的灵活性,但是在这一点上,我感觉我每天在等待gradle方面很容易就失去了一个多小时。我不确定灵活性是否对我来说那么重要。

我期待获得任何有关如何改进构建过程的指导。先感谢您。


13
知道有人在与我现在完全一样的境地真是令人欣慰!在此期间,您有什么进展吗?谢谢!
sjkm

自从我发布并尝试了我遇到的每一个建议以来已经有一段时间了,并获得了不同程度的成功。直到@ markdb314提到的Android Studio 2.1发行时,没人真正将构建速度提高到可以接受的水平。尽管可能以前可用,但是只有从该版本开始,才可以进行dex步骤。这将我的构建时间平均缩短了20-30秒。
贾斯汀·哈门加

只是好奇,您是否正在使用新的数据绑定框架?
tir38 '16

不,我没有在存在这些问题的项目中使用数据绑定框架。
贾斯汀·哈曼加

Answers:


14

升级到Android Studio 2.1和Android Gradle插件v2.1.0已在很大程度上解决了我的问题。安装更新的IDE后,还应提示您更新Gradle插件。如果您的root build.gradle文件包含以下行,您就会知道您使用的版本正确:

classpath 'com.android.tools.build:gradle:2.1.0'

重要信息:除了升级,您还需要将分配给Gradle守护程序的内存量增加到2048mb,以便它可以执行此昂贵的处理过程。为此,将以下内容添加到您的根gradle.properties文件中:

org.gradle.jvmargs = -Xmx2048m

与上述问题类似,我的构建时间也很慢,但是升级后,构建速度大大提高了。有关更多信息,请参见此处的Android Gradle插件v2.1.0发行说明:

http://developer.android.com/tools/revisions/gradle-plugin.html


1
在我的情况下,org.gradle.jvmargs = -Xmx2048m实际上将速度提高了一个数量级。

1
圣饼干!从15分钟到1分钟!谢谢 !
Yasser Sinjab

33

编辑:在这一点上,我建议与1.5安装并排运行Android Studio2.x。您可以访问即时运行,它以及所有更新的工具都非常有用。如果您停留在1.5,请继续阅读...

我设法将Android Studio 1.5调试版本从2分钟加快到30秒。这可能不适用于您的命令行执行,但是可能更快。

使用此配置,您的第一个IDE构建将花费相同的时间,但是即使您修改类,增量构建也会更快。如果修改附件库,则会损失一些收益。

步骤1.(如果您足够幸运地将minSdkVersion的目标定为> = 21,请跳过此步骤。)

@vanomart给出的minSdkVersion调试样式> = 21的答案是正确的,但唯一必要的部分是在模块(app)build.gradle中添加以下内容,并确保在调试时在Build Variants选项卡中以dev为目标:

android {
    [...]
    productFlavors {
        dev {
            minSdkVersion 21 //The important bit.
        }
        prod {
            minSdkVersion 15 //Example. Set to your real requirement.
        }
    }

第2步。增量构建和预消除库。

在您的模块(应用程序)build.gradle中设置以下配置。对于IDE构建,这是更快的速度,而对于每个构建都从头开始的构建器服务器来说,速度不那么快。

android {
    [...]
    dexOptions {
        preDexLibraries true
        javaMaxHeapSize "2g" // Use gig increments depending on needs
        incremental true
    }

源代码,做(部分)与“提高Build Server性能”相反的内容:http : //tools.android.com/tech-docs/new-build-system/tips#TOC-Improving-Build-Server-performance

步骤3.确保在模块(应用程序)build.gradle中使用最新的buildToolsVersion

android {
    buildToolsVersion "23.0.2"
    [...]

“ ...将所有模块中的构建工具版本更新为最新版本(23.0.2)。它将使用新的更快版本的dex,这有助于即时运行和完整构建更快。”

来源:http//tools.android.com/tech-docs/instant-run

步骤4.使用最新的Gradle构建工具

在您的项目build.gradle中,将其设置为最新(当前为2.0.0-alpha6)

buildscript {
    dependencies {
        classpath 'com.android.tools.build:gradle:2.0.0-alpha6'

更新列表:http : //tools.android.com/tech-docs/new-build-system

步骤5.使用最新的Gradle包装器。修改gradle-wrapper.properties,更新此行以使用2.10:

distributionUrl=https\://downloads.gradle.org/distributions/gradle-2.10-all.zip
#Alternative url if the above does not work:
#distributionUrl=https://services.gradle.org/distributions/gradle-2.10-all.zip

在Android Studio首选项中,确保已选择“使用默认Gradle包装器”。我建议重新启动Android Studio以确保Gradle守护进程重新启动。

“在许多情况下,执行增量构建时,Gradle 2.9比Gradle 2.8快得多。”

资料来源:docs.gradle.org/current/release-notes


非常感谢你!我的gradle版本现在快了50%(从2分钟到1分钟)!
卡·齐格勒

3
我已按照每个步骤进行操作,并正确设置了所有内容。还是很慢...多么糟糕的软件。Google令我非常失望。同时有任何进展吗?但是,构建时间从6分钟减少到56秒!因此,非常感谢您的大力帮助!
sjkm

谢谢戴森的回来。我的gradle速度显着提高,在某些情况下从2.5分钟缩短到了几秒钟。
Jose Ramon Garcia

在我的设置中,我打开了“ Legacy Multidex”,打开了“ reshResources”,打开了“ minifyEnabled”,并运行了proguard。我已经尝试了与该主题相关的所有建议的许多不同组合。最后,对我唯一有用的是在Android Studio 2.0中关闭“即时运行”。我的构建从6分30秒增加到1分41秒。
Eric Sc​​hlenz '16

哇...关于dexOptions的技巧使我的构建从4分钟降低到40ish秒。对于这个微小的应用程序来说仍然很糟糕,但是相比之下却令人惊讶
joshmcode

12

对我有用的唯一解决方案是禁用即时运行。

Android Studio->首选项->构建,执行,部署->即时运行->取消选中“启用即时运行[...]”

构建时间从2分钟以上延长到40秒。


谢谢!>>即时运行还删除了文件夹中内置的所有输出apk。我想知道为什么会发生
reidisaki

这对我也有用。建立时间从〜80秒增加到〜12。猜猜他们还有一些工作要做。
Cognitio

45s到
15s-

6

我遇到了同样的问题,我花了大约10个小时才终于解决它,所以我知道您的感觉。

我在Google上搜索了很多东西,我做了与您相同的配置工作,即使它有所帮助,编译和运行实际的应用程序仍然很麻烦(有时,我更改一行代码需要2-3分钟,但是当我做更多工作时,通常需要8分钟,并且在此期间我的计算机完全冻结了)。

但是有足够的讨论,让我们解决这个问题。“ app:transformClassesWithDexForDebug”的作用是解决了Dalvik(5.0之前的版本,API 21)操作系统版本的某些依赖关系,并且重要的是-这需要大量时间。您不需要开发它,因为您可以在> = 21上测试您的应用程序,因此可以为开发和发布创建单独的产品风格。这是我利用它的gradle构建:

apply plugin: 'com.android.application'

final VERSION_MAJOR = 0
final VERSION_MINOR = 0
final VERSION_PATCH = 0
final VERSION_BUILD = 1

android {
    compileSdkVersion 23
    buildToolsVersion "23.0.1"

    defaultConfig {
        applicationId "com.app"
        minSdkVersion 15
        targetSdkVersion 23
        multiDexEnabled true
        versionName "${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_PATCH}.${VERSION_BUILD}"
        versionCode VERSION_MAJOR * 10000000 + VERSION_MINOR * 100000 + VERSION_PATCH * 1000 + VERSION_BUILD
    }

    dexOptions {
        incremental = true;
        preDexLibraries = false
        javaMaxHeapSize "2g"
    }


    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }

    productFlavors {
        dev {
            minSdkVersion 21
            applicationId = "com.app.test"
        }
        prod {
            minSdkVersion 15
            applicationId = "com.app" // you don't need it, but can be useful

        }
    }

    compileOptions {
        sourceCompatibility JavaVersion.VERSION_1_7
        targetCompatibility JavaVersion.VERSION_1_7
    }
    packagingOptions {
        exclude 'META-INF/DEPENDENCIES.txt'
        exclude 'META-INF/LICENSE.txt'
        exclude 'META-INF/NOTICE.txt'
        exclude 'META-INF/NOTICE'
        exclude 'META-INF/LICENSE'
        exclude 'META-INF/DEPENDENCIES'
        exclude 'META-INF/notice.txt'
        exclude 'META-INF/license.txt'
        exclude 'META-INF/dependencies.txt'
        exclude 'META-INF/LGPL2.1'
        exclude 'META-INF/ASL2.0'
    }
    lintOptions {
        checkReleaseBuilds false
        abortOnError true
    }

}

afterEvaluate {
    tasks.matching {
        it.name.startsWith('dex')
    }.each { dx ->
        if (dx.additionalParameters == null) {
            dx.additionalParameters = ['--multi-dex']
        } else {
            dx.additionalParameters += '--multi-dex'
        }
    }
}

dependencies {
    compile fileTree(include: ['*.jar'], dir: 'libs')
   ... 
}

下一步是确保您实际上正在使用此构建变体构建应用程序 。单击查看->工具窗口->构建工具,并确保将构建变量设置为'devDebug'

对于某些人来说,这可能就足够了。我在SO中以及在Reddit上发现了很多线程,这些线程都以这种产品味道作为结尾,但这实际上并没有帮助我。帮助我的是手动升级gradle。既然您已经尝试过,那么我认为您的方向正确,但是我建议您使用较新的gradle版本2.9,该版本比2.8的性能提高40%


1
感谢您对vanomart的回应。这看起来确实很有希望,但是我还没有开始工作。它构建了新的devDebug风格,但仍在运行相同的任务。我需要在构建设置中看到的afterEvaluate或compileOptions部分吗?
贾斯汀·哈曼加2015年

您不需要编译选项和afterEvaluate。我发现当您仅下载新的gradle时,它不起作用,您必须在系统上正确安装它,以便正确地初始化所有gradle变量。另外,如果您查看项目中的.gradle目录,您将在其中看到一些缓存的内容。删除所有不是2.9的东西。TBH,我的构建运行得更快,有时只需要几秒钟,但有时又需要1-2分钟。
vanomart 2015年

0

这似乎是Android Studio 2.0预览版中引入的新即时运行机制的一部分,该机制负责检测应用程序中的每个方法,以创建执行分支以用于将来的代码补丁。恐怕这就是为什么它非常慢。

奇怪的是,即使禁用了“即时运行”,该任务仍在进行。我必须将“ c​​om.android.tools.build:gradle”降级到1.3.0以避免该任务。


即使我降级,我仍然看到该任务正在执行。这不是我要寻找的解决方案。谢谢你的建议。
贾斯汀·哈门加2015年

@JustinHammenga您将其降级到1.3.0吗?它在1.5.0中也存在,但在1.3.0中不存在。
绿洲峰

0

您的应用程序是否有数据库?数据库有大尺寸吗?

如是:

  • 从资产文件夹(或保存位置)中删除数据库并进行构建
  • 测量构建时间的差异
  • 我的情况:从45秒降低到15秒是一个巨大的差异

如果不:

  • 在增量构建期间监视Gradle控制台,并查看耗时最多的操作
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.