Vous pouvez le créer sous un nom généré aléatoirement, puis le renommer (mv -n random desired
) le mettre en place avec le nom souhaité. Le changement de nom échouera si le fichier existe déjà.
Comme ceci :
#!/bin/bash
touch randomFileName
mv -n randomFileName lockFile
if [ -e randomFileName ] ; then
echo "Failed to acquired lock"
else
echo "Acquired lock"
fi
Une solution bash 100 % pure :
set -o noclobber
{ > file ; } &> /dev/null
Cette commande crée un fichier nommé file
s'il n'y a pas de fichier nommé file
. S'il existe un fichier nommé file
, puis ne rien faire (mais renvoyer un code de retour différent de zéro).
Avantages par rapport au touch
commande :
- Ne met pas à jour l'horodatage si le fichier existe déjà
- Bash intégré à 100 %
- Code de retour comme prévu :échec si
file
existait déjà ou sifile
n'a pas pu être créé ; succès sifile
n'existait pas et a été créé.
Inconvénients :
- besoin de définir le
noclobber
option (mais ça va dans un script, si vous faites attention aux redirections, ou si vous la désactivez par la suite).
Je suppose que cette solution est vraiment la contrepartie bash du open
appel système avec O_CREAT | O_EXCL
.
Voici une fonction bash utilisant le mv -n
astuce :
function mkatomic() {
f="$(mktemp)"
mv -n "$f" "$1"
if [ -e "$f" ]; then
rm "$f"
echo "ERROR: file exists:" "$1" >&2
return 1
fi
}
Exemples :
$ mkatomic foo
$ wc -c foo
0 foo
$ mkatomic foo
ERROR: file exists: foo