2013-03-07 3 views
1

Преобразование скрипта оболочки в python и поиск наилучшего способа выполнить следующее. Мне нужно это, поскольку оно содержит переменные среды, которые мне нужны.Исходная командная строка Linux-оболочки в python

if [ -e "/etc/rc.platform" ]; 
then 
    . "/etc/rc.platform" 
fi 

У меня есть «if», но не уверен, как обращаться с. «/etc/rc.platform», поскольку источником является команда оболочки. До сих пор у меня есть следующие

if os.path.isfile("/etc/rc.platform"): 
    print "exists" <just to verify the if if working> 
    <what goes here to replace "source /etc/rc.platform"?> 

Я искал подпроцесс и execfile без успеха.

Сценарий питона нужно будет доступ к переменным окружения, установленным rc.platform

+3

Вам придется проанализировать '/ etc/rc.platform', извлечь имена и значения переменных среды и обновить [os.environ] (http://docs.python.org/2/library/os.html# os.environ) соответственно. – crayzeewulf

+0

@crazyeewulf - Речь идет не только о переменных среды, но также могут быть функции bash, которые могут быть экспортированы скриптом. Как вы планируете использовать их из сценария python, если только вы не попытаетесь повторно использовать ту же оболочку для всех скриптов, которые вызывают. – Tuxdude

+1

Я предлагаю переносить '/ etc/rc.platform' на Python, так как' .' очень похож на 'import'. – chepner

ответ

1

Слишком много работы для возвращения. Идти, чтобы сохранить небольшой скрипт оболочки, чтобы получить все env vars, которые нам нужны, и забыть прочитывать их в python.

0

Попробуйте это:

if os.path.exists ("/etc/rc.platform"): 
    os.system("/etc/rc.platform") 
+1

Это не будет иметь тот же эффект, что и сценарий оболочки, указанный в OP. 'os.system' запускает команду в подоболочке и, следовательно, родительский процесс не увидит каких-либо переменных среды, добавленных/измененных с помощью'/etc/rc.platform'. – crayzeewulf

+0

Вы не можете использовать сценарий sh или bash в процессе python, который не знает, как интерпретировать язык bash. Следовательно, вам нужно подойти, чтобы запустить bash и интерпретировать сценарий. Поскольку это выполняется в подоболочке, процесс python не сможет получить новые значения env. –

0

Поскольку source является встроенная команда оболочки, вам необходимо установить shell=True при вызове subprocess.call

>>> import os 
>>> import subprocess 
>>> if os.path.isfile("/etc/rc.platform"): 
...  subprocess.call("source /etc/rc.platform", shell=True) 

Я не уверен, что вы пытаетесь сделать здесь, но я все еще хотел упомянуть об этом: /etc/rc.platform может экспортировать некоторые функции оболочки, которые будут использоваться другими скриптами в rc.d. Поскольку они являются функциями оболочки, они будут экспортироваться только в экземпляр оболочки, вызванный subprocess.call(), и если вы вызовете еще один subprocess.call(), эти функции будут недоступны, так как вы создаете новую новую оболочку для вызова нового скрипта.

+2

Если вы запустите скрипт внутри подоболочки, это не поможет, потому что все параметры переменных среды будут отброшены. – grep

+0

@grep - я знаю об этом, и речь идет не только о переменных среды, но даже функции bash, экспортируемые с помощью '/ etc/rc/platform', были бы недоступны для скрипта python, и любые новые оболочки начали вызывать другие связанные скрипты from say '/ etc/rc.d' – Tuxdude

1

(Вот демонстрация crayzeewulf решения, описанная в комментарии.)

Если /etc/rc.platform содержит только переменные окружения, вы можете прочитать их и установить их в качестве окр варов для процесса Python.

Учитывая этот файл:

$ cat /etc/rc.platform 
FOO=bar 
BAZ=123 

чтения и набор переменных окружения:

>>> import os 
>>> with open('/etc/rc.platform') as f: 
...  for line in f: 
...   k, v = line.split('=') 
...   os.environ[k] = v.strip() 
... 
>>> os.environ['FOO'] 
'bar' 
>>> os.environ['BAZ'] 
'123' 
+0

Это не сработает, если переменные ссылаются на другие переменные в их декларации, например 'X = "$ Y/Foo"'. Кроме того, сценарий может использовать другие команды оболочки (например, awk, grep и т. Д.) Или встроенные переменные оболочки, которые, очевидно, не будут оцениваться. – l4mpi

+0

Хорошие очки. Я предполагаю, что консенсус здесь заключается в том, что для этого нет простого способа, кроме самого простейшего случая, который я использовал в качестве примера. –

+0

Мне нужно было что-то подобное однажды и закончилось тем, что породил подоболочку, запустив скрипт, а затем разобрав вывод 'env' ... может быть, я напишу ответ после обеда. – l4mpi

3

Несколько хака решения разобрать env вывод:

newenv = {} 
for line in os.popen('. /etc/rc.platform >&/dev/null; env'): 
    try: 
     k,v = line.strip().split('=',1) 
    except: 
     continue # bad line format, skip it 
    newenv[k] = v 
os.environ.update(newenv) 

редактирования: фиксированный раскол аргумент, благодаря @ l4mpi

+1

Хороший ответ, но второй аргумент 'split' должен быть 1, а не 2. Это число выполненных расщеплений, а не количество результирующих разделов. – l4mpi