Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python's sh module - Running 'source' command

Tags:

python

When using python's sh module, I would like to run a 'source' builtin command.

But I can't run it, because sh should have a binary as parameter.

How can I run builtin commands with sh module?

# source ./test.sh

sh.source('./test.sh') # wrong usage
sh.Command('source') # wrong usage
like image 794
hyde1004 Avatar asked Mar 26 '26 22:03

hyde1004


1 Answers

To invoke sh -c "source hello" via the Python sh module (ignoring that sh is not guaranteed to support the source command at all -- the POSIX-compliant equivalent is . hello):

sh.sh('-c', 'source test.sh')

That said, consider using subprocess.Popen() instead, which contains far less magic and thus behaves more predictably:

# ...if hardcoding the script to source in your Python code
# ...because shell=True uses /bin/sh instead of bash, use . instead of source
subprocess.Popen('. ./test.sh', shell=True)

# ...otherwise:
# ...because shell=True uses /bin/sh instead of bash, use . instead of source
subprocess.Popen(['. "$@"', './test.sh'], shell=True)

When an array is passed to the first argument of subprocess.Popen, the first argument is treated as the source to run, and subsequent arguments became $1, $2, etc. during operation of that script, allowing the combination of an array of string literals with /bin/sh invoked via the shell=True.


However: The intent and purpose behind sourcing content into a shell is generally to modify that shell's state. With either sh.sh or subprocess.Popen(), the shell only lasts as long as that single Python function call's invocation, so no state persists to future sh or subprocess calls, making it unlikely that any of these uses will actually accomplish your goals at hand.

What you really want is probably more like this:

sh.sh('-c', '. ./test.sh; do-something-else-here')

...where your do-something-else-here depends on changes to the shell and its environment made by source ./test.sh.

like image 107
Charles Duffy Avatar answered Mar 28 '26 10:03

Charles Duffy