hw-coder
hw-coder

Reputation: 43

Sourcing bash file in python and using the environment variable in same script

How to source the bash file in python script and use the environment variable (which is set in bash script) inside python? When I am removing source file from python script and sourcing it outside the ROOT_DIR which is an environment variable in bash script is able to recognise by my python script. Could you please suggest how can I achieve sourcing the bash script and use the variables there in python script. An example I have given below.

#!/usr/bin/python3

import sys, getopt
import os

def main(argv):

   os.system('source ./init.sh')


   root_dir =  os.environ['ROOT_DIR']
if __name__ == "__main__":
   main(sys.argv[1:])

The error I got is below:

Sourcing Successfully Done... Traceback (most recent call last):
File "test.py", line 213, in main(sys.argv[1:]) File "test.py", line 33, in main root_dir = os.environ['ROOT_DIR'] File "/usr/lib64/python3.6/os.py", line 669, in getitem raise KeyError(key) from None KeyError: 'ROOT_DIR'

My bash script is as below:

export ROOT_DIR=${PWD}
export TB_DIR=${PWD}/..

Upvotes: 1

Views: 3118

Answers (1)

AKX
AKX

Reputation: 168967

It won't work like that.

The shell script is run in a subprocess, which gets its own copy of the parent process's environment table.

You'd need to add e.g. printenv at the end of the shell script, then use e.g. subprocess.check_output(..., shell=True) to grab the printenv output, then parse it and copy the environment variables you need back into the Python process's environ.

Or, preferably, use a machine-readable, declarative format for that configuration to begin with, instead of an arbitrary program :)

Example

Assuming shell.sh is the script to run, and it declares export FOOFOO=bar:

output = subprocess.check_output("./shell.sh", shell=True)
# Parse the `printenv` output
exported_vars = dict(
    line.split("=", 1)
    for line in output.decode().splitlines()
    if line
)
# Filter to keep only variables that have new or changed values
changed_vars = {
    key: value
    for (key, value) in exported_vars.items()
    if value != os.environ.get(key)
}
pprint.pprint(changed_vars)

the output in repl.it is

{'COLUMNS': '93',
 'FOOFOO': 'bar',
 'LINES': '64',
 'SHLVL': '1',
 '_': '/usr/bin/printenv'}

Upvotes: 1

Related Questions