I have an annotation like this:
#Retention(RetentionPolicy.RUNTIME)
#Target({ElementType.FIELD, ElementType.METHOD, ElementType.TYPE})
public #interface MyAnnotation {
String name();
Class<InstanceConverter> converter();
What I'm trying to do is make name required and converter optional. It appears that all attributes of an annotation are required by default. How do I make converter optional?
I've read through two articles on annotations and none seem to mention optional attributes.
Thanks.
You should add a default clause at the right side of the field declaration statement in the annotation #interface definition:
#Retention(RetentionPolicy.RUNTIME)
#Target({ElementType.FIELD, ElementType.METHOD, ElementType.TYPE})
public #interface MyAnnotation {
String name(); // mandatory
Class<InstanceConverter> converter() default InstanceConverter.class; // optional
}
Related
I am trying to understand why I would use #interface. I see many tutorials explaining what all those annotations mean but no where could I find in simple terms how (or why) I can use them.
As a made up example
#Target({ElementType.TYPE })
#Retention(RetentionPolicy.RUNTIME)
#Inherited
#Documented
public #interface MyAnnotation {
String getAString() default "blah";
}
Suppose I use this annotation on a class.
#MyAnnotation
public class TestClass {
public String test(){
return this.getAString();
}
}
Can I call getAString() without using reflection?
If not, what can be
a possible use of it?
Here is an example on how you can use annotation fields:
#Retention(RetentionPolicy.RUNTIME)
#Target(ElementType.TYPE)
public #interface MyAnnotation {
public String name();
public String value();
}
for(Annotation annotation : annotations){
if(annotation instanceof MyAnnotation){
MyAnnotation myAnnotation = (MyAnnotation) annotation;
System.out.println("name: " + myAnnotation.name());
System.out.println("value: " + myAnnotation.value());
}
}
The example is taken from here:
http://tutorials.jenkov.com/java-reflection/annotations.html
Also see this:
#interface default declaration usage in Java
I'm trying to initialise an array of annotations but can't figure out the syntax.
public #interface Tag {
String key();
String value();
}
#Target({ElementType.ANNOTATION_TYPE})
#Retention(RetentionPolicy.RUNTIME)
public #interface BaseAnnotation {
String[] names();
Tag[] tags();
}
As you can see, BaseAnnotation has an array of Tag annotation and I want to use it to annotate another annotation like this:
#BaseAnnotation(names={"abcs", "bnm"},
tags = {key="aaa",value="bbb"}) //I can't figure out the syntax for this one
#Target({ElementType.METHOD})
#Retention(RetentionPolicy.RUNTIME)
public #interface ToBeUsedAnnotation {
}
The problem is that I've tried a few ways to set the values for tags but can't find any useful documentation on how to do it.
Thanks.
I'm trying to create a wrapped annotation but i don't know it is possible this, anybody do this before?
#Target({ ElementType.METHOD, ElementType.TYPE })
#Retention(RetentionPolicy.RUNTIME)
#Inherited
#PreAuthorize("#auth.hasAccess(token, id)")
public #interface HasAdminRole {
String token();
String id();
}
I expect that SpEL use the token and id values of #interface to call 'hasAccess' but don't do nothing.
how can I write a custom annotation that takes another annotation and the values?
#Target(ElementType.TYPE)
#Retention(RetentionPolicy.RUNTIME)
public #interface TestAnnotation{
Class<? extends TestAnnotationChild> annotation();
}
The second annotation
#Target(ElementType.TYPE)
#Retention(RetentionPolicy.RUNTIME)
public #interface TestAnnotationChild{
}
And I would like to do something like
#TestAnnotation(#TestAnnotationChild={values})
How can I do something like that?
This is how it is done.
#Target(ElementType.TYPE)
#Retention(RetentionPolicy.RUNTIME)
public #interface TestAnnotation {
TestAnnotationChild child();
// Or for an array
TestAnnotationChild[] children();
}
Usage
#TestAnnotation(
#TestAnnotationChild(
value = "42",
anotherValue = 42
)
)
However this part of your statement
and the values
does make me think you want to do something non-ordinary.
Could you clarify?
You should just use TestAnnotationChild value(); instead of Class<? extends TestAnnotationChild> annotation();.
#Target(ElementType.TYPE)
#Retention(RetentionPolicy.RUNTIME)
public #interface TestAnnotation{
TestAnnotationChild value();
}
#Target(ElementType.TYPE)
#Retention(RetentionPolicy.RUNTIME)
public #interface TestAnnotationChild {
// String or whatever Object you want
String[] value();
}
Now you can use the Annotations as you wanted:
#TestAnnotation(#TestAnnotationChild({"TEST"}))
you can just have a property of type TestAnnotationChild in your TestAnnotation, just like it was a string, or whatever else
I want to inject spring properties into Annotation but I can't do it directly.
I have annotation :
#Retention(RetentionPolicy.RUNTIME)
#Target({ElementType.METHOD})
#StepDefAnnotation
#Documented
public #interface When {
String value();
long timeout() default 0L;
}
And I want to insert it like this #When(value="some.value.from.properties")
or like this #When(value=#Value("some.value.from.properties"))