Удалите временные файлы в конце сценария оболочки bourne

Я пытался использовать trap для удаления временного файла в конце сценария оболочки Bourne, но это не сработало:

trap "trap \"rm \\\"$out\\\"\" EXIT INT TERM" 0

Между прочим, это внутри функции, отсюда и попытка вложенной ловушки.

Как мне это сделать?


person Robin Green    schedule 17.04.2013    source источник
comment
возможный дубликат выхода после срабатывания ловушки   -  person tripleee    schedule 18.04.2013
comment
Нет, это другое.   -  person Robin Green    schedule 18.04.2013


Ответы (1)


Для каждого сигнала можно установить только одну ловушку. Если разные части вашего скрипта должны выполнять разные действия по очистке, вам нужно будет создать списки действий по очистке. Затем установите единственный обработчик прерываний, который выполняет все необходимые действия по очистке.

Вот пример:

set -xv

PROG="$(basename -- "${0}")"

# set up your trap handler

TEMP_FILES=()

trap_handler() {
    for F in "${TEMP_FILES[@]}"; do
        rm -f "${F}"
    done
}

trap trap_handler 0 1 2 3 15

something_that_uses_temp_files() {
    mytemp="$(mktemp -t "${PROG}")"
    TEMP_FILES+=("${mytemp}")

    date > "${mytemp}"

    # ...
}

# ...

something_that_uses_temp_files

# ...

Существует единственный обработчик прерываний, но вы можете зарегистрировать действия по очистке из любого места скрипта, добавив их к массиву TEMP_FILES. Действия по очистке также могут быть зарегистрированы изнутри функций.


Если вы не используете оболочку с массивами, основная идея такая же, но детали реализации будут немного другими. Например, вы можете сохранить список как строковую переменную, разделенную двоеточиями, используя ${parameter%%word} расширения в каждой оболочке POSIX для перебора ее элементов в обработчике прерывания:

#!/bin/sh

set -xv

PROG="$(basename -- "${0}")"

# set up your trap handler

TEMP_FILES=""

trap_handler() {
    while [ -n "${TEMP_FILES}" ]; do
        CUR_FILE="${TEMP_FILES%%:*}"
        TEMP_FILES="${TEMP_FILES#*:}"
        if [ "${CUR_FILE}" = "${TEMP_FILES}" ]; then
            # there were no colons -- CUR_FILE is the last file to process
            TEMP_FILES=""
        fi

        if [ -n "${CUR_FILE}" ]; then
            rm -f "${CUR_FILE}"
        fi
    done }

trap trap_handler 0 1 2 3 15

something_that_uses_temp_files() {
    mytemp="$(mktemp -t "${PROG}")"
    TEMP_FILES="${TEMP_FILES}:${mytemp}"

    date > "${mytemp}"

    # ... }

# ...

something_that_uses_temp_files
something_that_uses_temp_files

# ...
person andrewdotn    schedule 17.04.2013
comment
Я думаю, вы говорите о bash, потому что в оболочке Bourne нет массивов. - person Robin Green; 18.04.2013