Passer un script Python en tâche de fond

Bonjour,

J’ai un script en Python3 que je lance par SSH (sur un serveur Debian) de mon téléphone (avec Termux). Le problème, c’est que le script met un peu de temps à s’exécuter.
Je souhaite le détacher de la connexion ssh dès qu’elle se lance. Un conseil pour ça proprement ?

Merci.

Ma réponse va paraître un peu simplette, mais j’ai du mal à en formuler une autre étant donné le peu de détail que tu donnes (commande/démarche exacte ?) : tu as essayé avec un & après ta commande ?

Si je fais ça, c’est sur le téléphone que ça va se mettre en arrière-plan et ça va le faire tout de suite.
Et l’esperluette ne fonctionne pas en Python3, je crois.

Du coup je pense que je comprends mal la démarche exacte. Ce que je m’imaginerais faire à ta place :

  • lancer un terminal SSH depuis mon téléphone,
  • lancer mon script en tâche de fond : ./monscript.py &,
  • fermer mon terminal SSH.

Où est-ce que j’ai faux ?

Ah, non, je lance le script directement avec ssh monserveur ./monscript.py. C’est pour ça que je veux gérer ça dans le script directement.

bg … ???

Si le script Python3 doit s’exécuter sur le serveur, il est peut-être possible d’utiliser la commande at depuis le serveur pour qu’elle lance le script Python3.

Python 3.4.2 (default, Oct  8 2014, 10:45:20) 
[GCC 4.9.1] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import bg
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named 'bg'
>>> bg
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'bg' is not defined

Inconnu au bataillon !

Ce n’est pas une tâche à planifier, c’est une tâche à lancer maintenant.

Excuse-moi … je suis PTR de ma propre bêtise ! Tsss …

Normal que bg soit inconnu, c’est une commande shell :stuck_out_tongue:

Je viens de comprendre que tu veux l’équivalent pour python !

Veuilles m’excuser. :smiley:

Comme le script mets un certain temps à s’exécuter, je me disais que c’était pas à la minute près : Si tu programme le lancement du script pour être lancé dans la minute suivante, tu peux te déconnecter tranquille de ta session ssh.

Ah oui, l’échelle. L’exécution prend entre dix et vingt secondes, donc, oui, je suis à une minute près.

Et ssh monserveur './monscript.py &' ne fonctionnerait pas ?

Et sinon le lancer dans un screen à l’aide de Screen ou Tmux ce ne serait pas plus simple comme ça tu détache le screen et tu laisse ton script se déroulé tranquillou.

Je vais peut être à nouveau dire une bêtise, mais :

ssh user@server nohup script.py

?


Sinon, en python, essaye de voir si tu peux récupérer son pid et de le mettre en arrière plan … il semblerait que subprocess.Popen() soit une réponse.


Comme quoi je ne suis pas si loin de la réponse :

Non, ça fait exactement la même chose, je ne sais pas pourquoi.

J’ai essayé de lancer ssh monserveur 'screen -d -m -S monscript -s ./monscript.py' et ça ne fonctionne pas du tout.

Pour ça, c’est pareil qu’avec l’esperluette, ça ne fait rien de mieux.[quote=“PengouinPdt, post:15, topic:71109”]
Comme quoi je ne suis pas si loin de la réponse :

  • exemple avec nohup
  • exemple avec subprocess
    [/quote]
    nohup python bgservice.py &
    cmd = 'ssh ' + ssh_options + ' ' + server_name + ' "/usr/bin/nohup /usr/bin/python /home/admin/run.py 2>&1 &"'
    C’est un peu pareil, non ? Et ce n’est toujours pas du Python. Et en plus, ça ne met toujours pas la tâche en fond.

Je peux me tromper (encore heureux), mais il me semble que si le fil d’exécution principal est fermé, les fils en descendant le seront aussi. Donc s’il lance son script et le quitte tout de suite après, les fils qu’il aura lancés seront automatiquement tués.

Tu n’aurais pas oublié la dernière commande ???
p = subprocess.Popen(cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE)

Non, le fil principal attend la terminaison des autres fils pour se fermer. Mais, ce n’est pas bon dans les deux cas.

Non, mais je cherche un moyen que le script fasse ça par lui-même, pas qu’il lance une commande qui lance un autre truc sur le script. Normalement, il devrait pouvoir faire ça sur lui-même et tout seul, non ?

Je viens de tester ça :

from sys import argv, stdin, stdout, stderr, exit
from os import fork

def double_fork ():
        stdin.close ()
        stdout.close ()
        stderr.close ()
        if fork () > 0:
                exit (0)
        if fork () > 0:
                exit (0)

print ('Starting mon script…')
double_fork ()
# Mon script

Ça fonctionne quand je le lance dans un interpréteur de commande, mais quand je le lance par ssh, il ne passe pas en tâche de fond.