byte-buddy icon indicating copy to clipboard operation
byte-buddy copied to clipboard

`MemberAttributeExtension.ForField().on(…)` does not consider previously added annotations

Open odrotbohm opened this issue 1 year ago • 3 comments

Assume I have some code that adds an annotation to a field using:

new MemberAttributeExtension.ForField()
  .annotate(…);

and a second declaration (in another ByteBuddy plugin) that would attempt the same, but guards against the presence of the potentially previously added annotation:

new MemberAttributeExtension.ForField()
  .annotate(…)
  .on(…) // Receiving a filter for the annotation to be added

The condition handed into ….on(…) seems to only consider the annotations originally present on the type. I essentially need to write code that adds the annotation once as the individual invocations to add it don't know about each other. Alternatively, I wonder if the addition of an annotation could be deduplicated for identical AnnotationDeclarations as otherwise invalid annotation declarations are produced.

odrotbohm avatar Dec 17 '23 21:12 odrotbohm

Unfortunately, the internal model is not currently strong enough to capture "on the fly changes" made by ASM visitors. Your best option right now would be to add a custom visitor that strips annotations by a given criteria and then write your own annotation after visiting everything that was added previously.

In order to avoid this, you can transform a type, write it to a byte array and then read it and reprocess it, but that is rather costly.

raphw avatar Dec 18 '23 11:12 raphw

I seem to run into this problem even with a single plugin declaring the annotation within Eclipse. I wonder whether this is related to m2e likely keeping the build plugin instance around. In that case, I think the class files are read once into TypeDescriptors, transformation logic is applied and the class files rewritten. A subsequent invocation of the plugin (the same instance) would then not re-read the TypeDescriptors, would it? Thus, the matching logic would still not see the guards and perform the annotation addition a second time?

Is there a way to tweak the ClassFileLocator so that it re-initializes for all invocations of the plugin instance?

odrotbohm avatar Dec 19 '23 19:12 odrotbohm

This might be the cache that is used? Can you try to use a PoolStrategy that uses a no-op cache?

raphw avatar Dec 21 '23 00:12 raphw