Today a coworker posed an interesting question to me.
Given a BIG-IP configuration file with thousands of records like this…
gtm pool /Common/p_example {
members {
/Common/2001:668:fc78:0:f811:3ef2:fed7:98cc:vs6_2001_668_fc78_0_f811-3ef2-fed7_98cc-80 {
order 0
}
}
monitor /Common/gateway_icmp
}
…how can we easily replace every colon in the name :
with \\:
?
In short, /Common/2001:668:fc78:0:f811:3ef2:fed7:98cc:vs6_2001_668_fc78_0_f811-3ef2-fed7_98cc-80
needed to become /Common/2001\\:668\\:fc78\\:0\\:f811\\:3ef2\\:fed7\\:98cc\\:vs6_2001_668_fc78_0_f811-3ef2-fed7_98cc-80
.
This must only be done on the lines with start with /Common
and which also contain the string vs6
. He could not guarantee that colons would not be found elsewhere in the file.
This required some Googling on my part before I realized that sed has this ability natively. In short, you can specify a regular expression or string which must be matched before sed will perform any substitutions.
Here’s what I came up with: sed '/\/Common.*vs6/s/:/\\\\:/g'
[18:24] james_simas@widget ~/Downloads $ cat example_file.txt
gtm pool /Common/p_example {
members {
/Common/2001:668:fc78:0:f811:3ef2:fed7:98cc:vs6_2001_668_fc78_0_f811-3ef2-fed7_98cc-80 {
order 0
}
}
monitor /Common/gateway_icmp
}
[18:24] james_simas@widget ~/Downloads $ cat example_file.txt | sed '/\/Common.*vs6/s/:/\\\\:/g'
gtm pool /Common/p_example {
members {
/Common/2001\\:668\\:fc78\\:0\\:f811\\:3ef2\\:fed7\\:98cc\\:vs6_2001_668_fc78_0_f811-3ef2-fed7_98cc-80 {
order 0
}
}
monitor /Common/gateway_icmp
}
[18:24] james_simas@widget ~/Downloads $