web-dev-qa-db-fra.com

Exécuter un script uniquement au tout premier démarrage

Existe-t-il un moyen idiomatique dans Ubuntu d’exécuter un script uniquement au premier démarrage d’une machine? (EC2).

12
Roberto Aloi

Non, mais vous voudrez peut-être placer votre script dans /etc/init.d/script et le supprimer lui-même:

#!/bin/bash

echo "Bump! I'm your first-boot script."

# Delete me
rm $0
14
Andrejs Cainikovs

Créez un fichier de suivi lors de l'exécution du script. Si le fichier existe déjà, quittez le script.

7
Tom

Combinaison des deux premières réponses En supposant que vous nommez votre script /usr/local/bin/firstboot.sh placez-le à la fin de /etc/rc.local (ce script est exécuté à chaque démarrage), il se présente comme suit:

 #!/bin/bash 
 
 FLAG = "/ var/log/firstboot.log" 
 si [! -f $ FLAG]; then 
 #Put ici vos phrases d'initialisation 
 echo "Ceci est le premier démarrage" 
 
 #la ligne suivante crée un fichier vide afin d'éviter d'exécuter le prochain démarrage 
, touchez $ FLAG 
 sinon 
7
Awi

Je suis surpris des résultats obtenus en recherchant un point d'ancrage "premier démarrage" Ubuntu bien défini et pris en charge. On dirait que la foule de Red Hat/Fedora/CentOS a eu cela cloué pour plus d'une décennie. L'équivalent Ubuntu le plus proche semble être oem-config-firstboot .

L’idée de simplement exécuter un rm $0 fonctionnera. Mais, techniquement, il existe une sémantique intéressante. Contrairement à la plupart des autres interpréteurs de script sous Unix, un script Shell est lu et traité ligne/instruction à la fois. Si vous dissociez (rm) le fichier situé en dessous, l'instance du shell qui traite ce script utilise maintenant un fichier anonyme (tout fichier ouvert mais non lié).

Considérons un fichier comme celui-ci:

#!/bin/bash
rm $0
echo "I've removed myself: $0"
ls -l $0
cat <<COMMENTARY
   This is a test.
   I'm still here, because the "here" doc is being fed to 'cat'
   via the anonymous file through the open file descriptor.
   But I cannot be re-exec'd
COMMENTARY
exec $0

Si vous enregistrez cela dans quelque chose comme rmself.sh et un lien (dur) avec quelque chose comme tst, alors exécuter ./tst devrait afficher quelque chose comme ceci en sortie:

$ ./tst 
I've removed myself: ./tst
ls: ./tst: No such file or directory
   This is a test.
   I'm still here, because the "here" doc is being fed to 'cat'
   via the anonymous file through the open file descriptor.
   But I cannot be re-exec'd
./tst: line 11: /home/jimd/bin/tst: No such file or directory
./tst: line 11: exec: /home/jimd/bin/tst: cannot execute: No such file or directory

Il existe maintenant quelques cas étranges possibles en ce qui concerne les liens symboliques et les cas dans lesquels le script a été appelé sous forme de nom simple (forçant le shell à rechercher le script avec le $PATH.

Mais il semble que bash (au moins dans la version 3.2) ajoute $0 au nom du chemin s'il a recherché le chemin et laisse sinon $ 0 défini sur le chemin relatif ou absolu utilisé pour appeler le script. Il ne semble pas faire de chemins relatifs de normalisation ou de résolution, ni de liens symboliques.

Le "premier démarrage" le plus propre pour Ubuntu serait probablement de créer un petit paquet (.deb) contenant un script à placer dans /etc/init.d/firstboot et un script de post-installation qui utilise update-rc.d pour le lier au niveau d'exécution 1 (/etc/rc1.d) (à l'aide d'une commande telle que : update-rc.d firstboot defaults) ... puis demandez à la dernière ligne de désactiver ou de supprimer en utilisant quelque chose comme: update-rc.d firstboot disable

Voici un lien vers le Guide de la mise à jour de Debian-rc.d

3
Jim Dennis

La question portait sur l'exécution d'un script au premier démarrage de EC2. Vous pouvez utiliser cloud-init à cette fin.

Lors du lancement d'une nouvelle instance EC2, vous avez la possibilité de définir User data sous Advanced datails. Si vous y placez le script cloud-init, il ne sera exécuté qu'au premier démarrage.

Par exemple, vous pouvez placer les éléments suivants dans User data:

#cloud-config

runcmd:
  - /usr/bin/command1.sh
  - /usr/bin/command2.sh

La sortie sera écrite dans /var/log/cloud-init-output.log

Cloud-init peut faire beaucoup plus que cela. Il est spécialement conçu pour effectuer une initialisation précoce d'instances de cloud. Voir la documentation ici: http://cloudinit.readthedocs.io/en/latest/index.html

0
Dima L.

Vous pouvez sauvegarder le fichier rc.local actuel sur rc.local.bak.

Ensuite, vous pouvez avoir ce que vous voulez faire dans rc.local et à la fin, juste mv /etc/rc.loca.bak /etc/rc.local.

0
lmojzis