Launching Programs
Sub-Process
If you want to execute another program on your machine, regardless of whether it’s a Python program or something else, you can use the subprocess module.
Let’s say you have another Python script called hello.py:
print("hello there!")
We could use subprocess from another Python program (say launch.py) to call this Python program like this:
import subprocess
import sys
completed = subprocess.run([sys.executable, 'hello.py'])
if completed.returncode == 0:
print('Program excited successfully')
else:
print('Program exited with an error code')
$ python launch.py
hello there!
Program excited successfully
To avoid having to make a list of all our arguments, we can set the shell argument to True and pass in a string:
import subprocess
import sys
completed = subprocess.run(f"{sys.executable} hello.py", shell=True)
if completed.returncode == 0:
print('Program excited successfully')
else:
print('Program exited with an error code')
$ python launch.py
hello there!
Program excited successfully
Capturing Output
If we wanted to capture standard output, we could do this:
import subprocess
import sys
completed = subprocess.run(f"{sys.executable} hello.py", capture_output=True, shell=True)
if completed.returncode == 0:
print('Program excited successfully')
else:
print('Program exited with an error code')
print('Output from subprocess:\n' + completed.stdout.decode('utf-8'), end='')
Note that on Windows you’ll likely need to decode with utf-16-le character encoding.
$ python launch.py
Program excited successfully
Output from subprocess:
hello there!
Asynchronous Execution
Let’s make our subprocess take a while to run and see what happens:
from time import sleep
print("hello there!")
sleep(2)
print("program ending")
Now when we run launch.py we’ll see our program hangs for a few seconds while it’s waiting for the subprocess to finish executing:
$ python launch.py
Program excited successfully
Output from subprocess:
hello there!
If we didn’t want to wait for our subprocess to complete before continuing execution, we could use the lower-level subprocess.Popen instead.
import subprocess
import sys
process = subprocess.Popen(
[sys.executable, 'hello.py'],
stdout=subprocess.PIPE,
)
# We can execute whatever we want here before we start waiting
print("The subprocess is executing now!")
process.wait() # Wait for process to complete
if process.returncode == 0:
print('Program excited successfully')
else:
print('Program exited with an error code')
print('Output from subprocess:\n' + process.stdout.read().decode('utf-8'), end='')
$ python launch.py
The subprocess is executing now!
Program excited successfully
Output from subprocess:
hello there!
program ending
For more on subprocess, see the documentation and Python Module of the week.