Linux Trap Command: Handle Script Interruptions
The Linux trap command enables shell scripts to
intercept and handle system signals, allowing processes to shut down
gracefully instead of terminating abruptly. By capturing signals such as
user interrupts or termination requests, scripts can execute predefined
cleanup routines, ensuring that temporary files are deleted, system
resources are freed, and child processes are stopped before the shell
exits.
Understanding Signals and the Trap Command
In a Linux environment, the operating system and users communicate with running processes by sending asynchronous notifications called signals. When a signal is received, the default behavior for most scripts is immediate termination, which often leaves behind temporary files, locked resources, or orphaned background tasks.
The trap command is a built-in feature of
POSIX-compliant shells (such as Bash, Dash, and Zsh) that overrides
these default termination behaviors. It allows developers to bind
specific shell commands or custom functions to particular signals.
Common Signals Handled by Trap
SIGINT(Signal 2): Triggered when a user interrupts a process manually, typically by pressingCtrl+C.SIGTERM(Signal 15): The standard termination signal sent by process management tools (likekillor system shutdown scripts) asking a program to stop.SIGHUP(Signal 1): Sent when the controlling terminal is closed or disconnected.EXIT(Signal 0): A shell-specific pseudo-signal that executes whenever the script terminates, whether it finishes successfully, encounters an error, or receives a caught termination signal.
Syntax and Basic Usage
The basic syntax for the trap command associates an
action with one or more signal names or numbers:
trap 'action' SIGNAL_LISTImplementing a Cleanup Routine
The most common use case for trap is cleaning up
temporary directories and resetting configurations before a script
terminates.
#!/bin/bash
# Create a temporary working directory
TEMP_DIR=$(mktemp -d /tmp/myscript.XXXXXX)
echo "Working directory created: $TEMP_DIR"
# Define the cleanup function
cleanup() {
echo "Signal received or script exiting. Cleaning up..."
rm -rf "$TEMP_DIR"
echo "Cleanup complete."
}
# Catch SIGINT, SIGTERM, and the EXIT pseudo-signal
trap cleanup SIGINT SIGTERM EXIT
# Simulate long-running work
for i in {1..10}; do
echo "Processing step $i..."
sleep 2
doneIn this script, whether the user presses Ctrl+C
(SIGINT), a system administrator runs
kill <PID> (SIGTERM), or the loop
finishes naturally (EXIT), the cleanup
function runs automatically, removing the temporary directory.
Ignoring and Resetting Signals
The trap command also provides mechanisms to
deliberately ignore signals or revert them back to system defaults.
Ignoring Signals
To make a critical section of code immune to user cancellation, assign an empty string as the action:
# Ignore interrupt signals during a critical task
trap '' SIGINT SIGTERM
echo "Executing critical task, cannot be interrupted..."
# Critical database update or file write occurs here
sleep 5
# Reset back to default behavior
trap - SIGINT SIGTERMResetting to Default Behavior
Passing a hyphen (-) as the action resets the specified
signals to their default operating system handlers:
trap - SIGINTBest Practices for Using Trap
- Keep Handlers Non-Blocking: The actions triggered
by
trapshould execute quickly to avoid hanging during system shutdowns. - Explicit Exit Codes: When trapping
SIGINTorSIGTERMmanually without theEXITpseudo-signal, explicitly exit with an appropriate status code (e.g.,exit 130forSIGINT) so upstream calling processes know the script did not complete successfully. - Clean Up Background Jobs: If a script spawns child
processes in the background using
&, the cleanup function can terminate them usingkill $(jobs -p)to prevent orphan processes.