我们如何从python调用bash函数

时间:2018-12-10 05:31:14

标签: python bash shell subprocess

比方说,我有一个bash函数,可以将其提供给shell。

# cat sample.sh 
function func()
{
    echo "Custom env : $CUSTOM_ENV"
}

现在,我在bash shell中获取此脚本: #source sample.sh

然后我定义:

export CUSTOM_ENV="abc"

,然后从bash shell调用func(),它显示:

#func
Custom env : abc

现在,如果我从同一shell调用python脚本, 我想从python脚本调用函数func()。无论如何要实现这一目标?

我尝试过的事情:

  1. 尝试过os.system('func')-不起作用
  2. 尝试过subprocess.check_output('func',shell = True,env = os.environ.copy())-不起作用

任何指导吗?

3 个答案:

答案 0 :(得分:1)

您遇到的问题是,其中涉及两个单独的bash流程:

  • 重击->了解func,运行python
  • Python,当您调用os.systemsubprocess.check_output时运行新的bash进程
  • 内部bash->由Python创建,与外部bash完全不同。

您在外层bash上所做的任何事情都是内层bash无法访问的。您需要将该函数提供给内部bash。

类似: subprocess.check_call("bash -c '. sample.sh && func'", shell=True)

这可能并不完全正确,但是希望您能想到这个想法-您希望由Python创建的内部bash在尝试运行func之前先了解该函数。

(具体来说,在此代码中,第三个外壳可能会生成一个第四个外壳-这样比较容易,但是如果您关心性能,则可能需要进行一些调整。)

答案 1 :(得分:0)

您需要export函数(使用-f选项):

$ function func()
> {
>     echo "Custom env : $CUSTOM_ENV"
> }
$ export -f func
$ export CUSTOM_ENV="abc"
$ python
Python 2.7.10 (default, Oct  6 2017, 22:29:07) 
[GCC 4.2.1 Compatible Apple LLVM 9.0.0 (clang-900.0.31)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import os
>>> os.system('func')
Custom env : abc
0

请注意,export对函数(和变量)的导出是将函数和变量的副本导出到要从中导出的Shell的子进程中。它们在父(或同级)进程中不可用。另外,在子流程中更改它们不会影响原始副本。

此外,导出函数仅适用于bash,因此仅当父shell和从python开始的shell均为bash时,此方法才有效。在bash不是默认值的操作系统上(例如Ubuntu和Debian的最新版本),您需要显式运行bash,否则它将无法正常工作。这一切都使其非常脆弱,正如@triplee指出的那样,这不是一个好主意。

答案 2 :(得分:-2)

在您的具体示例中:

import subprocess
import os

def run_bash(cmd):
    subprocess.Popen(['/bin/bash', '-c', cmd])

#run_bash('ls -ltra')
#run_bash("date '+%A %W %Y %X'")

os.environ["CUSTOM_ENV"] = "MJ"
run_bash('./sample.sh')

确保chmod +x sample.sh将sample.sh设为可执行文件

test_bash.py是:

import subprocess

def run_bash(cmd):
    subprocess.Popen(['/bin/bash', '-c', cmd])

run_bash('ls -ltra')
run_bash("date '+%A %W %Y %X'")

$ python test_bash.py 
Monday 50 2018 12:47:13 AM
total 668
-rw-r--r--. 1 jalal cs-grad   2590 Nov  4 16:46 data_loading.py
drwxr-xr-x. 8 jalal cs-grad    211 Nov  4 16:46 .git
drwxr-xr-x. 2 jalal cs-grad     85 Nov  4 22:44 .ipynb_checkpoints