How to use export with Python on Linux
Solution 1
export
is a command that you give directly to the shell (e.g. bash
), to tell it to add or modify one of its environment variables. You can't change your shell's environment from a child process (such as Python), it's just not possible.
Here's what's happening when you try os.system('export MY_DATA="my_export"')
...
/bin/bash process, command `python yourscript.py` forks python subprocess
|_
/usr/bin/python process, command `os.system()` forks /bin/sh subprocess
|_
/bin/sh process, command `export ...` changes its local environment
When the bottom-most /bin/sh
subprocess finishes running your export ...
command, then it's discarded, along with the environment that you have just changed.
Solution 2
You actually want to do
import os
os.environ["MY_DATA"] = "my_export"
Solution 3
Another way to do this, if you're in a hurry and don't mind the hacky-aftertaste, is to execute the output of the python script in your bash environment and print out the commands to execute setting the environment in python. Not ideal but it can get the job done in a pinch. It's not very portable across shells, so YMMV.
$(python -c 'print "export MY_DATA=my_export"')
(you can also enclose the statement in backticks in some shells ``)
Solution 4
Not that simple:
python -c "import os; os.putenv('MY_DATA','1233')"
$ echo $MY_DATA # <- empty
But:
python -c "import os; os.putenv('MY_DATA','123'); os.system('bash')"
$ echo $MY_DATA #<- 123
Solution 5
I have an excellent answer.
#! /bin/bash
output=$(git diff origin/master..origin/develop | \
python -c '
# DO YOUR HACKING
variable1_to_be_exported="Yo Yo"
variable2_to_be_exported="Honey Singh"
… so on
magic=""
magic+="export onShell-var1=\""+str(variable1_to_be_exported)+"\"\n"
magic+="export onShell-var2=\""+str(variable2_to_be_exported)+"\""
print magic
'
)
eval "$output"
echo "$onShell-var1" // Output will be Yo Yo
echo "$onShell-var2" // Output will be Honey Singh
Mr Alex Tingle is correct about those processes and sub-process stuffs
How it can be achieved is like the above I have mentioned. Key Concept is :
- Whatever
printed
from python will be stored in the variable in the catching variable inbash
[output
] - We can execute any command in the form of string using
eval
- So, prepare your
print
output from python in a meaningfulbash
commands - use
eval
to execute it in bash
And you can see your results
NOTE
Always execute the eval
using double quotes
or else bash
will mess up your \n
s and outputs will be strange
PS: I don't like bash but your have to use it
Comments
-
Kevin Campion almost 2 years
I need to make an export like this in Python :
# export MY_DATA="my_export"
I've tried to do :
# -*- python-mode -*- # -*- coding: utf-8 -*- import os os.system('export MY_DATA="my_export"')
But when I list export, "MY_DATA" not appear :
# export
How I can do an export with Python without saving "my_export" into a file ?
-
Kevin Campion over 14 yearsIndeed I do not see it like that !
-
Kevin Campion over 14 yearsI just realize, after a lot of test, that it's you who is right : I can't change my shell's environment from a child process (such as Python), it's just not possible.
-
Bernardo Kyotoku almost 12 yearsjust reminding that if you run the second line many times, the same amount of recursive bash children will be created.
-
Paco almost 11 yearsBasically, you just created a new bash instance on top of python which is on top of another bash
-
Shailen over 9 yearsThis solution is not correct. In a python script with many commands, the script will exit as the new bash instance is created.
-
Peter Jenkins over 8 yearsThis doesn't actually work (although it's a nicer way to do this):
$ python Python 2.7.10 (default, Sep 8 2015, 17:20:17) [GCC 5.1.1 20150618 (Red Hat 5.1.1-4)] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> import os >>> os.environ["MY_DATA"] = "my_export" >>> $ export | grep -c MY_DATA 0
-
Ian Gallagher over 8 yearsCan others comment as to why this got downvoted? It seems like a reasonable solution given the desired requirements. It doesn't start a new subshell, and does actually add new environment variables to the current, running shell process.
-
cubuspl42 about 8 years@KevinCampion Please change the accepted answer in such case.
-
Nico almost 8 yearsDon't do that, creating an entire new bash process just for environment variable is really bad practice.
-
xealits over 7 yearshm.. I tried running
subprocess.check_output( 'export x=foo && other_people_command_depending_on_x' )
and it didn't work somehow -- any ideas what happens there? Settingos.environ['x'] = 'foo'
for Python (and thus all its' child-processes) works. -
Krishna Oza over 7 yearsI recently have to do something similar , here is the issue and what has worked for me. The problem was to execute a python script which internally executes a ELF binary and I wanted a certain path to be set for this binary. The solution that worked for me was to fetch the current path variable from the python code and then just directly update the
PATH
variable usingos.putenv
. Though this will not update thePATH
variable of the shell from where the python script was originally invoked. -
kevr over 6 yearsThis doesn't answer the question at all, because this doesn't actually export to the current shell.
-
rhoerbe over 5 yearsActually quite cool. Better that writing a script and souring it later on.
-
dkb almost 5 yearsWelcome to SO, Thank you for your contribution, please add some explanation along with the code, which will help SO members to understand your answer better.
-
yann zerlaut over 4 yearsIt is indeed an excellent answer !! see also the answer by @mikepk, same idea
-
yann zerlaut over 4 yearsIndeed, quite cool. This and the more detailed version of @Akhil should be the best answer.
-
M Y over 4 yearsThat will take you to another shell inside the terminal, so, if you put that inside script that has several other commands after that command they will stuck till you return/exit from that new shell.
-
Macilias about 4 yearsexport MY_DATA=MY_EXPORT is what I was looking for
-
Rahul Reddy over 3 years
-
Kevin Campion over 3 yearsDone @RahulReddy