3

I'm using subprocess.Popen to launch an external program with arguments, but when I've opened it the script is hanging, waiting for the program to finish and if I close the script the program immediately quits.

I thought I was just using a similar process before without issue, so I'm unsure if I've actually done it wrong or I'm misremembering what Popen can do. This is how I'm calling my command:

 subprocess.Popen(["rv", rvFile, '-nc']) raw_input("= Opened file") 

The raw_input part is only there so the user has a chance to see the message and know that the file should be opened now. But what I end up getting is all the information that the process itself is spitting back out as if it were called in the command line directly. My understanding was that Popen made it an independent child process that would allow me to close the script and leave the other process open.

The linked duplicate question does have a useful answer for my purposes, though it's still not working as I want it.

This is the answer. And this is how I changed my code:

DETACHED_PROCESS = 0x00000008 pid = subprocess.Popen(["rv", rvFile, '-nc'], creationflags=DETACHED_PROCESS).pid raw_input("= Opened file") 

It works from IDLE but not when I run the py file through the command prompt style interface. It's still tied to that window, printing the output and quitting the program as soon as I've run the script.

5
  • 1
    possible duplicate of Calling an external command in Python Commented May 5, 2015 at 11:50
  • If you think you found a solution; don't put it in your question. Post it as an answer instead (to allow independent commenting, voting, jumping directly to answers). Commented May 9, 2015 at 17:38
  • You should probably redirect stdin, stdout, stderr (to DEVNULL if you want to ignore the output) Commented May 9, 2015 at 17:39
  • 1
    related: Python: Howto launch a full process not a child process and retrieve the PID Commented May 9, 2015 at 17:43
  • @J.F.Sebastian I might not have made it clear enough, but the answer I was linking to didn't sufficiently solve my problem, that said I did solve it by combining answers and I should answer with that now, thanks for the reminder! Commented May 11, 2015 at 7:22

3 Answers 3

2

The stackoverflow question Calling an external command in python has a lot of useful answers which are related.

Take a look at os.spawnl, it can take a number of mode flags which include NOWAIT, WAIT.

import os os.spawnl(os.P_NOWAIT, 'some command') 

The NOWAIT option will return the process ID of the spawned task.

Sign up to request clarification or add additional context in comments.

Comments

1

Sorry for such a short answer but I have not earned enough points to leave comments yet. Anyhow, put the raw_input("= Opened file") inside the file you are actually opening, rather than the program you are opening it from.

If the file you are opening is not a python file, then it will close upon finishing,regardless of what you declare from within python. If that is the case you could always try detaching it from it's parent using:

from subprocess import Popen, CREATE_NEW_PROCESS_GROUP subprocess.Popen(["rv", rvFile, '-nc'], close_fds = True | CREATE_NEW_PROCESS_GROUP) 

3 Comments

The file is actually in a different program. The script basically compiles a list of videos into a filetype and then opens that in a particular program. This solution again worked in IDLE but not the Command Prompt. I'm starting to wonder if the program that I'm opening could be the problem.
If I read you right you want to close the spawned process independently? For that you will need to create a new shell, shell = True. If the solution works in IDLE, it won't be your script, and you can be sure the code is correct. How are you running the command prompt? Is it from the windows scheduler by any chance? (Also, get rid of the raw_input)
It's a manual run of the python file, basically double clicking the python file in Windows. But using the combination of DETACHED_PROCESS and the shell did exactly what I wanted, it allows me to close the python script window and leave the other program still running. Thanks!
0

This is specifically for running the python script as a commandline process, but I eventually got this working by combining two answers that people suggested.

Using the combination of DETACHED_PROCESS suggested in this answer worked for running it through IDLE, but the commandline interface. But using shell=True (as ajsp suggested) and the DETACHED_PROCESS parameter it allows me to close the python script window and leave the other program still running.

DETACHED_PROCESS = 0x00000008 pid = subprocess.Popen(["rv", rvFile, '-nc'], creationflags=DETACHED_PROCESS, shell=True).pid raw_input("= Opened file") 

2 Comments

avoiding "python script window" looks like a different issue (you could use .pyw file extension or run your script using pythonw.exe explicitly). You should add close_fds=True (or redirect all stdin,stdout,stderr) and get rid of shell=True.
creationflags is only supported on Windows platform. (that's the error I got for python3.X)

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.