Chapter 9. Integration and migration

 

This chapter covers

  • Importing existing Ant projects
  • Using Ant tasks from Gradle
  • Converting Maven pom.xml into Gradle projects
  • Migration strategies from Ant and Maven to Gradle
  • Comparing build outcomes and upgrade testing

Long-running development projects are usually heavily invested in established build tool infrastructure and logic. As one of the first build tools, Gradle acknowledges that moving to a new system requires strategic planning, knowledge transfer, and acquisition, while at the same time ensuring an unobstructed build and delivery process. Gradle provides powerful tooling to integrate existing build logic and alleviate a migration endeavor.

If you’re a Java developer, you likely have at least some experience with another build tool. Many of us have worked with Ant and Maven, either by choice or because the project we’re working on has been using it for years. If you decide to move to Gradle as your primary build tool, you don’t have to throw your existing knowledge overboard or rewrite all the existing build logic. In this chapter, we’ll look at how Gradle integrates with Ant and Maven. We’ll also explore migration strategies to use if you decide to go with Gradle long-term.

9.1. Ant and Gradle

Gradle understands Ant syntax on two levels. On the one hand, it can import an existing Ant script and directly use Ant constructs from a Gradle build script as if they’re native Gradle language elements. This type of integration between Gradle and Ant doesn’t require any additional change to your Ant build. On the other hand, familiar Ant tasks (for example, Copy, FTP, and so on) can be used within your Gradle build script without importing any Ant script or additional dependency. Long-term Ant users will find themselves right at home and can reuse familiar Ant functionality with a convenient and easy-to-learn Groovy DSL notation. Chapter 2 demonstrated how to use the Echo task within a Gradle build.

An instance of the class org.gradle.api.AntBuilder is implicitly available to all Gradle projects, as well as to every class that extends DefaultTask through the property ant. In regular class files that don’t have access to a project or task, you can create a new instance. The following code snippet demonstrates how to do that in a Groovy class:

9.2. Maven and Gradle

Gradle’s integration with Ant is superb. It allows for importing existing Ant build scripts that translate targets in Gradle tasks, enable executing them transparently from Gradle, and provide the ability to enhance targets with additional Gradle functionality (for example, incremental build support). With these features in place, you can approach migrating from Ant to Gradle through various strategies.

Unfortunately, the same cannot be said about the current Maven integration support. At the time of writing, Gradle doesn’t provide any deep imports of existing Maven builds. This means that you can’t just point your Gradle build to an existing POM file to derive metadata at runtime and to execute Maven goals. But there are some counter strategies to deal with this situation, and we’ll discuss them in this section. Before we dive into migrating from Maven to Gradle, let’s compare commonalities and differences between both systems. Then, we’ll map some of Maven’s core concepts to Gradle functionality.

9.3. Comparing builds

The build comparison plugin was introduced with Gradle 1.2. It has the high goal of comparing the outcomes of two builds. When I speak of an outcome, I mean the binary artifact produced by a build—for example, a JAR, WAR, or EAR file. The plugin aims to support the following comparisons:

Your sample project creates three binary artifacts: two JAR files produced by the projects model and repository, and one WAR file produced by the web project. The WAR file includes the two other JAR files. A comparison between two builds would have to take into account these files. Let’s say you want to upgrade your project from Gradle 1.5 to 1.6. The following listing shows the necessary setup required to compare the builds.

9.4. Summary

In this chapter, we discussed how the traditional Java-based build tools Ant and Maven fit into the picture of integration and migration. As an Ant user, you have the most options and the most powerful tooling. Gradle allows for deep imports of an Ant build script by turning Ant targets into Gradle tasks. Even if you don’t import existing Ant builds, you can benefit from reusing standard and third-party Ant tasks. You learned that migrating from Ant to Gradle can be done in baby steps: first import the existing build, then introduce dependency management, and then translate targets into tasks using Gradle’s API. Finally, make good use of Gradle plugins.

Maven and Gradle share similar concepts and conventions. If you’re coming from Maven, the basic project layout and dependency management usage patterns should look strikingly familiar. We discussed some Maven features that are missing from Gradle, such as the provided scope and the concept of profiles. You saw that Gradle (and ultimately its underlying language Groovy) is flexible enough to find solutions to bridge the gap. Unfortunately, Gradle doesn’t support importing Maven goals from a POM at runtime, which makes migration less smooth than for Ant users. With Gradle’s maven2Gradle conversion task, you can get a head start on a successful migration by generating a build.gradle file from an effective POM.