comment faire pour exécuter des scripts shell au démarrage sur Yosemite

21

Il y a un répertoire dans System / Library pour les éléments de démarrage que je présume: StartupItems

J'ai besoin d'un script shell qui configurera l'interface Ethernet au démarrage, avec l'adresse réseau locale et le masque de sous-réseau. Je dois le faire car les préférences réseau pour la configuration de l'interface Ethernet ne le définiront PAS à l'aide de paramètres manuels. CECI semble être un bug grave, ou mon installation est mauvaise.

On m'a donné des conseils pour utiliser networksetup à partir de la ligne de commande, mais cela ne configurera pas l'interface Ethernet de telle manière que les configurations seront là au redémarrage.

Le script doit faire son travail avec les privilèges root, ou avec sudo, mais je suppose que s'il utilise sudo, une boîte de dialogue de mot de passe sera présentée au démarrage lorsque le processus de démarrage arrivera à ce script.

(J'ai suffisamment d'expérience avec FreeBsd et Linux pour me repérer dans le terminal, mais pas nécessairement comme cela s'applique à Mac OSX)

JeffK
la source

Réponses:

18

Une façon de le faire serait d'attribuer au script un service launchd:

Créez le script shell comme d'habitude. Ensuite, vous pouvez créer un service launchd pour l'exécuter au démarrage. Ceux-ci sont situés à /Library/LaunchDaemons. Ceux-ci sont au format de liste de propriétés XML. Créez-en un autre et remplissez-le avec quelque chose comme ceci:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
    <dict>
        <key>Label</key>
        <string>com.example.app</string>
        <key>ProgramArguments</key>
        <array>
            <string>/bin/sh</string>
            <string>/path/to/script</string>
        </array>
        <key>RunAtLoad</key>
        <true/>
        <key>KeepAlive</key>
        <false/>
    </dict>
</plist>

Changez com.example.app, /bin/shet /path/to/scriptau besoin.

Le script s'exécutera alors pendant le démarrage du système. S'il s'exécute trop tôt, vous pouvez soit écrire le script pour essayer de faire ce qu'il doit faire jusqu'à ce qu'il réussisse, soit le quitter avec un code d'erreur non nul et l'ajouter à la liste des propriétés avant la </dict>ligne:

<key>KeepAlive</key>
<dict>
     <key>SuccessfulExit</key>
     <false/>
</dict>

Pour en savoir plus sur les démons et services de lancement OS X, je suggère de rechercher ici une référence rapide sur leur création, ou ici une référence plus complète sur ce que launchd peut faire.

andonuts
la source
Comment appelez-vous ce document plist? Et le / path / to / script == / System / Library / StartupItems / script?
JeffK
1
Pour la première question: le nom du document plist utilise généralement ce que la clé Label dans la liste des propriétés est définie (dans ce cas, "com.example.app") avec une extension .plist.
andonuts
1
Pour la deuxième question: c'est correct, mais le script doit être déplacé ailleurs.
andonuts
Votre plist est mal formé. Vous avez besoin d'une clé: <key>Program</key>avec la valeur <string>/bin/sh</string>, puis <key>ProgramArguments</key>devrait juste avoir la valeur<string>/path/to/script</string>
Jon Brooks
En fait, le mien a tort aussi: <key>ProgramArguments</key>doit être un tableau ..
Jon Brooks
16

Il y a quelque temps, j'ai utilisé cron pour cela. Vous pouvez faire une entrée comme celle-ci

@reboot /path/to/my/script

Plus d'infos ici

Au lieu des cinq premiers champs, l'une des huit chaînes spéciales peut apparaître:

       string          meaning
       ------          -------@reboot ------@reboot
       @reboot         Run once, at startup.
       @yearly         Run once a year, "0 0 1 1 *".
       @annually       (same as @yearly)
       @monthly        Run once a month, "0 0 1 * *".
       @weekly         Run once a week, "0 0 * * 0".
       @daily          Run once a day, "0 0 * * *".
       @midnight       (same as @daily)
       @hourly         Run once an hour, "0 * * * *".
sjosen
la source
1
Très pratique à savoir!
geotheory
7
cronn'est pas la bonne façon de le faire sur OS X de nos jours. Utilisez plutôt LaunchAgent ou LaunchDeamon (launchd). Pour plus d'informations: developer.apple.com/library/mac/documentation/MacOSX/Conceptual/… Although it is still supported, cron is not a recommended solution. It has been deprecated in favor of launchd.
CousinCocaine
4
cronest beaucoup plus facile à configurer que launchd, cependant. Comparez simplement les deux réponses dans ce fil pour voir ce que je veux dire. cronprend une seule ligne dans un seul fichier, où a launchdbesoin d'un script pour décrire le script que vous souhaitez exécuter au démarrage.
Dannid
@Dannid Kron n'est pas sensible à la duplication, à la mise en mémoire tampon des files d'attente et autres. Bien que viable dans ce cas, ce n'est pas toujours une clé squelette, ni une solution idiomatique.
New Alexandria
Crontab est bien meilleur. C'est rapide et sale et établi depuis longtemps dans le monde Unix. Je creuse totalement ce mot-clé @reboot.
macetw