As far as I can tell, you need to manually specify what's going to be in the classpath when using Gradle's annotationProcessor dependency handler. I'm looking for a way to possibly automate that.
It feels like I'm missing something. Let's say I have an annotation processor called my.processor
, with javapoet as a dependency:
dependencies {
implementation 'com.squareup:javapoet:1.13.0'
}
However, when it's time to apply my processor to a given class, I need to manually specify that JavaPoet has to be present in the classpath:
dependencies {
// (other dependencies)
annotationProcessor 'my:processor:1.0.0'
annotationProcessor 'com.squareup:javapoet:1.13.0'
}
If I don't, it's going to throw an exception (TypeDefNotFoundException
if I recall correctly) lamenting that it can't find one of the javapoet classes - obviously, since it's not in the classpath.
Is it possible to just write:
dependencies {
// (other dependencies)
annotationProcessor 'my:processor:1.0.0'
}
and have the presence of javapoet (or any other dependency of my.processor
) be implied?
This is tricky. The short answer is NO, but here is my logic.
Marking your my-processor
library as an annotationProcessor
should pull over your transient dependencies which means javapoet
will be on the classpath through the implementation
dependency, but it would not be marked as an annotationProcessor
in your project. Just because javapoet
COULD be used an an annotationProcessor
doesn't mean it SHOULD be. Hence you must specify both annotation processors because your 3rd party project uses both. Gradle can't read your mind.
The only way I'd know if it would have any chance of working is if you specified javapoet
as an annotationProcessor
in your my-processor
project and by specifying my-processor
as an annotationProcess that had some transient dependency relationship and gradle would 'know' to pull over javapoet
too as an annotationProcessor
. But I don't know if that exists or not, and as I describe it; it sounds like a big reach. Here's why:
Consider this alternative that my-processor
had some annotations in its code base from javapoet
that it used to function internally. But it used javapoet
as an annotationProcessor
to create some code for its library to work, but wasn't piggy backing off a 3rd party project also using javapoet
. In that case the fact that javapoet
was marked as an annotationProcessor
wouldn't also be applied to other projects that were dependent on my-processor
. In which case you'd only register my-processor
and not javapoet
and that would be the expected case because the 3rd party project only used my-processor
and NOT javapoet
. That case would look exactly like what I described above with my-project
declaring annotationProcessor
for javapoet
. In one case you want isolation from dependencies' usage of annotationProcessor. And in the desired case you want it to transiently be applied to 3rd party cases. But the configuration of both of those situations is exactly the same so you couldn't differentiate what the developer wanted to happen. So my guess is NO you have to specify both annotation processors in your projects that directly use those libraries.