1

Add a line "allow = alaw" before a string "nat = no" in a file sip.conf or any text based file. If "allow = alaw" already exists before "nat = no" it should not be added.

File contents:

secret =
nat = no
progressinband = yes

allow = ulaw
allow = alaw
nat = no
progressinband = yes

disallow = all
allow = ulaw
nat = no
progressinband = yes

My attempt:

awk '/nat = no/ { if(lastLine == "allow = alaw") { print } } { lastLine = $0 }' sip.conf
3
  • What have you tried to do to solve the problem yourself? – Cyrus Jul 25 '20 at 10:34
  • I tried awk to grep the last line match, but how to add a line using sed missing and for loop will be required . ``` awk '/nat = no/ { if(lastLine == "allow = alaw") { print } } { lastLine = $0 }' sip.conf ``` – addi jeo Jul 25 '20 at 10:36
  • @addijeo Please add your attempts to the question when asking. I have edited your question to include it. Also, please try to provide a minimal, complete example with expected input and output. Your sample file is too large. – Quasímodo Jul 25 '20 at 11:50
1
awk -v add="allow = alaw" '/^nat = no$/&&lastLine!=add{print add}{lastLine=$0}1' sip.conf
  • -v add="allow = alaw" sets an variable add to awk.
  • /^nat = no$/&&lastLine!=add checks if current line is exactly "nat = no" and if the last line is not the line we want to add, "allow = alaw". If true,
    • {print add} prints the line to be added.
  • {lastLine=$0} saves the current line value, only in the next cycle it will be used.
  • 1 prints the current line.

On a minimal example sip.conf:

secret =
nat = no
progressinband = yes

allow = ulaw
allow = alaw
nat = no
progressinband = yes

disallow = all
allow = ulaw
nat = no
progressinband = yes
$ awk -v add="allow = alaw" '/^nat = no$/&&lastLine!=add{print add}{lastLine=$0}1' sip.conf > out
$ mv out sip.conf
$ cat sip.conf
secret =
allow = alaw
nat = no
progressinband = yes

allow = ulaw
allow = alaw
nat = no
progressinband = yes

disallow = all
allow = ulaw
allow = alaw
nat = no
progressinband = yes
6
  • Thanks for the help , by this cmd i'm able to print the desired output but its not getting saved/write in sip.conf. Please help in it – addi jeo Jul 25 '20 at 13:33
  • using "gawk -i inplace " able to write into file , but awk version should be 4.1.0 or later. gawk -i inplace -v add="allow = alaw" '/nat = no/{if(lastLine!=add){print add}}{lastLine=$0}1' sip.conf Thank you Quasímodo – addi jeo Jul 25 '20 at 15:01
  • 1
    Thanks @EdMorton, I have made the regex strict. Addijeo, to apply the modifications in the file, the cleanest way is to redirect the output to a temporary file and then overwrite the original file as I have done in the example (see edit). This requires no extension to awk such as the inplace option of GNU awk. – Quasímodo Jul 25 '20 at 16:39
  • ``` [general] allow = ulaw nat = no [providertrunk0] ;allow = alaw nat = no secret = nat = no progressinband = yes allow = ulaw allow = alaw nat = no ``` ``` I have one doubt, if I want to exclude the whole process for [general] and [providertrunk0] section, and apply in whole file then I am using '/general/,/providertrunk0/{next}' , but its not giving correct output. My command is as below ' awk -v add="allow = alaw" '/general/,/providertrunk0/{next} /^nat = no$/&&lastLine!=add{print add}{lastLine=$0}1' sip.conf ' ``` – addi jeo Jul 27 '20 at 15:13
  • @addijeo Sorry I cannot understand it, the comments mangle the line breaks so it is very difficult to read your question. Feel free to post a new question if you are stuck, though! – Quasímodo Jul 28 '20 at 0:24

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.