英文:
Named fields for another class
问题
I need to access some private fields via reflection. While this is considered bad, it is an external library and I have no other way to access it. The field names (and types) are known in advance (during compile time) and as a precaution for future library updates I want the compiler to throw an error when this field doesn't exist anymore.
Lombok has the annotation @FieldNameConstants which generates all field names as static Strings. When the field doesn't exist anymore, the static variable won't generate and the compiler will throw an error. This would be a great solution, but as this is an external library class I cannot annotate it with lombok.
英文:
I need to access some private fields via reflection. While this is considered bad, it is an external library and I have no other way to access it. The field names (and types) are known in advance (during compile time) and as a precaution for future library updates I want the compiler to throw an error when this field doesn't exist anymore.
Lombok has the annotation @FieldNameConstants which generates all field names as static Strings. When the field doesn't exist anymore, the static variable won't generate and the compiler will throw an error. This would be a great solution, but as this is an external library class I cannot annotate it with lombok.
答案1
得分: 2
如果在编译时无法失败,第二好的方法是添加一个单元测试,调用您的反射代码。这样,如果您在每次依赖更新后运行测试(无论如何都应该这样做),如果您依赖的实现细节发生更改,您的测试就会失败。
如果您绝对想要在编译时失败,您需要某种预处理器。例如,您可以构建一个小型的专用代码生成器,根据您考虑的反射生成一个桥接口,但在不能解析的字段上生成方法失败。然后只使用生成的桥接代码。我不知道有哪个库可以直接实现这一点,但在特定情况下编写它并不太难(它不需要很灵活)。
这仍然可能导致运行时问题,例如如果依赖项的编译时和运行时版本不同,或者由于某种原因未替换旧生成的代码。因此,请确保还添加单元测试。
英文:
If you cannot fail during compile time, the second best thing is to add a Unit Test that invokes your reflection code. That way, if you run your tests after every dependency update (you should do that anyway), your test will fail if the implementation details you rely on change.
If you absolutely want to fail compilation, you'll need some kind of preprocessor. You could, for example, build a small, specialized code generator that generates a bridge interface based on the reflection you have in mind, but fails to generate methods for fields it cannot resolve. Then you only use the generated bridge code. I'm not aware of a library that can do this out of the box, but it's not very hard to write in the specific case (it does not need to be flexible).
This could still lead to runtime problems, for example if the compiletime and runtime versions of your dependencies differ, or if old generated code is not replaced for some reason. So make sure to also add Unit Tests.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论