-
Notifications
You must be signed in to change notification settings - Fork 593
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
False positive for THROWS_METHOD_THROWS_CLAUSE_THROWABLE #2040
Comments
Thanks for opening your first issue here! 😃 |
I suspect that this is because Spotbugs doesn't handle lambdas well. |
The I believe it is a problem of the interface provided by jOOQ. As a workground, you can filter or suppress the warning reported by SpotBugs, or replace the lamdba with an anonymous class like below: new ConnectionCallable<YourClass>() {
@Override
public YourClass run(Connection connection) /* no `throws Throwable` here */ {
// your code
}
} |
Labeling this as a third party bug seems wrong to me. Spotbugs should rather not raise that issue for lambdas used in third party methods. I get that warning hundreds of times for trivial AssertJ assertions like this:
just because the "isThrownBy(...)" method of course must handle every kind of throwable. I would expect the same to be reported for JUnit, Hamcrest and similar assertion libraries, if people start upgrading to spotbugs 4.7.0. Any change on my side to avoid the spotbugs issue just makes the code worse to read, and doesn't improve the security/fault tolerance or any other criteria. |
See spotbugs/spotbugs#2040 for discussion of the warning.
I understand, and in the case of AssertJ, it is understandable to throw However, in case the case of jOOQ, it should not throw And generally, static analysis prefers false-positive over false-negative, then I think the current SpotBugs implementation itself is OK. It is technically possible to treat AssertJ, you may send a PR to realize. :) |
This reverts commit 101b55e. The reason is spotbugs/spotbugs#2040
The problem is not about whether some method is reasonable to throw exception. The problem is about the signature being defined outside of the project being analyzed, and Spotbugs raising an error for any derived usage of that unchangable signature. I would fully understand the error being raised for any class declaration in my analyzed files that is not a subclass of such an external class. |
Actually I do not believe this will work as a workaround. At least with JDK17 there will be a synthetic bridge method defined with the Throwable and SpotBugs will report the same violation against it. See #2050 . |
I confirm that this rule is messing with my projects unit-tests for exceptions. It reports every line with assertThrows. For example:
The signature of the Application class is like this:
So I don't even understand why it is reporting this. |
Almost every one of my repos is failing on this check when upgrading |
Same here, JUnit5's Executable type throws Throwable, which is failing this check. Technically, all @KengoTODA Re-writing all of my tests to use an anonymous class instead of lambdas is not a reasonable ask. Neither is adding a suppression to all test classes. Plus, I don't think this will actually work in practice without re-wrapping everything in a runtime exception. @oroszbd I'm not sure how technically feasible this is, but a few suggestions for how to make this work with JUnit:
I have not really thought about the ramifications of each of these suggestions, so I understand if any or all of them are not doable or not preferred. I definitely have to skip this release in all of my projects that use JUnit (i.e. all of my projects) since this update makes this tool very unfeasible for use with JUnit. (Happy Monday, everyone! 😝) |
@trancexpress : FYI. I think that's what we see too, right? The detector is coming from #1956 Reading #1956 description we see link to which says it is a direct conclusion from which, in my personal opinion, it a fully academic rule, writen by someone who never maintained complex software with dozens of 3rd party dependencies and lives in an ideal world where every API used in a product can be fixed by the responsible engineers. Even assumimg I have full source code and ability to recompile every bit of software I use in a product, there are still valid cases where catching or throwing runtime exceptions is necessary (like in lambdas or some generic error handlers). But in reality we use libraries with bugs known for years and never fixed, and not catching NPE's or not re-throwing some generic exceptions is not even possible. Ideally such detectors shouldn't be enabled by default, or produce low prio/severity warnings, as they rarely find real issues. |
Yes, we have a few occurrences of this when switching to There are a lot more
Essentially we will add the following filters without even looking into the multiple problems reported by the newer
|
Personally, when writing unit tests in Java where the code can throw an exception, I always mark the test as IMHO this is preferable in test code and another valid use case that the new |
I think @Bananeweizen 's (and @leviem1 's option one) is the best solution for production code by far:
|
I have tried to apply this version to our projects (production, not test code) and come up against many of these and THROWS_METHOD_THROWS_RUNTIMEEXCEPTION and THROWS_METHOD_THROWS_CLAUSE_BASIC_EXCEPTION. In some cases they have been valid and allowed me to improve our code however most have been in cases where a 3rd party class/interface has been extended/implemented and adding a suppression annotation would just add a lot of noise to our code. For me this and the other 2 rules do have utility, but only if they apply to the class/interface adding the exception/throwable to the method signature, not derived instances, otherwise I'm going to have to exclude these rules. |
This also happens on basic code just calling JDK methods, even without lambdas:
(the lambda version also triggers the warning) While this may or may not be poor design of API of Callable, it's unlikely to change ever. This results in hundreds of false-positives in my project which means I have to exclude this otherwise useful check, so it might as well not even be there. This issue appeared when upgrading to 4.7.0 spotbugs from 4.6.0. I'd also agree that throwing Exception on test code is desirable, maybe even best practice. |
This avoids many false positives reported via spotbugs#2040
We tried to reach the author but without success so far. I will look into the code now and try to fix it. |
Thanks. In doubt (too complicated / too many false positives / too less time), I would prefer to disable first and work on fixes without any time pressure. But next SpotBugs release should have that thing fixed or disabled. |
If it helps, I've submitted a PR to exclude methods on synthetics classes (#2067). This should fix most of the noise. This means you won't get bug reports on lines that use lambdas to implement methods that are However, I'm still in favour of these new checks being off by default. I think there are perfectly valid cases where code should be marked as In short, my vote is to merge both #2067 and #2063, so that the check is off by default, and doesn't generate loads of false positives when turned on. |
I already made a partial fix but I am still working on the last step which are generics. I hope to submit a PR this week. |
This PR fixes issue spotbugs#2040 by limiting the errors reported by the detector `ThrowingExceptions` to cases where `java.lang.Exception` or `lava.lang.Throwable` appears in the exception specification of th method but it is neither inherited from an overridden method nor is is coming from another method that the method invokes. Syntathic methods are also omitted as well as methods which throw generic exceptions.
I have the same issue with JUnit, and I bet TestNG and other test frameworks won't be any different. |
This PR fixes issue spotbugs#2040 by limiting the errors reported by the detector `ThrowingExceptions` to cases where `java.lang.Exception` or `lava.lang.Throwable` appears in the exception specification of th method but it is neither inherited from an overridden method nor is is coming from another method that the method invokes. Syntathic methods are also omitted as well as methods which throw generic exceptions.
Hi all, would you set expectations as to when this change will be released in 4.7.x? |
Relates to: spotbugs/spotbugs#2040 Change-Id: I03acac9f4335dd8c87236a7bc0f66489cb42ee04
Hi,
Updating to 4.7.0 ( alexpdp7/zqxjkcrud#315 ) is causing the following warning for me:
But the line it's pointing to doesn't make sense?
https://github.com/alexpdp7/zqxjkcrud/blob/c247e3be1daf02dce1340eee436889b7c2fd1786/src/main/java/net/pdp7/zqxjkcrud/dao/CatalogRepository.java#L23
Cheers,
Álex
The text was updated successfully, but these errors were encountered: