Executing PowerShell commands with Python 3.5
我一直在研究一个需要Python脚本通过PowerShell命令行运行的问题。 该脚本应将命令传递到命令行并保存输出。 但是,我遇到了无法识别某些命令行参数的问题。
1 2 3 4 5 6 7 8
| import subprocess
try:
output = subprocess.check_output\
(["Write-Output 'Hello world'"], shell=True)
# (["dir"], shell=True)
except subprocess.CalledProcessError as e:
print(e.output)
print('^Error Output^') |
如果我将当前命令与check_output命令一起使用,则会收到一条错误消息,指出:
1 2
| '"Write-Output 'Hello world'"' is not recognized as an internal or external command,
operable program or batch file. |
如果仅使用"dir"行,则脚本可以正常运行。 我在这里为什么会发生这样的说法有分歧。 这不是我正在运行的确切脚本,但是它在我的机器上产生了同样的问题。 如果仅在命令行中输入问题命令,它将按预期输出"Hello world"到新行中。
对于为什么会发生这种情况的任何见解将不胜感激。 如果相关,我不想使用任何类型的管理员特权解决方法。
我相信这是因为在Windows中,默认的Shell不是PowerShell,您可以执行Powershell命令,通过使用所需的参数执行Powershell来调用可执行文件。
例如
1 2 3 4 5 6 7
| POWERSHELL_COMMAND = r'C:\WINDOWS\system32\WindowsPowerShell\v1.0\powershell.exe'
subprocess.Popen([POWERSHELL_COMMAND,
'-ExecutionPolicy', 'Unrestricted',
'Write-Output', 'Hello World'],
stdout = subprocess.PIPE,
stderr = subprocess.PIPE) |
如果powershell不在路径中,则可以使用可执行文件的完整路径
或者,如果它在路径中,请小心使用POWERSHELL_COMMAND ="powershell"作为命令,并使用反斜杠的Windows路径,以避免错误,可以使用原始字符串。
要验证路径中是否具有Powershell,可以转到配置并进行检查,或者可以打开cmd并键入powershell,如果它可以正常工作,则可以假定Powershell在路径中。
从文档:
On Windows with shell=True, the COMSPEC environment variable specifies the default shell.
因此,set COMSPEC=powershell允许使shell=True使用powershell作为默认值,而不是cmd
-
您能解释一下为什么您正确地将原始前缀用于powershell命令的完整路径吗?有没有办法避免整个路径?在我的机器上,我只需要powershell,因为它已经在路径中
-
"在具有shell = True的Windows上,COMSPEC环境变量指定默认的shell":这是您的答案,可使其与shell = True和powershell一起使用
-
原始字符串前缀,这是由于Windows文件路径中的反斜杠引起的,我只是尝试使用powershell命令,它也可以工作。我只是使用了可执行文件的整个路径,以防系统路径中没有powershell的情况。如果要在没有完整路径的情况下使用它,只需将powershell添加到路径(以防不存在),您可以检查是否打开cmd并键入powershell,如果可以,则可以假定它在Windows路径中。
-
@ tarruda23如果答案足以满足您的要求,请记住将其标记为已回答,否则请告知我。
-
@ekiim我感谢您的帮助。但是,-ExecutionPolicy, Unrestricted需要管理员特权,而我在这台计算机上没有该特权。只需删除该选项即可使代码正常工作。我遇到的问题是将您的解决方案应用于更一般的情况。如果我有一个安装命令行选项的程序,但是在通过python时无法识别这些选项,我是否只需指定该程序可执行文件的路径而不是powershell?
-
如果必须将参数传递给命令,则应将其作为列表的元素来执行,例如,如果要执行dir A B C:\ ,则应将列表作为[dir, rA, rB, rC:\]传递,这将起作用。 [rdir A B C:\],您可能会遇到麻烦。关于特权,那么,您必须授予脚本特权,因此它以admin身份执行所有脚本,因为据我所知,没有命令将Admin Privileges授予Windows中的单个执行(也许有,但是我不知道那)