Example #1
0
 private void configureAnnotationFromDefinition(AnnotationNode definition, AnnotationNode root) {
   ClassNode type = definition.getClassNode();
   if (!type.isResolved()) return;
   Class clazz = type.getTypeClass();
   if (clazz == Retention.class) {
     Expression exp = definition.getMember("value");
     if (!(exp instanceof PropertyExpression)) return;
     PropertyExpression pe = (PropertyExpression) exp;
     String name = pe.getPropertyAsString();
     RetentionPolicy policy = RetentionPolicy.valueOf(name);
     setRetentionPolicy(policy, root);
   } else if (clazz == Target.class) {
     Expression exp = definition.getMember("value");
     if (!(exp instanceof ListExpression)) return;
     ListExpression le = (ListExpression) exp;
     int bitmap = 0;
     for (Expression e : le.getExpressions()) {
       PropertyExpression element = (PropertyExpression) e;
       String name = element.getPropertyAsString();
       ElementType value = ElementType.valueOf(name);
       bitmap |= getElementCode(value);
     }
     root.setAllowedTargets(bitmap);
   }
 }
Example #2
0
 @Test(dataProvider = "retentionPolicyTestCase")
 public void annotationTest(RetentionPolicy policy) {
   assertEval("import java.lang.annotation.*;");
   String annotationSource =
       "@Retention(RetentionPolicy." + policy.toString() + ")\n" + "@interface A {}";
   assertEval(annotationSource);
   String classSource =
       "@A class C {\n"
           + "   @A C() {}\n"
           + "   @A void f() {}\n"
           + "   @A int f;\n"
           + "   @A class Inner {}\n"
           + "}";
   assertEval(classSource);
   String isRuntimeVisible = policy == RetentionPolicy.RUNTIME ? "true" : "false";
   assertEval("C.class.getAnnotationsByType(A.class).length > 0;", isRuntimeVisible);
   assertEval(
       "C.class.getDeclaredConstructor().getAnnotationsByType(A.class).length > 0;",
       isRuntimeVisible);
   assertEval(
       "C.class.getDeclaredMethod(\"f\").getAnnotationsByType(A.class).length > 0;",
       isRuntimeVisible);
   assertEval(
       "C.class.getDeclaredField(\"f\").getAnnotationsByType(A.class).length > 0;",
       isRuntimeVisible);
   assertEval("C.Inner.class.getAnnotationsByType(A.class).length > 0;", isRuntimeVisible);
 }
Example #3
0
 public static void configureAnnotationFromDefinition(
     AnnotationNode definition, AnnotationNode root) {
   ClassNode type = definition.getClassNode();
   if ("java.lang.annotation.Retention".equals(type.getName())) {
     Expression exp = definition.getMember("value");
     if (!(exp instanceof PropertyExpression)) return;
     PropertyExpression pe = (PropertyExpression) exp;
     String name = pe.getPropertyAsString();
     RetentionPolicy policy = RetentionPolicy.valueOf(name);
     setRetentionPolicy(policy, root);
   } else if ("java.lang.annotation.Target".equals(type.getName())) {
     Expression exp = definition.getMember("value");
     if (!(exp instanceof ListExpression)) return;
     ListExpression le = (ListExpression) exp;
     int bitmap = 0;
     for (Expression e : le.getExpressions()) {
       if (!(e instanceof PropertyExpression)) return;
       PropertyExpression element = (PropertyExpression) e;
       String name = element.getPropertyAsString();
       ElementType value = ElementType.valueOf(name);
       bitmap |= getElementCode(value);
     }
     root.setAllowedTargets(bitmap);
   }
 }
  @Nullable
  private static String doCheckRepeatableAnnotation(@NotNull PsiAnnotation annotation) {
    PsiAnnotationOwner owner = annotation.getOwner();
    if (!(owner instanceof PsiModifierList)) return null;
    PsiElement target = ((PsiModifierList) owner).getParent();
    if (!(target instanceof PsiClass) || !((PsiClass) target).isAnnotationType()) return null;
    PsiClass container = getRepeatableContainer(annotation);
    if (container == null) return null;

    PsiMethod[] methods = container.findMethodsByName("value", false);
    if (methods.length == 0) {
      return JavaErrorMessages.message(
          "annotation.container.no.value", container.getQualifiedName());
    }

    if (methods.length == 1) {
      PsiType expected =
          new PsiImmediateClassType((PsiClass) target, PsiSubstitutor.EMPTY).createArrayType();
      if (!expected.equals(methods[0].getReturnType())) {
        return JavaErrorMessages.message(
            "annotation.container.bad.type",
            container.getQualifiedName(),
            JavaHighlightUtil.formatType(expected));
      }
    }

    RetentionPolicy targetPolicy = getRetentionPolicy((PsiClass) target);
    if (targetPolicy != null) {
      RetentionPolicy containerPolicy = getRetentionPolicy(container);
      if (containerPolicy != null && targetPolicy.compareTo(containerPolicy) > 0) {
        return JavaErrorMessages.message(
            "annotation.container.low.retention", container.getQualifiedName(), containerPolicy);
      }
    }

    Set<PsiAnnotation.TargetType> repeatableTargets =
        PsiImplUtil.getAnnotationTargets((PsiClass) target);
    if (repeatableTargets != null) {
      Set<PsiAnnotation.TargetType> containerTargets = PsiImplUtil.getAnnotationTargets(container);
      if (containerTargets != null && !repeatableTargets.containsAll(containerTargets)) {
        return JavaErrorMessages.message(
            "annotation.container.wide.target", container.getQualifiedName());
      }
    }

    return null;
  }
Example #5
0
 @DataProvider(name = "retentionPolicyTestCase")
 public Object[][] retentionPolicyTestCaseGenerator() {
   List<Object[]> list = new ArrayList<>();
   for (RetentionPolicy policy : RetentionPolicy.values()) {
     list.add(new Object[] {policy});
   }
   return list.toArray(new Object[list.size()][]);
 }
Example #6
0
 private void configureAnnotation(AnnotationNode node, Annotation annotation) {
   Class type = annotation.annotationType();
   if (type == Retention.class) {
     Retention r = (Retention) annotation;
     RetentionPolicy value = r.value();
     setRetentionPolicy(value, node);
     node.setMember(
         "value",
         new PropertyExpression(
             new ClassExpression(ClassHelper.makeWithoutCaching(RetentionPolicy.class, false)),
             value.toString()));
   } else if (type == Target.class) {
     Target t = (Target) annotation;
     ElementType[] elements = t.value();
     ListExpression elementExprs = new ListExpression();
     for (ElementType element : elements) {
       elementExprs.addExpression(
           new PropertyExpression(
               new ClassExpression(ClassHelper.ELEMENT_TYPE_TYPE), element.name()));
     }
     node.setMember("value", elementExprs);
   } else {
     Method[] declaredMethods;
     try {
       declaredMethods = type.getDeclaredMethods();
     } catch (SecurityException se) {
       declaredMethods = new Method[0];
     }
     for (Method declaredMethod : declaredMethods) {
       try {
         Object value = declaredMethod.invoke(annotation);
         Expression valueExpression = annotationValueToExpression(value);
         if (valueExpression == null) continue;
         node.setMember(declaredMethod.getName(), valueExpression);
       } catch (IllegalAccessException e) {
       } catch (InvocationTargetException e) {
       }
     }
   }
 }
  @Nullable
  private static RetentionPolicy getRetentionPolicy(PsiClass annotation) {
    PsiModifierList modifierList = annotation.getModifierList();
    if (modifierList != null) {
      PsiAnnotation retentionAnno =
          modifierList.findAnnotation(CommonClassNames.JAVA_LANG_ANNOTATION_RETENTION);
      if (retentionAnno == null) return RetentionPolicy.CLASS;

      PsiAnnotationMemberValue policyRef = PsiImplUtil.findAttributeValue(retentionAnno, null);
      if (policyRef instanceof PsiReference) {
        PsiElement field = ((PsiReference) policyRef).resolve();
        if (field instanceof PsiEnumConstant) {
          String name = ((PsiEnumConstant) field).getName();
          try {
            return RetentionPolicy.valueOf(name);
          } catch (Exception e) {
            LOG.warn("Unknown policy: " + name);
          }
        }
      }
    }

    return null;
  }
 public void visitEnum(String name, String desc, String value) {
   myRetentionPolicy = RetentionPolicy.valueOf(value);
 }