Forum: PC-Programmierung [Python] Laufendes Python Skript in Hintergrund verschieben


von Dennis X. (Gast)


Lesenswert?

Hallo zusammen,
aktuell stehe ich vor einem kleinen Problem und ich weiß nicht genau wie 
ich das in Python realisiere.
Ich habe bisher mein Python Skript immer mit "nohup test.py &" direkt in 
Hintergrund getrennt von der Konsole gestartet.
Nun ist die Sache, dass ich gerne beim Start ein paar Eingaben mit input 
abfragen möchte, das Programm dann einige Zeit laufen lassen und nach 
ein paar Zyklen quasi den gleichen Zustand wie mit nohup erreichen 
möchte.
Ist das direkt aus Python heraus möglich? Entweder ich suche falsch oder 
das ist nicht so ein Anwendungsfall den man oft braucht.
Sollte ich hier vielleicht anders vorgehen? Eigentlich kann ich an der 
Vorgehensweise nichts ändern, ich weiß nur nicht wie ich aus Python 
heraus das Programm in den Hintergrund verschiebe (am besten ohne 
unterbrechung) und es von dort vom Terminal löse, damit es nach dem 
Logout weiter läuft.

Jemand Tipps?
Grüße Dennis

von Rolf M. (rmagnus)


Lesenswert?

Siehe den Code auf 
http://stackoverflow.com/questions/1603109/how-to-make-a-python-script-run-like-a-service-or-daemon-in-linux

Alternativ kannst du statt nohup auch screen verwenden. Damit hast du 
sogar die Möglichkeit, sich später irgendwann wieder mit deinem Programm 
zu verbinden.

von fork (Gast)


Lesenswert?

Müsste z.B. auch mir forking gehen.

von Dennis X. (Gast)


Lesenswert?

Ja nohup kann ich ja nur beim Start zu Beginn verwenden. Ein nohup -p 
PID ist bei mir nicht auf dem System installiert.
Eine Klasse habe ich in Python nicht programmiert, es ist ein kleines 
Skript welches ein paar Werte abfragt.
Ich glaube ich schaue mir screen einmal genauer an.

von Rolf M. (rmagnus)


Lesenswert?

Dennis X. schrieb:
> Ich glaube ich schaue mir screen einmal genauer an.

Einfach mal screen test.py starten, damit tun, was tu tun willst und 
dann das Skript (bzw. die screeen-Session) mit Strg+a d vom Terminal 
abkoppeln. Später kannst du dich per screen -R wieder damit verbinden, 
bzw. wenn mehrere laufen mit screen -list eine Liste der laufenden 
Sessions ausgeben lassen und mit screen -r <session-name> dann eine zum 
verbinden auswählen.

von Dennis X. (Gast)


Lesenswert?

Rolf M. schrieb:
> Strg+a d

Die pid meines Prozesses hol ich mir gleich zu Beginn. Kann ich das dann 
über ein kill -xyz ebenso realisieren? Würde da gerne direkt aus dem 
Code machen.

von Daemon (Gast)


Lesenswert?


von Dennis X. (Gast)


Lesenswert?

Also so richtig funktioniert das alles noch nicht wie ich das möchte. 
Ich würde gerne einmalig die Mainloop durchlaufen um dann das ganze in 
den Hintergrund zu verschieben. Screen hört sich sehr interessant an, 
aber wie geht das direkt aus Python heraus?
Gibt es noch andere Möglichkeiten?

von db8fs (Gast)


Lesenswert?

Kannste nicht einfach Strg-Z drücken und das Skript per 'bg' in den 
Hintergrund packen? Müsste dann mit 'jobs' aufgelistet werden.

von Bernd K. (prof7bit)


Lesenswert?

machs doch einfach so daß das script sich selbst nochmal mit nohup 
startet, und die ursprüngliche Instanz sich dann beendet. Gib alle 
benötigten Daten aus dem ersten Teil der Ausführung über die 
Kommandozeile an die neue Instanz so daß diese weiß daß und wo sie 
weitermachen soll. So würde ich das machen, kurz und schmerzlos.

: Bearbeitet durch User
von Bernd K. (prof7bit)


Lesenswert?

Dennis X. schrieb:
> Screen hört sich sehr interessant an

tmux ist die aktuell empfohlene Weiterempfehlung davon, screen ist schon 
etwas angestaubt, es gibt keinen Grund das heute noch zu verwenden.

tmux verwende ich gern wenn ich mich per ssh auf nen entfernten Rechner 
einlogge, das ist so ziemlich das erste was ich in die Konsole tippe 
nach dem login. Wenn ich dann grad 5 virtuelle Terminals mit 
angefangener Arbeit oder laufenden Prozessen offen habe kann jederzeit 
jemand über mein Netwerkkabel stolpern oder das Telefon klingelt und ich 
muss weg, alles kein Problem. Später setz mich dann an irgend nen 
anderen Rechner, verbinde mich wieder und mit tmux a finde ich alle 
meine Terminals wieder exakt so vor wie ich sie verlassen habe, 
inclusive laufender Prozesse. Feine Sache ist das.

: Bearbeitet durch User
von db8fs (Gast)


Lesenswert?

Bernd K. schrieb:
> machs doch einfach so daß das script sich selbst nochmal mit nohup
> startet, und die ursprüngliche Instanz sich dann beendet. Gib alle
> benötigten Daten aus dem ersten Teil der Ausführung über die
> Kommandozeile an die neue Instanz so daß diese weiß daß und wo sie
> weitermachen soll. So würde ich das machen, kurz und schmerzlos.

Wozu einen neuen Prozess starten, wenn man das mit dem Prozessmanagement 
der Shell lösen kann? Und die meisten Terminalemulatoren sowie Bash, 
Dash, zsh u, können mit dem SIGTSTP (tty stop) einen Prozess pausieren 
und bieten dann mit Foreground ('fg') oder Background ('bg') 
Möglichkeiten zur Steuerung an. Kannste auch kill dafür nehmen, wenns 
denn sein muss: kill -TSTP <pid>

von Bernd K. (prof7bit)


Lesenswert?

db8fs schrieb:
> Wozu einen neuen Prozess starten, wenn man das mit dem Prozessmanagement
> der Shell lösen kann?

Ich dachte er wills automatisieren, so daß es sich nach dem Start und 
ein paar Fragen an den Benutzer automatisch in den Hintergrund 
verabschiedet.

von db8fs (Gast)


Lesenswert?

Bernd K. schrieb:
> Ich dachte er wills automatisieren, so daß es sich nach dem Start und
> ein paar Fragen an den Benutzer automatisch in den Hintergrund
> verabschiedet.

Hmm, jo, könnte sein, aber aus den Antworten oben mit 'screen' hatte ich 
eigentlich einen manuellen Eingriff seinerseits angenommen. D.h er 
drückt aufn Knopf, lässt das Skript laufen und schickts dann, wenn er 
gesehen hat, was er sehen wollte, einfach in den Hintergrund.

Mach ich bei den meisten Sachen so, und wenn's der Texteditor im 
Vordergrund ist. Kurz in den Hintergrund, fix das Editierte kompiliert 
und dann Editor wieder nach vorne geholt. Komplett ohne screen und co.

Wenn's vollautomatisiert laufen soll, dass das ganze im Vordergrund 
anläuft und dann selber in den Hintergrund wechselt, würde ich das aber 
dennoch lieber auf der Shellebene lösen wollen - das Pythonskript selber 
sollte nicht sich selber steuern können, das geht schief (also 
Parent-Prozess manipulieren). Und selbst Funktionen, die Teilprozesse 
starten, würden andere Pythonskripte erfordern - man dreht sich also im 
Kreis. Daher lieber per Shell.

von Rolf M. (rmagnus)


Lesenswert?

db8fs schrieb:
> Mach ich bei den meisten Sachen so, und wenn's der Texteditor im
> Vordergrund ist. Kurz in den Hintergrund, fix das Editierte kompiliert
> und dann Editor wieder nach vorne geholt. Komplett ohne screen und co.

Natürlich geht das. Nur ist das Programm halt weg, wenn du die Konsole 
schließt, was ja hier ausdrücklich nicht passieren soll. Deshalb der 
Tipp mit screen.

: Bearbeitet durch User
von Dennis X. (Gast)


Lesenswert?

Screen ist toll. Ich muss auch nie wieder an diesen Prozess ran, weil ab 
dann eine Server API die Steuerung darstellt. Daher eigentlich nur noch 
die Frage wie kann ich aus python heraus eine aufterufenes Skript durch 
"screen python skript.py" nach hinten schieben?

von Bernd K. (prof7bit)


Lesenswert?

Rolf M. schrieb:
> Deshalb der
> Tipp mit screen.

lieber tmux empfehlen anstelle von screen im Jahre 2016. Das kann man 
übrigens sogar von innen heraus komplett scripten, sein Python Script 
könnte also rein theoretisch sich selbst in einer neuen tmux-Sitzung 
starten, den interaktiven Teil erledigen und dann die tmux-Sitzung 
detachen. Allerdings wäre das ein etwas unkonventionelles (um nicht zu 
sagen extrem schräges) Verhalten, meist pflegt der tmux Nutzer gerne 
selbst die Kontrolle behalten zu wollen und detached manuell wenn ihm 
danach ist oder er erzeugt einfach schnell ein weiteres Fenster wenn 
grad alle belegt sind.

von Bernd K. (prof7bit)


Lesenswert?

Dennis X. schrieb:
> Screen ist toll.

Vergiss es bevor Du zuviel Zeit investierst. Nimm stattdessen dessen 
aktuellen Nachfolger tmux und lass das alte screen auf dem Friedhof 
ruhen.

von Rolf M. (rmagnus)


Lesenswert?

Bernd K. schrieb:
> lieber tmux empfehlen anstelle von screen im Jahre 2016.

Die aktuelle stable-Version 4.4 von screen ist von Juni 2016.

Bernd K. schrieb:
> Nimm stattdessen dessen aktuellen Nachfolger tmux und lass das alte
> screen auf dem Friedhof ruhen.

Also auf der Webseite von screen steht nix von einem Nachfolger. tmux 
hab ich noch nicht verwendet. Es scheint einfach nur eine Alternative, 
aber nicht der "aktuelle Nachfolger" von screen zu sein.

: Bearbeitet durch User
von Norbert (Gast)


Lesenswert?

1
Programm normal starten.
2
Eingaben tätigen.
3
Ctrl-Z
4
# bg <Enter>
5
# disown <Enter>

Fertich... ;-)

von Dennis X. (Gast)


Lesenswert?

Bernd K. schrieb:
> Vergiss es bevor Du zuviel Zeit investierst. Nimm stattdessen dessen
> aktuellen Nachfolger tmux und lass das alte screen auf dem Friedhof
> ruhen.

Danke Bernd,
ich habe mich ein wenig in tmux eingelesen und finde es echt toll! Mach 
das jetzt auch bei jeder SSH Session als erstes, sofern installiert.
Eine Frage bleibt auch nach überfliegen der Doku noch.
Ich hab im einen Terminal tmux laufen und befinde mich hier in einem 
Programm. Durch eine andere Shell würde ich nun gerne Fenster 1 wieder 
auf den eigentlichen SSH screen bringen und tmux einfach nach hinten 
schieben.
Geht das? Wenn ja, wäre mein Problem gelöst!

Grüße

von Bernd K. (prof7bit)


Lesenswert?

Neue Sitzung                     tmux
Detach:                          Ctrl-b  d
Attach zu laufender Sitzung:     tmux a
Sitzungen auflisten:             tmux list-sessions

Neues Fenster:                   Ctrl-b  c
Fenster beenden:                 Ctrl-d (einfach die shell beenden)
Fenster wechseln:                Alt-Links, Alt-Rechts
Fenster wechseln (GUI):          Ctrl-b  w
Sitzung/Fenster wechseln (GUI):  Ctrl-b  s

: Bearbeitet durch User
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.