Shell & Scripting20 min
Bash — Essential Commands Cheat Sheet
Dense Bash reference — navigation, file ops, pipes, redirects, text processing, loops, functions, and must-know one-liners.
Navigation & File System
pwd # Current directory
cd /path/to/dir # Change directory
cd ~ # Home
cd - # Previous directory
ls -la # List all with details
ls -lhS # Sort by size, human-readable
tree -L 2 # Tree view, 2 levels
du -sh */ # Size of each subdir
df -h # Disk usage by filesystem
File Operations
# Create
touch file.txt # Create/update timestamp
mkdir -p a/b/c # Create nested dirs
# Copy / Move
cp -r src/ dest/ # Copy directory
mv old.txt new.txt # Move / rename
rsync -av src/ dest/ # Sync with progress
# Delete
rm -rf directory/ # Delete recursively (careful!)
find . -name "*.tmp" -delete # Find and delete
# View
cat file.txt # Print file
less file.txt # Page through (q to quit)
head -n 20 file.txt # First 20 lines
tail -f /var/log/app.log # Follow live log
Pipes & Redirects
cmd > file.txt # Stdout → file (overwrite)
cmd >> file.txt # Stdout → file (append)
cmd 2> err.txt # Stderr → file
cmd &> all.txt # Both stdout + stderr
cmd < input.txt # Stdin from file
cmd1 | cmd2 # Pipe stdout to cmd2
cmd1 | tee file.txt | cmd2 # Pipe and also write file
Finding Files
find . -name "*.log" # By name
find . -type f -size +10M # Files > 10 MB
find . -mtime -7 # Modified last 7 days
find . -name "*.sh" -exec chmod +x {} \; # Find & execute
grep -r "pattern" ./src/ # Recursive content search
grep -rn "TODO" . --include="*.py" # With line numbers, filtered
Text Processing
# grep
grep -i "error" app.log # Case-insensitive
grep -v "DEBUG" app.log # Invert match
grep -E "warn|error" app.log # Extended regex
# sed
sed 's/old/new/g' file.txt # Replace all
sed -i 's/localhost/prod.db/g' config.env # In-place
sed -n '10,20p' file.txt # Print lines 10-20
# awk
awk '{print $1, $3}' file.txt # Print fields 1 and 3
awk -F: '{print $1}' /etc/passwd # Custom delimiter
awk 'NR==5' file.txt # Print line 5
awk '{sum+=$1} END{print sum}' # Sum a column
# sort / uniq
sort -k2 -n file.txt # Sort by 2nd column numerically
sort file.txt | uniq -c | sort -rn # Count + sort by frequency
# cut / wc
cut -d: -f1,3 /etc/passwd # Cut fields 1 and 3
wc -l file.txt # Count lines
Variables & Strings
NAME="Alice"
echo "Hello $NAME"
echo "${NAME:-default}" # Use default if empty
echo "${#NAME}" # String length
echo "${NAME:0:5}" # Substring
echo "${NAME,,}" # Lowercase
echo "${NAME//old/new}" # Replace all
# Special vars
$0 # Script name
$1 # First argument
$@ # All arguments
$# # Argument count
$? # Last exit code
$$ # Current PID
Conditionals & Loops
# if / else
if [[ -f file.txt ]]; then echo "exists"; fi
if [[ "$A" -gt 10 ]]; then echo "big"; else echo "small"; fi
# Common tests
[[ -f file ]] # File exists
[[ -d dir ]] # Dir exists
[[ -z "$V" ]] # Empty string
[[ -n "$V" ]] # Non-empty string
# for
for i in {1..5}; do echo $i; done
for f in *.txt; do echo "$f"; done
# while
while IFS= read -r line; do echo "$line"; done < file.txt
Functions
greet() {
local name="$1"
echo "Hello, $name!"
}
greet "Alice" # Hello, Alice!
# Return a value via stdout
add() { echo $(($1 + $2)); }
result=$(add 3 7) # result=10
Process Management
command & # Run in background
jobs # List background jobs
fg %1 # Bring job 1 to foreground
kill -9 <PID> # Force kill
nohup cmd & # Survive terminal close
wait # Wait for all background jobs
Useful One-Liners
# Watch command every 2s
watch -n 2 'df -h'
# Check port is open
nc -zv hostname 443
# Disk usage top 20 dirs
du -sh */ | sort -rh | head -20
# Count files by extension
find . -type f | sed 's/.*\.//' | sort | uniq -c | sort -rn
# JSON pretty print
echo '{"a":1}' | jq .
cat file.json | python3 -m json.tool
# Generate random password
openssl rand -base64 16
# Base64 encode/decode
echo "hello" | base64
echo "aGVsbG8K" | base64 -d
# Archive / extract
tar -czf archive.tar.gz dir/ # Create
tar -xzf archive.tar.gz # Extract
Script Template
#!/usr/bin/env bash
set -euo pipefail
IFS=$'\n\t'
log() { echo "[$(date '+%F %T')] $*"; }
die() { log "ERROR: $*"; exit 1; }
main() {
[[ $# -lt 1 ]] && die "Usage: $0 <arg>"
log "Starting with: $1"
# your logic
log "Done"
}
main "$@"
