尝试为非注释类型创建代理

时间:2019-02-05 15:35:41

标签: java reflection proxy annotations

当我试图从字段中获取注释列表时,为什么会得到java.lang.annotation.AnnotationFormatError: Attempt to create proxy for a non-annotation type.

我的注释:

@Target({ ElementType.FIELD })
@Retention(RetentionPolicy.RUNTIME)
private @interface TypicalAnnotation
{
    int size();
}

用法:

public static class MockAnnotatedClass
{
    @TypicalAnnotation(size = 3)
    public Integer number = 2;
}

致电:

ReflectionUtils.getAllFields(clazz1).getAnnotations() <- got the exception.

1 个答案:

答案 0 :(得分:0)

当我使用Jdeveloper 12.2.1.0.0并集成了启用了快速交换功能的Weblogic时,我遇到了同样的问题。

如果您查看源代码(github),将会看到如果该类型不是注释或实现多个接口或未实现java.lang.annotation,则将引发异常。注释界面:

AnnotationInvocationHandler(Class<? extends Annotation> type, Map<String, Object> memberValues) {
    Class<?>[] superInterfaces = type.getInterfaces();
    if (!type.isAnnotation() ||
        superInterfaces.length != 1 ||
        superInterfaces[0] != java.lang.annotation.Annotation.class)
        throw new AnnotationFormatError("Attempt to create proxy for a non-annotation type.");
    this.type = type;
    this.memberValues = memberValues;
}

使用此代码,我检查了注释实现的接口:

注释声明:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation {}

检查类型:

Class<?> type = MyAnnotation.class;

System.out.println("type.isAnnotation() " + type.isAnnotation());
System.out.println("type.getInterfaces().length " + type.getInterfaces().length);

for (Class<?> superType : type.getInterfaces()) {
    System.out.println("type.getInterfaces()[i] " + superType);
}

输出:

type.isAnnotation() true
type.getInterfaces().length 2
type.getInterfaces()[i] interface java.lang.annotation.Annotation
type.getInterfaces()[i] interface com.bea.wls.redef.Redefinable     // << ??????

事实证明,另一个接口已添加到注释中。 我没有找到专门关于com.bea.wls.redef.Redefinable的信息。经过一番搜索,我意识到快速交换功能使用了com.bea.wls.redef包。

我看到2种解决方案:

  1. 禁用快速交换功能。

  2. 将所有自定义注释移动到单独的jar中。这就是我所做的。

也许有一种方法可以关闭注释的换行。但是我没有找到。