Why are compile dependencies of java plugin transitive?


I was wondering, if there is a reason for the java compile dependencies to be transitive by default. Transitivity makes it easy to forget declaring direct compile dependencies of a project. Your code compiles successfully because some declared dependency (D1) brought in (transitively) another dependency (D2) your module directly depends on, but you have not declared D2 explicitly. Now imagine D1 stops depending on D2. Your build gets broken for no apparent reason. This makes the build brittle.

Maybe I’m missing something, but I think you shouldn’t need transitive compile dependencies (maybe except for annotations), so why make it default? I know I can change the behavior easily setting transitive to false, but I’d like to get the full picture (with possible consequences) before making that decision.

Thans, Rado

Hi Rado,

In the early days of Gradle (and in Maven 1.x), compile dependencies were non transitive by default, but over time a pragmatic decision was made to favour convenience over correctness. Maven 2 made compile dependencies transitive, and given that the majority of Java based projects in the wild using dependency management were based on Maven 2, it was considered more useful to be transitive by default.

You are right in that being non transitive is more correct though, and many Gradle users choose to opt in to this more correct mode.

Maybe this should go at least as a hint (“better be explicit…”) into the User Guide?