Bash / Sed / Awkを使用してテンプレートファイルで変数名を見つけますか?

Bash / Sed / Awkを使用してテンプレートファイルで変数名を見つけますか?

現在、うまく機能するenvsubstを使用して処理しているいくつかのテンプレートファイルがあります。

<?php

$config['db_host'] = '${DB_HOST}';
$config['db_port'] = '${DB_PORT}';
$config['url'] = 'http://${WEB_HOST}/${WEB_PATH}';

// Please do NOT change this value
$config['maxSize'] = 25;

bashスクリプトを使用してファイルをスキャンして設定する必要があるすべての環境変数のリストを生成し、次のように.envファイルにダンプする方法を見つけようとします。

DB_HOST=
DB_PORT=
WEB_HOST=
WEB_PATH=

sedで可能だと思いましたが、30分間Googleで検索した例はすべてインライン変数を置き換える方法に関するものであり、一致を印刷する方法に関するものではありませんでした。

答え1

あなたの基準は次のとおり${です}

gawkこれは単独で使用することも、grepパターンマッチング部分を簡素化することもできます(ただし、後で追加の書式が必要です)。


グヌawk

gawk -v 'RS=[$]{' -F '}' '$1 ~ /^[A-Z_]+$/ && !a[$1]++ {printf "%s=\n", $1}' FILE
  • GNU awkはレコード区切り文字の正規表現を受け入れるので、それを割り当てると、パターンが発生するたびにRS=[$]{入力をレコードに分割します。FILE${
  • フィールド区切り文字が次に設定されています}- 各レコードの最初のフィールドを確認して、他の基準と一致することを確認できるようになりました。[A-Z_]
  • 重複エントリは次のように&& !a[$1]++削除されます。
  • =print ステートメントは、目的の出力に一致するように各行の末尾に等号を追加します。
  • また、注:ファイルの最初の部分は開始されていなくても常に最初のレコードとしてカウントされます。${つまり、ファイルが次のよう[A-Z_]+}に始まる場合(可能性なし)、これらの大文字/下線は「一致」して印刷されます。出力の最初の行

grep+フォーマット

grep-o/オプションのおかげで、理解しやすくなります--only-matching

grep -o '${[A-Z_]\+}' FILE
  • ただし、これは出力形式を指定しません。sedパイプを介してこれを行うことができます。
grep -o '${[A-Z_]\+}' FILE | sed 's/${\(.*\)}/\1=/'
  • 重複項目は削除されません。sort -u出力をパイピングするか、awkを介して一度パイピングして実行します。
grep -o '${[A-Z_]\+}' FILE | awk -F '[{}]' '!a[$0]++{printf "%s=\n", $2}'

答え2

これが私がしたことです。

cat file | grep -o '${\w*}' | sed -e 's|${||g' -e 's|}|=|g'

DB_HOST=
DB_PORT=
WEB_HOST=
WEB_PATH=

きれいではなくてもかなりよく似合いそうです!

または他の方法(で修正済み)https://unix.stackexchange.com/a/13467/229729):

cat file | sed -n -e 's/.*${\(\w\+\)}.*/\1=/p'

関連情報