Closed mttjj closed 1 year ago
Hi, This unfortunately cannot be fixed.
The retention policy set to at least class or runtime is correct. This ensures that the annotation can be seen after compilation in class files. But this is correct in you case and hasn't anything to do with the problem at all.
Field initialization here is the main problem. Actually in class files there is no way to see the right side of field declarations in field declarations. The suppressions are only be visible for the declaration of the field. The right side is of field (initializer) is hidden by the java compiler behind a invisible method:
static void clinit()
. There is no way to add a suppression to this field. Workaround is to wrap the call into a method.In generat the workaround for field initialization is to add a static method that can get the suppression.
Sorry this is a limitation of class files format.
Actually there might be a way to identify those calls from byte code analysis by heuristics: any putfield opcode in constructor that has a line number different than the others might be a way to detect it. But this is very hard and depends on the internals of compiler and may break.
Unfortunate but totally understandable. Thankfully, the scenario I described is rare in our codebase and the annotation at the class level won't cause too many problems for us for these particular classes. Thanks for looking into this!
Summary
In short, we have a class that is mostly (but not all) generated code that uses an API that we have forbidden in a field declaration. We would like to suppress the violation on just the field but have not been able to do so. Adding a suppression annotation to the class declaration works but has the downside of suppressing everything in the class including the non-generated code. This is less than ideal.
Setup
Given
signatures.txt
:and
FooBar.java
:The following expected failure is the result of running the maven plugin:
The suppression annotation is declared as:
Tests
The following annotations do not suppress any of the three violations:
The following annotations do suppress the second and third violations:
And then, naturally, a single annotation at the class level suppresses all three violations:
Conclusion
I suppose the ultimate question is, are suppression annotations supposed to work on anything other than classes and methods? The maven documentation states
"...Those annotations must have at least RetentionPolicy.CLASS. They can be applied to classes, their methods, or fields..."
Based on the way that's worded, I can understand if the annotations aren't meant to work on local variables (bars
) or method parameters (date
) but it seems like it should work for the field (foos
).Can you provide some insight into this functionality? As mentioned at the top, we'd really like to be able to annotate a single field with this so we aren't accidentally suppressing the rest of the class that is not generated code but as it stands, we have to add the annotation to the class declaration for it to work.
Please let me know if you would like any clarification or need more information about our scenario.