Exemple: utilisation de flock pour forcer les scripts à s'exécuter en série avec des verrous de fichiers
Un exemple consiste à utiliser le verrouillage de fichier pour forcer les scripts à s'exécuter en série sur l'ensemble du système. Ceci est utile si vous ne voulez pas que deux scripts du même type agissent sur les mêmes fichiers. Sinon, les deux scripts pourraient interférer et éventuellement altérer des données.
#exit if any command returns a non-zero exit code (like flock when it fails to lock)
set -e
#open file descriptor 3 for writing
exec 3> /tmp/file.lock
#create an exclusive lock on the file using file descriptor 3
#exit if lock could not be obtained
flock -n 3
#execute serial code
#remove the file while the lock is still obtained
rm -f /tmp/file.lock
#close the open file handle which releases the file lock and disk space
exec 3>&-
Utilisez fonctionnellement flock en définissant verrouiller et déverrouiller
Vous pouvez également intégrer cette logique de verrouillage / déverrouillage à des fonctions réutilisables. Le trap
shell suivant libère automatiquement le verrou de fichier lorsque le script se termine (erreur ou succès). trap
aide à nettoyer vos verrous de fichiers. Le chemin /tmp/file.lock
doit être un chemin codé en dur afin que plusieurs scripts puissent essayer de le verrouiller.
# obtain a file lock and automatically unlock it when the script exits
function lock() {
exec 3> /tmp/file.lock
flock -n 3 && trap unlock EXIT
}
# release the file lock so another program can obtain the lock
function unlock() {
# only delete if the file descriptor 3 is open
if { >&3 ; } &> /dev/null; then
rm -f /tmp/file.lock
fi
#close the file handle which releases the file lock
exec 3>&-
}
La unlock
logique ci-dessus consiste à supprimer le fichier avant que le verrou ne soit libéré. De cette façon, il nettoie le fichier de verrouillage. Comme le fichier a été supprimé, une autre instance de ce programme peut obtenir le verrou de fichier.
Utilisation des fonctions de verrouillage et de déverrouillage dans les scripts
Vous pouvez l'utiliser dans vos scripts comme dans l'exemple suivant.
#exit if any command returns a non-zero exit code (like flock when it fails to lock)
set -e
#try to lock (else exit because of non-zero exit code)
lock
#system-wide serial locked code
unlock
#non-serial code
Si vous voulez que votre code attende jusqu'à ce qu'il soit capable de se verrouiller, vous pouvez ajuster le script comme suit:
set -e
#wait for lock to be successfully obtained
while ! lock 2> /dev/null; do
sleep .1
done
#system-wide serial locked code
unlock
#non-serial code