Reputation: 532
I'm looking to build a startup script that will add a string of text between two patterns.
8.34.217.13 cds.rhel.updates.googlecloud.com
10.128.0.2 instance-1.c.testenvio1.internal instance-1 **want to add string here** # Added by Google
169.254.169.254 metadata.google.internal # Added by Google
I want it to look like this:
8.34.217.13 cds.rhel.updates.googlecloud.com
10.128.0.2 instance-1.c.testenvio1.internal instance-1 104.197.247.254 instance1.com # Added by Google
169.254.169.254 metadata.google.internal # Added by Google
I'm using the following sed command but it inserts my string when it encounters the first "instance-1"
sed -i 's/\<instance-1\>/& 104.197.247.254 instance1.com/' /etc/hosts
8.34.217.13 cds.rhel.updates.googlecloud.com
10.128.0.2 instance-1 104.197.247.254 instance1.com.c.testenvio1.internal instance-1 # Added by Google
169.254.169.254 metadata.google.internal # Added by Google
Upvotes: 3
Views: 2650
Reputation: 11469
Include the whitespace after instance-1
which distinguishes it from the first occurrence:
$ sed -i 's/instance-1 /&104.197.247.254 instance1.com /g' inputFile
OR
if you know it is always the second occurrence, then use, /2
to replace it,
$ sed -i 's/instance-1/& 104.197.247.254 instance1.com /2' inputFile
For future reference, if you want to add a string between two patterns
$ sed '/pattern1/,/pattern2/s//& INSERT THIS TEXT/g' inputFile
For this example, it would look like,
# You still need that whitespace to distinguish the second occurrence from first:
$ sed '/instance-1 /,/# Added/s//&104.197.247.254 instance1.com /g' inputFile
Upvotes: 0
Reputation: 21955
Perhaps some insight about where the data is coming from is certainly helpful here.
The # Added by Google
suggests that those lines contain information about Google Compute Engine instances. More importantly, they are lines added by Google and fortunately follows a predefined pattern.
In that case, something like below would help
$ sed -Ei -- 's/([[:blank:]]+instance-1[[:blank:]]+)(#.*)$/\1 104.197.247.254 instance1.com \2/' /etc/hosts
Output
8.34.217.13 cds.rhel.updates.googlecloud.com
10.128.0.2-instance-1-c.testenvio1.internal instance-1 104.197.247.254 instance1.com # Added by Google
169.254.169.254 metadata.google.internal # Added by Google
Sidenote: The actual number of spaces are preserved too.
Upvotes: 1
Reputation: 6377
Try this:
sed -i 's/^\([0-9.]* [^ ]* \<instance-1\>\)/\1 104.197.247.254 instance1.com/' /etc/hosts
This expression will read the first two fields, and then try to match instance-1
in the third field only (this assumes that the fields are seperated by a single space delimiter -- you can adjust the regex if that's not the case...)
The \(
and \)
indicate that sed should store the matched text in variable \1
. The ^
forces it to only match from the beginning of the line. The rest is pretty straight forward
Upvotes: 0