Wie starte ich nginx erst neu, nachdem der Konfigurationstest unter Ubuntu erfolgreich war?

111

Wenn ich den nginx-Dienst über eine Befehlszeile auf einem Ubuntu-Server neu starte, stürzt der Dienst ab, wenn eine nginx-Konfigurationsdatei Fehler enthält. Auf einem Server mit mehreren Standorten werden alle Standorte gelöscht, auch diejenigen ohne Konfigurationsfehler.

Um dies zu verhindern, führe ich zuerst den Nginx-Konfigurationstest aus:

nginx -t

Nachdem der Test erfolgreich ausgeführt wurde, konnte ich den Dienst neu starten:

/etc/init.d/nginx restart

Oder laden Sie nur die nignx-Site-Konfigurationen ohne Neustart neu:

nginx -s reload

Gibt es eine Möglichkeit, diese beiden Befehle zu kombinieren, bei denen der Befehl zum Neustart vom Ergebnis des Konfigurationstests abhängig ist?

Ich konnte dies online nicht finden und die offizielle Dokumentation dazu ist ziemlich einfach. Ich kenne mich mit Linux nicht so gut aus, daher weiß ich nicht, ob das, wonach ich suche, direkt vor mir liegt oder überhaupt nicht möglich ist.

Ich verwende Nginx v1.1.19.

jan
quelle
Was ist mit einem kleinen Shell-Skript, das den Rückgabestatus von nginx -t (mit $?) Überprüft und dann den Neustart abhängig vom Rückgabestatus durchführt?
TeTeT

Antworten:

49

Soweit ich weiß, würde nginx eine leere Nachricht anzeigen und nicht neu starten, wenn die Konfiguration schlecht ist.

Die einzige Möglichkeit, es zu vermasseln, besteht darin, einen Nginx-Stopp durchzuführen und dann erneut zu starten. Es würde gelingen aufzuhören, aber nicht zu starten.

Mohammad AbuShady
quelle
1
Über welche Version von Nginx sprechen Sie? Ich arbeite mit Version 1.1.19 und es wird versucht, unabhängig von Fehlern in den Konfigurationsdateien neu zu starten. Es wird mir mitteilen , dass es ein Problem ist, aber dann ist es schon zu spät
Januar
5
Ok, ich habe es gerade getestet, mein Laptop hat Nginx 1.2 und es hat wie beschrieben funktioniert, mein VPS hat 1.1.19 wie deins und es hat dasselbe getan, wie Sie es in Ihrer Frage beschrieben haben. Also ich denke, dies wurde in 1.2
Mohammad AbuShady
Toll! Danke, dass du das für mich herausgefunden hast. Ich werde die Frage halten länger ein wenig öffnen , um zu sehen , ob niemand eine Antwort für nginx <v1.2 hat
Januar
1
Ich denke , ich werde dann :-) benötigt sowieso eine Entschuldigung aktualisieren müssen
Januar
1
service nginx reloadzeigt nichts an, ob die Konfiguration korrekt geladen wurde oder nicht, daher ist es nutzlos, wenn Sie den Verdacht haben, dass die Konfiguration falsch ist. service nginx restartstoppt den Server, wenn die Konfiguration einen Fehler hat!
Dan Dascalescu
80

Ab Nginx 1.8.0 ist die richtige Lösung

sudo nginx -t && sudo service nginx reload

Beachten Sie, dass aufgrund eines Fehlers configtestimmer ein Exit-Code von Null zurückgegeben wird, auch wenn in der Konfigurationsdatei ein Fehler vorliegt.

Dan Dascalescu
quelle
3
nginx -t && sudo nginx -s reload
MechanisM
5
@MechanisM: nginx -tOhne Sudo wird es mit ziemlicher Sicherheit an Berechtigungsfehlern scheitern.
Dan Dascalescu
Ich wollte hauptsächlich den letzten Teil zum Nachladen zeigen. In meinem Fall habe ich nginx benutzerdefiniert kompiliert und habe nicht einmal Skripte in /etc/init.d und so weiter. In meinem Fall wird "service nginx reload" also nichts bewirken
MechanisM
39

Ich verwende den folgenden Befehl, um Nginx (Version 1.5.9) nur dann neu zu laden, wenn ein Konfigurationstest erfolgreich war:

/etc/init.d/nginx configtest && sudo /etc/init.d/nginx reload

Wenn Sie dies häufig tun müssen, möchten Sie möglicherweise einen Alias ​​verwenden. Ich benutze folgendes:

alias n='/etc/init.d/nginx configtest && sudo /etc/init.d/nginx reload'

Der Trick hier wird durch das "&&" gemacht, das den zweiten Befehl nur ausführt, wenn der erste erfolgreich war. Sie können sehen , hier eine ausführlichere Erklärung der Verwendung des „&&“ Operator.

Sie können "Neustart" anstelle von "Neuladen" verwenden, wenn Sie den Server wirklich neu starten möchten.

Mauricio Sánchez
quelle
Vorsicht vor Nginx 1.4.2 Ich habe festgestellt pkill -1 nginx(effektiv, was mein rel.d / nginx-Reload bewirkt), dass es NICHT neu geladen wird, wenn die Konfiguration fehlschlägt und irreführend erfolgreich zurückgibt. Überprüfen Sie Ihre eigenen Versionen.
KCD
2
Das funktioniert bei mir nicht. Beide Befehle werden auch dann ausgeführt, wenn der Test fehlschlägt.
Mario Campa
2
configtest gibt immer einen Null-Exit-Code zurück , zumindest in nginx 1.8.0. Verwenden Sie nginx -tstattdessen.
Dan Dascalescu
8
alias nginx.start='sudo nginx -c /etc/nginx/nginx.conf'
alias nginx.stop='sudo nginx -s stop'
alias nginx.reload='sudo nginx -s reload'
alias nginx.config='sudo nginx -t'
alias nginx.restart='nginx.config && nginx.stop && nginx.start'
alias nginx.errors='tail -250f /var/logs/nginx.error.log'
alias nginx.access='tail -250f /var/logs/nginx.access.log'
alias nginx.logs.default.access='tail -250f /var/logs/nginx.default.access.log'
alias nginx.logs.default-ssl.access='tail -250f /var/logs/nginx.default.ssl.log'

und verwenden Sie dann die Befehle "nginx.reload" etc ..

Mechanismus
quelle
6

Sie können mit /etc/init.d/nginx reloadund neu ladensudo service nginx reload

Wenn nginx -tein Fehler auftritt, wird er nicht neu geladen

Verwenden Sie also &&, um beide gleichzeitig auszuführen

mögen

nginx -t && /etc/init.d/nginx neu laden

Gokul Kandasamy
quelle
Lassen Sie mich Ihnen etwas über Bash beibringen. && nicht run both at a same timeDer Befehl auf der rechten Seite wird ausgeführt, wenn der Befehl auf der linken Seite einen Exit-Code von 0 zurückgibt. Wenn Sie nginx -teinen Fehler auslösen, ist der Exit-Code nicht 0, sodass der zweite Befehl nicht ausgeführt wird. Es ist nginx -s reloadsowieso
Miknik
@miknik Ich denke, das wollte er sagen, es kam einfach nicht richtig heraus. Er sagt If nginx -t throws some error then it won't reload. Die Anweisung run both at a same timekann auch als einzelner Befehl oder als eine Zeile interpretiert werden. Ich interpretiere ihn in diesem Fall nicht unbedingt so in parallel.
Matt
2

Sie können Signale verwenden, um Nginx zu steuern.

Laut Dokumentation müssen Sie das HUP-Signal an den Nginx-Master-Prozess senden.

HUP - Änderung der Konfiguration, Einhaltung einer geänderten Zeitzone (nur für FreeBSD und Linux), Starten neuer Arbeitsprozesse mit einer neuen Konfiguration, ordnungsgemäßes Herunterfahren alter Arbeitsprozesse

Überprüfen Sie die Dokumentation hier: http://nginx.org/en/docs/control.html

Sie können das HUP-Signal wie folgt an die PID des Nginx-Master-Prozesses senden:

kill -HUP $( cat /var/run/nginx.pid )

Der obige Befehl liest die Nginx-PID von /var/run/nginx.pid. Standardmäßig wird nginx pid geschrieben /usr/local/nginx/logs/nginx.pid, dies kann jedoch in der Konfiguration überschrieben werden. Überprüfen Sie nginx.config, wo die PID gespeichert wird.

hcristea
quelle
1

Zumindest unter Debian verfügt das Nginx-Startskript über eine Reload-Funktion, die Folgendes bewirkt:

reload)
  log_daemon_msg "Reloading $DESC configuration" "$NAME"
  test_nginx_config
  start-stop-daemon --stop --signal HUP --quiet --pidfile $PID \
   --oknodo --exec $DAEMON
  log_end_msg $?
  ;;

Alles, was Sie tun müssen, ist anzurufen, service nginx reloadanstatt restartes anzurufen test_nginx_config.

Daenney
quelle
service nginx reloadgibt keinen Hinweis darauf, ob die Konfiguration in Ordnung getestet wurde oder nicht oder ob sie neu geladen wurde oder nicht.
Dan Dascalescu
Was macht test_nginx_configman dann in diesem Fall?
Daenney
1
Ich denke, Sie haben beide einen Punkt. service nginx reloadist in der Befehlszeile ausreichend, aber manchmal möchten Sie möglicherweise die stderr-Ausgabe erfassen und diese zur Fehlerbehebung an ein Skript zurückgeben. nginx -twürde Ihnen sagen, welche Datei den ungültigen Parameter hatte und in welcher Zeile.
anastymous