Reputation: 1996
I have a source file containing a specific string, and would like to replace the first (in this case, only) instance of that string with the contents of another file. Something like:
> cat source.txt
Hello
KEYWORD
Hi
> cat replacement.txt
Replacement
> <sed command>
> cat source.txt
Hello
Replacement
Hi
Is there a way to do this with sed? Or any other editor?
Upvotes: 0
Views: 781
Reputation: 195239
I think awk may do this job easier:
if you want to keep the ending linebreak in replace.txt:
awk -v RS="\0" -v ORS="" 'NR==FNR{r=$0;next}{sub(/KEYWORD/,r)}1' replace.txt source.txt
if you want to strip the ending \n
from replace.txt:
awk -v RS="\0" -v ORS="" 'NR==FNR{r=$0;sub(/\n$/,"",r);next}{sub(/KEYWORD/,r)}1' replace.txt source.txt
the above line works no matter your replace.txt has single or multiple lines.
e.g.:
kent$ head file1 file2
==> file1 <==
Hello
KEYWORD
Hi
KEYWORD
==> file2 <==
rep_line1
rep_line2
kent$ awk -v RS="\0" -v ORS="" 'NR==FNR{r=$0;next}{sub(/KEYWORD\n/,r)}1' file2 file1
Hello
rep_line1
rep_line2
Hi
KEYWORD
you can see, only the first KEYWORD
in file1 was replaced. however Awk cannot write change back to the input file. what we could do is:
awk '...' replace.txt src.txt > /tmp/t.txt && mv /tmp/t.txt /path/to/src.txt
the awk one-liner was tested with gawk. No guarantee that it will work for all awk implementations. you should test it, if you got a non-gnu awk.
thank Ed Morton's suggestions.
Upvotes: 1
Reputation: 15238
$ cat source.txt
Hello
KEYWORD
Hi
KEYWORD
KEYWORD
$ cat replacement.txt
Replacement
multiline?
$ sed -ir "0,/KEYWORD/s//$(cat replacement.txt | sed 's/$/^M/'|tr -d '\n' ) )/" source.txt
$ cat source.txt
Hello
Replacement
multiline?
Hi
KEYWORD
KEYWORD
$
Upvotes: 0
Reputation: 3085
A quick and easy way:
sed s/KEYWORD/`cat replacement.txt`/ source.txt > output.txt
Upvotes: 0