Bash、grep - キャレットを含むコマンドがサブシェルで機能しないのはなぜですか?

Bash、grep - キャレットを含むコマンドがサブシェルで機能しないのはなぜですか?

git add特定のアクションによって予想される修正が作成されたことを確認しようとしています。次は対話型シェルで機能します。

$ BASE_DIR=foo/bar/baz
$ git add "${BASE_DIR}"
$ git status --porcelain
M  foo/bar/baz/a.txt
M  foo/bar/baz/b.txt
$
$ git status --porcelain | grep "^M  ${BASE_DIR}"
$ echo $?
0

台本で書きたい

if $(git status --porcelain | grep "^M  ${BASE_DIR}"); then
  git commit -m "changes added"
  git push
fi

ただし、コマンドをサブシェルに移動すると失敗します。

$ if $(git status --porcelain | grep "^M  ${BASE_DIR}"); then echo true; fi
M: command not found

サブシェルのカラットの特別な点は何ですか?

答え1

(質問を作成するためにすべての操作を実行した後にエラーが見つかったために公開されました。)

文字列のカラットには特別なものはありません。このコマンドは$(git status --porcelain | grep "^M ${BASE_DIR}")与えられたテストを正しく実行しています捕獲サブシェルの出力です。これの出力(「M foo/bar/baz/a.txt」と同様)は次のとおりです。処刑された引数として指定すると、if「M:コマンドが見つかりません」というエラーが発生します。

この問題を解決するには、角かっこを削除して出力を削除します。戻り値はパイプラインの最後のコマンド値です。

if git status --porcelain | grep --quiet "^M  ${BASE_DIR}"; then ...

関連情報