Hi,

initially I just wanted to fix an annoying NPE but then I stumbled across bug 1523582 [1]. For some reason which is still unknown to me the parameter string (although quoted correctly by pydev) does not make it to python.

To be more exact, the string gets through but the quoting is missing so Python complains that it can't find the script file which is used to detect Python's library directories. This is not bound to path names which contain spaces, a command line like 'python -c "import sys; print sys.path"' doesn't work either (syntax error after "import"). I always

Fortunately the solution is quite easy: Do not munge the command line parameters (which are available as a String[]) into a String but pass them as String[]. If you do this, there is no problem as the command line parameters will not be split (getRuntime().exec is not a shell).

Generally speaking it is much better (safer) not to munge parameters but just
to pass them to the exec call.

With the patch attached I can launch Eclipse and configure the Python interpreter. Without the patch I always the error described in [1]. The code has be cleaned up a bit but I was not sure what coding style etc. you guys prefer. Furthermore I did not get the tests to run (some setup problem on my side) so maybe I broke something.

happy hacking,

[1]http://sourceforge.net/tracker/index.php?func=detail&aid=1523582&group_id=85796&atid=577329

--
Felix Schwarz
Dipl.-Informatiker

Gubener Str. 38
10243 Berlin
Germany

www.schwarz.eu - software development and consulting

### Eclipse Workspace Patch 1.0
#P org.python.pydev
Index: src/org/python/pydev/runners/SimpleRunner.java
===================================================================
RCS file: /cvsroot/pydev/org.python.pydev/src/org/python/pydev/runners/SimpleRunner.java,v
retrieving revision 1.22
diff -u -r1.22 SimpleRunner.java
--- src/org/python/pydev/runners/SimpleRunner.java	13 Apr 2008 16:55:23 -0000	1.22
+++ src/org/python/pydev/runners/SimpleRunner.java	11 May 2008 23:23:08 -0000
@@ -303,19 +303,10 @@
         return runAndGetOutput(script, args, workingDir, null);
     }
 
-    /**
-     * This is the method that actually does the running (all others are just 'shortcuts' to this one).
-     * 
-     * @param executionString this is the string that will be executed
-     * @param workingDir this is the directory where the execution will happen
-     * @param project this is the project that is related to the run (it is used to get the environment for the shell we are going to
-     * execute with the correct pythonpath environment variable).
-     * @param monitor this is the monitor used to communicate the progress to the user
-     * 
-     * @return the string that is the output of the process (stdout) and the stderr (o2)
-     */
-    public Tuple<String,String> runAndGetOutput(String executionString, File workingDir, IProject project, IProgressMonitor monitor) {
-        monitor.setTaskName("Executing: "+executionString);
+
+    public Tuple<String, String> runAndGetOutput(String[] arguments, File workingDir, IProject project, IProgressMonitor monitor) {
+    	String executionString = getCommandLineAsString(arguments);
+    	monitor.setTaskName("Executing: "+executionString);
         monitor.worked(5);
         Process process = null;
         try {
@@ -327,12 +318,17 @@
                     throw new RuntimeException(StringUtils.format("Working dir must be an existing directory (received: %s)", workingDir));
                 }
             }
-            process = Runtime.getRuntime().exec(executionString, envp, workingDir);
+            process = Runtime.getRuntime().exec(arguments, envp, workingDir);
         } catch (Exception e) {
             throw new RuntimeException(e);
         }
 
-        if (process != null) {
+        return getProcessOutput(process, executionString, monitor);
+	}
+
+	private Tuple<String, String> getProcessOutput(Process process,
+			String executionString, IProgressMonitor monitor) {
+		if (process != null) {
 
             try {
                 process.getOutputStream().close(); //we won't write to it...
@@ -376,6 +372,40 @@
 
         }
         return new Tuple<String, String>("","Error creating process - got null process("+ executionString + ")"); //no output
+	}
+
+
+    /**
+     * This is the method that actually does the running (all others are just 'shortcuts' to this one).
+     * 
+     * @param executionString this is the string that will be executed
+     * @param workingDir this is the directory where the execution will happen
+     * @param project this is the project that is related to the run (it is used to get the environment for the shell we are going to
+     * execute with the correct pythonpath environment variable).
+     * @param monitor this is the monitor used to communicate the progress to the user
+     * 
+     * @return the string that is the output of the process (stdout) and the stderr (o2)
+     */
+    public Tuple<String,String> runAndGetOutput(String executionString, File workingDir, IProject project, IProgressMonitor monitor) {
+        monitor.setTaskName("Executing: "+executionString);
+        monitor.worked(5);
+        Process process = null;
+        
+        try {
+            monitor.setTaskName("Making pythonpath environment..."+executionString);
+            String[] envp = getEnvironment(PythonNature.getPythonNature(project), null); //should get the environment for the default interpreter and the given project
+            monitor.setTaskName("Making exec..."+executionString);
+            if(workingDir != null){
+                if(!workingDir.isDirectory()){
+                    throw new RuntimeException(StringUtils.format("Working dir must be an existing directory (received: %s)", workingDir));
+                }
+            }
+            process = Runtime.getRuntime().exec(executionString, envp, workingDir);
+        } catch (Exception e) {
+            throw new RuntimeException(e);
+        }
+
+        return getProcessOutput(process, executionString, monitor);
     }
 
     /**
Index: src/org/python/pydev/runners/SimplePythonRunner.java
===================================================================
RCS file: /cvsroot/pydev/org.python.pydev/src/org/python/pydev/runners/SimplePythonRunner.java,v
retrieving revision 1.9
diff -u -r1.9 SimplePythonRunner.java
--- src/org/python/pydev/runners/SimplePythonRunner.java	26 Jun 2006 23:40:46 -0000	1.9
+++ src/org/python/pydev/runners/SimplePythonRunner.java	11 May 2008 23:23:08 -0000
@@ -51,12 +51,8 @@
      * @return the string with the command to run the passed script with jython
      */
     public static String makeExecutableCommandStr(String script, String[] args) {
-        String[] s = new String[]{
-            PydevPlugin.getPythonInterpreterManager().getDefaultInterpreter() , 
-            "-u" ,
-            script ,
-        };
-
+        String interpreter = PydevPlugin.getPythonInterpreterManager().getDefaultInterpreter();
+		String[] s = preparePythonCallParameters(interpreter, script, args);
         return getCommandLineAsString(s, args);
     }
 
@@ -72,7 +68,7 @@
      * 
      * @return the stdout of the run (if any)
      */
-    public Tuple<String,String>  runAndGetOutputWithInterpreter(String interpreter, String script, String[] args, File workingDir, IProject project, IProgressMonitor monitor) {
+    public Tuple<String,String> runAndGetOutputWithInterpreter(String interpreter, String script, String[] args, File workingDir, IProject project, IProgressMonitor monitor) {
         monitor.setTaskName("Mounting executable string...");
         monitor.worked(5);
         
@@ -81,16 +77,24 @@
             throw new RuntimeException("The script passed for execution ("+script+") does not exist.");
         }
         
-        String[] s = new String[]{
-            interpreter, 
-            "-u" ,
-            script ,
-        };
-
+        String[] s = preparePythonCallParameters(interpreter, script, args);
         monitor.worked(1);
-        return runAndGetOutput(getCommandLineAsString(s,args), workingDir, project, monitor);
+        return runAndGetOutput(s, workingDir, project, monitor);
     }
 
+	private static String[] preparePythonCallParameters(String interpreter, String script, String[] args) {
+		if (args == null) {
+			args = new String[0];
+		}
+		String[] s = new String[3 + args.length];
+        s[0] = interpreter;
+        s[1] = "-u";
+        s[2] = script;
+        for (int i=0; i<args.length; i++) {
+        	s[i+3] = args[i];
+        }
+		return s;
+	}
 
 
 

-------------------------------------------------------------------------
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference 
Don't miss this year's exciting event. There's still time to save $100. 
Use priority code J8TL2D2. 
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone
_______________________________________________
pydev-code mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/pydev-code

Reply via email to