What's new in Gradle 5.0

Gradle 5.0 is the fastest, safest, and most capable Gradle release ever.

Improved incremental compilation and incremental annotation processing build upon a solid performance foundation that already featured build caching and up-to-date checking.

Dependency constraints, dependency alignment, and version locking provide a dependency management model that is scalable and flexible.

Build scans have improved dramatically with new performance, dependency management, logging, and deprecated API use inspections.

A statically-typed Kotlin DSL brings a breath of fresh air to our IDE users by providing code completion, refactoring, and other IDE assistance when authoring build logic.

We’ve broken down the major improvements in recent releases into the following categories:

Finally, you can read how to upgrade to Gradle 5.0 further on.

Faster builds

Slow builds waste a lot of money. Building only what you need by using the new build cache and incremental processing features in Gradle 5.0 will make developers and business executives happy.

Your builds will already be a bit faster immediately after upgrading to Gradle 5.0, and you can improve their performance further by using and configuring the other features described in this section.

Incremental compile 1000-module Java project
Configuring Java project w/1000 modules

Build caching

Avoiding work by reusing the results of previous executions makes Gradle fast. Gradle 4.0 introduced the build cache, whose purpose is to reuse outputs from any previous invocation of Gradle.

Today, the plugins for Android, Kotlin, C++, Scala, and many other plugins have made tasks cacheable and thus reusable across different machines. Effective use of the build cache has been found to reduce build times by up to 90%.

Furthermore, the build cache in Gradle 5.0 is also enabled in more scenarios, such as when a task declares a Collection of @OutputDirectories or @OutputFiles.

Incremental Java compilation

In Gradle 5.0, the incremental compiler is highly optimized and now the default.

This is fantastic news as CompileJava tasks won’t need to recompile all the source files except the first time with a clean build.

Incremental annotation processing

The incremental compiler in Gradle 5.0 supports incremental annotation processing, significantly increasing the effectiveness of incremental compilation when annotation processors are present. This is an important innovation because of the increasing number of projects that rely on annotation processors.

To take advantage of incremental annotation processing, make sure you upgrade to versions of annotation processors that have opted into this feature. You can find out if a given annotation process is incremental through --info logging or in this table of popular annotation processors.

Use the new annotationProcessor configuration to easily manage your annotation processors and put them on the annotation processor path.

Build scans

Build scans have improved dramatically with new inspections for performance, dependency management, logging and the use of deprecated APIs. This is a free service offered to Gradle users — just add --scan when executing Gradle on the command line or apply and configure the build scan plugin.

Fine-grained transitive dependency management

Gradle 5.0 provides several new features for customizing how dependencies are selected and features improved POM and BOM support:

  • Dependency constraints allow you to define versions or version ranges to restrict direct and transitive dependency versions (not supported by Maven).
  • Platform definitions, aka Maven BOM dependencies are natively supported, allowing importing things like the Spring Boot platform definition without using an external plugin.
  • Dependency alignment allows different modules in a logical group (Jackson modules, for example) to be aligned to the same version.
  • Dynamic dependency versions can now be locked to allow better build reproducibility.

Dependency constraints

Dependency constraints provide robust control of transitive dependencies. Declared constraints are listed in the improved dependency insight report and build scans.

dependencies {
    implementation 'org.apache.httpcomponents:httpclient'
    constraints {
        implementation('org.apache.httpcomponents:httpclient:4.5.3') {
            because 'previous versions have a bug impacting this application'
        }
        implementation('commons-codec:commons-codec:1.11') {
            because 'version 1.9 pulled from httpclient has bugs affecting this application'
        }
    }
}
dependencies {
    implementation("org.apache.httpcomponents:httpclient")
    constraints {
        add("implementation", "org.apache.httpcomponents:httpclient:4.5.3") {
            because("previous versions have a bug impacting this application")
        }
        add("implementation", "commons-codec:commons-codec:1.11") {
            because("version 1.9 pulled from httpclient has bugs affecting this application")
        }
    }
}

BOM support

Gradle 5.0 can import bill of materials (BOM) files.

dependencies {
    // import a BOM
    implementation platform('org.springframework.boot:spring-boot-dependencies:1.5.8.RELEASE')

    // define dependencies without versions
    implementation 'com.google.code.gson:gson'
    implementation 'dom4j:dom4j'
}
dependencies {
    // import a BOM
    implementation(platform("org.springframework.boot:spring-boot-dependencies:1.5.8.RELEASE"))

    // define dependencies without versions
    implementation("com.google.code.gson:gson")
    implementation("dom4j:dom4j")
}

In addition, Gradle 5.0 provides a more seamless experience when consuming dependencies produced by a Maven build.

Dependency alignment

Dependency version alignment allows different modules belonging to the same logical group (a platform) to have identical versions in a dependency graph.

This solves the problem of ensuring that all your Spring or Hibernate dependencies have the same version (where applicable). In fact, there are many libraries that are published as a set, with each library in the set having the same version. There are other use cases for this feature, so please follow the link above to learn more from the docs.

Dependency version locking

You can lock dynamic or ranged dependencies to specific versions using Gradle 5.0 to make dependency resolution more deterministic and reproducible. This prevents changes in transitive dependencies from breaking your builds unexpectedly.

Writing Gradle build logic

You can now write your Gradle build scripts in Kotlin. Furthermore, gradle init has been expanded with project types and interactivity.

Kotlin DSL provides IDE assistance

Kotlin DSL 1.0 is production-ready as of Gradle 5.0. Static-typing in Kotlin allows tools to provide better IDE assistance, including debugging and refactoring of build scripts, auto-completion and everything else you would expect.

If you are interested in authoring your builds in Kotlin, start with the Gradle Kotlin DSL Primer.

Expanded and interactive gradle init

Users wanting to create new Gradle builds have additional project types to choose from: kotlin-library and kotlin-application. Additionally, you can choose to generate Groovy or Kotlin DSL build scripts, and customize the project name and package. Finally, a new interactive UI makes the experience especially pleasant.

More navigable and use-case oriented documentation

The Gradle documentation and getting started guides are more informative, discoverable, and accessible with:

More memory efficient Gradle execution

Features like --fail-fast for tests and command-line arguments for JVM apps allow for better dev workflows, while lower memory requirements and cache cleanup reduce Gradle’s overhead on your system.

Lower memory requirements

Not only will your builds be faster just by upgrading, but they’ll also use significantly less memory. Many caching mechanisms have been optimized in Gradle 5.0, and as a result the default maximum memory for Gradle processes has been greatly reduced.

Process Type Gradle 4.x default heap Gradle 5.0 default heap
Command-line client 1 GB 64 MB
Gradle Daemon 1 GB 512 MB
Worker processes 1/4 of physical memory 512 MB

Periodic Gradle cache cleanup

The days of manually cleaning up gigabytes of old Gradle caches are over. Gradle now cleans up stale caches periodically. Gradle also tracks stale task outputs more precisely, and cleans them up in cases where not doing so could lead to incorrect results.

New Gradle invocation options

Testing

Gradle 5.0 includes support for JUnit 5: JUnit Platform, JUnit Jupiter, and JUnit Vintage. This support allows you to enable test grouping and filtering, and to include custom test engines.

test {
    useJUnitPlatform {
        excludeTags 'slow'
        includeEngines 'junit-vintage'
        failFast = true
    }
}
tasks.test {
    useJUnitPlatform {
        excludeTags("slow")
        includeEngines("junit-vintage")
        failFast = true
    }
}

You can use the --fail-fast flag to enable a quicker red-green cycle, which is improved further by Gradle 5.0 executing failed tests first by default.

Logging

In Gradle 5.0, log messages are now grouped by the task that generated them for non-interactive environments like continuous integration execution.

In addition to showing which tests are executing, Gradle’s rich command-line console shows a colored build status that tells you at a glance whether any have failed. You can also ask Gradle to log tasks as they execute using the “verbose” console mode.

Finally, Gradle warning logs can be summarized, silenced, or expanded by configuring the warning-mode. This will be very helpful for upgrading your build to Gradle 5.0.

Build Scan Deprecations View

Composite Builds

Composite builds allow you to include other independent projects so that you can, for instance, develop an application and a library that it depends on simultaneously.

You can now inspect composite builds using build scans. Composite builds are also compatible with --continuous.

They build in parallel by default, and can now be nested.

Command-line arguments for JVM applications

Running Java applications with custom arguments gets a lot easier with Gradle 5.0 because you can simply specify them using --args on the command line or through your IDE.

New Gradle task and plugin APIs

Gradle 5.0 features many new APIs that enable faster and more versatile build logic.

Performance APIs

The new Worker API allows for safe parallel and asynchronous execution. Follow our guide to using the Worker API to enable faster builds for your custom tasks.

Without Worker API
With Worker API

Improved task I/O

Properly declaring inputs and outputs is crucial for correct incremental build and build cache behavior. Gradle 5.0 enforces tighter constraints and introduces new APIs for input/output declarations that help you avoid issues of correctness.

Configuration avoidance

Some projects create lots and lots of tasks. It doesn’t make sense to configure all of them when only some will be executed. This is where Gradle 5.0’s new Configuration Avoidance APIs help. Large projects can save up to 10% of configuration time by adopting these in their custom tasks.

Publishing APIs

Gradle 5.0 introduces new APIs to improve publishing to Maven and Ivy repositories:

Task timeouts

You can now specify a timeout duration for a task, after which it will be interrupted.

Custom CLI args

Gradle 5.0 gives you new ways to allow users to configure your custom tasks.

First and foremost, you can create custom command-line options using @Option. These can be discovered by users by executing gradle help --task your-task:

public class UrlVerify extends DefaultTask {
    private String url;

    @Option(option = "url", description = "Configures the URL to be verified.")
    public void setUrl(String url) {
        this.url = url;
    }

    @Input
    public String getUrl() {
        return url;
    }

    @TaskAction
    public void verify() {
        getLogger().quiet("Verifying URL '{}'", url);

        // verify URL by making a HTTP call
    }
}

Custom Nested DSLs

Providing a custom, nested DSL for your tasks used to require use of internal APIs. Gradle 5.0 provides first-class APIs for nested DSL elements, giving you more flexibility in considering how your users configure tasks.

Gradle 5.0 provides additional API conveniences around calculated (or lazy) task inputs and outputs. This enables custom task authors to wire together Gradle models without worrying when a given property value will be known or to avoid resource intensive work during task configuration.

How to upgrade

We’ve provided a document to help you upgrade from Gradle 4.x to Gradle 5.0. Before upgrading, we recommend you:

  • Upgrade to Gradle 4.10.2 using the Gradle wrapper. gradle wrapper --gradle-version=4.10.2
  • Run gradle help --scan to list all use of deprecated Gradle APIs with their locations, including plugins.
  • Update your Gradle plugins, especially those listed in the deprecations report from the build scan.
  • Upgrade to JDK 8 or higher, required to run Gradle 5.0.
  • See the troubleshooting guide or reach out on the community forums if you get stuck.

You can share feedback with the Gradle team via @gradle on Twitter. Go forth and Build Happiness!