用於在沒有互動式編輯器的情況下編輯配置文件值的命令行
許多配置文件是基於格式的
Key value
,或者Key=value
每個配置文件都有一行。許多包提供了一個預設配置文件,其中這些可用的配置鍵已經用它們的預設值寫入和/或被註釋。我想知道是否有一種工具可以更改此類文件而無需打開互動式編輯器並且比
sed
(可能建構在它之上)更高級別。那將是簡單的:
$ conftool file key value
它會在文件中找到鍵,刪除註釋符號(如果有),更改值並保存結果。
據我所知,沒有通用的配置換行工具。我想創建這樣的工具會很困難,因為有很多不同的配置文件語法。
如果要更改特定配置文件中的特定值,則可以為該特定任務編寫專用工具。
這裡有兩個使用 sed 和 awk 的範例來幫助您入門
一個簡單的 sed 命令,用於替換鍵的值以獲得簡單的
key value
語法$ sed 's/^key2 value2$/key2 newvalue2/' config
例子
$ cat config key1 value1 key2 value2 key3 value3 $ sed 's/^key2 value2$/key2 newvalue2/' config key1 value1 key2 newvalue2 key3 value3
但請注意:如果有更多
key2 value2
行(可能在配置文件的其他部分),那麼所有行都將被替換。這在 sed 中很難防止(可能但很難),在 awk 中更容易。請參閱下面的有關部分的 awk 命令。解釋:
此 sed 命令大致執行以下操作:
for every line: if line is "key2 value2": print "key2 newvalue2"
此 sed 命令
s/pattern/replace/
意味著:在每一行中搜尋pattern
,如果找到,則替換為replace
.pattern
可以是普通字元串或正則表達式(正則表達式)。正則表達式中的
^
and&
被稱為錨點,分別表示行首和行尾。如果沒有錨,此模式key2 value2
也將匹配此行xkey2 value2x
,結果將是xkey2 newvalue2x
.這裡有一些例子,我們可以如何改變模式的行為。
也適用於
key=value
語法$ sed 's/^key2=value2$/key2=newvalue2/' config
無論舊值如何,都只匹配鍵
$ sed 's/^key2=.*/key2=newvalue2/' config
刪除可能的評論標誌
$ sed 's/^#\?key2 value2$/key2 newvalue2/' config
如果您重定向輸出,您還可以列印到 stderr
$ sed 's/^#\?key2 value2$/key2 newvalue2/ w /dev/stderr' config > newconfig
您可以使用正確的正則表達式做更多事情。但這將是另一個問題的另一個答案。
這是一個也可以處理配置部分的 awk 腳本
/^\[section2\]$/ { print insection2=1 next } insection2 && /^#?key2=value2$/ { print "key2=newvalue2" next } /^\[.*\]$/ { insection2=0 } 1
像這樣使用
$ awk -f configer.awk config
例子
$ cat config [section1] key1=value1 key2=value2 [section2] key1=value1 key2=value2 [section3] key1=value1 key2=value2 $ awk -f configer.awk config [section1] key1=value1 key2=value2 [section2] key1=value1 key2=newvalue2 [section3] key1=value1 key2=value2
您還可以向 stderr 添加詳細輸出,以便在重定向輸出時查看發生了什麼變化
insection2 && /^#?key2=value2$/ { print "key2=newvalue2" print "changed line "NR > "/dev/stderr" next }
awk 腳本的簡短說明
第一條規則查找
[config2]
節標題。它將insection2
標誌設置為真第二條規則查找該
key2=value2
行。但前提是insection2
標誌為真。然後它將使用新值列印該行。第三條規則查找任何其他節標題。它會將
insection2
標誌重置為假。最後一條規則(唯一的
1
)是“預設規則”。它只會列印未更改的行。在虛擬碼中
for every line: if line is [section2]: note that we are in section2 else if we are in section2 and line is key2=value2: print modified line else if line is any other section header: note that we are no longer in section2 else print line unchanged