在 Bash 脚本中使用 Python

在 Bash 脚本中使用 Python

如果我尝试在 bash 脚本中启动 python,该脚本将停止运行,并且在调用“Python”后不会执行任何命令。在这个简单的例子中,“TESTPRINT”将不会被打印。剧本似乎就这样停止了。

#!/bin/bash

python

print("TESTPRINT")

Echo

如何让脚本在进入Python后继续运行?我相信几年前我在编写一个首先需要 shell 到 Android 手机中的脚本后也遇到过同样的问题。我不记得当时是怎么解决的。

答案1

要从脚本运行一组 Python 命令bash,您必须向 Python 解释器提供要运行的命令,可以从您在脚本中创建的文件(Python 脚本)中执行,如下所示

#!/bin/bash -e

# Create script as "script.py"
cat >script.py <<'END_SCRIPT'
print("TESTPRINT")
END_SCRIPT

# Run script.py
python script.py

rm script.py

(这将创建一个名为的新文件,script.py如果该文件已存在,则覆盖该文件,然后指示 Python 运行它;然后将其删除)

...或直接通过某种形式的重定向,例如此处文档:

#!/bin/bash

python - <<'END_SCRIPT'
print("TESTPRINT")
END_SCRIPT

它的作用是运行python -,指示 Python 解释器从标准输入读取脚本。然后,shell 将 Python 脚本的文本(END_SCRIPT在 shell 脚本中以 分隔)发送到 Python 进程的标准输入流。

请注意,上面的两段代码略有不同,因为第二个脚本的 Python 进程的标准输入连接到它正在读取的脚本,而第一个脚本的 Python 进程可以自由地从标准输入读取脚本以外的数据。如果您的 Python 代码从标准输入读取,这一点很重要。

Python 还可以通过其选项直接从命令行获取一组命令-c

#!/bin/bash

python -c 'print("TESTPRINT")'

你什么不能做就是在脚本中间“切换到Python” bash

脚本中的命令被bash一个接一个地执行,并且在执行命令时,脚本本身会等待它终止(如果它不是后台作业)。

这意味着您的原始脚本将以交互模式启动 Python,暂时挂起bash脚本的执行,直到 Python 进程终止。然后该脚本将尝试print("TESTPRINT")作为 shell 命令执行。

ssh在脚本中使用类似的问题:

ssh user@server
cd /tmp
ls

(这可能与您所说的几年前尝试过的类似)。

这个会不是连接到远程系统并在那里运行cdls命令。它将在远程系统上启动一个交互式 shell,一旦该 shell 终止(将控制权交还给脚本),cd就会ls在本地运行。

相反,要在远程计算机上执行命令,请使用

ssh user@server "cd /tmp; ls"

(这是一个蹩脚的例子,但你可能明白了)。


下面的示例显示了您实际上可以如何执行您的建议。但它带有几个警告标签和警告,你永远不应该写这样的代码(因为它很混乱,因此无法维护,而且我敢说,非常糟糕)。

python -
print("TESTPRINT")

运行它:

$ sh -s <script.sh
TESTPRINT

这里发生的情况是脚本正在由 运行sh -s。选项-sto sh(和 to bash) 告诉 shell 执行通过标准输入流到达的 shell 脚本。

然后脚本开始python -,它告诉Python运行通过标准输入流传入的任何内容。该流上的下一个内容sh -s是 Python 命令,因为它是由 Python 继承的(因此连接到我们的脚本文本文件)print("TESTPRINT")

然后,Python 解释器将继续从脚本文件读取并执行命令,直到用完或执行 Python 命令exit()

答案2

除了 Kusalananda 的答案之外,如果您希望整个脚本由 python 运行,您只需将第一行更改为#!/usr/bin/env python3并像任何普通 shell 脚本一样运行它。这样您就不必记住必须使用哪个解释器运行哪个脚本。

答案3

您还可以尝试使用<<<(Here Strings) 运算符来保存行:

$ python <<< 'print("MyTest")'
MyTest

答案4

您还可以在从 bash 脚本调用 python 文件时设置 python 路径:

export PYTHONPATH=/tmp/python_dep.zip && python test_my.py

相关内容