Bash Read File Line by Line Using while read

To Read File line by line in Bash Scripting, following are some of the ways explained in detail.

Reading a file line by line is useful when each line has to be processed separately, such as a list of names, paths, configuration values, or log records. In Bash, the common pattern is to use a while loop with the read command and redirect the file into the loop.

For most scripts, prefer while IFS= read -r line. This form keeps leading and trailing spaces and prevents backslashes from being interpreted as escape characters.

Example 1 – Read File Line by Line Using While Loop

Following is the syntax of reading file line by line in Bash using bash while loop.

Syntax

</>
Copy
while read line; do    
    # line is available for processing
    echo $line    
done < fileName

Input File

Learn Bash Scripting.
Welcome to TutorialKart!
Learn Bash with examples.

Bash Script File

</>
Copy
#!/bin/sh

i=1

while read line; do    
    # line is available for processing
    echo Line $i : $line    
    i=$(( i + 1 ))
done < sampleFile.txt

Output

~/workspace/bash/file$ ./read-file-line-by-line 
Line 1 : Learn Bash Scripting.
Line 2 : Welcome to TutorialKart!
Line 3 : Learn Bash with examples.

This example reads sampleFile.txt one line at a time. The variable line holds the current line inside the loop, and the variable i is used to print the line number.

The simple read line form is easy to understand, but it may trim whitespace and treat backslashes specially. The next examples show how to avoid those issues.

Example 2 – Read File Line by Line Preventing Backslash Escapes

To prevent backslash escapes while reading file line by line in bash, use -r option of read command.

Syntax

</>
Copy
while read -r line; do    
    # line is available for processing
    echo $line    
done < fileName

Bash Script File

</>
Copy
#!/bin/sh

i=1

while read -r line; do    
    # line is available for processing
    echo Line $i : $line    
    i=$(( i + 1 ))
done < sampleFile.txt

Output

~/workspace/bash/file$ ./read-file-line-by-line 
Line 1 : Learn Bash Scripting.
Line 2 : Welcome to TutorialKart!
Line 3 : Learn Bash with examples.

The -r option tells read to read backslashes literally. This is important when the file contains Windows paths, escape sequences, regular expressions, or any text where a backslash should remain unchanged.

Example 3 – Prevent Trimming Leading or Trailing Whitespaces

To prevent trimming of leading or trailing white-spaces while reading file line by line in bash, use IFS command in conjunction with read command :

Syntax

</>
Copy
while IFS= read line; do    
    # line is available for processing
    echo $line    
done < fileName

Bash Script File

</>
Copy
#!/bin/sh

i=1

while IFS= read line; do    
    # line is available for processing
    echo Line $i : $line    
    i=$(( i + 1 ))
done < sampleFile.txt

Output

~/workspace/bash/file$ ./read-file-line-by-line 
Line 1 : Learn Bash Scripting.
Line 2 : Welcome to TutorialKart!
Line 3 : Learn Bash with examples.

Setting IFS= for the read command prevents Bash from removing leading and trailing whitespace from the line. This matters when indentation, padding, or blank spacing in the file is meaningful.

Bash while IFS= read -r line Pattern for Safe Line Reading

The safest general-purpose pattern is to combine IFS= and -r. This reads each line more accurately because spaces and backslashes are preserved.

</>
Copy
while IFS= read -r line; do
    # process "$line"
done < fileName

Example Bash script using the recommended form:

</>
Copy
#!/usr/bin/env bash

i=1

while IFS= read -r line; do
    printf 'Line %d : %s\n' "$i" "$line"
    i=$((i + 1))
done < sampleFile.txt
Line 1 : Learn Bash Scripting.
Line 2 : Welcome to TutorialKart!
Line 3 : Learn Bash with examples.

In scripts, printf is usually preferred over echo because it gives predictable formatting. The variable "$line" is quoted so that spaces and wildcard characters in the file content are not changed by the shell.

Bash Read File Line by Line Without Losing the Last Line

Some files do not end with a final newline character. To make sure the last line is still processed, add a second condition that checks whether the line variable has content.

</>
Copy
#!/usr/bin/env bash

while IFS= read -r line || [ -n "$line" ]; do
    printf '%s\n' "$line"
done < sampleFile.txt

The condition || [ -n "$line" ] handles a final line that has text but no newline at the end of the file. This is useful when reading files generated by different tools or operating systems.

Bash Read File Path Stored in a Variable

If the file name is stored in a variable, quote the variable when redirecting it into the loop. Quoting helps the script work correctly when the file path contains spaces.

</>
Copy
#!/usr/bin/env bash

file_path="sampleFile.txt"

while IFS= read -r line; do
    printf '%s\n' "$line"
done < "$file_path"

The redirection < "$file_path" opens the file for input and sends it to the while loop. Always quote file path variables unless you have a specific reason not to.

Bash Check File Exists Before Reading Line by Line

A script should give a clear message when the input file is missing or not readable. The following example checks the file before starting the loop.

</>
Copy
#!/usr/bin/env bash

file_path="sampleFile.txt"

if [ ! -f "$file_path" ]; then
    printf 'File not found: %s\n' "$file_path" >&2
    exit 1
fi

if [ ! -r "$file_path" ]; then
    printf 'File is not readable: %s\n' "$file_path" >&2
    exit 1
fi

while IFS= read -r line; do
    printf '%s\n' "$line"
done < "$file_path"

The -f test checks whether the path is a regular file. The -r test checks whether the current user can read it. Error messages are sent to standard error using >&2.

Bash Read File Line by Line and Split Each Line into Fields

Sometimes each line contains multiple fields. For example, a file may contain a name and a role separated by a comma. You can set IFS to the delimiter and read values into separate variables.

</>
Copy
Asha,Developer
Ravi,Tester
Meena,Designer
</>
Copy
#!/usr/bin/env bash

while IFS=, read -r name role; do
    printf 'Name: %s, Role: %s\n' "$name" "$role"
done < team.txt
Name: Asha, Role: Developer
Name: Ravi, Role: Tester
Name: Meena, Role: Designer

This approach is suitable for simple delimited text. For complex CSV files with quoted fields and embedded commas, use a proper CSV parser instead of a small shell loop.

Bash while read vs for Loop for Reading File Lines

A common mistake is to read file lines with for line in $(cat fileName). That method splits the file by whitespace, not by actual lines. A sentence with spaces can become several separate values.

</>
Copy
# Avoid this for line-by-line file reading
for line in $(cat fileName); do
    echo "$line"
done

Use a while read loop when the input must be processed line by line.

RequirementRecommended Bash patternReason
Read each line exactlywhile IFS= read -r linePreserves spaces and backslashes.
Read from a file path variabledone < "$file_path"Works safely with paths that contain spaces.
Handle final line without newlineread -r line || [ -n "$line" ]Prevents missing a non-empty final line.
Read simple delimited valuesIFS=, read -r first secondSplits each line into fields using the delimiter.
Avoid whitespace splittingDo not use for line in $(cat file)It splits on words, not lines.

Common Mistakes While Reading a Bash File Line by Line

  • Using read line when spaces matter: use IFS= read -r line to preserve the content more accurately.
  • Not quoting the line variable: use "$line" so that the shell does not split the content or expand wildcard characters.
  • Using a pipe into the loop when variables must remain available later: depending on the shell, a piped loop may run in a subshell. Redirect the file into the loop instead.
  • Using for line in $(cat file): this reads words, not lines, and breaks lines containing spaces.
  • Ignoring missing files: check the file path with -f and -r when the script must fail clearly.

FAQs on Bash Read File Line by Line

How do I read a file line by line in Bash?

Use while IFS= read -r line; do ... done < fileName. The variable line contains the current line during each loop iteration.

Why should I use IFS= read -r line in Bash?

IFS= prevents trimming of leading and trailing whitespace. -r prevents backslashes from being treated as escape characters. Together, they make file reading safer for plain text.

How do I read a file line by line from a variable file path?

Store the path in a variable and quote it in the redirection: done < "$file_path". This works even when the file name or directory path contains spaces.

How do I avoid missing the last line when reading a file in Bash?

Use while IFS= read -r line || [ -n "$line" ]; do ... done < fileName. The second condition processes a final non-empty line even when it has no newline character at the end.

Can I use a for loop to read a file line by line in Bash?

A for loop with $(cat file) is not recommended for line-by-line reading because it splits content by whitespace. Use a while read loop instead.

Bash Read File Line by Line Editorial QA Checklist

  • Confirm that the recommended example uses IFS= read -r line for safe line reading.
  • Check that existing examples still run with the sample file content shown in the tutorial.
  • Verify that new file path examples quote "$file_path".
  • Ensure output blocks use the output class and new Bash examples use language-bash.
  • Confirm that the tutorial clearly warns against for line in $(cat file) for line-based processing.

Conclusion: Reading a Bash File Line by Line Safely

In this Bash Tutorial, we have learnt to read a file line by line in bash scripting with examples.

For simple demonstrations, while read line shows the basic idea. For practical scripts, while IFS= read -r line is the better default because it preserves whitespace and backslashes. When the script must be reliable, also quote file path variables, check that the file exists, and handle the final line even when the file does not end with a newline.