shebang中哪种类型的路径更可取?


20

在脚本中,第一行应指定解释器的路径。
但是在不同的服务器Linux,Unix或BSD上,此路径可能不同。

什么更可取?

#!/usr/bin/env bash 

要么

#!/bin/bash 

Answers:


22

如果要使用安装在标准位置的给定解释器的系统安装版本,请使用直接路径。如果要使用解释器的第一个版本出现在用户的版本中$PATH,请使用#!/usr/bin/env ...

env命令调用指定的命令,可让您设置或取消设置环境变量:

env FOO=BAR do-something
env DISPLAY=:0.0 xterm -ls &

如果您未指定任何环境变量或其他选项,它将仅调用命名的命令。(以这种方式使用可以说是一个小技巧。)

编写shebang的目的是

#!/usr/bin/env interp

是调用interp中首先出现的内容$PATH

这意味着你不必知道,写剧本的时候,正是interp为(比方说,如果它的形式可以是/bin/usr/bin/usr/local/bin)。当然,你必须知道env/usr/bin/env,但是,这似乎是相当普遍的。

这样做的好处是,它会调用解释器的第一个版本,该版本首先出现在用户的中$PATH。的缺点是,它调用哪个解释的第一个版本出现在用户的$PATH

例如,假设我已经perl在主目录as下安装了一个个人版本$HOME/bin/perl,并且我$HOME/bin在的前面$PATH。如果我运行的脚本的shebang是

#!/usr/bin/env perl

然后它将与我自己安装的perl可执行文件一起运行-可能不是一件好事。该脚本的作者可能还没有使用我一个月前从源代码构建的尖端Perl对其进行测试。

对于像Perl或Bash这样的东西,它们可能会安装在大多数系统上的一致位置(分别为/usr/bin/perl/bin/bash),我将使用命令的直接路径。对于可能在不同系统上不同安装的更晦涩的东西,我要么使用/usr/bin/env技巧,要么编写一个安装程序来在安装脚本时调整shebang行。(我以前必须在Perl脚本中这样做。)

更新:我在Unix&Linux站点上对这个问题的回答中更加详细了。


我刚刚开始研究Ruby,为了便于移植,我发现Ruby中的约定以[code]#!/ usr / bin / env ruby​​ [/ code]开头。一些人指出,这很难为ruby解释器提供命令行参数,例如'-w',这对于Perl也是一个问题。
bgvaughan 2011年

@bgvaughan对于Perl来说,如今是很传统的用法#!/usr/bin/perl,然后use strict; use warnings;在脚本正文中使用,而不是使用#!/usr/bin/perl -w。但是-T必须在shebang上。
基思·汤普森

那么,如果我们只想要第一个路径,为什么不使用#!perl?
whered那名字来自

@wheredidthatnamecomefrom:因为那不起作用。#!线路的处理不使用$PATH。您必须指定解释器的路径。(我只是意识到,至少在我的系统上,它可能是相对路径,但这很少有用。)
Keith Thompson

6

最佳做法是:

#!/usr/bin/env bash 
#!/usr/bin/env sh
#!/usr/bin/env python

等等...

当Ubuntu首次开始使用破折号时,一些脚本中断了。有关于它的讨论。大多数脚本是写到#!/bin/sh/ bin / bash的链接的。共识是:脚本编写者负责指定解释器。因此,如果应始终使用BASH调用脚本,请从环境中进行指定。这省去了猜测路径的麻烦,这在各种Unix / Linux系统上都是不同的。另外,如果明天/ bin / sh成为到其他外壳程序(如/ bin / wthsh)或其他一些废话的链接,它将起作用。


破折号问题的明显替代解决方案是编写#!/bin/bash。我同意脚本编写者负责指定解释器,但这仅是如果您需要bash,请说bash而不是sh
Martin Bonner支持Monica

1

仅供参考,这是一个爆炸声#!,您需要#。您可以使用此行来标识运行脚本的解释器。

默认情况下,Ubuntu链接/bin/sh到破折号

根据您可能希望了解多少有关破折号以及为什么将破折号用于系统或守护进程shell的信息,请参阅:

cyberciti.biz破折号

Ubuntu破折号手册页

Bash是大多数Linux用户使用的默认Shell,其功能与破折号不同。如果使用破折号运行,则为bash编写的脚本可能会或可能不会正确运行,脚本越复杂,运行的可能性就越小。

为Perl,Python等脚本编写不会在所有运行/bin/sh/bin/bash

因此,当您编写脚本时,您会确定在Shee-bang中应使用哪种解释器

脚本的作者选择了要使用的内容,一个不比另一个好,它们都有各种功能,优点和缺点。


By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.