-
Notifications
You must be signed in to change notification settings - Fork 10.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Forcing guava JRE versions in Android projects with new metadata is too tedious #6801
Comments
I'm able to work around the 3rd issue by forcing tests to fork every 1 test and think that bit's actually unrelated to guava. The result is this configuration appears to work tasks.withType<CheckAarMetadataTask>().configureEach { enabled = false }
dependencies.constraints {
testImplementation("com.google.guava:guava") {
attributes {
attribute(
TargetJvmEnvironment.TARGET_JVM_ENVIRONMENT_ATTRIBUTE,
objects.named(TargetJvmEnvironment.STANDARD_JVM)
)
}
}
}
configurations.configureEach {
resolutionStrategy.capabilitiesResolution.withCapability("com.google.guava:guava") {
select(candidates.single { it.variantName.contains("jreRuntimeElements") })
}
resolutionStrategy.capabilitiesResolution.withCapability(
"com.google.collections:google-collections"
) {
select(candidates.single { it.variantName.contains("jreRuntimeElements") })
}
} This is a lot of tedium to have to do though 😬 |
Thanks for all the details, and sorry for not making the time for this yet. In hindsight, one question that I should have looked into before merging the metadata is the question of whether a rollback of the metadata could itself lead to problems. Maybe @jjohannes has thoughts? I predict that @jjohannes's first thought is that we should avoid rolling back... and to be fair, that's still my hope, as well :) But that is hard to feel great about that when things are broken for some users and I'm not sure how soon I can do much about it. I will say that I should probably have anticipated that some users would use the (I do wonder if your experiences here imply that forcing the Android flavor is also more difficult than our instructions suggest. Maybe it works OK for a single simple library (which is the primary use case—a cross-platform library that can be used from either Android or JRE) but falls apart for more complex projects. This is the kind of thing that I will hopefully get a better sense of when I look back through the various commits and issues linked from the various threads here.) If we were to break I recognize that there's also still the larger question of whether the aggregate disruption we're seeing with the metadata is worth the cost, even assuming that we successfully add Java 8 APIs to |
I think that breaking I think the right move is to remove the metadata, it's overly prescriptive to the point of being an active and invasive issue to consumers, and gradle's cumbersome API surface area makes it too tedious for people without deep domain knowledge to do anything about the issues it leads to. |
The thing I should have mentioned in my last post is that the Android flavor has a number of implementation changes that reduce memory usage and binary size. So, if we could get all the APIs you need into that flavor, it would provide the best of both worlds. It is of course possible that those changes aren't significant in your case. And it is indisputable that we haven't made the APIs you need available yet. I wouldn't want you to sit down and compile a list of exactly what you need, but do you have a sense of whether there's more than the various My hope for the Gradle metadata has been that users will get the appropriate version automatically, avoiding problems like cashapp/paparazzi#552 from Truth's dependency on |
I don't know all the little bits and pieces, but my perception at a broad level is that D8/R8/L8 on android tooling are pretty aggressively paced and outpacing guava's efforts to backport functionality to a separate I don't want to get tooooo close into the realm of "should guava android still exist", but it does feel like it's circling around that. To that end, I'd argue that it shouldn't. |
Another way this issue manifests: some tools resolve dependencies that use guava via Gradle configurations in projects that are not inherently jvm or android projects, such as gradle tasks that invoke formatters or generate code (i.e. Spotless). In this case, it will always fail to resolve due to gradle not being able to decide between available variants.
|
For the "problem" posted above: Projects that do not yet apply any Java/Android/JVM plugin have to apply the For the problem posted in the description: could you please provide a reproducer for that problem @ZacSweers? We should find out why the situation(s) are in which General feedback on the topic of "Gradle Metadata for Guava" (my personal opinion and impressions): When I read through this discussions and some of #6612 it sounds like things are broken. But so far all concrete problems I have seen, analyzed, reproduced were either fixed by the patch releases or came down to misconfiguration/misunderstanding in user projects that 'by chance' worked with older Guava versions with less precise metadata. What I find particularly frustrating is folks asking about why it is broken for them but then do not even share the whole error message (happened on the other issue several times) let alone a reproducer. This also gives a bad and wrong impression for others looking at these issues, where the actual helpful advice is buried between a lot of noise. I also would appreciate if you could avoid wording like "silly workarounds" @ZacSweers. I don't think any of this is silly.
@cpovirk I personally don't see the evidence for why this should be rolled back unless I fully understand the problems that currently exist (like the one described in this issue, which I would need to reproduce first). But it's not my call and since you asked: If you would roll back the change (remove the Gradle Metadata) in the next release it should not cause any problems. (Only for me because I have to adjust my metadata patching plugin again 😃.) Gradle selects one version and only then looks at the metadata. If a version without Gradle Metadata is selected, no Gradle Metadata is used. |
Hi @jjohannes. There is a lot to unpack there, but unfortunately my takeaway here is that you are taking this issue personally and it makes it hard to know how to engage with most of what you said. So, I'll just address the two issues. For the issue in the description: attempt to use guava JRE in an android project that runs paparazzi tests, observe that they all fail because paparazzi requires guava JRE but the metadata choice forces guava android. It's easy to repro, but if you're serious about looking into it I can spin up a repro project for you. For the issue with spotless: I don't really know what to tell you. This error message
in no way leads one to this (great!) explanation you offered
You can explain it because you know happened to know about it. You used to work at Gradle and are a well known Gradle build tool expert in the industry. Most people that would see that error message are not those things. The string Sure, I'm holding it wrong, but the error message didn't exactly tell me how to hold it or where to learn either. That's why I filed this issue, because when this system falls over, it's going to result in most users just not updating guava instead. |
@ZacSweers which version of Gradle is this with?
This would be very helpful to me to understand where this is going wrong. I can barely spell paparazzi. :)
100% agree, these error messages are not helpful. We're going to land a small change to provide breadcrumbs to documentation for this in 8.6, but ultimately, these messages should go away and said something useful. |
Here you go: slackhq/circuit#993 |
Thank you for the project. Unfortunately, I cannot reproduce the problem. If I only add this part back and remove the rest of the "workaround block" it works as I would expect:
The tests are running (https://scans.gradle.com/s/c4hsvnqakzbzq) and it gets to the same point as when you have the whole "workaround block" (https://scans.gradle.com/s/gxfcsn7xhsdx4). This is, in my mind, the correct way now to explicitly select the |
I suspect the added work we have to do internally is because we apply the guava bom internally, which is mentioned in the doc on that workaround section but not sure if you saw. In my mind, the "correct" way to explicitly select the In a way, it reminds me of how kotlin multiplatform works, where there is a common target and then platform targets that gradle automatically selects based on the source set. However, if I depended on a |
Dropping this here, because I think it's tightly related: Also contains an isolated (no Paparazzi, @big-guy ;) repro for a similar (if not the same) issue. |
We have an Android project with minSdk 29 and target Java 17, which means we can freely use newer APIs and the guava JRE artifact. With the introduction of the new Gradle metadata though, this has become
an insurmountablea battle that actually breaks our infrastructure with libraries that also use Guava.The ideal goal is to force use of JRE regardless. However, in my testing I've found that's
fundamentally not possible anymorepossible but with lots of tedium. The release notes advice was not helpful (and in some places invalid code), below is everything I attempted.1. Dependency constraints
My first attempt was to apply dependency constraints like so
However, this results in the following failed resolution
2. Resolution strategies
This approach adds on to the above by also configuring a resolution strategy to force the JRE version.
This results in another error about missing google-collections
So I fix this by adding a strategy for that too
This gets farther, but now I get a failure with AGP's
CheckAarMetadataTask
, which sees invalid metadata in the produced library jar. So, I disable that task to try to get further.3. JVMNevermind, this part is fixedSIGSEGV
Finally, I'm able to proceed running tests, only to find that after all the above it actually crashes the JVM entirely. I've attached a crash log of this, but the tombstone looks like this.
hs_err_pid21676.log
Conclusion
At this point, we cannot update Guava 32.0.0 because of the introduction of these metadata rules. I completely understand the intention and goal behind it, and it may even be that Guava is not really at fault here vs Gradle tooling. However, the end result is that it's made Guava in android projects at-best annoying and at-worst impossible. I articulated this at length here: #6612 (comment)
Quoting here with emphasis on the ask again :)
The text was updated successfully, but these errors were encountered: