リモートマシンでスクリプトを実行したかったのです。簡単な解決策は次のとおりです。
ssh remote1 some-script
これは、リモートスクリプトが、このようなインタラクティブな認証を必要とする別のリモートマシン(remote2
)に接続する必要がなくなるまで機能します(この場合、remote2
はremote1
を介してのみ到達可能です) :
ssh remote1 "ssh remote2 some-script"
この問題の解決策は、sshに-t
オプションを使用することです。
ssh -t remote1 "ssh remote2 some-script"
これは機能しますが、これを使用するとプローブが表示されます(some-script
がさらにsshコマンドを実行する可能性があります)。
ssh -t remote1 some-script
-t
オプションを使用しない場合に設定されるいくつかの環境変数が設定されていないことがわかりました。これらの環境変数は、/etc/profile.d
のスクリプトで設定されます。 -t
オプションを使用すると、これらのスクリプトは何らかの理由で実行されないと思いますが、使用しない場合は実行されます。
これの理由は何ですか?それを回避する方法はありますか? SUSE linux(バージョン10)を使用しています。
編集:追加の調査を行いました。私はいくつかの出力行を次の場所に配置しました:
/etc/profile.d
の1つのファイル~/.bash_profile
(ファイルは以前は存在しませんでした)~/.bashrc
(ファイルは以前は存在しませんでした)次に、いくつかのシナリオで、どの出力をどのような順序で取得するかを確認しました(確認した環境変数は$PATH
です)。
ssh remote1
:profile.d
、.bashrc
、.bash_profile
。 $PATH
OK。ssh -t remote1
:profile.d
、.bashrc
、.bash_profile
。 $PATH
OK。ssh remote1 echo '$PATH'
:.bashrc
のみ。 $PATH
OK。ssh -t remote1 echo '$PATH'
:スクリプト出力なし。 $PATH
いいえ。今、私は何が起こっているのか本当に理解していません。インタラクティブシェルを実行すると、すべてが正常に機能しているように見えます(ただし、~/.bashrc
が~/.bash_profile
の前に含まれているのは奇妙です)。 -t
なしで非対話型シェルを起動すると、プロファイルスクリプトが実行されていないように見えますが、環境変数は設定されています。 -t
で非対話型シェルを開始すると、プロファイルスクリプトが実行されず、環境変数が設定されません。誰かがこれについて説明がありますか?
問題の理由は見つかりませんでした。多分それはプラットフォーム(SLES 10または私が使用するバリエーション)に固有です。代わりに回避策を見つけました:
ssh -t remote1 "/bin/bash --login -c some-script"
これにより、プロファイルスクリプトを実行するログインシェルが強制されます。
すべての質問は、bashのmanページの「INVOCATION」セクションで回答されます。
Bashが対話型ログインシェルとして、または--loginオプションを指定した非対話型シェルとして呼び出されると、最初にファイル/ etc/profile(ファイルが存在する場合)からコマンドを読み取って実行します。そのファイルを読み取った後、〜/ .bash_profile、〜/ .bash_login、〜/ .profileの順に検索し、最初に存在して読み取り可能なコマンドからコマンドを読み取って実行します。 --noprofileオプションは、シェルの起動時にこの動作を禁止するために使用できます。
ログインシェルが終了すると、bashはファイル〜/ .bash_logout(存在する場合)からコマンドを読み取って実行します。
ログインシェルではない対話型シェルが開始されると、bashは〜/ .bashrcからコマンドを読み取り、実行します(そのファイルが存在する場合)。これは、-norcオプションを使用することで禁止できます。 --rcfile fileオプションは、bashに〜/ .bashrcではなくファイルからコマンドを読み取って実行するように強制します。
ご覧のとおり、インタラクティブシェルは.bashrc
のみをソースし、多くの場合.bash_profile
はそこからソースされます。これは、表示されている順序を説明しています。
多くの場合、これらのファイルには、インタラクティブシェルの特定のセクションのみを解析する条件([[ $- == *i* ]]
)もあります。これは、非インタラクティブシェルの一部が欠落しているように見える理由を説明します。
の違い
ssh remote1 echo '$PATH'
そして
ssh -t remote1 echo '$PATH'
bashのマンページでも説明されています。
Bashは、リモートシェルデーモン(通常は
rshd
)またはセキュアシェルデーモンsshd
によって実行される場合のように、標準入力がネットワーク接続に接続された状態で実行されているかどうかを判断しようとします。 bashは、この方法で実行されていると判断した場合、~/.bashrc
[これらのファイルが存在して読み取り可能であれば/etc/bash.bashrc
]と~/.bashrc
からコマンドを読み取って実行します。
最初の例では、bash
のstdinがネットワーク接続に接続されているため、~/.bashrc
が実行されます。 2つ目は、そのstdinが疑似端末からのものであるため、そうではありません。