
de.saumya.mojo.ruby.script.ScriptFactory Maven / Gradle / Ivy
/**
*
*/
package de.saumya.mojo.ruby.script;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.codehaus.classworlds.ClassRealm;
import org.codehaus.classworlds.DuplicateRealmException;
import org.codehaus.classworlds.NoSuchRealmException;
import de.saumya.mojo.ruby.Logger;
import de.saumya.mojo.ruby.ScriptUtils;
public class ScriptFactory {
public static List NO_CLASSPATH = Collections.emptyList();
final Arguments switches = new Arguments();
final Arguments jvmArgs = new Arguments();
private final Map env = new HashMap();
final File jrubyStdlibJar;
final Logger logger;
final ClassRealm classRealm;
final File jrubyJar;
final List classpathElements;
final boolean fork;
final Launcher launcher;
public ScriptFactory(final Logger logger, final ClassRealm classRealm,
final File jrubyJar,
final List classpathElements, final boolean fork) throws ScriptException, IOException {
this(logger, classRealm, jrubyJar, jrubyJar, classpathElements, fork);
}
public ScriptFactory(final Logger logger, final ClassRealm classRealm,
final File jrubyJar, File stdlibJar,
final List classpathElements, final boolean fork) throws ScriptException, IOException {
this.logger = logger;
this.jrubyStdlibJar = stdlibJar;
this.jrubyJar = jrubyJar;
if(this.jrubyJar != null){
this.logger.debug("script uses jruby jar:" + this.jrubyJar.getAbsolutePath());
}
this.classpathElements = classpathElements == null
? NO_CLASSPATH
: Collections.unmodifiableList(classpathElements);
this.fork = fork;
if (classRealm != null && jrubyJar != null) {
this.classRealm = getOrCreateClassRealm(classRealm, jrubyJar);
}
else {
this.classRealm = classRealm;
}
if (fork) {
this.launcher = new AntLauncher(logger, this);
}
else {
this.launcher = new EmbeddedLauncher(logger, this);
}
}
private static synchronized ClassRealm getOrCreateClassRealm(final ClassRealm classRealm, final File jrubyJar) throws MalformedURLException, ScriptException {
ClassRealm jruby;
try {
jruby = classRealm.getWorld().getRealm("jruby");
}
catch (final NoSuchRealmException e) {
try {
jruby = classRealm.getWorld().newRealm("jruby");
if(jrubyJar != null){
jruby.addConstituent(jrubyJar.toURI().toURL());
}
}
catch (final DuplicateRealmException ee) {
throw new ScriptException("could not setup classrealm for jruby",
ee);
}
}
return jruby;
}
public Script newScriptFromSearchPath(final String scriptName)
throws IOException {
return new Script(this, scriptName, true);
}
public Script newScriptFromJRubyJar(final String scriptName)
throws IOException {
try {
// the first part only works on jruby-complete.jar
URL url = new URL("jar:file:"
+ this.jrubyStdlibJar.getAbsolutePath()
+ "!/META-INF/jruby.home/bin/" + scriptName);
url.openConnection().getContent();
return new Script(this, url);
}
catch (Exception e) {
try {
// fallback on classloader
return newScriptFromResource("META-INF/jruby.home/bin/" + scriptName);
}
catch (FileNotFoundException ee) {
// find jruby-home
String base = ".";
if ( this.env.containsKey( "JRUBY_HOME" ) ) {
base = this.env.get( "JRUBY_HOME" );
}
else if ( System.getProperty( "jruby.home" ) != null ) {
base = System.getProperty( "jruby.home" );
}
else {
for( String arg : this.jvmArgs.list ){
if (arg.startsWith("-Djruby.home=")){
base = arg.substring("-Djruby.home=".length());
break;
}
}
}
File f = new File( base, new File( "bin", scriptName ).getPath() );
if ( f.exists() ){
return new Script(this, f);
}
else {
throw ee;
}
}
}
}
public Script newScriptFromResource(final String scriptName)
throws IOException {
URL url = this.classRealm != null ? this.classRealm.getClassLoader()
.getResource(scriptName) : null;
if (url == null) {
url = ScriptUtils.getScriptFromResource(scriptName);
}
if (url.getProtocol().equals("file")) {
return new Script(this, url.getPath(), false);
}
else {
return new Script(this, url);
}
}
public Script newArguments() {
return new Script(this);
}
public Script newScript(final String script) throws IOException {
return new Script(this, script);
}
public Script newScript(final File file) {
return new Script(this, file);
}
public void addJvmArgs(final String args) {
this.jvmArgs.parseAndAdd(args);
}
public void addSwitch(final String name) {
this.switches.add(name);
}
public void addSwitch(final String name, final String value) {
this.switches.add(name, value);
}
public void addSwitches(final String switches) {
this.switches.parseAndAdd(switches);
}
public void addEnv(final String name, final File value) {
if (value != null) {
this.env.put(name, value.getAbsolutePath());
}
else {
this.env.put(name, null);
}
}
public Map environment(){
return env;
}
public void addEnv(final String name, final String value) {
this.env.put(name, value);
}
public void addEnvs(final String environmentVars) {
for (final String var : environmentVars.split("\\s+")) {
final int index = var.indexOf("=");
if (index > -1) {
this.env.put(var.substring(0, index), var.substring(index + 1));
}
}
}
@Override
public String toString() {
// TODO
final StringBuilder buf = new StringBuilder(getClass().getName());
// for (final String arg : this.switches) {
// buf.append(arg).append(" ");
// }
return buf.toString().trim();
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy