findで見つけたフォルダの代わりに空白行が表示されるのはなぜですか?
ssh -o stricthostkeychecking=no -o userknownhostsfile=/dev/null \
-o batchmode=yes -o passwordauthentication=no [email protected] \
"sudo find /folder/CFGKCP/KCS\ Pro/Job\ Setup -name JOBCFG.info \
| while read linea; do echo $linea; done";
答え1
Romeoが指摘したように、コマンドの周りに二重引用符を使用します。これは、コマンドを実行する前に変数が拡張されることを意味しますssh
。したがって、whileループの本文は次のようになります。
echo $linea
以前は存在しなかった可能性があるため、渡されssh
linea
たコマンドは空の文字列にecho
置き換えられます。linea
コマンドパラメータの周りに一重引用符を使用すると、パラメータ拡張が発生せず、文字列がそのまま渡されるので問題ありません。
ssh -o stricthostkeychecking=no -o userknownhostsfile=/dev/null -o batchmode=yes -o passwordauthentication=no [email protected] 'sudo find /folder/CFGKCP/KCS\ Pro/Job\ Setup -name JOBCFG.info | while read linea; do echo $linea; done'
あるいは、エスケープすると$
シェルが拡張しないように指示します。
答え2
二重引用符を使用しているからです。これは、$linea
実行前に拡張されたことを意味します。ssh
以下を使用してこれをテストできますset -x
。
$ set -x
$ ssh user@host "find /var | while read line; do echo $line; done"
+ ssh user@host 'find /var | while read line; do echo ; done'
ご覧のとおり、実際に実行されるコマンドにはecho
変数はありません。これを防ぐには、二重引用符の代わりに一重引用符を使用できます。
ssh user@host 'find /var | while read line; do echo "$line"; done'
またはローカルでwhileループを実行します。
ssh user@host find /var | while read line; do echo "$line"; done
上記の例では、コマンドの出力に従ってfind
リモートホストで実行され、ローカルで実行されます。while
ssh
答え3
ループを避けてくださいwhile read
。
ssh [email protected] '
sudo find "/folder/CFGKCP/KCS Pro/Job Setup" -name JOBCFG.info -exec sed -i "
/^\[General]/,/^\[/ {
s/^JobRoot = .*/JobRoot = C:\\\\LOTES\\\\TMP\\\\\r/
}" {} +'
または一重引用符を使用してください。
ssh [email protected] '
sudo find "/folder/CFGKCP/KCS Pro/Job Setup" -name JOBCFG.info -exec sed -i '\''
/^\[General]/,/^\[/ {
s/^JobRoot = .*/JobRoot = C:\\LOTES\\TMP\\\r/
}'\'' {} +'
(これは\r
すでにGNUに固有のものであるため、これを使用することもできます-i
。)
答え4
変数を引用符で拡張する方法について説明していただきありがとうございます。これで問題が始まる場所を理解しました。エコーの代わりに順序を使用するため、入れ子になった単一引用符を使用する必要があります。より詳細な例は次のとおりです。
ssh [email protected] '
sudo find /folder/CFGKCP/KCS\ Pro/Job\ Setup -name JOBCFG.info|
while read line; do
sudo sed '/^\[General\]/,/^\[/ {s/^JobRoot = .*/JobRoot = C:\\LOTES\\TMP\\\r/}' "$line" |sudo tee "$line".modificado; sudo mv -f "$line".modificado "$line";
done
';