Передать массив как значение параметра аннотации в JavaPoet

Используя JavaPoet, я пытаюсь аннотировать класс аннотацией, которая имеет массив в качестве значения параметра, т.е.

@MyCustom(param = { Bar.class, Another.class })
class Foo { 
}

Я использую AnnotationSpec.builder и его метод addMember():

List<TypeMirror> moduleTypes = new ArrayList<>(map.keySet());
AnnotationSpec annotationSpec = AnnotationSpec.builder(MyCustom.class)
   .addMember("param", "{ $T[] } ", moduleTypes.toArray() )
   .build();
builder.addAnnotation(annotationSpec);

person kosiara - Bartosz Kosarzycki    schedule 07.03.2017    source источник


Ответы (2)


Возможно, это не оптимальное решение, но передать массив в аннотацию в JavaPoet можно следующим образом:

List<TypeMirror> moduleTypes = new ArrayList<>(map.keySet());
CodeBlock.Builder codeBuilder  = CodeBlock.builder();
boolean arrayStart = true;
codeBuilder.add("{ ");
for (TypeMirror modType: moduleTypes)
    if (!arrayStart)
        codeBuilder.add(" , ");
    arrayStart = false;
    codeBuilder.add("$T.class", modType);
codeBuilder.add(" }");

AnnotationSpec annotationSpec = AnnotationSpec.builder(MyCustom.class)
    .addMember("param", codeBuilder.build() )
    .build();
builder.addAnnotation(annotationSpec);
person kosiara - Bartosz Kosarzycki    schedule 07.03.2017

CodeBlock имеет сборщик соединений, и вы можете использовать его для потоковой передачи, делая что-то вроде следующего (если, например, это было перечисление). Вы можете сделать это для любых типов, просто изменится карта.

AnnotationSpec.builder(MyCustom.class)
   .addMember(
      "param",
      "$L",
      moduleTypes.stream()
         .map(type -> CodeBlock.of("$T.$L", MyCustom.class, type))
         .collect(CodeBlock.joining(",", "{", "}")))
   .build()
person amurka    schedule 04.05.2020