package net.sourceforge.javautil.groovy.script;
import groovy.lang.Binding;
import groovy.lang.GroovyClassLoader;
import groovy.lang.GroovyObject;
import groovy.lang.Script;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import net.sourceforge.javautil.common.ReflectionUtil;
import net.sourceforge.javautil.common.exception.ThrowableManagerRegistry;
import net.sourceforge.javautil.common.io.ModifiableInputSource;
import net.sourceforge.javautil.common.io.VirtualFile;
import org.codehaus.groovy.control.CompilationFailedException;
/**
* This makes setting up the binding context and invoking a {@link Script} simpler.
*
* @author elponderador
* @author $Author$
* @version $Id$
*/
public class ScriptContext extends Binding {
protected final ModifiableInputSource mis;
protected final GroovyClassLoader gcl;
public ScriptContext(ModifiableInputSource mis) { this(GroovyClassLoader.class.getClassLoader(), mis); }
public ScriptContext(ClassLoader cl, ModifiableInputSource mis) {
this.mis = mis;
this.gcl = new GroovyClassLoader(cl);
}
/**
* @param name The name to bind the object to
* @param object The object to associate with the bound name
* @return This for chaining
*/
public ScriptContext bind (String name, Object object) {
this.setVariable(name, object); return this;
}
public Object run () { return run(Object.class); }
/**
* Run the script with the bindings that have been setup.
*
* @return Whatever is returned by the script execution
*/
public <T> T run (Class<T> type) {
InputStream input = null;
try {
Class<Script> clazz = gcl.parseClass(mis.getInputStream());
Script script = (Script) ReflectionUtil.newInstance(clazz, new Class[0]);
script.setBinding(this);
return (T) script.run();
} catch (CompilationFailedException e) {
throw ThrowableManagerRegistry.caught(e);
} catch (IOException e) {
throw ThrowableManagerRegistry.caught(e);
} finally {
if (input != null) try { input.close(); } catch (IOException e) {
ThrowableManagerRegistry.caught(e);
}
}
}
}