# Werte einer Java 5 Annotation zur Laufzeit ändern.



## Thomas Darimont (22. Oktober 2006)

Hallo!

here is another funny hack 

```
package de.tutorials.training;
 
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import java.lang.reflect.Field;
import java.lang.reflect.Proxy;
import java.util.HashMap;
import java.util.Map;
 
public class AnnotationValueChangeExample {
 
    public static void main(String[] args) {
        Foo foo = new Foo();
        
        System.out.println(foo.getClass().isAnnotationPresent(SomeAnnotation.class));
        
        SomeAnnotation someAnnotation = foo.getClass().getAnnotation(SomeAnnotation.class);
        System.out.println(someAnnotation);
        changeValuesOfAnnotation(someAnnotation, new HashMap<String, String>(){{put("value", "Test2");}});
        System.out.println(foo.getClass().getAnnotation(SomeAnnotation.class));
    }
 
    private static void changeValuesOfAnnotation(
            Object someAnnotation,
            Map<String, String> newValues) {
        if (Proxy.isProxyClass(someAnnotation.getClass())) {
            Object invocationHandler = Proxy.getInvocationHandler(someAnnotation);
            try {
                Field field = invocationHandler.getClass().getDeclaredField("memberValues");
                field.setAccessible(true);
                field.set(invocationHandler, newValues);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
 
    @SomeAnnotation("Test")
    static class Foo {
    }
 
    @Target(ElementType.TYPE)
    @Retention(RetentionPolicy.RUNTIME)
    static @interface SomeAnnotation {
        String value();
    }
 
}
```

Ausgabe:

```
true
@de.tutorials.training.AnnotationValueChangeExample$SomeAnnotation(value=Test)
@de.tutorials.training.AnnotationValueChangeExample$SomeAnnotation(value=Test2)
```

Gruß Tom


----------



## kopfpilot (13. Juni 2013)

Der Beitrag ist etwas älter, aber dennoch excellent 

Nachdem die Manipulation von Klassen Annotationen damit wunderbar bedient wird.
Frage ich mich wie das ganze für Methoden aussieht.

Klasse Foo mit annotierter Methode:

```
@SomeAnnotation("Test")
    static class Foo {
          @AnnotherAnnotation(value = "test.csv")
          public void method(){};
    }
```

Annotation für die Methode:

```
@Retention(RetentionPolicy.RUNTIME)
    static @interface AnnotherAnnotation{
        String value();
    }
```

Test:

```
public void overrideAnnotation() {
        //set annotation
        for (Method m : this.getClass().getDeclaredMethods()) {
            if (m.isAnnotationPresent(AnotherAnnotation.class)) {
                Annotation annotation = m.getAnnotation(AnotherAnnotation.class);
                System.out.println(annotation);
                Map<String,Object> newValues = new LinkedHashMap<String,Object>();
                newValues.put("value", "new.csv");
                ModifyAnnotationValues.changeValueOfAnnotation(annotation, newValues);
                System.out.println(annotation);
            }
        }
        // re-read annotation value
        for (Method m : this.getClass().getDeclaredMethods()) {
            if (m.isAnnotationPresent(AnotherAnnotation.class)) {
                Annotation annotation = m.getAnnotation(myAnnotation.class);
                System.out.println(annotation);
            }
        }
    }
```

Output:

```
@package.AnotherAnnotation(value=test.csv)         // Wert der Annotattion vor set 
@package.AnotherAnnotation(value=new.csv)        // Wert der Annotation nach set
@package.AnotherAnnotation(value=test.csv)        // Wert der Annotation nach wiederholtem einlesen
```

Kann mir jmd sagen, warum das setzen der Annotions-Werte bei einer Klasse funktioniert, aber bei einer annotierten Methode nicht?

Gruß,
kopfpilot


----------

