Java Annotations

From NovaOrdis Knowledge Base
Jump to navigation Jump to search

External

Internal

Overview

Annotations are a form of syntactic metadata providing data about a program that is not part of the program itself. Syntactically, they are a special kind of interface type.

An annotation may have multiple data members, which can be used to configure the annotation:

@RequestMapping(path = "/a", produces = "application/json")

Annotations have no direct effect on the operation of the code they annotate.

Annotations have been first Introduced to the language in Java 5 and enhanced with JSR-308 in Java 8.

Custom Annotations

Java programs can declare custom annotations that may be used to add custom semantic metadata to the code. Once custom metadata are deployed in the code, reflection can be used at runtime to detect them - for those with a runtime retention policy - and use the information to influence the execution of the program. Alternatively, a custom compiler plugin, named annotation processor, can be written and used to process them at the compilation phase. There is a Pluggable Annotation Processing API, specified by JSR 269, which provides support for developing custom annotation processors. For more details see:

Java Annotation Processor

Annotation type declarations are similar to normal interface declarations. An at-sign (@) precedes the interface keyword.

public @interface Encrypted {
}

Each method declaration defines an element of the annotation type. Method declarations must not have any parameters or a throws clause. Return types are restricted to primitives, String, Class, enums, annotations, and arrays of the preceding types. Methods can have default values.

public @interface SomeAnnotation {
  boolean debug() default false;
  int count() default 1;
  String color() default "blue";
  String shape(); // "shape" must always declared and given a value when the annotation is used
  //String form() = null; /* this will not compile */
}

If a method does not have a default value, then a value MUST be specified when the annotation is used in code. null cannot be specified as default value.

The compiler reserves a set of special annotations (including @Deprecated, @Override and @SuppressWarnings) for syntactic purposes.

Annotations themselves may be annotated to indicate where and when they can be used:

@Retention(RUNTIME)
@Target({METHOD, FIELD, TYPE})
public @interface Encrypted {
}

@Retention

@Retention(RetentionPolicy.RUNTIME)

@Retention is a meta-annotation that specifies how long the annotations annotated with it are to be retained. Possible values:

  • RetentionPolicy.SOURCE: annotations are to be discarded by the compiler.
  • RetentionPolicy.CLASS (default): Annotations are to be recorded in the class file by the compiler but need not be retained by the VM at run time.
  • RetentionPolicy.RUNTIME: Annotations are to be recorded in the class file by the compiler and retained by the VM at run time, so they may be read reflectively.

A Retention meta-annotation has effect only if the meta-annotated type is used directly for annotation.

@Target

@Target({ElementType.METHOD})

@Target is a meta-annotation that indicates the context in which the annotated annotation is applicable. Possible values:

  • ElementType.TYPE - for Class, interface (including annotation type) or enum declaration.
  • ElementType.FIELD - for field declaration (includes enum constants).
  • ElementType.METHOD - for method declaration.
  • ElementType.PARAMETER - for parameter declaration.
  • ElementType.CONSTRUCTOR - for constructor declaration.
  • ElementType.LOCAL_VARIABLE - for local variable declaration.
  • ElementType.ANNOTATION_TYPE - for annotation type declaration.
  • ElementType.PACKAGE - for method declaration.
  • ElementType.TYPE_PARAMETER - for package declaration.
  • ElementType.TYPE_USE - for use of a type.
  • ElementType.MODULE - for module declaration.

Meta-Annotation

Annotations that are applied to other annotations: @Retention, @Target.

Predefined Annotations

JSR 308 Annotations on Java Types