[英]Replace placeholders with corresponding env variables
我有一個帶有像這樣的占位符的配置文件(本示例存儲在/tmp/var
中)
ldap_bind_dn='${bind_dn}'
現在我想將${bind_dn}
替換為同名的環境變量(在 Docker 中設置)。
export $bind_dn=CN=my-user,CN=Users,DC=example,DC=com
處理上述測試文件后的預期結果將是
ldap_bind_dn='CN=my-user,CN=Users,DC=example,DC=com'
我試過sed
但它沒有將它替換為 env 變量的值
$ sed "s#\${\(.*\)}#$\1#" /tmp/var
bind_dn='$bind_dn'
為什么sed
替換為$bind_dn
而不是值? 我希望變量被處理,因為我沒有轉義$
符號。
表達式本身有效,只有替換無效:
$ sed "s#\${\(.*\)}#test123#" /tmp/var
bind_dn='test123'
當目標變量被硬編碼時,替換也正確完成
$ sed "s#\${\(.*\)}#$bind_dn#" /tmp/var
bind_dn='CN=my-user,CN=Users,DC=example,DC=com'
但由於我們有一堆配置變量,我想自動替換所有格式${NAME}
的環境變量。
不是最優雅的解決方案,但這個適用於 bash:
sed 's#\${\(.*\)}#`{echo,"$\1"}`#' /tmp/var | xargs -n1 -I{} echo echo "{}" | bash -s
這有點棘手,因為您需要執行 bash 來執行變量替換,這就是為什么我將它傳遞給bash -s
雖然可以通過使用mapfile
執行eval
來解析 env 變量,但這似乎不適合我,因為它是一個 ini 配置文件。 標有[general]
等括號的部分會引發錯誤。 而且我還擔心只執行允許執行任何命令的整行。
這是由以下awk
的:
awk '{while(match($0,"[$]{[^}]*}")) {var=substr($0,RSTART+2,RLENGTH -3);gsub("[$]{"var"}",ENVIRON[var])}}1' < /tmp/var > /tmp/var
為什么 sed 替換為 $bind_dn 而不是值?
因為sed不應該在其模式空間中進行 shell 參數擴展。 這主要是 shell 的工作。
使用 GNU sed :
~> cat /tmp/var
ldap_bind_dn='${bind_dn}'
~> export bind_dn=CN=my-user,CN=Users,DC=example,DC=com
~> sed -E 's/^\w+=.*/echo "&"/e' /tmp/var
ldap_bind_dn='CN=my-user,CN=Users,DC=example,DC=com'
e
命令(GNU 擴展)
sed -E 's/^\w+=.*/echo "&"/e'
執行在模式空間中找到的命令並將模式空間替換為 output。 對於此示例,模式空間是ldap_bind_dn='${bind_dn}'
,並替換為echo "ldap_bind_dn='${bind_dn}'"
( &
引用echo "&"
中的模式空間的整個匹配部分)。 由於echo
的參數是雙引號,所以在shell執行時會受到參數擴展的影響。
警告:確保文件(本例中為 /tmp/var)來自受信任的來源。 否則它可能包含像foo='$(some_nasty_command)'
這樣的行,當上面的sed命令運行時執行。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.