Skip to content
shellhacks.dev
Debugging

Print each line as it is read

Print every script line as the shell reads it, before expansion, with set -v. Pair it with set -x to see the source line and the expanded command.

1 min read
Summarize in AI

A trace shows the commands after variables are filled in, and sometimes what you need is the line as written.

Shell
set -v
name=world
echo "hello $name"
set +v
echo done
echo ---
set -vx
echo "hello $name"
set +vx
Text
name=world
echo "hello $name"
hello world
set +v
done
---
echo "hello $name"
+ echo 'hello world'
hello world
set +vx
+ set +vx

set -v is the verbose option. It prints each line of input exactly as read, with the variables still unexpanded, before the shell runs it. set -x prints the command after expansion. Used together, the second block shows the source line and then the traced command with the value filled in, which makes it clear which part of a line produced a surprising result. Both are in the set builtin documentation. The line that turns verbose mode off is shown because it is read before it runs.

Verbose output goes to standard error and prints lines in the order they are read, so a function body appears when it is defined and not when it is called. It prints comments and blank lines too. Running bash -v script.sh applies it to the whole file, which is long for any real script.

Share

More snippets

Debugging

Stop on the first error and show where

Report where a script failed with trap '...' ERR and set -E. LINENO gives the line, BASH_COMMAND the command and $? the status, even inside functions.

1 min read
Debugging

Trace only part of a script

Trace only the lines you are debugging by wrapping them in set -x and set +x. Write { set +x; } 2>/dev/null so the switch-off command is not traced itself.

1 min read

Get new posts by email

One email when a new post is published. No spam.

Unsubscribe in one click. No spam, ever.