バッシュマニュアル は言う:
Bashは、標準の入力がネットワーク接続に接続された状態で実行されているとき、リモートシェルデーモン(通常はrshd)またはセキュアシェルデーモンsshdによって実行されている場合を判断します。この方法で実行されているとBashが判断した場合、そのファイルが存在して読み取り可能であれば、〜/ .bashrcからコマンドを読み取って実行します。
このBashソース~/.bashrc
:
ssh user@Host :
しかし、このBashは~/.bash_profile
:
ssh user@Host
仕様によると、これら2つのコマンドに違いはありません。どちらの場合もstdinはネットワーク接続に接続されていませんか?
ログインシェルは最初に/etc/profile
を読み取り、次に~/.bash_profile
を読み取ります。
非ログインシェルは/etc/bash.bashrc
から読み取り、次に~/.bashrc
から読み取ります。
なぜそれが重要なのですか?
man ssh
のこの行のため:
commandが指定されている場合、ログインシェルではなくリモートホストで実行されます。
言い換えると、sshコマンドにオプションのみ(コマンドではなく)がある場合、次のようになります。
ssh user@Host
ログインシェルが起動し、ログインシェルは~/.bash_profile
を読み取ります。
commandのあるsshコマンド:
ssh user@Host :
コマンドが:
である(または何もしない)。
notがログインシェルを開始するため、~/.bashrc
が読み取られます。
リモートコンピューターの/ dev/stdinに提供されたtty接続は、実際のttyまたはその他の何かである可能性があります。
ために:
$ ssh sorontar@localhost
/etc/profile sourced
$ ls -la /dev/stdin
lrwxrwxrwx 1 root root 15 Dec 24 03:35 /dev/stdin -> /proc/self/fd/0
$ ls -la /proc/self/fd/0
lrwx------ 1 sorontar sorontar 64 Dec 24 19:34 /proc/self/fd/0 -> /dev/pts/3
$ ls -la /dev/pts/3
crw--w---- 1 sorontar tty 136, 3 Dec 24 19:35 /dev/pts/3
これは、開始されたbashが認識しているTTY(ネットワーク接続ではない)で終わります。
コマンドを使用したssh接続の場合:
$ ssh sorontar@localhost 'ls -la /dev/stdin'
sorontar@localhost's password:
lrwxrwxrwx 1 root root 15 Dec 24 03:35 /dev/stdin -> /proc/self/fd/0
TTYのリストも同じですが、/ etc/profileが提供されていないことに注意してください。
$ ssh sorontar@localhost 'ls -la /proc/self/fd/0'
sorontar@localhost's password:
lr-x------ 1 sorontar sorontar 64 Dec 24 19:39 /proc/self/fd/0 -> pipe:[6579259]
これは、接続が(ネットワーク接続ではなく)パイプであることをシェルに伝えます。
したがって、どちらのテストケースでも、シェルは接続がネットワークからのものであることを認識できないため、~/.bashrc
を読み取りません(ネットワークへの接続についてのみ話している場合)。 〜/ .bashrcを読み取りますが、別の理由があります。
「どうして」ではなく「なぜ」を問うので、そういう視点で答えていきます。以下は、物事が過去に起こって今日のように起こった理由のかなりの根拠になります。
2つの異なるスタートアップファイル( "profile"と "rc")がある理由は、以前はマシンで作業する一般的な方法が次のとおりだったからです。
ある種の実際の端末または他のワークステーションからログインして、ログインシェルを取得します。このシェルは/etc/profile
および~/.profile
を呼び出し、ユーザーの環境をセットアップします。
ユーザーが入力したい環境を呼び出します。この環境はXorgである可能性がありますが、ほとんどの場合、GNU画面などのマルチプレクサでした。
環境(例:GNU screen)は、親のログインシェルから環境を継承する追加の(非ログイン)シェルを呼び出します。
これは、csh
およびbash
が開発されている間、UNIXマシンにログインする一般的な方法でした。したがってとにかく環境を継承していたシェルで~/.profile
をもう一度読み取ることは無駄であると見なされました。
bash
次に、これらの非ログインシェルの追加設定のために~/.bashrc
を追加しました。 csh
(およびtcsh
)は、非ログインシェル用の「rc」ファイルを一切追加していません。 csh
はボーンシェル(POSIXの一部)と互換性のあるシェルではありませんが、tcsh
/bash
はシェルと互換性がないことに注意してください。別のボーン互換シェルksh
は、環境変数(ENV
と呼ばれる)を追加しました。これが定義されていれば、非ログイン用の実行コマンド( "rc")ファイルとして使用されますksh
。
そう、そうです、新しいバージョンのbourneシェルは、GNU画面(または類似の)によって多重化されたシェル内に存在するが、シェルには存在しないエイリアスやその他のクイックオプションの便宜として、追加の構成ファイルを追加しました最初にマシンに入ったときに取得します。
グラフィカルディスプレイマネージャー(GDM)の登場により、GDMには独自の初期化ファイル(例:~/.xinit
および~/.xsession
)があるため、「プロファイル」ファイルと「rc」ファイルの区別は無意味になりました。次に、GDM内から記述されたシェルは、ユーザーの気まぐれに応じてログインシェルまたは非ログインシェルである可能性があり、非ログインシェルが常にログインシェルである親を持つケースはもはや当てはまりません。
シェルの起動ファイルの比較についての私の お気に入りのテーブル の1つは、bourne Shell互換シェルがprofile
ファイルをどのように使用するのか、他のシェルは使用しないのかを示しています。これは、以前は最初のシェル(マルチプレクサを起動したシェル)がボーン互換シェルである必要があったためです。