Esegui uno script solo al primo avvio


12

Esiste un modo idiomatico in Ubuntu per eseguire uno script solo al primo avvio di una macchina? (EC2).

Risposte:


14

No. Ma potresti voler inserire il tuo script /etc/init.d/scripted eliminarlo automaticamente:

#!/bin/bash

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

# Delete me
rm $0

Nota: $0è specifico per bash (versione> = 3). Ai fini della compatibilità è possibile fornire invece il nome del file di script, rendendolo meno generico:rm /etc/init.d/script
Andrejs Cainikovs,

4
$ 0 NON è specifico per bash ed è stato supportato per molto più tempo di bash 3.x è stato in circolazione (ed è supportato in Bourne, Korn, zsh e altri). Il punto critico è se $ 0 contiene una specifica del percorso completa o relativa. Ecco un link a un modo affidabile per ottenere il percorso completo se ne hai bisogno: stackoverflow.com/questions/4774054/…
Jim Dennis,

7

Crea un file di tracciamento quando viene eseguito lo script. Se il file esiste già, esci dallo script.


3
Anche se potrebbe non sembrare così a prima vista, questa potrebbe essere una soluzione migliore rispetto all'eliminazione dello script in quanto conserva la possibilità di attivarlo di nuovo, se mai lo desideri.
msanford,

7

Combinando le prime due risposte Supponendo che tu chiami il tuo script /usr/local/bin/firstboot.shmettilo alla fine di /etc/rc.local(questo script viene eseguito ad ogni avvio) gli script vanno così

#! / Bin / bash

FLAG = "/ var / log / firstboot.log"
Se [ ! -f $ FLAG]; poi
   #Metti qui le tue frasi di inizializzazione
   echo "Questo è il primo avvio"

   #la riga successiva crea un file vuoto in modo che non esegua il prossimo avvio
   toccare $ FLAG
altro
   echo "Non fare nulla"
fi

Questo non funziona necessariamente con sysmtemd. Devo aggiungere un sleep 20 per essere sicuro che sia l'ultimo script eseguito.
mrossi,

Se lo chiami /etc/rc.local/99-firstboot.sh dovrebbe funzionare per ultimo.
JohnDavid,

3

Sono sorpreso dei risultati che sto vedendo per la ricerca di un hook "primo avvio" di Ubuntu ben definito e supportato. Sembra che la folla di Red Hat / Fedora / CentOS lo abbia inchiodato per oltre un decennio. L'equivalente Ubuntu più vicino sembra essere oem-config-firstboot .

L'idea di eseguire semplicemente una rm $0volontà funzionerà. Ma tecnicamente ci sono alcune semantiche interessanti coinvolte. A differenza della maggior parte degli altri interpreti di script in Unix, uno script di shell viene letto ed elaborato una riga / istruzione alla volta. Se scolleghi ( rm) il file da sotto di esso, allora l'istanza della shell che sta elaborando quello script ora funziona con un file anonimo (qualsiasi file aperto ma non collegato).

Prendi in considerazione un file come questo:

#!/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

Se lo salvi su qualcosa di simile rmself.she (difficile) il link a qualcosa di simile, l' tstesecuzione in esecuzione ./tstdovrebbe mostrare qualcosa di simile come output:

$ ./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

Ora ci sono alcuni casi angolari possibili strani per quanto riguarda i collegamenti simbolici e i casi in cui lo script è stato invocato come un nome nudo (costringendo la shell a cercare $PATHlo script.

Ma sembra che bash(almeno nella versione 3.2) si prepaga $0con il percorso se ha cercato il percorso e altrimenti lascia $ 0 impostato su qualunque percorso relativo o assoluto sia stato usato per invocare lo script. Non sembra fare alcun percorso relativo di normalizzazione o risoluzione né collegamenti simbolici.

Probabilmente il "primo avvio" più pulito per Ubuntu sarebbe quello di creare un piccolo pacchetto (.deb) contenente uno script da inserire /etc/init.d/firstboote uno script post-installazione che usi update-rc.dper collegarlo al runlevel 1 ( /etc/rc1.d) (usando un comando come:) update-rc.d firstboot defaults. .. e quindi fare in modo che l'ultima riga esegua una disattivazione o elimini usando qualcosa come:update-rc.d firstboot disable

Ecco un link al Debian update-rc.d HOWTO


0

È possibile eseguire il backup di rc.local corrente su rc.local.bak

Quindi puoi avere le cose che vuoi fare in rc.local e alla fine solo mv /etc/rc.loca.bak /etc/rc.local.


0

La domanda riguardava l'esecuzione di uno script al primo avvio di EC2. È possibile utilizzare cloud-initper questo scopo.

Quando si avvia una nuova istanza EC2, è possibile definire un'opzione User datain Advanced datails. Se si posiziona lo cloud-initscript lì, verrà eseguito solo al primo avvio.

Ad esempio è possibile inserire quanto segue in User data:

#cloud-config

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

L'output verrà scritto in /var/log/cloud-init-output.log

Cloud-initpuò fare molto di più di questo. È progettato appositamente per eseguire l'inizializzazione precoce delle istanze cloud. Consulta i documenti qui: http://cloudinit.readthedocs.io/en/latest/index.html

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.