Index: org/python/util/JythonTask.java =================================================================== RCS file: org/python/util/JythonTask.java diff -N org/python/util/JythonTask.java --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ org/python/util/JythonTask.java 10 Jan 2004 21:34:03 -0000 @@ -0,0 +1,247 @@ +package org.python.util; + +import org.apache.tools.ant.BuildException; +import org.apache.tools.ant.Task; + +import org.python.util.PythonInterpreter; + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.util.ArrayList; +import java.util.Iterator; +import java.util.Properties; +import java.lang.System; +import org.apache.tools.ant.types.Reference; +import org.apache.tools.ant.types.Path; +import org.apache.tools.ant.Project; + + +/** + * The JythonTask is an Ant task + * that executes a single jython script. To use the task you must + * first define the task with the taskdef element once within the + * build xml file: + *
+ *   <taskdef name="jython" classname="org.python.util.JythonTask"
+ *           classpath="/foo/bar/jython/jython.jar" />
+ * 
+ * The simplest way to run a python script is with the below example + * target. This will execute the foo.py file. From within the python + * script you will be able access any java classes in the ant + * classpath, but no python libraries. Also, a python variable 'var1' + * will be initialized with the value of '123'. + *
+ *    <target name="runjython">
+ *      <jython pythonFile="foo.py">
+ *        <defvar name="var1" value="123" />
+ *      </jython>
+ *    </target>    
+ * 
+ * Additional Examples: + *
+ *      <jython pythonFile="foo.py" jythonHome="/foo/bar/jython">
+ *        <arg value="123" />
+ *        <arg value="456" />
+ *      </jython>
+ * 
+ * Run script foo.py. Set the jythonHome attribute to the + * jython distribution directory. This will allow access to the + * standard python libraries. The arg elements will pass the values + * '123' and '456' as command line parameters to the script. + * sys.argv[1] and sys.argv[2] respectively will contain these values. + *
+ *      <jython pythonFile="foo.py" jythonHome="/foo/bar/jython"
+ *              pythonPath="/foo/bar/mypythonlib">
+ *        <defvar name="var1" value="123" />
+ *      </jython>
+ * 
+ * Using pythonPath will provide jython a path to search for python + * libraries referenced in the script (either .py or .pyc files). + * By setting jythonHome the task will be able to find the standard + * python libraries. Howerver, the standard library directory could + * also be found by the task if the library directory is added to + * pythonPath. + * + * @author Byron Foster (Base2 Corporation ) + */ +public class JythonTask extends Task +{ + + private File pythonFile = null; + private File jythonHome = null; + private Path pythonPath = null; + + private ArrayList varList = new ArrayList(); + private ArrayList argList = new ArrayList(); + private Reference pathRef = null; + + public void execute() throws BuildException + { + // Do some param checking + + if (pythonFile == null) + { + throw new BuildException("Property pythonFile must be set"); + } + else if (!pythonFile.exists()) + { + throw new BuildException("pythonFile: " + pythonFile + "' does not exist"); + } + else if (!pythonFile.canRead()) + { + throw new BuildException("pythonFile '" + pythonFile + + "' exists but it is not readable"); + } + + if (jythonHome != null && !jythonHome.exists()) + { + throw new BuildException("jythonHome: '" + jythonHome + "' does not exist"); + } + + if (pythonPath != null && pathRef != null) + { + throw new BuildException("Attributes pythonPath and pathRef cannot both be set"); + } + + FileInputStream fileStream = null; + try + { + fileStream = new FileInputStream(pythonFile); + } + catch (FileNotFoundException e) + { + // We've already tested above if the file exists, + // and if it is readable so we should never get here! + throw new BuildException(e); + } + + log("Running python script: " + pythonFile, Project.MSG_DEBUG); + log("With arguments:", Project.MSG_DEBUG); + + Properties jyprops = new Properties(); + + //convert list to array of strings. + String argv[] = new String[argList.size()+1]; + argv[0] = pythonFile.getPath(); + for (int i=argList.size()-1; i >= 0; i--) + { + JythonTaskArg arg = (JythonTaskArg)argList.get(i); + argv[i+1] = arg.getValue(); + log("arg " + i + ": " + argv[i], Project.MSG_DEBUG); + } + + if (jythonHome == null) + { + // if jython home is not defined then place the cached directory + // in the same directory as the build script, otherwise jython + // will place the cache directory in home. + jyprops.put("python.cachedir", ".jythoncache"); + log("property python.path: " + + jyprops.getProperty("python.cachedir"), Project.MSG_DEBUG); + } + else + { + jyprops.put("python.home", jythonHome.getAbsolutePath()); + log("property python.home: '" + jythonHome.getAbsolutePath() + + "'", Project.MSG_DEBUG); + } + + // If the user has defined PythonPathRef then use it for the + // python.path, else use the system classpath. + if (pathRef != null) + { + Path pypath = new Path(getProject()); + pypath.setRefid(pathRef); + jyprops.put("python.path", pypath.toString()); + } + else if (pythonPath != null) + { + jyprops.put("python.path", pythonPath.toString()); + } + else + { + jyprops.put("python.path", System.getProperty("java.class.path")); + } + + log("property python.path: " + jyprops.getProperty("python.path"), Project.MSG_DEBUG); + + PythonInterpreter.initialize(System.getProperties(), jyprops, argv); + + PythonInterpreter interpreter = new PythonInterpreter(); + + // read the defined variables specified in the ant script and + // add them to the interpreter. + Iterator itr = varList.iterator(); + while (itr.hasNext()) + { + JythonTaskVar element = (JythonTaskVar) itr.next(); + log("defined var name: " + + element.getName() + + " value: " + + element.getValue(), Project.MSG_DEBUG); + interpreter.set(element.getName(), element.getValue()); + } + + interpreter.execfile(fileStream); + } + + /** + * Path to the python script to run. Required + */ + public void setPythonFile(File file) + { + pythonFile = file; + } + + /** + * Python path consisting either of directories or jar files that + * contain python files to load. The pythonPath and pythonPathRef + * attributes cannot both be set. Not Required + */ + public void setPythonPath(Path path) + { + pythonPath = path; + } + + /** + * Directory of a Jython distribution. Not Required. + */ + public void setJythonHome(File file) + { + jythonHome = file; + } + + /** + * For the nested <defvar name="foo" value="bar"> element. The defvar + * element Defines initial variable names and values for the python + * script. See the class documentation for examples. + */ + public void addDefvar(JythonTaskVar variable) + { + varList.add(variable); + } + + /** + * For the nested <arg value="foo"> element. The arg element + * defines arguments that are passed to the python script as command + * line arguments. These argument can then be read from within the + * script with the sys.argv list. + */ + public void addArg(JythonTaskArg arg) + { + argList.add(arg); + } + + /** + * A path reference to be used as the python path. The python path + * consists of directories or jar files that + * contain python files to load. The pythonPath and pythonPathRef + * attributes cannot both be set. Not Required + */ + public void setPythonPathRef(Reference r) + { + pathRef = r; + } + +} Index: org/python/util/JythonTaskArg.java =================================================================== RCS file: org/python/util/JythonTaskArg.java diff -N org/python/util/JythonTaskArg.java --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ org/python/util/JythonTaskArg.java 10 Jan 2004 21:34:03 -0000 @@ -0,0 +1,22 @@ +package org.python.util; + +/** + * We use this class to read in variable inner elements + * of the JythonTask + * @author Byron Foster (Base2 Corporation ) + */ +public class JythonTaskArg +{ + private String arg = null; + + public String getValue() + { + return arg; + } + + public void setValue(String arg) + { + this.arg = arg; + } +} + Index: org/python/util/JythonTaskVar.java =================================================================== RCS file: org/python/util/JythonTaskVar.java diff -N org/python/util/JythonTaskVar.java --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ org/python/util/JythonTaskVar.java 10 Jan 2004 21:34:03 -0000 @@ -0,0 +1,46 @@ +package org.python.util; + +/** + * We use this class to read in variable inner elements + * of the JythonTask + * @author Byron Foster (Base2 Corporation ) + */ +public class JythonTaskVar +{ + private String name = null; + private String value = null; + /** + * @return String + */ + public String getName() + { + return name; + } + + /** + * Sets the name. + * @param name The name to set + */ + public void setName(String name) + { + this.name = name; + } + + /** + * @return String + */ + public String getValue() + { + return value; + } + + /** + * Sets the value. + * @param value The value to set + */ + public void setValue(String value) + { + this.value = value; + } + +}