View Javadoc
1   /*
2    * Copyright (C) 2008 the original author or authors.
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    *     http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   */
16  
17  package org.codehaus.plexus.metadata.ann;
18  
19  import java.lang.reflect.InvocationHandler;
20  import java.lang.reflect.Method;
21  import java.net.URL;
22  import java.net.URLClassLoader;
23  import java.util.Arrays;
24  import java.util.Map;
25  
26  import org.objectweb.asm.Type;
27  
28  /**
29   * @author Eugene Kuleshov
30   */
31  public class AnnInvocationHandler implements InvocationHandler {
32      private final Ann ann;
33      private final ClassLoader cl;
34      private final Class<?> c;
35  
36      public AnnInvocationHandler(Ann ann, ClassLoader cl, Class<?> c) {
37          this.ann = ann;
38          this.cl = cl;
39          this.c = c;
40      }
41  
42      public Object invoke(Object proxy, Method m, Object[] args) throws Throwable {
43          String name = m.getName();
44  
45          if ("toString".equals(name)) {
46              StringBuilder sb = new StringBuilder(ann.getType());
47              sb.append("[");
48              String sep = "";
49              for (Map.Entry<String, Object> e : ann.getParams().entrySet()) {
50                  // TODO conversion for class, array, enum, and annotation types
51                  sb.append(sep).append(e.getKey()).append("=").append(e.getValue());
52                  sep = "; ";
53              }
54              sb.append("]");
55              return sb.toString();
56          }
57  
58          Object value = ann.getParams().get(name);
59          if (value != null) {
60              if (value instanceof Type) {
61                  String className = ((Type) value).getClassName();
62                  try {
63                      return Class.forName(className, false, cl);
64                  } catch (ClassNotFoundException ex) {
65                      if (cl instanceof URLClassLoader) {
66                          URL[] urls = ((URLClassLoader) cl).getURLs();
67                          throw new RuntimeException(
68                                  "Unable to load class " + className + " from " + Arrays.toString(urls), ex);
69                      }
70                      throw new RuntimeException("Unable to load class " + className + " from " + cl, ex);
71                  }
72              }
73              // TODO conversion for class, array, enum, and annotation types
74              return value;
75          } else {
76              Method am = c.getDeclaredMethod(m.getName(), m.getParameterTypes());
77              return am.getDefaultValue();
78          }
79      }
80  }