他のスクリプトから取得したスクリプトの中には、シバン#!/path/to/NAME
が含まれているものがあります。 他の人(同じツール、NAMEを使用)はシバン#!/usr/bin/env NAME
を持っています 。
どちらも正常に動作しているようです。チュートリアル(たとえばPython)では、後者のシバンの方が優れているという提案があるようです。しかし、なぜそうなのかよくわかりません。
後者のシバンを使用するには、NAMEがPATHに含まれている必要がありますが、最初のシバンにはこの制限がないことを理解しています。
また、NAMEがどこにあるかを正確に指定しているので、(私には)最初の方がより良いシバンであるように見えます。したがって、この場合、NAMEのバージョンが複数ある場合(たとえば、/ usr / bin / NAME、/ usr / local / bin / NAME)、最初のケースでどちらを使用するかを指定します。
私の質問は、なぜ最初のシバンが2番目のシバンよりも好まれるのかということです。
承認された回答:
目的の基準/要件:
絶対を使用するかどうかを決定する際に または論理的 (/usr/bin/env
)彼女の通訳への道-強打、(2)重要な考慮事項があります:
a)通訳 ターゲットシステムで見つけることができます
b)正しいバージョン 通訳の ターゲットシステムで見つけることができます
同意する場合 その「b) 」が望ましいです。同意します :
c)スクリプトが失敗することが望ましい 誤ったインタプリタバージョンを使用して実行し、一貫性のない結果をもたらす可能性があるのではなく。
同意しない場合 その「b) 」が重要な場合は、見つかった通訳ならどれでも十分です。
テスト:
論理を使用してから パス-/usr/bin/env
she-bangのインタプリタは、同じインタプリタへの異なるパスを持つターゲットホストで同じスクリプトを正常に実行できるようにする最も拡張可能なソリューションです。人気があるため、Pythonを使用してテストし、それが満たされるかどうかを確認します。私たちの基準。
-
/usr/bin/env
を実行します 人気の予測可能で一貫した場所に住んでいる (「すべて」ではありません ") オペレーティングシステム? はい :
- RHEL 7.5
- Ubuntu 18.04
- Raspbian 10(「バスター」)
- OSX 10.15.02
- 以下のPythonスクリプトは、仮想エンベロープの内側と外側の両方で実行されます( Pipenv 使用)テスト中:
#!/usr/bin/env pythonX.x import sys print(sys.version) print('Hello, world!')
- スクリプトのshe-bangは、必要なPythonバージョン番号によって切り替えられました(すべて同じホストにインストールされています):
- #!/ usr / bin / env python2
- #!/ usr / bin / env python2.7
- #!/ usr / bin / env python3
- #!/ usr / bin / env python3.5
- #!/ usr / bin / env python3.6
- #!/ usr / bin / env python3.7
-
期待される結果:その
print(sys.version)
=env pythonX.x
。毎回./test1.py
インストールされている別のPythonバージョンを使用して実行された場合、she-bangで指定された正しいバージョンが印刷されました。 -
テストノート:
- テストはPythonのみに限定されていました
- Perl:Pythonのように-必須
/usr/bin
に住んでいます FHSによると - Linuxy / Unixオペレーティングシステムのすべての可能な数と各オペレーティングシステムのバージョンで、可能なすべての組み合わせを試したわけではありません。
結論:
#!/usr/bin/env python
というのは本当ですが ユーザーのパスで見つかったPythonの最初のバージョンを使用します。#!/usr/bin/env pythonX.x
などのバージョン番号を指定することで、この動作を緩和できます。 。実際、開発者はどのインタプリタが「最初に」見つかるかを気にしません。 「彼らが気にしているのは、コードと互換性があることがわかっている指定されたインタープリターを使用してコードを実行し、一貫した結果を保証することです。ファイルシステム内のどこにでも存在する可能性があります …
移植性/柔軟性の観点から、論理的を使用 – /usr/bin/env
–絶対ではなく パスは、さまざまなバージョンの Python を使用したテストの要件a)、b)、c)を満たしているだけではありません。 、しかし、ファジーロジックが異なるオペレーティングシステム上の異なるパスに存在する場合でも、同じバージョンのインタープリターを見つけるという利点もあります。そしてほとんど ディストリビューションはFHSを尊重しますが、すべてが尊重するわけではありません。
したがって、スクリプトが失敗する バイナリが異なる絶対に存在する場合 次に、パスをshebangで指定します。これは、論理を使用した同じスクリプトです。 パス成功 一致するものが見つかるまで続行するため、プラットフォーム間での信頼性と拡張性が向上します。