サーチ…


構文

  • トラップアクションsigspec ...#シグナルのリストで "アクション"を実行する
  • trap sigspec ...#省略するとシグナルのトラップがリセットされます

パラメーター

パラメータ意味
-p 現在インストールされているトラップを一覧表示する
-l リスト信号名と対応する番号

備考

trapユーティリティは、特別なシェルを内蔵しています。これはPOSIX定義されていますが、bashでは便利な拡張もいくつか追加されています。

#!/bin/shで始まるPOSIX互換の例と、 #!/bin/bashで始まる例は、bash拡張を使用します。

シグナルは、シグナル番号、シグナル名(SIG接頭辞なし)、または特殊キーワードEXITいずれかです。

POSIXによって保証されているものは次のとおりです。

ノート
0 出口終了コードに関係なく常にシェル出口で実行する
1 SIGHUP
2 SIGINT これが^C送るものです
3 SIGQUIT
6 SIGABRT
9 SIGKILL
14 SIGALRM
15 SIGTERM これはデフォルトでkill送信するものです

SIGINTまたはCtl + Cをキャッチする

トラップはサブシェルのためにリセットされるので、 sleep^Cによって送られたSIGINTシグナル(通常は終了することによって)に対しても動作しますが、親プロセス(シェルスクリプト)は実行しません。

#!/bin/sh

# Run a command on signal 2 (SIGINT, which is what ^C sends)
sigint() {
    echo "Killed subshell!"
}
trap sigint INT

# Or use the no-op command for no output
#trap : INT

# This will be killed on the first ^C
echo "Sleeping..."
sleep 500

echo "Sleeping..."
sleep 500

また、 ^C 2回押してメインプログラムを終了できるようにした変種:

last=0
allow_quit() {
    [ $(date +%s) -lt $(( $last + 1 )) ] && exit
    echo "Press ^C twice in a row to quit"
    last=$(date +%s)
}
trap allow_quit INT

はじめに:一時ファイルのクリーンアップ

trapコマンドを使用してシグナルをtrapすることができます。これは、シェルと等価であるsignal()又はsigaction()信号を捕捉するためにCおよび他のほとんどのプログラミング言語で呼び出します。

trap最も一般的な使い方の1つは、予期しない終了と予期しない終了の両方で一時ファイルをクリーンアップすることです。

残念ながら、十分なシェルスクリプトではこれを行いません:-(

#!/bin/sh

# Make a cleanup function
cleanup() {
  rm --force -- "${tmp}"
}

# Trap the special "EXIT" group, which is always run when the shell exits.
trap cleanup EXIT

# Create a temporary file
tmp="$(mktemp -p /tmp tmpfileXXXXXXX)"

echo "Hello, world!" >> "${tmp}"

# No rm -f "$tmp" needed. The advantage of using EXIT is that it still works
# even if there was an error or if you used exit.

終了時に実行するトラップ作業のリストを累積します。

テンポラリファイルをクリーンアップするためのtrapを追加することを忘れたり、終了時に他の作業をしたりしたことがありますか?

別のものをキャンセルしたトラップを1つ設定しましたか?

このコードを使用すると、コードのどこかに大きなtrap文が1つずつあるのではなく、一度に1つの項目を終了するときに行う作業を簡単に追加できます。

# on_exit and add_on_exit
# Usage:
#   add_on_exit rm -f /tmp/foo
#   add_on_exit echo "I am exiting"
#   tempfile=$(mktemp)
#   add_on_exit rm -f "$tempfile"
# Based on http://www.linuxjournal.com/content/use-bash-trap-statement-cleanup-temporary-files
function on_exit()
{
    for i in "${on_exit_items[@]}"
    do
        eval $i
    done
}
function add_on_exit()
{
    local n=${#on_exit_items[*]}
    on_exit_items[$n]="$*"
    if [[ $n -eq 0 ]]; then
        trap on_exit EXIT
    fi
}

終了時の子プロセスの強制終了

トラップ式は個々の関数またはプログラムである必要はなく、より複雑な式でもあります。

jobs -pkillを組み合わせることで、終了時にシェルの子プロセスをすべて終了させることができます。

trap 'jobs -p | xargs kill' EXIT

端末のウィンドウサイズの変化に反応する

信号WINCH(WINdowCHange)があります。これは、端末ウィンドウのサイズを変更すると起動します。

declare -x rows cols
 
update_size(){
  rows=$(tput lines) # get actual lines of term
  cols=$(tput cols)  # get actual columns of term
  echo DEBUG terminal window has no $rows lines and is $cols characters wide
}

trap update_size WINCH


Modified text is an extract of the original Stack Overflow Documentation
ライセンスを受けた CC BY-SA 3.0
所属していない Stack Overflow