/************************************************************************************** * Copyright (c) Jonas Bon?r, Alexandre Vasseur. All rights reserved. * * http://aspectwerkz.codehaus.org * * ---------------------------------------------------------------------------------- * * The software in this package is published under the terms of the LGPL license * * a copy of which has been included with this distribution in the license.txt file. * **************************************************************************************/ package test.aopc; import org.codehaus.aspectwerkz.exception.WrappedRuntimeException; import java.io.File; import java.lang.reflect.Array; import java.lang.reflect.Method; import java.net.MalformedURLException; import java.net.URL; import java.net.URLClassLoader; /** * Test helper for AspectContainer, emulates a ClassLoader hierarchy sys/sub/ sys/sub/a sys/sub/b * * FIXME - rewrite with ASM * * @author <a href="mailto:alex@gnilux.com">Alexandre Vasseur </a> */ public class ClassCreator { /** * ClassLoader.defineClass(name, bytes, from, to) */ private static Method CLASSLOADER_DEFINECLASS_METHOD; static { try { Object b = Array.newInstance(byte.class, 1); CLASSLOADER_DEFINECLASS_METHOD = ClassLoader.class.getDeclaredMethod( "defineClass", new Class[]{ String.class, b.getClass(), int.class, int.class } ); CLASSLOADER_DEFINECLASS_METHOD.setAccessible(true); } catch (Throwable t) { t.printStackTrace(); } } public static Object createInstance(String name, Class classPrototype, ClassLoader loader) { try { return createClass(name, classPrototype, loader).newInstance(); } catch (Throwable t) { throw new WrappedRuntimeException(t); } } public static Class createClass(String name, Class classPrototype, ClassLoader loader) { return classPrototype; // try { // ClassPool cp = new ClassPool(null); // cp.appendClassPath(new LoaderClassPath(loader)); // CtClass prototype = cp.get(classPrototype.getName()); // prototype.setName(name); // return define(prototype.toBytecode(), name, loader); // } catch (Throwable throwable) { // throw new WrappedRuntimeException(throwable); // } } public static void main(String[] a) throws Throwable { ClassLoader myCL = new URLClassLoader( new URL[]{ getPathFor(Callable.class.getResource("META-INF/aop.xml")) }, ClassLoader.getSystemClassLoader() ); ClassLoader mySubCLA = new URLClassLoader( new URL[]{ getPathFor(Callable.class.getResource("a/META-INF/aop.xml")) }, myCL ); Callable ca = (Callable) (createClass("test.aopc.a.Callee", CallablePrototype.class, mySubCLA)).newInstance(); ca.methodAround(); ca.debug(); ClassLoader mySubCLB = new URLClassLoader(new URL[]{}, myCL); Callable cb = (Callable) (createClass("test.aopc.b.Callee", CallablePrototype.class, mySubCLB)).newInstance(); cb.methodAround(); cb.debug(); } public static URL getPathFor(URL definition) { try { System.out.println(definition); System.out.println(definition.getFile()); File f = new File(definition.getFile()); if (!f.exists()) { System.err.println("<WARN> could not find " + f); } String path = new File(f.getParent()).getParent(); File testExists = new File(path); if (!testExists.isDirectory()) { System.err.println("<WARN> could not find " + path); } return new File(path).toURL(); } catch (MalformedURLException e) { throw new WrappedRuntimeException(e); } } /** * Helper to define a Class within a specific ClassLoader * * @param b * @param name * @param loader * @return @throws Throwable */ public static Class define(byte[] b, String name, ClassLoader loader) throws Throwable { Object k = CLASSLOADER_DEFINECLASS_METHOD.invoke( loader, new Object[]{ name, b, new Integer(0), new Integer(b.length) } ); return (Class) k; } }