July 17, 2026
The Terminal Trick That Changed My Entire Workflow
One Discovery, Years of Saved Time

By Fateyaly
4 min read
Most improvements in productivity don't come from learning new commands.
They come from combining existing ones.
Early in my Linux journey, I treated the terminal as a place to execute isolated commands.
Run a command.
Read the output.
Run another command.
Repeat.
It worked, but every task required unnecessary repetition.
Searching logs meant opening another terminal.
Monitoring a process meant rerunning the same command every few seconds.
Finding a file meant copying its path into another command.
As my workflow became more complex, I realized the real strength of Linux wasn't the commands themselves.
It was the ability to connect them into reusable workflows.
The discovery that changed everything wasn't a new utility.
It was understanding pipes, standard streams, command substitution, and composable pipelines.
Once you stop thinking about commands individually and start thinking about data flowing between processes, the terminal becomes far more than a command interpreter.
It becomes a data processing engine.
Every Linux Program Speaks the Same Language
Most Unix utilities follow a simple design philosophy.
They read from Standard Input (stdin).
They write to Standard Output (stdout).
Errors are written to Standard Error (stderr).
stdin (0)
↓
Command
↓
stdout (1)
stderr (2)stdin (0)
↓
Command
↓
stdout (1)
stderr (2)Because every program follows this convention, one command's output becomes another command's input.
Instead of manually copying information between programs, Linux lets processes communicate directly.
That single design decision is why shell pipelines remain one of the most powerful features of Unix-like operating systems.
The Pipe Changed Everything
Suppose you want to identify every failed SSH login.
Instead of searching manually:
cat /var/log/auth.logcat /var/log/auth.logFilter the output:
grep "Failed password" /var/log/auth.loggrep "Failed password" /var/log/auth.logNeed the most recent failures?
grep "Failed password" /var/log/auth.log | tail -20grep "Failed password" /var/log/auth.log | tail -20Want the source IP addresses?
grep "Failed password" /var/log/auth.log | awk '{print $(NF-3)}'grep "Failed password" /var/log/auth.log | awk '{print $(NF-3)}'Count repeated attempts:
grep "Failed password" /var/log/auth.log \
| awk '{print $(NF-3)}' \
| sort \
| uniq -c \
| sort -nrgrep "Failed password" /var/log/auth.log \
| awk '{print $(NF-3)}' \
| sort \
| uniq -c \
| sort -nrNo temporary files.
No scripting.
Each command performs one task.
Together they become an investigation pipeline.
Stop Reading Entire Files
Large log files can contain millions of lines.
Searching them manually wastes both time and attention.
Instead:
journalctl -u nginx --since "1 hour ago" \
| grep "500"journalctl -u nginx --since "1 hour ago" \
| grep "500"Or inspect kernel events:
journalctl -k \
| grep -i "oom"journalctl -k \
| grep -i "oom"You're no longer reading logs.
You're extracting evidence.
Command Substitution Eliminates Manual Work
One of the biggest workflow improvements came from letting commands generate arguments for other commands.
Suppose you need to inspect the process currently listening on port 443.
Without command substitution:
Run lsof
↓
Copy PID
↓
Paste into psRun lsof
↓
Copy PID
↓
Paste into psInstead:
ps -fp $(lsof -ti:443)ps -fp $(lsof -ti:443)The shell executes:
lsof -ti:443lsof -ti:443first, captures the output, and inserts it into the ps command automatically.
The workflow becomes repeatable.
No manual copying required.
xargs Turns Lists Into Actions
Many commands generate lists.
xargs transforms those lists into executable workflows.
Find every log file older than seven days:
find /var/log -name "*.log" -mtime +7find /var/log -name "*.log" -mtime +7Compress them:
find /var/log -name "*.log" -mtime +7 \
| xargs gzipfind /var/log -name "*.log" -mtime +7 \
| xargs gzipOr locate every Python file importing a deprecated package:
rg "^import imp" -l \
| xargs sed -n '1,20p'rg "^import imp" -l \
| xargs sed -n '1,20p'Instead of writing custom scripts, pipelines solve many operational tasks in a single command.
tee Lets You Observe Without Interrupting
Normally, pipeline output disappears into the next command.
Sometimes you want both.
Example:
journalctl -u docker \
| tee docker.log \
| grep ERRORjournalctl -u docker \
| tee docker.log \
| grep ERRORThe stream is
- Saved to a file.
- Displayed on the terminal.
- Passed into the next command.
This is particularly useful during incident response when preserving raw evidence matters.
Watch Data Instead of Repeating Commands
Many engineers still press the Up Arrow followed by Enter every few seconds.
Linux already solved that problem.
Monitor active TCP sessions:
watch -n 2 'ss -ant'watch -n 2 'ss -ant'Observe memory usage:
watch -n 1 free -hwatch -n 1 free -hTrack filesystem utilization:
watch -n 5 df -hwatch -n 5 df -hContinuous observation often reveals trends that a single snapshot cannot.
Redirect Errors Separately
One overlooked feature is that output and errors are independent streams.
Capture only errors:
command 2> errors.logcommand 2> errors.logDiscard normal output:
command > /dev/nullcommand > /dev/nullIgnore errors:
command 2> /dev/nullcommand 2> /dev/nullCombine everything:
command > output.log 2>&1command > output.log 2>&1Understanding file descriptors makes troubleshooting scripts significantly easier.
Many automation failures originate from mixing diagnostic output with operational data.
Process Text Like Structured Data
Commands become substantially more powerful when combined.
Example:
Find the ten largest files:
find /var/log -type f \
-exec du -h {} + \
| sort -hr \
| headfind /var/log -type f \
-exec du -h {} + \
| sort -hr \
| headIdentify processes consuming the most memory:
ps aux \
| sort -rk4 \
| headps aux \
| sort -rk4 \
| headSummarize HTTP status codes from an access log:
awk '{print $9}' access.log \
| sort \
| uniq -c \
| sort -nrawk '{print $9}' access.log \
| sort \
| uniq -c \
| sort -nrThese aren't shell tricks.
They're lightweight data pipelines.
Build Repeatable Investigations
During production incidents, the same questions appear repeatedly.
Which process owns this port?
lsof -i :8080lsof -i :8080Which connections are established?
ss -antss -antWhich service restarted?
journalctl -u nginxjournalctl -u nginxWhich files are still open?
lsoflsofInstead of running unrelated commands, connect them.
Example:
lsof -ti:8080 \
| xargs ps -fplsof -ti:8080 \
| xargs ps -fpThe investigation becomes deterministic instead of manual.
Pipelines Scale Better Than Scripts
Many engineers immediately reach for Python when automating repetitive work.
Sometimes that's the correct decision.
Often it isn't.
Consider this pipeline:
find . -type f -name "*.conf" \
| xargs grep -l "localhost"find . -type f -name "*.conf" \
| xargs grep -l "localhost"Finding matching configuration files doesn't require writing a parser.
Unix utilities already provide optimized building blocks.
The shell simply connects them.
Understanding this philosophy often reduces hundreds of lines of automation into a handful of composable commands.
The Real Discovery Wasn't a Command
The biggest improvement to my workflow wasn't learning another Linux utility.
It was learning how Linux utilities cooperate.
Every command becomes more valuable when it produces input for another.
Every pipeline eliminates manual work.
Every reusable workflow reduces mistakes.
Modern Linux systems expose enormous amounts of operational data through logs, process tables, network sockets, kernel interfaces, and filesystem metadata.
The challenge isn't accessing that information.
It's moving it efficiently from one tool to the next.
That's what Unix pipelines were designed to solve decades ago.
And despite the growth of cloud-native platforms, containers, and distributed systems, they're still one of the most effective productivity features available to engineers today.
The terminal isn't powerful because it has thousands of commands.
It's powerful because every command can become part of something larger.