Frage Die Ausgabe eines Daemons mit Upstart protokollieren


Ich habe einen benutzerdefinierten Daemon, der von Upstart auf meinem Ubuntu-Server verwaltet wird. Es funktioniert perfekt, außer dass ich die Ausgabe des Daemons erfassen (loggen) muss. Das offizielle Strophen-Seite sagt, dass ich benutzen kann console logged um dies zu tun, aber welche Datei protokolliert es?

Das habe ich auch gelesen console logged ist keine gültige Strophe mehr. Ich verwende derzeit 0.3.9 (Hardy), werde aber in ein paar Monaten auf 0.6.x (Lucid) upgraden. Ob console logged in der Tat wird nicht mit späteren Versionen arbeiten, was verwende ich stattdessen?


34
2018-02-17 23:25


Ursprung


Können Sie Ihren benutzerdefinierten Daemon einfach aktualisieren, um die Ausgabe an syslog oder an eine Protokolldatei zu senden, die in der Konfigurationsdatei des Daemons angegeben ist? - Zoredache


Antworten:


Dieses Snippet leitet die Ausgabe Ihres Dienstes weiter in Logger, während Sie immer noch das Ausführen der Serviceprozess (ersetzt somit den Shell-Prozess) damit der Emporkömmling nicht verwirrt wird. Es macht auch Sicher, dass der Logger-Prozess in init repariert wird, also es ist kein Kind von deinem Dienst, und es vermeidet verlassenen craft sitzt im Dateisystem sogar obwohl es vorübergehend ein Fifo erstellen muss.

script
  mkfifo /tmp/myservice-log-fifo
  ( logger -t myservice </tmp/myservice-log-fifo & )
  exec >/tmp/myservice-log-fifo
  rm /tmp/myservice-log-fifo
  exec myservice 2>/dev/null
end script

So funktioniert das:

  1. mkfifo /tmp/myservice-log-fifo macht einfach die fifo spezielle datei (aka Named Pipe). Art man 7 fifo Für mehr Information.
  2. ( logger ... </tmp/myservice-log-fifo & )  Startet den Logger-Lesevorgang vom Fifo im Hintergrund. Die Parens bewirken, dass der Logger-Prozess zu init repariert wird, anstatt ein Kind des aktuellen Shell-Prozesses zu bleiben.
  3. exec >/tmp/myservice-log-fifo leitet das Stdout der aktuellen Shell zum Fifo um. Jetzt haben wir einen offenen Dateideskriptor für diesen Fifo, und wir brauchen den Dateisystemeintrag nicht mehr ...
  4. rm /tmp/myservice-log-fifo also werden wir es entfernen.
  5. exec myservice 2>/dev/null führt den Dienst einfach auf die übliche Weise aus. Stdout geht bereits zum FIFO, und das wird sich nicht ändern, wenn das neue Programm ausgeführt wird.

AKTUALISIEREN:  set -e wird nicht benötigt, da Upstart Skripte mit dieser Option standardmäßig ausführt (siehe http://upstart.ubuntu.com/cookbook/#develop-scripts-using-bin-sh)


34
2017-09-29 00:56



großartige Antwort und lässt keine Fifo-Dateien irgendwo herumliegen. - Ash Berlin-Taylor
Was ist der set -e? - Peter Mounce
Das set -e bewirkt, dass das Skript sofort beendet wird, wenn ein Befehl fehlschlägt. Ohne diese Zeile würde das Skript nachfolgende Befehle nutzlos (und möglicherweise gefährlich) ausführen. - Keith Rarick
Fügen Sie die Zeile hinzu, um sowohl stderr als auch stdout zu protokollieren exec 2>&1 über rm Linie, und entfernen Sie die 2>/dev/null von der letzten Zeile. - itsadok


Für aktuelle Ubuntu-Versionen (12.04+) einfach verwenden

console log

Und die Daemon-Ausgabe (STDOUT & STDERR) wird angehängt /var/log/upstart/<service>.log

http://upstart.ubuntu.com/cookbook/#console-log


31
2018-01-13 17:05



Das wäre sauber und nett, aber leider funktioniert es nicht auf CentOS 6.x, das noch eine alte Version von Emporkömmling liefert, die das nicht unterstützt. - Cristian Măgherușan-Stanciu


Wenn du das benutzt console output  Stropheund leiten Sie dann die Ausgabe des Skripts an logger (die Shell-Befehlsschnittstelle zum Systemprotokollmodul syslog (3)), dann wird das funktionieren.

Zum Beispiel

console output
exec /my/script | logger

wird einloggen /var/log/messages

Zum Beispiel

console output
exec /my/script | logger -t my-script

wird einloggen /var/log/messages und markieren Sie jede Nachricht mit my-script

logger --help für Logger-Nutzungsoptionen.

(Ich bin auf dem Amazon Linux AMI, das ist Centos 5.x basiert; YMMV)


11
2018-06-20 12:43



Es stellt sich heraus, dass dies keine gute Lösung ist. Upstart verriegelt auf die PID von loggernicht von dem Prozess, den Sie eigentlich verwalten wollen. - Peter Mounce


Ich habe das nicht bekommen mkfifo Trick, um zufriedenstellend zu arbeiten; es scheint nicht stderr zu erfassen, und versucht, verursacht Upstart ohne Fehler zu bailen.

Es hat auch eine unglückliche Nebenwirkung der Herstellung der logger Prozess herumhängen als ein Kind von init, also ist die Information darüber, wer den Logger "besitzt", verloren, und jeder, der das nicht bereits bemerkt hat mkfifo könnte annehmen, dass es sich um einen baumelnden Prozess handelt, der getötet werden kann.

Stattdessen endete ich mit der folgenden Lösung, die alle diese Probleme löst. Es verursacht loggerum ein Kindprozess zu werden, während der Service als Root-Prozess erhalten bleibt. Leider erfordert es die Ausführung bash, aber es ist einfach sieht aus schmutzig.

script
  # ... setup commands here, e.g. environment, cd, ...
  exec bash <<EOT
    exec 1> >(logger -t myservice) 2>&1
    exec myservice
EOT
end script

Dies verwendet einen Trick, der stdout und stderr zu einem Befehl umleitet. Da wir den Service innerhalb der bash Befehl, dies hat den Nebeneffekt, die Shell zu ersetzen und magisch Bash zu einem Kind Prozess des Dienstes zu machen, wie von gezeigt ps aufxw:

myservice 
 \_ bash -c exec 1> >(logger -t myservice) 2>&1 && exec myservice
    \_ logger -t myservice

Aus irgendeinem Grund muss der obige Befehl in a eingehüllt werden bash -c. Ich nehme an, das liegt daran, dass Upstart nur vorgibt, Ihr Skript über Bash auszuführen, aber eigentlich nicht. Wenn jemand einen Weg vorschlagen kann, die extra Bash Shell zu vermeiden, wäre das großartig.


9
2018-02-12 03:17



Ja! Ich bin so froh, dass ich das gefunden habe. Sieht besser aus als die mkfifo Variante und in meinem Fall musste ich exec bash -l << EOF also kein Verlust da. - thom_nic


Das ist hässlich, aber bis jetzt das Beste, was ich gefunden habe

exec / Pfad / zu / Server >> /tmp/upstart.log 2> & 1


6
2018-03-16 09:22



Die Lösung ist nicht gut, wenn es um die Protokollrotation geht, da sich die Anwendung direkt in der Datei anmeldet. Das Protokollieren durch Syslog vermeidet damit verbundene Probleme. - Mark Stosberg


Sie können die Ausgabe auch an syslog umleiten, z.

exec $SERVER 2>&1 | logger -t myservice -p local0.info

Die Pipeline kann jedoch dazu führen, dass der Startvorgang die PID des Protokollierungsprozesses mit der PID des Daemon verwechselt.


3
2018-04-01 21:30



Der Daemon, der die PID verwirrt, ist eigentlich ein nutzloser Daemon, da er den Prozess beobachten und respawnen soll. Irgendeine Idee, um sicherzustellen, dass die richtige PID überwacht wird? - Johann Philipp Strathausen
Ich denke (aber habe nicht versucht), dass du das willst expect fork oder expect daemon Strophe. Oder du könntest cat die pid-Datei in die Log-Nachricht sonst, denke ich. - Peter Mounce


Eine andere Alternative ist die Verwendung von Tee wie:

exec $SERVER 2>&1 | tee /dev/stderr | logger -t myservice

um sowohl die Upstart-Datei als auch die Syslog-Ausgabe zu erhalten


1
2017-12-16 13:17