Hanfei Sun
Hanfei Sun

Reputation: 47061

Does the `shell` in `shell=True` in subprocess mean `bash`?

I was wondering whether

subprocess.call("if [ ! -d '{output}' ]; then mkdir -p {output}; fi", shell=True)

will be interpreted by sh or zsh instead of bash in different servers.

What should I do to make sure that it's interpreted by bash?

Upvotes: 21

Views: 13284

Answers (3)

unutbu
unutbu

Reputation: 879391

To specify the shell, use the executable parameter with shell=True:

If shell=True, on Unix the executable argument specifies a replacement shell for the default /bin/sh.

In [26]: subprocess.call("if [ ! -d '{output}' ]; then mkdir -p {output}; fi", shell=True, executable='/bin/bash')
Out[26]: 0

Clearly, using the executable parameter is cleaner, but it is also possible to call bash from sh:

In [27]: subprocess.call('''bash -c "if [ ! -d '{output}' ]; then mkdir -p {output}; fi"''', shell=True)
Out[27]: 0

Upvotes: 5

John Zwinck
John Zwinck

Reputation: 249133

You can explicitly invoke the shell of your choice, but for the example code you posted this is not the best approach. Instead, just write the code in Python directly. See here: mkdir -p functionality in Python

Upvotes: 3

Pavel Anossov
Pavel Anossov

Reputation: 62898

http://docs.python.org/2/library/subprocess.html

On Unix with shell=True, the shell defaults to /bin/sh

Note that /bin/sh is often symlinked to something different, e.g. on ubuntu:

$ ls -la /bin/sh
lrwxrwxrwx 1 root root 4 Mar 29  2012 /bin/sh -> dash

You can use the executable argument to replace the default:

... If shell=True, on Unix the executable argument specifies a replacement shell for the default /bin/sh.

subprocess.call("if [ ! -d '{output}' ]; then mkdir -p {output}; fi",
                shell=True,
                executable="/bin/bash")

Upvotes: 40

Related Questions