Question

Existe-t-il des considérations spéciales concernant l'utilisation de Python dans un script 'init.d' exécuté via init ? (c'est-à-dire démarrer Ubuntu)

D'après ce que j'ai compris lors de la recherche sur Google et des tests sur Ubuntu, les variables d'environnement fournies à un script 'init.d' sont rares et l'utilisation de "! #! / usr / bin / env python " pourrait ne pas fonctionner.

Autre chose?

Était-ce utile?

La solution

Cela met en évidence le plus gros problème avec python dans un script init.d - la complexité ajoutée.

Python n’a pas de spécification, et l’environnement n’a même pas à pointer vers cpython. Si vous améliorez et pauses python, vous devrez vous mordre la langue. Et il y a beaucoup plus de chances que python se brise que sh (la valeur sûre pour les scripts init.d). Raison d'être, utilité simple:

ecarroll@x60s:/etc/init.d$ ldd /usr/bin/python
    linux-gate.so.1 =>  (0xb7ff7000)
    libpthread.so.0 => /lib/tls/i686/cmov/libpthread.so.0 (0xb7fc9000)
    libdl.so.2 => /lib/tls/i686/cmov/libdl.so.2 (0xb7fc5000)
    libutil.so.1 => /lib/tls/i686/cmov/libutil.so.1 (0xb7fc0000)
    libz.so.1 => /lib/libz.so.1 (0xb7faa000)
    libm.so.6 => /lib/tls/i686/cmov/libm.so.6 (0xb7f84000)
    libc.so.6 => /lib/tls/i686/cmov/libc.so.6 (0xb7e21000)
    /lib/ld-linux.so.2 (0xb7ff8000)
ecarroll@x60s:/etc/init.d$ ldd /bin/sh
    linux-gate.so.1 =>  (0xb803f000)
    libc.so.6 => /lib/tls/i686/cmov/libc.so.6 (0xb7ec7000)
    /lib/ld-linux.so.2 (0xb8040000)

Python relie entre autres libpthread, libdl, libutil, libz, libm, etc. Python fait simplement plus.

-rwxr-xr-x 1 root root  86K 2008-11-05 01:51 /bin/dash
-rwxr-xr-x 1 root root 2.2M 2009-04-18 21:53 /usr/bin/python2.6

Vous pouvez en savoir plus sur ce dont vous parlez spécifiquement avec les variables env ici: http://www.debian.org/doc/ debian-policy / ch-opersys.html # s9.9 Le problème principal est que les valeurs par défaut pour env peuvent être définies dans / etc / profile, ce qui ne s’exécuterait que si le script est exécuté sous un shell qui le lit.

Autres conseils

Je suppose que cela exécute une sorte de démon écrit en python. Sinon, cela pourrait ne pas s'appliquer.

Vous voudrez (probablement) faire la même chose qu’un standard fork et rediriger les descripteurs de fichiers. C’est celui que j’utilise (Adapté d’une recette de code ActiveState dont l’url m’échappe pour le moment).

def daemonize(stdin, stdout, stderr, pidfile):
    if os.path.isfile(pidfile):
        p = open(pidfile, "r")
        oldpid = p.read().strip()
        p.close()
        if os.path.isdir("/proc/%s"%oldpid):
            log.err("Server already running with pid %s"%oldpid)
            sys.exit(1)
    try:
        pid = os.fork()
        if pid > 0:
            sys.exit(0)
    except OSError, e:
        log.err("Fork #1 failed: (%d) %s"%(e.errno, e.strerror))
        sys.exit(1)
    os.chdir("/")
    os.umask(0)
    os.setsid()
    try:
        pid = os.fork()
        if pid > 0:
            if os.getuid() == 0:
                pidfile = open(pidfile, "w+")
                pidfile.write(str(pid))
                pidfile.close()
            sys.exit(0)
    except OSError, e:
        log.err("Fork #2 failed: (%d) %s"%(e.errno, e.strerror))
        sys.exit(1)
    try:
        os.setgid(grp.getgrnam("nogroup").gr_gid)
    except KeyError, e:
        log.err("Failed to get GID: %s"%e)
        sys.exit(1)
    except OSError, e:
        log.err("Failed to set GID: (%s) %s"%(e.errno, e.strerror))
        sys.exit(1)
    try:
        os.setuid(pwd.getpwnam("oracle").pw_uid)
    except KeyError, e:
        log.err("Failed to get UID: %s"%e)
        sys.exit(1)
    except OSError, e:
        log.err("Failed to set UID: (%s) %s"%(e.errno, e.strerror))
        sys.exit(1)
    for f in sys.stdout, sys.stderr:
        f.flush()
    si = open(stdin, "r")
    so = open(stdout, "a+")
    se = open(stderr, "a+", 0)
    os.dup2(si.fileno(), sys.stdin.fileno())
    os.dup2(so.fileno(), sys.stdout.fileno())
    os.dup2(se.fileno(), sys.stderr.fileno())

Lancez-le avant de démarrer votre boucle démon et il fera probablement la bonne chose.

En note de bas de page, j’utilise #! / usr / bin / env python comme ligne shebang dans un script sur Ubuntu et cela fonctionne très bien pour moi.

Vous voudrez probablement toujours rediriger stdout / stderr vers un fichier même si vous n’exécutez pas de démon pour fournir des informations de débogage.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top