我有文件unbound.conf
如下
## Simple recursive caching DNS, UDP port 53
## unbound.conf -- https://calomel.org
#
server:
access-control: 10.0.0.0/8 allow
verbosity: 1
forward-zone:
name: "."
forward-addr: 8.8.4.4 # Google
forward-addr: 8.8.8.8 # Google
forward-zone:
name: "example.com"
forward-addr: 50.116.23.211 # Open
some-other-config:
key: "value"
我从变量说FORWARD_ZONES获得前向区域,其样本值为
forward-zone:
name: "somedns.com"
forward-addr: 1.1.1.1
forward-addr: 2.2.2.2
forward-zone:
name: "someotherdns.com"
forward-addr: 3.3.3.3
forward-addr: 4.4.4.4
我需要删除conf文件中的所有前向区域,并根据收到的输入json数组创建新区域。
因此,在应用正则表达式结束时,我希望基于以上输入进行跟踪
## Simple recursive caching DNS, UDP port 53
## unbound.conf -- https://calomel.org
#
server:
access-control: 10.0.0.0/8 allow
verbosity: 1
forward-zone:
name: "somedns.com"
forward-addr: 1.1.1.1
forward-addr: 2.2.2.2
forward-zone:
name: "someotherdns.com"
forward-addr: 3.3.3.3
forward-addr: 4.4.4.4
some-other-config:
key: "value"
我应该使用什么正则表达式使用sed来实现上述
sed -i "whatShouldBeRegexStringHereThatUses_FORWARD_ZONES_variable" unbound.conf
编辑: 这是一个操场,也展示了我做了什么 https://regex101.com/r/x0H2p3/1/
答案 0 :(得分:0)
我相信可以通过以下方式awk
实现这一目标:
awk 'BEGIN{p=1}
/^[-a-zA-Z]*:[[:blank:]]*$/{p=1}
/^forward-zone:[[:blank:]]*$/{p=0}
(p==0&&v==0){print var;print ""; v=1}
p' var=$FORWARD_ZONES foo.conf
如果需要打印一行,它基本上会检查变量p
。如果它找到带有正则表达式^[-a-zA-Z]*:[[:blank:]]*$
的新配置块,则它将默认设置printflag p=1
,但是如果配置块为^forward-zone:[[:blank:]]*$
,它将禁用打印。第一次禁用打印时,它会注入$FORWARD_ZONES
。
如果您的前方区域位于另一个名为forward_zones.conf
的文件中,那么您可以使用
awk 'BEGIN{p=1}
/^[-a-zA-Z]*:[[:blank:]]*$/{p=1}
/^forward-zone:[[:blank:]]*$/{while(getline line<f2){print line); p=0}
(p==0&&v==0){print ""; v=1}
p' f2=forward_zones.conf foo.conf
答案 1 :(得分:0)
在GNU sed中:sed -e "/forward-zone/,/^\s*$/d;/some-other/i $FORWARD_ZONES" input-file
使用/START/,/END/d
和/some-other/i
插入$FORWARD_ZONES
示例输出:
$ export FORWARD_ZONES="newjunk\nnewjunk\n" $ sed -e "/forward-zone/,/^\s*$/d;/some-other/i $FORWARD_ZONES" fz.txt server: access-control: 10.0.0.0/8 allow verbosity: 1 newjunk newjunk some-other-config: key: "value"
如果您希望使用GNU sed插入另一个文件的内容,可以插入new.txt
:
sed -e "/forward-zone/,/^\s*$/d;/some-other/e cat new.txt" fz.txt
使用GNU sed e
命令转出cat new.txt
,该命令会立即附加到输出流中。
非GNU sed可能需要i
之后的换行符,并且不支持e
命令。简单的解决方法是创建一个用于sed -f
的命令文件。
答案 2 :(得分:0)
以下为我工作
sed -zri 's/(forward-zone:\s*\n\s*name: \".*\"\s*\n\s*(forward-addr: [0-9\.]*.*\s*\n\s*)+\s*\n\s*)+/$FORWARD_ZONES/' unbound.conf
我需要获得有效的正则表达式 https://regex101.com/r/x0H2p3/2
然后使用sed和
'-z'
'--null-data'
'--zero-terminated'
Treat the input as a set of lines, each terminated by a zero byte
(the ASCII 'NUL' character) instead of a newline. This option can
be used with commands like 'sort -z' and 'find -print0' to process
arbitrary file names.
和
'-E'
'-r'
'--regexp-extended'
Use extended regular expressions rather than basic regular
expressions. Extended regexps are those that 'egrep' accepts; they
can be clearer because they usually have fewer backslashes.
Historically this was a GNU extension, but the '-E' extension has
since been added to the POSIX standard
(http://austingroupbugs.net/view.php?id=528), so use '-E' for
portability. GNU sed has accepted '-E' as an undocumented option
for years, and *BSD seds have accepted '-E' for years as well, but
scripts that use '-E' might not port to other older systems. *Note
Extended regular expressions: ERE syntax.