IT Share you

Linux에서 Python으로 내보내기를 사용하는 방법

shareyou 2021. 1. 9. 10:54
반응형

Linux에서 Python으로 내보내기를 사용하는 방법


Python에서 다음과 같이 내 보내야합니다.

# export MY_DATA="my_export"

나는 시도했다 :

# -*- python-mode -*-
# -*- coding: utf-8 -*-
import os
os.system('export MY_DATA="my_export"')

하지만 내보내기를 나열 할 때 "MY_DATA"가 나타나지 않습니다.

# export

"my_export"를 파일에 저장하지 않고 Python으로 내보내기를 수행하려면 어떻게해야합니까?


당신은 실제로하고 싶어

import os
os.environ["MY_DATA"] = "my_export"

exportbash환경 변수 중 하나를 추가하거나 수정 하도록 쉘에 직접 제공하는 명령입니다 (예 :). 자식 프로세스 (예 : Python)에서 셸의 환경을 변경할 수 없으며 불가능합니다.

여기에 무슨 일이 일어나고 있는지 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 local environment

최하위 /bin/sh하위 프로세스가 export ...명령 실행을 마치면 방금 변경 한 환경과 함께 삭제됩니다.


이 작업을 수행하는 또 다른 방법은 서두르고 해키 뒷맛이 마음에 들지 않는 경우 bash 환경에서 Python 스크립트의 출력을 실행하고 Python에서 환경 설정을 실행하는 명령을 인쇄하는 것입니다. 이상적이지는 않지만 작업을 빠르게 완료 할 수 있습니다. 셸간에 이식성이 매우 낮으므로 YMMV입니다.

$(python -c 'print "export MY_DATA=my_export"')

(일부 셸에서 백틱으로 문을 묶을 수도 있습니다 .``)


그렇게 간단하지 않습니다.

python -c "import os; os.putenv('MY_DATA','1233')"
$ echo $MY_DATA # <- empty

그러나:

python -c "import os; os.putenv('MY_DATA','123'); os.system('bash')"
$ echo $MY_DATA #<- 123

대신 os.environ [ "MY_DATA"]를 사용해 볼 수 있습니다.


훌륭한 대답이 있습니다.

#! /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

Alex Tingle 씨는 이러한 프로세스 및 하위 프로세스 항목에 대해 정확합니다.

그것을 달성 할 수있는 방법은 위에서 언급 한 것과 같습니다. 주요 개념은 다음과 같습니다.

  1. printed파이썬에서 무엇이든 bash[ output] 의 캐치 변수에있는 변수에 저장됩니다 .
  2. 다음을 사용하여 문자열 형태로 모든 명령을 실행할 수 있습니다. eval
  3. So, prepare your print output from python in a meaningful bash commands
  4. 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 \ns and outputs will be strange

PS: I don't like bash but your have to use it


Kind of a hack because it's not really python doing anything special here, but if you run the export command in the same sub-shell, you will probably get the result you want.

import os

cmd = "export MY_DATA='1234'; echo $MY_DATA" # or whatever command
os.system(cmd)

In the hope of providing clarity over common cinfusion...

I have written many python <--> bash <--> elfbin toolchains and the proper way to see it is such as this:

Each process (originator) has a state of the environment inherited from whatever invoked it. Any change remains lokal to that process. Transfering an environment state is a function by itself and runs in two directions, each with it's own caveats. The most common thing is to modify environment before running a sub-process. To go down to the metal, look at the exec() - call in C. There is a variant that takes a pointer to environment data. This is the only actually supported transfer of environment in typical OS'es.

Shell scripts will create a state to pass when running children when you do an export. Otherwise it just uses that which it got in the first place.

In all other cases it will be some generic mechanism used to pass a set of data to allow the calling process itself to update it's environment based on the result of the child-processes output.

Ex:

ENVUPDATE = $(CMD_THAT_OUTPUTS_KEYVAL_LISTS)
echo $ENVUPDATE > $TMPFILE
source $TMPFILE

The same can of course be done using json, xml or other things as long as you have the tools to interpret and apply.

The need for this may be (50% chance) a sign of misconstruing the basic primitives and that you need a better config or parameter interchange in your solution.....

Oh, in python I would do something like... (need improvement depending on your situation)

import re

RE_KV=re.compile('([a-z][\w]*)\s*=\s*(.*)')

OUTPUT=RunSomething(...) (Assuming 'k1=v1 k2=v2')

for kv in OUTPUT.split(' ')
  try:
    k,v=RE_KV.match(kv).groups()
    os.environ[k]=str(v)
  except:
    #The not a property case...
    pass

One line solution:

eval `python -c 'import sysconfig;print("python_include_path={0}".format(sysconfig.get_path("include")))'`
echo $python_include_path  # prints /home/<usr>/anaconda3/include/python3.6m" in my case

Breakdown:

Python call

python -c 'import sysconfig;print("python_include_path={0}".format(sysconfig.get_path("include")))'

It's launching a python script that

  1. imports sysconfig
  2. gets the python include path corresponding to this python binary (use "which python" to see which one is being used)
  3. prints the script "python_include_path={0}" with {0} being the path from 2

Eval call

eval `python -c 'import sysconfig;print("python_include_path={0}".format(sysconfig.get_path("include")))'`

It's executing in the current bash instance the output from the python script. In my case, its executing:

python_include_path=/home/<usr>/anaconda3/include/python3.6m

In other words, it's setting the environment variable "python_include_path" with that path for this shell instance.

Inspired by: http://blog.tintoy.io/2017/06/exporting-environment-variables-from-python-to-bash/


import os
import shlex
from subprocess import Popen, PIPE


os.environ.update(key=value)

res = Popen(shlex.split("cmd xxx -xxx"), stdin=PIPE, stdout=PIPE, stderr=PIPE,
            env=os.environ, shell=True).communicate('y\ny\ny\n'.encode('utf8'))
stdout = res[0]
stderr = res[1]


os.system ('/home/user1/exportPath.ksh')

exportPath.ksh:

export PATH=MY_DATA="my_export"

ReferenceURL : https://stackoverflow.com/questions/1506010/how-to-use-export-with-python-on-linux

반응형