如何在Java中使用自定义类型注释
Java 8具有名为Type annotations( JSR 308 )的function。 我想将它用于简单的Object to Object映射器框架。 我想像这样定义注释@ExpectedType
@Target({ElementType.TYPE_PARAMETER, ElementType.TYPE_USE}) @Retention(RetentionPolicy.RUNTIME) public @interface ExpectedType { public Class value(); }
然后在我的代码中使用它,如下所示:
public class SomeServiceImpl() { public @ExpectedType(ObjectA_DTO.class) IObjectA doSomething(@ExpectedType(ObjectA_Entity.class) IObjectA obj) { return (ObjectA_Entity) obj; // it's correct } }
IObjectA
是由ObjectA_DTO
和ObjectA_Entity
类实现的接口。 我想用这种方式服务:
// it's correct assert someService.doSomething(new ObjectA_DTO()).getClass() == ObjectA_DTO.class;
我想更改SomeServiceImpl方法的调用以使用Object mapper。 它可以通过使用JSR 269或AOP生成的代码来实现。
问题是我编写了简单的注释处理器,它根本不处理类型注释。 简单注释处理器的来源如下所示:
@SupportedAnnotationTypes("*") @SupportedSourceVersion(SourceVersion.RELEASE_8) public class SimpleAnnotationsProcessor extends AbstractProcessor { public boolean process(Set annotations, RoundEnvironment roundEnv) { Messager messager = processingEnv.getMessager(); try { for (TypeElement e : annotations) { messager.printMessage(Diagnostic.Kind.NOTE, e.toString()); for (Element elem : roundEnv.getElementsAnnotatedWith(e)) { messager.printMessage(Diagnostic.Kind.NOTE, elem.toString()); } } } catch (Exception e) { e.printStackTrace(); } return true; } }
有关SimpleAnnotationsProcessor如何使用或如何访问类型注释的任何想法? 使用Pluggable Annotation Processing API对我来说不是必需的我认为它会比Javareflection具有更好的性能。 无论如何我也不知道如何通过Java Reflection访问类型注释。
我不确定我理解你想要实现的目标,但这里有一个例子,你可以用Javareflectionapi访问你的注释:
package test; import java.lang.annotation.Annotation; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; import java.lang.reflect.AnnotatedType; import java.lang.reflect.Method; public class TypeParameterTest { @Target({ElementType.TYPE_PARAMETER, ElementType.TYPE_USE}) @Retention(RetentionPolicy.RUNTIME) public @interface ExpectedType { public Class> value(); } public static interface IObjectA {} public static class ObjectA_DTO implements IObjectA {} public static class ObjectA_Entity implements IObjectA {} public static class SomeServiceImpl { public @ExpectedType(ObjectA_DTO.class) IObjectA doSomething(@ExpectedType(ObjectA_Entity.class) IObjectA obj) { return (ObjectA_Entity) obj; } } public static void main(String[] args) throws NoSuchMethodException, SecurityException { Method m = SomeServiceImpl.class.getMethod("doSomething", IObjectA.class); AnnotatedType returnType = m.getAnnotatedReturnType(); Annotation returnTypeAnnotation = returnType.getAnnotation(ExpectedType.class); System.out.println(returnTypeAnnotation); AnnotatedType[] parameters = m.getAnnotatedParameterTypes(); for (AnnotatedType p : parameters) { Annotation parameterAnnotation = p.getAnnotation(ExpectedType.class); System.out.println(parameterAnnotation); } } }
输出如下:
@test.TypeParameterTest$ExpectedType(value=class test.TypeParameterTest$ObjectA_DTO) @test.TypeParameterTest$ExpectedType(value=class test.TypeParameterTest$ObjectA_Entity)
但请注意,并非所有可能的类型注释都可以通过reflectionapi访问,但是如果需要,您可以始终从字节代码中读取它们(请参阅我的答案)。
我认为你在运行时混淆了注释的使用,而不是在各种工具的“编译”时间使用注释。 Processor
接口用于工具(编译器,javadoc生成器),而不是在运行时代码中。
@Documented @Retention(RetentionPolicy.RUNTIME) @Target(ElementType.FIELD) public @interface SearchDefinition { public String identifier() default ""; }
@SearchDefinition – 可以在任何地方使用
- ClassLoader.getSystemResourceAsStream和getClass()之间的区别.getResourceAsStream()
- Java赋值问题 – 这是primefaces的吗?