2

I have two following files - 'tempFile' and 'File1'

tempFile

tempFile 01
tempFile 02
tempFile 03
tempFile 03

File1

File1
 @type ABCDF #---Insert 'tempfile' content below First occurrence '@type ABCDF'
File2
File3
 @type ABCDF
File4
 @type ABCDF
File5

I tried to insert content of 'tempFile' to another file 'File1' at first occurrence of statement '@type ABCD' with following script

lineNumber=$(grep -n -m 1 '@type ABCD' File1 | awk -F':'  '{print $1}' | head -1)
sed -i "${lineNumber}r tempFile" File1

However, the above script inserted content of tempFile in File1 multiple times as mentioned below Please help me to insert content of tempFile in File1 only once/ Script generates following output

File1
 @type ABCDF #---Insert 'tempfile' content below First occurrence '@type ABCDF'
 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03

 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03

 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03

 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03

 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03

 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03
File2
File3
 @type ABCDF
File4
 @type ABCDF
File5

Expected output of the script

File1
 @type ABCDF #---Insert 'tempfile' content below First occurrence '@type ABCDF'
 tempFile 01
 tempFile 02
 tempFile 03
 tempFile 03
File2
File3
 @type ABCDF
File4
 @type ABCDF
File5
Anindya Kar
  • 45
  • 1
  • 7
  • 1
    Related, see [How to parse XML in Bash?](https://stackoverflow.com/q/893585/608639), [How to parse XML using shellscript?](https://stackoverflow.com/q/4680143/608639) and friends. – jww Dec 22 '19 at 05:17
  • I want to just insert the content of tempFile into File1 at specific position. For your convenience, I have changed the content of tempFile and File1 – Anindya Kar Dec 22 '19 at 09:00

2 Answers2

0

This worked for me:

touch result                                                          #Intermediate file
lineNumber=$(grep -n -m 1 '@type ABCD' File1 | awk -F':'  '{print $1}' | head -1)
head -n $lineNumber File1 >> result                                   #First two lines
cat tempfile >> result                                                #Append your tempfile
sed -n "3,`wc -l File1 | awk ' { print $1}'`p" File1 >> result        #Rest of File1
mv result File1                                                       #Rename it to File1
Parsa Mousavi
  • 1,052
  • 1
  • 13
  • 31
0

You can do it with awk fairly easily using a variable to serve as a flag to only write the contents of tempfile once after the first occurrence of "@type ABCDF". The approach is simple, you output every line with the first {print} rule, then if /@type ABCDF/ && n, you loop with getline reading each line from tempfile and outputting it. When done outputting the file, you simply set n=0 and it will skip all the other occurrences of "@type ABCDF" in the file, e.g.

awk -vn=1 '{print}; /@type ABCDF/ && n{while (getline <"tempfile") print;n=0}' file1 

Example Input file1

$ cat file1
File1
 @type ABCDF #---Insert 'tempfile' content below First occurrence '@type ABCDF'
File2
File3
 @type ABCDF
File4
 @type ABCDF
File5

Example Use/Output

$ awk -vn=1 '{print}; /@type ABCDF/ && n{while (getline <"tempfile") print;n=0}' file1
File1
 @type ABCDF #---Insert 'tempfile' content below First occurrence '@type ABCDF'
tempFile 01
tempFile 02
tempFile 03
tempFile 03
File2
File3
 @type ABCDF
File4
 @type ABCDF
File5

You can redirect the output to a temporary file and then replace the original to emulate an in-place addition of the lines.

David C. Rankin
  • 81,885
  • 6
  • 58
  • 85