it-swarm.com.de

Eine saubere Art, ein Shell-Skript im Hintergrund von Jenkins aus zu starten

Was ist der richtige Weg, um ein Skript von jenkins aus zu starten, den Build nicht hängen zu lassen und den Prozess laufen zu lassen? Ich kann es scheinbar nicht zum Laufen bringen. Entweder läuft das Skript nicht oder der Build hängt.

Wenn ich den "Execute Shell" -Schritt des Builds bash relaunch.sh & Oder relaunch.sh > output.log & Oder Nohup bash relaunch.sh & Eingebe, passiert nichts. Build wird beendet, aber der Prozess wird nicht ausgeführt. Ich denke, es kann damit zusammenhängen, dass Jenkins darauf wartet, dass die Fehlerpipe geschlossen wird .

Wenn ich Nohup bash relaunch.sh 2>&1 > output.log Wie hier vorgeschlagen tue , wird die Ausgabe ordnungsgemäß umgeleitet, aber der Build bleibt hängen (wird nicht beendet), und die Prozess stirbt, wenn ich den Build töte.

Hinzufügen von export BUILD_ID=dontKillMe, Wie vorgeschlagen hier , hier , und hier , entweder zum Schritt "Shell ausführen" oder das Skript selbst hilft auch nicht. Der Build hängt und der Prozess stirbt, wenn ich den Build töte. Unnötig zu erwähnen, dass meine Linux-Kenntnisse sehr begrenzt sind.

Wie machen die Leute das sauber?

21
garci560

Eine bequeme Möglichkeit, dies zu erreichen, besteht darin, die Umgebungsvariable BUILD_ID Unter Ausführen der Shell zu ändern, wobei Jenkins'sProcessTreeKiller sucht.

Indem Sie tun,

BUILD_ID=dontKillMe Nohup bash relaunch.sh &

Jenkins geht davon aus, dass der Hintergrundjob nicht vom Build erzeugt wird und beendet ihn nach Beendigung des Jobs nicht.

Vielen Dank an Joshua für seine Beobachtung, dass Sie auch JENKINS_NODE_COOKIE Als verwenden könnten

JENKINS_NODE_COOKIE=dontKillMe
26
Inian

Ich hatte genau das gleiche Problem. Am Ende habe ich dies behoben, indem ich Folgendes in das Feld "Jenkins Execute Shell" geschrieben habe:

BUILD_ID=dontKillMe ./grid.sh

Ich habe den & innerhalb der Skriptdatei. So sieht das Skript aus:

#!/bin/bash
Java -jar Selenium-server-standalone-3.0.1.jar -role hub &

Hoffentlich hilft das jemandem!

9
user2671131

Interessante Lösungen. Hat jemand Bildschirm ausprobiert?

So führe ich es aus (für RTL-Simulation mit ModelSim-ASE):

screen -S $testname -d -m -L bash -c 'cd build_sim ; make; make sim'
echo Waiting for simulator ...

Ich warte dann darauf, dass unser Simulator in einen Wartezustand übergeht, indem ich den screenlog.0 anschaue

until ((`fgrep -c 'Ready for simulation' screenlog.0`)) ;do
    sleep 1
done

Wenn die anderen Jobs, für die die Simulation erforderlich ist, ausgeführt werden (oder Jenkins einen Fehler feststellt), führen Sie in der Nachbearbeitung Folgendes aus:

screen -S $testname -X kill

Die einzige Einschränkung ist, dass wenn Jenkins irgendwie stirbt, bevor der Job aufräumt, theoretisch ein Simulator Ressourcen auffrisst, während er darauf wartet, dass etwas passiert.

Um es ein wenig aufzuschlüsseln: Mit screen ordnet '-S' der Sitzung einen Titel zu (oder adressiert eine laufende Sitzung mit diesem Titel), '-d' wird losgelöst ausgeführt, '-m' erzeugt zuerst eine Abzweigung (die sich versteckt) Jenkins wachsame Augen), und -L aktiviert die Protokollierung (was auch praktisch ist, wenn etwas im Simulator kaputt geht - Sie haben jetzt ein Protokolldatei-Artefakt mit der Ausgabe). Der Rest wird einfach innerhalb der Bildschirmsitzung geschlagen.

1
GrueMaster