Contesto:Bash non intrappolare gli interrupt durante rsync/subshell dichiarazioni exec
Ho uno script bash che contiene una subshell e una trappola per il pseudosignal EXIT, e non è intrappolando correttamente gli interrupt durante una rsync
. Ecco un esempio:
#!/bin/bash
logfile=/path/to/file;
directory1=/path/to/dir
directory2=/path/to/dir
cleanup() {
echo "Cleaning up!"
#do stuff
trap - EXIT
}
trap '{
(cleanup;) | 2>&1 tee -a $logfile
}' EXIT
(
#main script logic, including the following lines:
(exec sleep 10;);
(exec rsync --progress -av --delete $directory1 /var/tmp/$directory2;);
) | 2>&1 tee -a $logfile
trap - EXIT #just in case cleanup isn't called for some reason
L'idea dello script è questo: la maggior parte della logica importante viene eseguito in una subshell che viene convogliata attraverso tee
e ad un file di log, quindi non c'è bisogno di tee
ogni singola riga di la logica principale per ottenere tutto registrato. Ogni volta che la subshell termina o lo script viene interrotto per qualsiasi motivo (lo pseudosignal EXIT deve acquisire tutti questi casi), il trap lo intercetterà ed eseguirà la funzione cleanup()
e quindi rimuoverà il trap. I comandi rsync
e sleep
(il sonno è solo un esempio) vengono eseguiti tramite exec
per impedire la creazione di processi zombie se si elimina lo script padre mentre sono in esecuzione e ogni comando potenzialmente a lunga esecuzione è racchiuso nella propria sottoshell in modo che al termine di exec
, non verrà terminato l'intero script.
Il problema:
Se interrompo lo script (via kill
o CTRL + C) durante l'exec/subshell avvolto sleep
di comando, la trappola funziona correttamente, e vedo "Pulizia up!" echeggiato e registrato. Se interrompo lo script durante il comando rsync
, vedo rsync
e scrivo rsync error: received SIGINT, SIGTERM, or SIGHUP (code 20) at rsync.c(544) [sender=3.0.6]
sullo schermo, quindi lo script muore; nessuna pulizia, nessuna trappola. Perché l'interruzione/uccisione di rsync
non attiva la trappola?
Ho provato a utilizzare lo switch --no-detach
con rsync, ma non ha modificato nulla. Ho bash 4.1.2, rsync 3.0.6, centOS 6.2.
Questo non è il motivo del tuo problema ma la tua registrazione non è affidabile, perché scrivi sullo stesso file con due programmi diversi contemporaneamente. – ceving
il tuo 'trap - EXIT' si trova in una subshell (esplicitamente), quindi non avrà un effetto dopo che la funzione cleanup restituisce – sehe
Esecuzione in esecuzione in una subshell equivale a eseguire il comando normalmente - non è necessario il punteggiatura extra. –