Protecting Project Integrity

Our recent security report shows that supply chain attacks targeting the build process through the Gradle Wrapper exist in the wild. This blog post explains how to protect your project or you, as a developer, against similar attacks.

A build process, by design, executes code. The components of the build process all carry their own risks:

  1. The bootstrapping script to run the build tool could be compromised. (see How to ensure Gradle wrapper integrity?)
  2. The build tool itself could be compromised. (see How to ensure Gradle distribution integrity?)
  3. The build tool could download third-party dependencies that are themselves compromised. (see How to ensure third party dependencies’ integrity?)
  4. Malicious code could be hidden in the project code, tests or build configuration. (see How to ensure project integrity?)

Because of all those possible attack vectors, you should exercise caution when you are not fully confident in the source of the changes. In the case of the attack against MinecraftOnline analyzed in our report, Gradle wrapper updates were done by a new contributor.

Similarly, contributing to open source potentially exposes you to such attacks. It would be best to validate new projects you are looking into similarly.

The key point is that you should only run a build if you trust the project or change set.

The following recommendations can help establish trust in a local Gradle build.

How to ensure Gradle wrapper integrity?

Firstly, ensure the integrity of Gradle Wrapper on each change of the wrapper JAR, especially coming from external contributors. Gradle publishes the checksums of the gradle-wrapper.jar for each Gradle version.

Wrapper integrity for maintainers

  • Gradle wrapper JARs should always be validated when updated in a repository
    • For those using GitHub actions, Gradle publishes a dedicated action that will validate wrapper checksums
    • For any other setup, automating that verification can be done by expanding on our validation instructions
  • Prefer to update the wrapper yourself instead of merging a PR from an external contributor. Regenerate the gradlew, gradle-wrapper.properties, and gradle-wrapper.jar from a known good Gradle distribution. Invoking a local Gradle with gradle wrapper will not run the gradle-wrapper.jar of the project but it will configure the build.

Wrapper integrity for contributors

  • If you do not trust the project you are building, prefer using a known good, local Gradle distribution over a wrapper.

How to ensure Gradle distribution integrity?

Secondly, ensure the integrity of the Gradle distribution itself. Alongside the wrapper checksums, you can also find the distribution checksums.

Distribution integrity for maintainers

Distribution integrity for contributors

  • Here again, relying on a known good, local Gradle distribution can be safer.

How to ensure third party dependencies’ integrity?

Ensuring the integrity of third-party dependencies involves evaluating multiple factors, such as the familiarity and reliability of the dependencies or plugins being used, as well as the trustworthiness of the repositories they originate from. Considering all these factors together is essential to properly verify their integrity.

Dependencies integrity for maintainers

  • Gradle allows you to enable dependency verification. This feature ensures that third party dependencies, both build plugins and project dependencies, match the trusted signature or checksums that are configured.
  • Be wary of any changes to build scripts that use unusual repositories, plugins, or dependencies.

Dependencies integrity for contributors

  • Be wary of any build scripts that use unusual repositories, plugins, or dependencies. Dependency verification is not a guarantee of trustworthiness, it only ensures that what is used by the build matches expectations.

How to ensure project integrity?

This is potentially a major effort, and the level of scrutiny will depend on many factors. However, it’s important to understand that any time you run someone else’s code you are exposed to a potential security risk.

Project integrity for maintainers and contributors

  • Inspect the build scripts and any contributed code before running any tasks or importing a project into the IDE. Even running gradle help could do something malicious.
  • Consider using throw away environments when running untrusted code, both locally and in a continuous integration environment.

Conclusion

Supply chain attacks are a sad reality as we showed in our recent security report.

The Gradle team will continue to look for ways to improve the security of the Gradle Build Tool and its community. Please report any suspicious projects, wrappers, or distributions to us. However, in the end, security is the responsibility of every project and developer. You should assess your risks, and needs. And then act accordingly.

Let us know if you have any questions on our forums or Gradle Community Slack, or start a discussion below.