// 
//     Licensed to the Apache Software Foundation (ASF) under one
//     or more contributor license agreements.  See the NOTICE file
//     distributed with this work for additional information
//     regarding copyright ownership.  The ASF licenses this file
//     to you under the Apache License, Version 2.0 (the
//     "License"); you may not use this file except in compliance
//     with the License.  You may obtain a copy of the License at
// 
//       http://www.apache.org/licenses/LICENSE-2.0
// 
//     Unless required by applicable law or agreed to in writing,
//     software distributed under the License is distributed on an
//     "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
//     KIND, either express or implied.  See the License for the
//     specific language governing permissions and limitations
//     under the License.
//

= Annotations Part II: Using Custom Annotation Processors
:jbake-type: tutorial
:jbake-tags: tutorials 
:jbake-status: published
:icons: font
:syntax: true
:source-highlighter: pygments
:toc: left
:toc-title:
:description: Annotation Processors Support in the NetBeans IDE, Part II: Using Own Custom Annotation Processors in the IDE - Apache NetBeans
:keywords: Apache NetBeans, Tutorials, Annotation Processors Support in the NetBeans IDE, Part II: Using Own Custom Annotation Processors in the IDE

The previous part of the annotations tutorial (link:annotations-lombok.html[Part I: Using Lombok for Custom Annotations]) showed how custom annotations work within NetBeans.

In this section of the tutorial, you will learn how to add a self-written custom annotation processor to a project in the IDE. This tutorial does not teach you how to write an annotation processor. It explains how to add it to a NetBeans IDE project.

The sample application used in this section was created by Jesse Glick and published as an link:http://wiki.netbeans.org/FaqApt[+FAQ entry+] for the previous IDE releases.

The annotation processor used as the example generates a parent class for the annotated class. The generated parent class also contains a method that is called from the annotated class. Follow the instructions below on how to create and add a custom annotation processor to an IDE's project.

== Requirements

To complete this tutorial, you need the following software and resources.

[cols="3,1"]
|===
|Software or Resource |Version Required 

|link:https://netbeans.org/download/index.html[+NetBeans IDE+] | 9.0 or greater

|link:http://www.oracle.com/technetwork/java/javase/downloads/index.html[+Java Development Kit (JDK)+] |version 6 or greater

|link:http://code.google.com/p/projectlombok/downloads/list[+lombok.jar+] |v1.12.4 or newer 
|===


== Defining an Annotation and Creating an Annotation Processor

In this exercise you will create a class library project.

1. Choose File > New Project and select the Java Class Library project type in the Java category. Click Next.
2. Type ``AnnProcessor`` as the Project Name and specify a location for the project. Click Finish.

When you click Finish, the IDE creates the class library project and lists the project in the Projects window.




. Right-click the AnnProcessor project node in the Projects window and choose Properties.


. In the Sources category, confirm that either JDK 6 or JDK 7 are specified as the source/binary format.


. Select the Libraries tab and confirm that the Java platform is set to either JDK 1.6 or JDK 1.7. Click OK to close the Project Properties window.

In this exercise you will create two Java packages and one Java class in each of the packages.

1. Right-click the Source Packages node under the AnnProcessor project node and choose New > Java Package.
2. Type ``ann`` for the Package Name and click Finish to create the new Java package.
3. Repeat the two previous steps to create a Java package named ``proc``.

After you create the two Java packages, the structure of the project should be similar to the following image.

image::images/packages.png[title="The structure of the project for the annotation processor."]




. Right-click the  ``ann``  Java package and choose New > Java class.


. Type ``Handleable`` for the Class Name. Click Finish.


. Modify the new  ``Handleable.java``  file to make the following changes. Save the file.

[source,java]
----

package ann;

public @interface Handleable {

}
----

This is how annotations are declared, and it is quite similar to an interface declaration. The difference is that the  ``interface``  keyword must be preceded with an  ``at``  sign (@). This annotation is called  ``Handleable`` .

TIP: In annotation declarations, you can also specify additional parameters, for example, what types of elements can be annotated, e.g. classes or methods. You do this by adding  ``@Target(value = {ElementType.TYPE})``  for classes and  ``@Target(value = {ElementType.METHOD}).``  So, the annotation declaration becomes annotated itself with _meta-annotations_.

You now need to add code for the annotation processor to process the  ``Handleable``  annotation.




. Right-click the ``proc`` Java package and choose New > Java class.


. Type ``HandleableProcessor`` for the Class Name. Click Finish.


. Modify the  ``HandleableProcessor.java``  class to add the following code. Save your changes.

NOTE: The value of  ``@SupportedSourceVersion``  will depend upon the version of the JDK that you are using and will be either  ``(SourceVersion.RELEASE_7)``  or  ``(SourceVersion.RELEASE_6)`` .


[source,java]
----

package proc;

import ann.Handleable;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.Writer;
import java.util.Set;
import javax.annotation.processing.AbstractProcessor;
import javax.annotation.processing.RoundEnvironment;
import javax.annotation.processing.SupportedAnnotationTypes;
import javax.annotation.processing.SupportedSourceVersion;
import javax.lang.model.SourceVersion;
import javax.lang.model.element.Element;
import javax.lang.model.element.ElementKind;
import javax.lang.model.element.TypeElement;
import javax.lang.model.type.TypeMirror;
import javax.tools.Diagnostic;
import javax.tools.JavaFileObject;

@SupportedAnnotationTypes("ann.Handleable")
@SupportedSourceVersion(SourceVersion.RELEASE_7)
public class HandleableProcessor extends AbstractProcessor {

    /** public for ServiceLoader */
    public HandleableProcessor() {
    }

    public boolean process(Set<? extends TypeElement> annotations,
            RoundEnvironment roundEnv) {
        for (Element e : roundEnv.getElementsAnnotatedWith(Handleable.class)) {
            if (e.getKind() != ElementKind.FIELD) {
                processingEnv.getMessager().printMessage(
                        Diagnostic.Kind.WARNING,
                        "Not a field", e);
                continue;
            }
            String name = capitalize(e.getSimpleName().toString());
            TypeElement clazz = (TypeElement) e.getEnclosingElement();
            try {
                JavaFileObject f = processingEnv.getFiler().
                        createSourceFile(clazz.getQualifiedName() + "Extras");
                processingEnv.getMessager().printMessage(Diagnostic.Kind.NOTE,
                        "Creating " + f.toUri());
                Writer w = f.openWriter();
                try {
                    PrintWriter pw = new PrintWriter(w);
                    pw.println("package "
                            + clazz.getEnclosingElement().getSimpleName() + ";");
                    pw.println("public abstract class "
                            + clazz.getSimpleName() + "Extras {");
                    pw.println("    protected " + clazz.getSimpleName()
                            + "Extras() {}");
                    TypeMirror type = e.asType();
                    pw.println("    /** Handle something. */");
                    pw.println("    protected final void handle" + name
                            + "(" + type + " value) {");
                    pw.println("        System.out.println(value);");
                    pw.println("    }");
                    pw.println("}");
                    pw.flush();
                } finally {
                    w.close();
                }
            } catch (IOException x) {
                processingEnv.getMessager().printMessage(Diagnostic.Kind.ERROR,
                        x.toString());
            }
        }
        return true;
    }

    private static String capitalize(String name) {
        char[] c = name.toCharArray();
        c[0] = Character.toUpperCase(c[0]);
        return new String(c);
    }
}
----

Let's take a closer look at the main parts that constitute the code for the annotation processor (note that for convenience, only parts of the code are provided).

At first, you specify the annotation types that the annotation processor supports (by using  ``@SupportedAnnotationTypes`` ) and the version of the source files that are supported (by using  ``@SupportedSourceVersion`` ), in this case the version is JDK 6: 


[source,java]
----

@SupportedAnnotationTypes("ann.Handleable")
@SupportedSourceVersion(SourceVersion.RELEASE_6)
----

Then, you declare a public class for the processor that extends the  ``AbstractProcessor``  class from the  ``javax.annotation.processing``  package.  ``AbstractProcessor``  is a standard superclass for concrete annotation processors that contains necessary methods for processing annotations.


[source,java]
----

public class HandleableProcessor extends AbstractProcessor {
...
}
----

You now need to provide a public constructor for the class.


[source,java]
----

public class HandleableProcessor extends AbstractProcessor {
  public HandleableProcessor() {
  }
...

}
----

Then, you call the  ``process`` () method of the parent  ``AbstractProcessor``  class. Through this method the annotations available for processing are provided. In addition, this method contains information about the round of processing.


[source,java]
----

public class HandleableProcessor extends AbstractProcessor {
   ...
   public boolean process(Set<? extends TypeElement> annotations,
            RoundEnvironment roundEnv) {
     ...
     }
}
----

The annotation processor's logic is contained within the  ``process()``  method of the  ``AbstractProcessor``  class. Note that through  ``AbstractProcessor`` , you also access the  ``ProcessingEnvironment``  interface, which allows annotation processors to use several useful facilities, such as Filer (a filer handler that enables annotation processors to create new files) and Messager (a way for annotation processors to report errors).


[source,java]
----

public class HandleableProcessor extends AbstractProcessor {
   ...
     public boolean process(Set<? extends TypeElement> annotations,
            RoundEnvironment roundEnv) {//For each element annotated with the Handleable annotation
            for (Element e : roundEnv.getElementsAnnotatedWith(Handleable.class)) {

// Check if the type of the annotated element is not a field. If yes, return a warning.
if (e.getKind() != ElementKind.FIELD) {
processingEnv.getMessager().printMessage(
Diagnostic.Kind.WARNING,
"Not a field", e);
continue;
}
            //Define the following variables: name and clazz.
String name = capitalize(e.getSimpleName().toString());
TypeElement clazz = (TypeElement) e.getEnclosingElement();
//Generate a source file with a specified class name. 
            try {
JavaFileObject f = processingEnv.getFiler().
createSourceFile(clazz.getQualifiedName() + "Extras");
processingEnv.getMessager().printMessage(Diagnostic.Kind.NOTE,
"Creating " + f.toUri());
Writer w = f.openWriter();
//Add the content to the newly generated file.
                    try {
PrintWriter pw = new PrintWriter(w);
pw.println("package "
+ clazz.getEnclosingElement().getSimpleName() + ";");
pw.println("public abstract class "
+ clazz.getSimpleName() + "Extras {");
pw.println("    protected " + clazz.getSimpleName()
+ "Extras() {}");
TypeMirror type = e.asType();
pw.println("    /** Handle something. */");
pw.println("    protected final void handle" + name
+ "(" + type + " value) {");
pw.println("        System.out.println(value);");
pw.println("    }");
pw.println("}");
pw.flush();
} finally {
w.close();
}
} catch (IOException x) {
processingEnv.getMessager().printMessage(Diagnostic.Kind.ERROR,
x.toString());
}
}return true;
     }
...
}
----

The last block in this code declares the  ``capitalize``  method that is used to capitalize the name of the annotated element.


[source,java]
----

public class HandleableProcessor extends AbstractProcessor {
   ...

  private static String capitalize(String name) {
    char[] c = name.toCharArray();
    c[0] = Character.toUpperCase(c[0]);
    return new String(c);
  }
}
----




. Build the project by right-clicking the  ``AnnProcessor``  project and choosing Build.


== Using the Annotation Processor in the IDE

In this section you will create a Java Application project in which the annotation processor will be used.

1. Choose File > New Project and select the Java Application project type in the Java category. Click Next.
2. In the Name and Location page, type ``Demo`` as the Project Name and specify the project location.
3. Type ``demo.Main`` in the Create Main Class field. Click Finish.

image::images/demo-project-wizard.png[title="Creating the Demo project in the New Project wizard."]




. Open the Project Properties window and confirm that either JDK 6 or JDK 7 are selected as the source/binary format in the Sources panel and that the Java platform is set to JDK 1.6 or JDK 1.7 in the Libraries panel.


. Modify the  ``Main.java``  class to add the following code. Save your changes.

[source,java]
----

package demo;

import ann.Handleable;

public class Main extends MainExtras {

    @Handleable
    private String stuff;

    public static void main(String[] args) {
        new Main().handleStuff("hello");
    }
}
----

This code contains the following elements:

* import statement for the custom annotation processor  ``ann.Handleable`` 
* the public class  ``Main``  that extends the  ``MainExtras``  class ( ``MainExtras``  should be generated by the annotation processor during compilation)
* a private field named  ``stuff``  that is annotated with the  ``@Handleable``  annotation
* the  ``main``  method that calls the  ``handleStuff``  method, which is declared in the automatically generated  ``MainExtras``  class

In this simple example, the  ``handleStuff``  method only prints out the current value. You can modify this method to perform other tasks.

After you save the  ``Main.java``  code you will see that the IDE reports multiple compilation errors. This is because the annotation processor has not been added yet to the project.




. Right-click the  ``Demo``  project node in the Projects window, choose Properties, then select the Libraries category in the Project Properties window.


. In the Compile tab, click Add Project and locate the  ``AnnProcessor``  project.

image::images/demo-properties-compile.png[title="Compile tab in Libraries category of the project's Properties window"]

The Compile tab corresponds to the  ``-classpath``  option of the link:http://download.oracle.com/javase/6/docs/technotes/tools/windows/javac.html#options[+Java compiler+]. Because the annotation processor is a single JAR file that contains both the annotation definition and the annotation processor, you should add it to the project's classpath, which is the Compile tab.




. Select the Compiling category in the Project Properties window and select the Enable Annotation Processing and Enable Annotation Processing in Editor checkboxes.


. Specify the annotation processor to run by click the Add button next to the Annotation Processors text area and typing * ``proc.HandleableProcessor`` * in the Annotation Processor FQN field. 

image::images/demo-processor-fqn.png[title="Annotation Processor FQN dialog box"]

The Compiling category in the Project Properties window should look like the following image.

image::images/demo-properties-compiling.png[title="Compiling category in the project's Properties window"]




. Click OK in the Properties window.

NOTE: In the  ``Main.java``  file you might still see compilation errors. This is because the IDE cannot yet find the  ``MainExtras.java``  file that declares the  ``handleStuff``  method. The  ``MainExtras.java``  file will be generated after you build the Demo project for the first time. If Compile On Save is enabled for you project, the IDE compiled the project when you saved  ``Main.java`` .




. Right-click the Demo project and choose Build.

After you build the project, if you look at the project in the Projects window you can see a new  ``Generated Sources``  node with the  ``demo/MainExtras.java``  file.

image::images/demo-generated-sources.png[title="Projects window with Generated Sources"]

If you review the contents of the generated  ``MainExtras.java``  file, you can see that the annotation processor generated the  ``MainExtras``  class with the  ``handleStuff``  method. The  ``handleStuff``  method is the one invoked from the annotated  ``Main.java``  file.


[source,java]
----

package demo;
public abstract class MainExtras {
    protected MainExtras() {}
    /** Handle something. */
    protected final void handleStuff(java.lang.String value) {
        System.out.println(value);
    }
}
----




. Right-click the Demo project and choose Run.

When you click Run you should see the following in the Output window. The Demo project compiles and prints the message.

image::images/demo-run.png[title="Projects window with Generated Sources"]

== See Also

See the following resources for more information about annotations in Java applications:

* The previous part of the annotations tutorial: link:annotations-lombok.html[Part I: Using Lombok for Custom Annotations]).
* Java SE Documentation - link:http://download.oracle.com/javase/6/docs/technotes/guides/language/annotations.html[+Annotations+]
* Java SE Tutorial - link:http://download.oracle.com/javase/tutorial/java/javaOO/annotations.html[+Annotations+]
* link:http://download.oracle.com/javase/6/docs/technotes/tools/windows/javac.html#processing[+Java Compiler: Annotation Processing Options+]
* link:http://blogs.oracle.com/darcy/[+Joseph D. Darcy's Weblog+] - useful tips from the JSR-269 specification lead

