Read file line by line

How to read a file line by line in Bash

Reading a file into a bash script on a per-line basis is pretty simple:

1while read -r line; do command "${line}"; done < src.file

here we read a line from stdin and as long as a line was read the line is passed to command as a single command argument.

the -r option prevents backslash escapes in the line being interpreted.

If you want to prevent leading or trailling whitespace from being removed from the line then add IFS= to the line:

1while IFS= read -r line; do command "${line}"; done < src.file

Within scripts

The above is useful when writing something quick on the command line, but in a script it's more customary to write this across multiple lines.

What I tend to do is wrap the while loop within ( ) with the input redirect after the parentheses. To me this makes it clearer on what the bounds of the script relates to the input.

For example, here we have a script which writes the content of a file to stdout but adds line numbers to the output:

#!/bin/bash input="$1" ( lc=1 while IFS= read -r line do printf "%03d %s\n" ${lc} "${line}" lc=$((lc+1)) done ) < "${input}"

When run against itself:

$ ./ 001 #!/bin/bash 002 input="$1" 003 ( 004 lc=1 005 while IFS= read -r line 006 do 007 printf "%03d %s\n" ${lc} "${line}" 008 lc=$((lc+1)) 009 done 010 ) < "${input}"

Last modified January 21, 2022: Change dir name (bdb7dc4)