我有几个python3脚本使用hashbang将其标识为python3脚本。这些脚本可以根据文件扩展名被标识为python,因为它们没有任何扩展名(就像在任何其他*nix系统中一样)。在
我已经讨论过相关的问题,但是它们没有解决这个特殊的需求,并且似乎依赖于*.py
扩展来获得识别。在
所以我的脚本名为:myscript
,文件的第一行是:
#!/usr/bin/env python3
...
如何让Windowspowershell识别并使用位于^{
更新-1
为了澄清,我想从powershellCLI运行它,而不是单击它。
另外,我刚刚发现(让我感到恐怖的是)当您将pip install
与本机Windows Python3一起使用时,第一行hashbang会自动替换为:
#!c:\python37\python.exe
哎哟!在
更新-2
多亏了@eryksun的评论,我设法得到了一个PowerShell脚本来为我做一些基本的检查。但是,它需要被修复以支持比Python更多的内容。在
test4script.ps1
:
结果是:
$ Get-Content -Path nonscript -TotalCount 3
#This aint right
echo "hello"
$ Get-Content -Path pip-describe -TotalCount 3
#!c:\python37\python.exe
# pip-describe - Show full text package description from PyPI
# -*- coding: utf-8 -*-
$ .\test4script.ps1 nonscript
File is not a known script. No shebang fund in file!
$ .\test4script.ps1 pip-describe
DEBUG: checking for common shebangs
DEBUG: found shebang for: python3
Usage: pip-describe <package-name>
This will return the full-text package description (usually the README)
as found on PyPI, for any given <package-name>.
...
现在我们应该能够使用命令行.exe使用:
cmd /c assoc .=unknown
cmd /c "ftype unknown=""C:\mybin\test4script.ps1"" %1"
但是,如果使用PowerShell独立地执行此操作,而不必跳过CMD,则会更好。在
eryksun提供了关于这个问题的很好的注释,基于它们的编辑显示了如何安装一个通用的、机器范围的shebang行感知启动器,用于通过将
.
添加到$env:PATHEXT
来执行的无扩展脚本。在这种方法需要注意的事项:
PowerShell当前(从PowerShell Core 6.2.0开始)总是在新的控制台窗口中执行无扩展名的文件,这使得PowerShell中的此配置无效—不过,从
cmd.exe
开始,它确实按预期工作。在该机制存在潜在的安全风险,因为任何没有扩展名且带有shebang行的纯文本文件都会有效地变为可执行文件,从而可能会绕过针对具有已知可执行扩展名的文件的安全功能。
通过[PowerShell]脚本实现文件类型定义的默认操作总是需要使用脚本文件的解释器创建一个子进程,在本例中,这意味着使用其}。
-File
参数调用{powershell.exe
的启动性能成本非常高,这会延迟执行。如果您确实想实现这种通用机制,请参见底部的
Install-ShebangSupport.ps1
脚本。鉴于上述情况,这里有一个更轻量级的Python特定方法,它基于自动为无扩展shebang行Python脚本创建单个
*.ps1
包装脚本:这充分利用了PowerShell只允许按文件名执行自己的
*.ps1
脚本文件这一事实。在限制:
您需要至少运行一次包装器脚本生成脚本(如下所示),每次添加新的无扩展的Python脚本时。
可以想象,可以使用一个文件系统观察程序来触发生成脚本,但是设置它是一项非常重要的工作。
好的一面是,包装器脚本比基于文件类型的通用解决方案执行得更快,因为不涉及额外的PowerShell实例(子进程)。在
从无扩展Python脚本所在的目录运行以下脚本[1]:
对于每个无扩展的Python脚本}的退出代码被传递。
somescript
,都会创建一个配套的somescript.ps1
文件,该文件将somescript
传递给Python启动器py.exe
,以及任何命令行参数;exit $LASTEXTICODE
确保{正如eryksun所说,
py.exe
应该能够解释shebang行以调用适当的Python可执行文件。在如果您不想让包装器文件扰乱系统,自动生成函数作为另一种选择,但请注意,您必须将它们加载到每个会话中才能使用,通常通过
^{pr2}$$PROFILE
文件:注意:
这将使当前目录的无扩展名Python脚本可用,就好像它们位于
$env:PATH
中列出的目录中一样,无论当前目录是否列在那里。每个目标Python脚本都被硬编码到一个同名的函数中,并始终以该脚本为目标。在
*.ps1
包装器脚本文件方法允许在给定目录中进行目标调用,类似于.\foo
。在Invoke-Expression
的这种特殊用法是安全的,可以根据可扩展字符串定义函数,但是^{脚本
Install-ShebangSupport.ps1
用于安装直接执行的通用支持基于Windows的无扩展shebang行脚本:该脚本支持在当前用户级别(默认情况下或使用
-Scope CurrentUser
)或所有用户级别安装(使用-Scope AllUsers
,需要以管理员身份运行)。假设当前目录中存在,运行
Get-Help .\Install-ShebangSupport
以获得基本帮助。不带参数调用脚本将打印一个确认提示,其中包含对系统所需修改的详细信息;Ctrl-C可用于在不安装的情况下中止;传递
-Force
执行安装而不提示确认。要稍后卸载,请传递
-Uninstall
;请注意,您必须匹配安装期间使用的(隐含的)-Scope
值。实现说明:通过
cmd.exe
-内部命令assoc
和ftype
定义无扩展名文件类型对所有用户都有效,因为这些定义存储在HKEY_LOCAL_MACHINE\Software\Classes
的注册表中;而且,调用也总是需要提升(管理权限)。但是,可以通过直接操作注册表来创建用户级定义,这也是该脚本用于计算机级定义的方法。
注意:语法突出显示在下面的代码中被打断,但它确实起作用。
[1]在Windows PowerShell中,您可以使用
Get-ChildItem -File -Filter *.
来更方便、更高效地查找无扩展名的文件,但从v6.2.0开始,PowerShellCore中该功能已被破坏-请参见this GitHub issue。相关问题 更多 >
编程相关推荐