funwithlinux blog

Redirect stdout to /dev/null and stderr to stdout in Shell: Clean One-Line sh Solution

In shell scripting and command-line usage, controlling where output goes is critical for keeping your terminal clean, managing logs, or ensuring background processes don’t spam you with unnecessary messages. Two common output streams you’ll encounter are stdout (standard output) and stderr (standard error). While stdout handles regular program output, stderr is reserved for error messages.

But what if you want to silence both streams entirely? The classic solution is redirecting stdout to /dev/null (the "black hole" of the system) and stderr to stdout—ensuring all output, including errors, disappears. This guide will break down the portable, POSIX-compliant one-liner to achieve this in sh (Bourne shell) and explain how it works, with practical examples and troubleshooting tips.

2026-01

Table of Contents#

  1. Understanding Shell Redirection Basics
    • What Are stdout and stderr?
    • What Is /dev/null?
  2. The One-Line POSIX Solution: > /dev/null 2>&1
    • Breaking Down the Syntax
    • Why Order Matters: A Critical Detail
    • Bash-Specific Shortcuts (and Why They’re Not Portable)
  3. Practical Examples: See It in Action
    • Example 1: Silencing a Noisy Command
    • Example 2: Cron Jobs and Background Processes
  4. Common Use Cases
  5. Troubleshooting: Avoid These Mistakes
    • Mistake 1: Reversing Redirection Order
    • Mistake 2: Using Bash-Specific &> in sh Scripts
    • Mistake 3: Forgetting Commands That Output to Stderr by Default
  6. Advanced Variations
    • Redirecting to a Log File Instead of /dev/null
    • Appending Output with >>
  7. Conclusion
  8. References

1. Understanding Shell Redirection Basics#

Before diving into the solution, let’s clarify the fundamentals of shell output streams and redirection.

What Are stdout and stderr?#

Every Unix-like shell command interacts with three standard I/O streams by default:

  • stdin (Standard Input): Data input to the command (file descriptor 0).
  • stdout (Standard Output): Regular program output (file descriptor 1).
  • stderr (Standard Error): Error messages and diagnostic output (file descriptor 2).

By default, both stdout and stderr print to your terminal. For example:

# stdout: "Hello World" (fd 1)
echo "Hello World"  
 
# stderr: "Error: File not found" (fd 2)
echo "Error: File not found" >&2  

What Is /dev/null?#

/dev/null is a special device file in Unix-like systems that discards all data written to it. Think of it as a "digital trash can"—anything sent here vanishes. It’s often used to suppress unwanted output.

2. The One-Line POSIX Solution: > /dev/null 2>&1#

To redirect both stdout and stderr to /dev/null in a portable, POSIX-compliant way (works in sh, bash, dash, etc.), use this one-liner:

command > /dev/null 2>&1  

Breaking Down the Syntax#

Let’s dissect this command step by step:

ComponentPurpose
commandThe command whose output you want to silence (e.g., ls, curl).
> /dev/nullRedirects stdout (fd 1) to /dev/null (discards regular output).
2>&1Duplicates stderr (fd 2) to stdout (fd 1), so stderr now follows stdout’s redirection (to /dev/null).

Why Order Matters: A Critical Detail#

The order of redirections is not arbitrary. To ensure both streams are silenced, > /dev/null (stdout redirection) must come before 2>&1 (stderr redirection to stdout).

Why?#

  • When you run command > /dev/null 2>&1, the shell first redirects stdout to /dev/null. Then, 2>&1 tells the shell: "make stderr point to wherever stdout is currently pointing" (which is /dev/null).

  • If you reverse the order (command 2>&1 > /dev/null), disaster strikes:

    1. 2>&1 first duplicates stderr to the original stdout (your terminal).
    2. Then > /dev/null redirects stdout to /dev/null.

    Result: Stdout is silenced, but stderr still prints to your terminal!

Example of the mistake:

# ❌ Wrong order: stderr still prints to terminal
ls -l /nonexistent > /dev/null 2>&1  # Correct (silences both)  
ls -l /nonexistent 2>&1 > /dev/null  # ❌ Stderr still prints!  

Bash-Specific Shortcuts (and Why They’re Not Portable)#

Bash and Zsh offer a shortcut: &> /dev/null (or >& /dev/null), which redirects both streams to /dev/null in one step. For example:

# Bash/Zsh only! Not POSIX-compliant.
command &> /dev/null  

Problem: This fails in POSIX sh (e.g., dash, BusyBox sh, or scripts with #!/bin/sh). For portability (e.g., writing scripts that work across all shells), use the POSIX form > /dev/null 2>&1.

3. Practical Examples: See It in Action#

Let’s test the redirection with real commands to see how it silences output.

Example 1: Silencing a Noisy Command#

Consider ls -l /valid /invalid, where /valid exists and /invalid does not. Normally, this outputs:

  • stdout: The directory listing of /valid.
  • stderr: An error about /invalid.
# Without redirection: both stdout and stderr print to terminal
ls -l /valid /invalid  
# Output:
# ls: cannot access '/invalid': No such file or directory  # stderr
# total 0                                                  # stdout (from /valid)

Now apply the redirection:

# With redirection: no output at all!
ls -l /valid /invalid > /dev/null 2>&1  

Both stdout and stderr are discarded.

Example 2: Cron Jobs and Background Processes#

Cron jobs email you their output by default. To prevent this, silence all output:

# Cron job entry (crontab -e)
0 3 * * * /path/to/backup-script.sh > /dev/null 2>&1  

For background processes, avoid cluttering the terminal:

# Run a long-running command in the background with no output
nohup ./long-running-process.sh > /dev/null 2>&1 &  

4. Common Use Cases#

When should you use > /dev/null 2>&1?

  • Silence Unnecessary Output: Commands like mkdir -p or rm -f often output nothing on success but may spam errors—silence them if you don’t care about failures.
  • Cron Jobs: Prevent cron from emailing you trivial output (e.g., "backup completed").
  • Background Services: Run daemons or scripts in the background without terminal clutter.
  • Testing: Verify a command runs successfully without checking its output (e.g., command > /dev/null 2>&1 && echo "Success!").

5. Troubleshooting: Avoid These Mistakes#

Mistake 1: Reversing Redirection Order#

As explained earlier, command 2>&1 > /dev/null leaves stderr printing to the terminal. Always use > /dev/null 2>&1.

Mistake 2: Using Bash-Specific &> in sh Scripts#

If your script starts with #!/bin/sh (not #!/bin/bash), &> /dev/null will fail with a syntax error. Stick to the POSIX form.

Mistake 3: Forgetting Commands That Output to Stderr by Default#

Some commands intentionally send all output to stderr (e.g., curl with --silent suppresses stdout but still outputs errors to stderr). Always test with 2>&1 to catch these.

6. Advanced Variations#

The same redirection logic works beyond /dev/null. Here are useful variations:

Redirecting to a Log File Instead of /dev/null#

To capture both stdout and stderr in a log file (instead of discarding them), replace /dev/null with a filename:

# Log both stdout and stderr to app.log
./my-app > app.log 2>&1  

Appending Output with >>#

Use >> instead of > to append output to a file (instead of overwriting it):

# Append stdout/stderr to app.log (instead of replacing it)
./my-app >> app.log 2>&1  

7. Conclusion#

Redirecting stdout to /dev/null and stderr to stdout is a cornerstone of shell scripting for silencing output. The POSIX-compliant one-liner > /dev/null 2>&1 ensures portability across all shells, while understanding the order of redirections prevents common pitfalls.

Whether you’re writing cron jobs, background processes, or just cleaning up terminal clutter, this technique will keep your output streams under control.

8. References#