If we put aside for a moment the fact you shouldn't cat
a file to a variable and then echo
it for sed
filtering, the reason why your command is not working is because you're not quoting the file content variable, fileC
when echo
ing. This will munge together multiple whitespace characters and turn them into a single space. So, you're losing newlines from the file, as well as multiple spaces, tabs, etc.
To fix it, you can write:
fileC=$(cat test.log)
output=$(echo "$fileC" | sed -n "/$word/,/$upto/p")
Note the double-quotes around fileC
(and a fixed sed
expression, similar to your second example). Without the quotes (try echo $fileC
), your fileC
is expanded (with the default IFS
) into a series of words, each being one argument to echo
, and echo
will just print those words separated with a single space. Additionally, if the file contains some of the globbing characters (like *
), those patterns are also expanded. This is a common bash pitfall.
Much better would be to write it like this:
output=$(sed -n "/$word/,/$upto/p" test.log)
And if your patterns include some of the sed
metacharacters, you should really escape them before using with sed
, like this:
escape() {
sed 's/[^^]/[&]/g; s/\^/\\^/g' <<<"$1";
}
output=$(sed -n "/$(escape "$word")/,/$(escape "$upto")/ p" test.log)