001: /*
002: * All content copyright (c) 2003-2006 Terracotta, Inc., except as may otherwise be noted in a separate copyright notice. All rights reserved.
003: */
004: package com.tc.aspectwerkz.reflect.impl.java;
005:
006: import com.tc.aspectwerkz.reflect.ClassInfo;
007: import com.tc.aspectwerkz.reflect.MethodInfo;
008: import com.tc.aspectwerkz.reflect.ReflectHelper;
009: import com.tc.backport175.bytecode.AnnotationElement;
010:
011: import java.lang.reflect.Method;
012:
013: /**
014: * Implementation of the MethodInfo interface for java.lang.reflect.*.
015: *
016: * @author <a href="mailto:jboner@codehaus.org">Jonas BonŽr </a>
017: */
018: public class JavaMethodInfo extends JavaMemberInfo implements
019: MethodInfo {
020:
021: /**
022: * The return type.
023: */
024: private ClassInfo m_returnType = null;
025:
026: /**
027: * A list with the parameter types.
028: */
029: private ClassInfo[] m_parameterTypes = null;
030:
031: /**
032: * A list with the exception types.
033: */
034: private ClassInfo[] m_exceptionTypes = null;
035:
036: /**
037: * The signature of the method.
038: */
039: private String m_signature;
040:
041: /**
042: * Creates a new method meta data instance.
043: *
044: * @param method
045: * @param declaringType
046: */
047: JavaMethodInfo(final Method method,
048: final JavaClassInfo declaringType) {
049: super (method, declaringType);
050: m_signature = ReflectHelper.getMethodSignature(method);
051: }
052:
053: /**
054: * Returns the method info for the method specified.
055: *
056: * @param method the method
057: * @return the method info
058: */
059: public static MethodInfo getMethodInfo(final Method method) {
060: Class declaringClass = method.getDeclaringClass();
061: JavaClassInfoRepository repository = JavaClassInfoRepository
062: .getRepository(declaringClass.getClassLoader());
063: ClassInfo classInfo = repository.getClassInfo(declaringClass
064: .getName());
065: if (classInfo == null) {
066: classInfo = JavaClassInfo.getClassInfo(declaringClass);
067: }
068: return classInfo.getMethod(ReflectHelper.calculateHash(method));
069: }
070:
071: /**
072: * Returns the signature for the element.
073: *
074: * @return the signature for the element
075: */
076: public String getSignature() {
077: return m_signature;
078: }
079:
080: public String getGenericsSignature() {
081: // XXX implement
082: throw new RuntimeException();
083: }
084:
085: /**
086: * Returns the annotations.
087: *
088: * @return the annotations
089: */
090: public AnnotationElement.Annotation[] getAnnotations() {
091: return getDeclaringType().getAnnotationReader()
092: .getMethodAnnotationElements(m_member.getName(),
093: m_signature);
094: }
095:
096: /**
097: * Returns the return type.
098: *
099: * @return the return type
100: */
101: public ClassInfo getReturnType() {
102: if (m_returnType == null) {
103: Class returnTypeClass = ((Method) m_member).getReturnType();
104: if (m_classInfoRepository.hasClassInfo(returnTypeClass
105: .getName())) {
106: m_returnType = m_classInfoRepository
107: .getClassInfo(returnTypeClass.getName());
108: } else {
109: m_returnType = JavaClassInfo
110: .getClassInfo(returnTypeClass);
111: m_classInfoRepository.addClassInfo(m_returnType);
112: }
113: }
114: return m_returnType;
115: }
116:
117: /**
118: * Returns the parameter types.
119: *
120: * @return the parameter types
121: */
122: public ClassInfo[] getParameterTypes() {
123: if (m_parameterTypes == null) {
124: Class[] parameterTypes = ((Method) m_member)
125: .getParameterTypes();
126: m_parameterTypes = new ClassInfo[parameterTypes.length];
127: for (int i = 0; i < parameterTypes.length; i++) {
128: Class parameterType = parameterTypes[i];
129: ClassInfo metaData;
130: if (m_classInfoRepository.hasClassInfo(parameterType
131: .getName())) {
132: metaData = m_classInfoRepository
133: .getClassInfo(parameterType.getName());
134: } else {
135: metaData = JavaClassInfo
136: .getClassInfo(parameterType);
137: m_classInfoRepository.addClassInfo(metaData);
138: }
139: m_parameterTypes[i] = metaData;
140: }
141: }
142: return m_parameterTypes;
143: }
144:
145: /**
146: * Returns the parameter names as they appear in the source code.
147: * <p/>
148: * This information is not available from Reflect.
149: * We may use ASM to grab it - is that needed ?
150: *
151: * @return null / not supported for now.
152: */
153: public String[] getParameterNames() {
154: return null;
155: }
156:
157: /**
158: * Returns the exception types.
159: *
160: * @return the exception types
161: */
162: public ClassInfo[] getExceptionTypes() {
163: if (m_exceptionTypes == null) {
164: Class[] exceptionTypes = ((Method) m_member)
165: .getExceptionTypes();
166: m_exceptionTypes = new ClassInfo[exceptionTypes.length];
167: for (int i = 0; i < exceptionTypes.length; i++) {
168: Class exceptionType = exceptionTypes[i];
169: ClassInfo metaData;
170: if (m_classInfoRepository.hasClassInfo(exceptionType
171: .getName())) {
172: metaData = m_classInfoRepository
173: .getClassInfo(exceptionType.getName());
174: } else {
175: metaData = JavaClassInfo
176: .getClassInfo(exceptionType);
177: m_classInfoRepository.addClassInfo(metaData);
178: }
179: m_exceptionTypes[i] = metaData;
180: }
181: }
182: return m_exceptionTypes;
183: }
184:
185: public boolean equals(Object o) {
186: if (this == o) {
187: return true;
188: }
189: if (!(o instanceof MethodInfo)) {
190: return false;
191: }
192: MethodInfo methodInfo = (MethodInfo) o;
193: if (!m_declaringType.getName().equals(
194: methodInfo.getDeclaringType().getName())) {
195: return false;
196: }
197: if (!m_member.getName().equals(methodInfo.getName())) {
198: return false;
199: }
200: Class[] parameterTypes1 = ((Method) m_member)
201: .getParameterTypes();
202: ClassInfo[] parameterTypes2 = methodInfo.getParameterTypes();
203: if (parameterTypes1.length != parameterTypes2.length) {
204: return false;
205: }
206: for (int i = 0; i < parameterTypes1.length; i++) {
207: if (!parameterTypes1[i].getName().equals(
208: parameterTypes2[i].getName())) {
209: return false;
210: }
211: }
212: return true;
213: }
214:
215: public int hashCode() {
216: int result = 29;
217: result = (29 * result) + m_declaringType.getName().hashCode();
218: result = (29 * result) + m_member.getName().hashCode();
219: Class[] parameterTypes = ((Method) m_member)
220: .getParameterTypes();
221: for (int i = 0; i < parameterTypes.length; i++) {
222: result = (29 * result)
223: + parameterTypes[i].getName().hashCode();
224: }
225: return result;
226: }
227:
228: public String toString() {
229: return m_member.toString();
230: }
231: }
|