Bash grep Tutorial: Search, Filter, and Extract Text Like a Pro
March 17, 2026
Bash grep is one of the most-used command-line tools — it searches file contents for patterns and prints matching lines. Whether you're scanning logs for errors, filtering command output, or extracting specific data from text files, grep is the fastest way to find what you need. This tutorial covers all essential grep flags, regex patterns, AND/OR/NOT searches, and real-world log analysis examples.
1. Essential grep Flags
# -i case insensitive
grep -i "error" /var/log/app.log
# -r recursive (search all files in directory)
grep -r "TODO" /home/user/projects/
# -n show line numbers
grep -n "ERROR" /var/log/app.log
# -c count matching lines (not print them)
grep -c "ERROR" /var/log/app.log # → 42
# -v invert match (print lines that do NOT match)
grep -v "^#" /etc/hosts # print non-comment lines
# -l list only filenames with matches
grep -rl "password" /etc/ # find files containing "password"
# -w whole word match only
grep -w "fail" logfile.txt # won't match "failure" or "failover"
# -A N lines After match
# -B N lines Before match
# -C N lines of Context (both before and after)
grep -A 3 "ERROR" app.log # print matching line + 3 lines after
grep -C 5 "CRASH" app.log # 5 lines before AND after each match
2. Basic Regex Patterns
# ^ anchors to start of line
grep "^root" /etc/passwd # lines starting with "root"
# $ anchors to end of line
grep "bash$" /etc/passwd # lines ending with "bash"
# . matches any single character
grep "t.st" file.txt # matches "test", "tast", "t3st"
# * zero or more of preceding char
grep "erro*r" file.txt # "errr", "error", "errorr"
# [] character class
grep "[Ee]rror" file.txt # "Error" or "error"
grep "[0-9]" file.txt # lines containing any digit
# [^] negated character class
grep "[^0-9]" file.txt # lines with any non-digit
# Extended regex with -E (or egrep)
grep -E "error|warning|critical" app.log # OR
grep -E "^[0-9]{4}-[0-9]{2}" log.txt # date-like lines
3. AND, OR, NOT Searches
# OR — extended regex
grep -E "error|warning" app.log
grep -e "error" -e "warning" app.log # equivalent
# AND — pipe two greps
grep "error" app.log | grep "database" # lines with BOTH
# NOT — invert
grep -v "debug" app.log # exclude debug lines
# Combining: lines with "error" but NOT "404"
grep "error" app.log | grep -v "404"
# Count lines matching AND pattern
grep -c "ERROR" app.log # total error lines
grep "ERROR" app.log | grep -c "database" # database errors only
4. Practical Log Analysis Examples
log="/var/log/nginx/access.log"
# Find all 404 errors
grep ' 404 ' "$log"
# Count 500 errors
grep -c ' 500 ' "$log"
# Find all requests from a specific IP
grep "^192.168.1.100" "$log"
# Find slowest requests (over 2 seconds in response time field)
grep -E '"[0-9.]+" [0-9]+ [0-9]+ [2-9]\.' "$log"
# Find failed SSH login attempts
grep "Failed password" /var/log/auth.log | awk '{print $11}' | sort | uniq -c | sort -rn
# Find all unique IPs in an nginx log
grep -oE '[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+' "$log" | sort -u
# Check if a config option is set
grep -q "ssl_certificate" /etc/nginx/nginx.conf && echo "SSL configured"
5. grep with Pipes
# Filter running processes
ps aux | grep "nginx" | grep -v "grep"
# Find listening ports
ss -tlnp | grep ":80 "
# Search command history
history | grep "git push"
# Filter Docker containers
docker ps | grep "running"
# Find environment variables matching a pattern
env | grep -i "path"
6. Performance on Large Files
For files with millions of lines, grep is very fast because it's compiled C. A few tips to make it faster:
- Use
-F(fixed string) instead of regex when searching for a literal string — it's significantly faster - Use
-lto stop after finding the first match per file - Use
LC_ALL=C grepto bypass Unicode processing when files are ASCII - Prefer
grep -rwith a--include="*.log"filter rather than grepping all files
# Fixed-string search (no regex, much faster for literals)
grep -F "exact string to find" bigfile.log
# Restrict recursive search to specific file types
grep -r --include="*.py" "import os" /projects/
# Fast ASCII search
LC_ALL=C grep "ERROR" /var/log/huge.log
For processing the matched lines further — extracting columns, summing values — combine grep with the bash sed command or awk. For file-by-file operations, see the bash file existence check guide to verify files before grepping them.
Summary
The workhorse flags are -i (case insensitive), -r (recursive), -n (line numbers), -v (invert), -c (count), -l (filenames only), and -C N (context lines). Use -E for extended regex with | OR patterns. Pipe grep outputs together for AND logic, and use -F when searching for literal strings in large files.