001 /******************************************************************************* 002 * Portions created by Sebastian Thomschke are copyright (c) 2005-2011 Sebastian 003 * Thomschke. 004 * 005 * All Rights Reserved. This program and the accompanying materials 006 * are made available under the terms of the Eclipse Public License v1.0 007 * which accompanies this distribution, and is available at 008 * http://www.eclipse.org/legal/epl-v10.html 009 * 010 * Contributors: 011 * Sebastian Thomschke - initial implementation. 012 *******************************************************************************/ 013 package net.sf.oval.internal.util; 014 015 import java.io.IOException; 016 import java.io.Serializable; 017 import java.lang.reflect.Method; 018 import java.util.WeakHashMap; 019 020 import net.sf.oval.internal.Log; 021 022 /** 023 * Serializable Wrapper for java.lang.reflect.Method objects since they do not implement Serializable 024 * 025 * @author Sebastian Thomschke 026 */ 027 public final class SerializableMethod implements Serializable 028 { 029 private static final Log LOG = Log.getLog(SerializableMethod.class); 030 031 private static final WeakHashMap<Method, SerializableMethod> CACHE = new WeakHashMap<Method, SerializableMethod>(); 032 033 private static final long serialVersionUID = 1L; 034 035 public static SerializableMethod getInstance(final Method method) 036 { 037 /* 038 * intentionally the following code is not synchronized 039 */ 040 SerializableMethod sm = CACHE.get(method); 041 if (sm == null) 042 { 043 sm = new SerializableMethod(method); 044 CACHE.put(method, sm); 045 } 046 return sm; 047 } 048 049 private final Class< ? > declaringClass; 050 private transient Method method; 051 private final String name; 052 053 private final Class< ? >[] parameterTypes; 054 055 private SerializableMethod(final Method method) 056 { 057 this.method = method; 058 name = method.getName(); 059 parameterTypes = method.getParameterTypes(); 060 declaringClass = method.getDeclaringClass(); 061 } 062 063 /** 064 * @return the declaringClass 065 */ 066 public Class< ? > getDeclaringClass() 067 { 068 return declaringClass; 069 } 070 071 /** 072 * @return the method 073 */ 074 public Method getMethod() 075 { 076 return method; 077 } 078 079 /** 080 * @return the name 081 */ 082 public String getName() 083 { 084 return name; 085 } 086 087 /** 088 * @return the parameterTypes 089 */ 090 public Class< ? >[] getParameterTypes() 091 { 092 return parameterTypes; 093 } 094 095 private void readObject(final java.io.ObjectInputStream in) throws IOException, ClassNotFoundException 096 { 097 in.defaultReadObject(); 098 try 099 { 100 method = declaringClass.getDeclaredMethod(name, parameterTypes); 101 } 102 catch (final NoSuchMethodException ex) 103 { 104 LOG.debug("Unexpected NoSuchMethodException occured.", ex); 105 throw new IOException(ex.getMessage()); 106 } 107 } 108 }