CentOS 7 startet zu schnell und das Netzwerk ist beim Ausführen von Cron-Skripten nicht bereit

9

Ich habe gerade ein Upgrade von CentOS 6.5 auf 7.0 durchgeführt und bin nicht sehr glücklich, da das neue systemdmir wahrscheinlich Probleme bereitet. Es scheint, als würde es einfach zu schnell booten, Prozesse asynchron starten und Dienstabhängigkeiten vermasseln.

Zum Beispiel habe ich einige Skripte eingerichtet, cronddie nach einem Neustart ausgelöst werden:

@reboot    /root/scripts/check_gmail.sh
@reboot    /root/scripts/start_gps_listener.sh

Dies führt zu allen möglichen seltsamen Fehlern (von denen nur einer angezeigt wird):

Warning: stream_socket_client(): unable to connect to tcp://192.168.20.4:4001 
  (Network is unreachable) in /root/scripts/check_gmail.php on line 137
  ERROR: Network is unreachable (101)

Oben schreibe ich an einen TCP-Socket. Mir ist ziemlich klar, dass crondes gestartet wird, bevor das Netzwerk ordnungsgemäß als das initialisiert wird network is unreachable.

Das gleiche gilt für Apache und MySQL (MariaDB). MySQL startet nur sehr langsam (viele Daten), was bedeutet, dass sowohl Apache als auch viele meiner crondStartskripte fehlschlagen, da die MySQL-Datenbank beim Aufrufen der Skripte nicht ausgeführt wird.

Ich habe versucht, Abhängigkeiten einzurichten, aber ohne Glück; Ich habe angehängt networkund mysqlDienstleistungen an [Unit](wie mit gesehen systemctl list-dependencies). Im Idealfall warten alle Dienste, bis MySQL betriebsbereit ist:

vi /lib/systemd/system/httpd.service
  [Unit]
  Description=The Apache HTTP Server
  After=network.target remote-fs.target nss-lookup.target network.service mysql.service

vi /lib/systemd/system/crond.service
  [Unit]
  Description=Command Scheduler
  After=syslog.target auditd.service systemd-user-sessions.service time-sync.target network.service mysql.service

Beim Booten mit den oben genannten bekomme ich die gleichen Fehler. Ich erhalte auch die E-Mails, mailqda das Netzwerk / DNS bei der Verarbeitung von Cron-Skripten nicht bereit ist. Einige Minuten nach dem Start werden sie korrekt gesendet.

Kann jemand helfen, dies richtig zu machen, indem er sicherstellt, dass die Dienste in der richtigen Reihenfolge ausgelöst werden? Es scheint sehr falsch zu sein, dass es so schnell bootet und im Idealfall auf die gute alte Art und Weise "einen Dienst starten ... warten ... einen neuen Dienst starten ... warten ... so weiter").

Beachten Sie, dass ich nicht sicher bin, ob dies systemdmein Problem ist - es ist nur meine Theorie dessen, was ich aus dem Netz lesen kann.

DHS
quelle
Könnten Sie die Ausgabe von posten grep -i concurrency /etc/default/rcS? Ich vermische vielleicht meine Init-Systeme, aber ich erinnere mich, dass dies steuert, ob Prozesse aufeinander warten, bis sie abgeschlossen sind.
Terdon
Ich habe keine Dateien mit/etc/default/rc*
DHS
Entschuldigung, ich weiß nicht, wo das CentOS-Äquivalent wäre. Ich habe darüber nachgedacht, was hier für Debian beschrieben wird, wodurch Dienste parallel gestartet werden. Möglicherweise gibt es in Ihrem Fall einen ähnlichen Satz.
Terdon
2
Versuchen Sie Requires=network.target, die oben genannten Einheiten zu ergänzen.
Casey
Immer noch das gleiche Problem nach dem Einfügen Requires=network.targetin/lib/systemd/system/crond.service
DHS

Antworten:

9

Nach viel mehr Lesen fand ich die Lösung, die für mich funktioniert.

Ich habe dieses Handbuch gelesen: Ausführen von Diensten, nachdem das Netzwerk aktiv ist . Ein kleines Zitat aus dem Leitfaden:

Dadurch wird sichergestellt, dass alle konfigurierten Netzwerkgeräte aktiv sind und eine IP-Adresse zugewiesen wurde, bevor der Startvorgang fortgesetzt wird.

Dies ist genau das, was ich wollte, also habe ich diesen Dienst aktiviert und die Abhängigkeitsregel in der Dienstdatei festgelegt für crond:

[root@srv]# systemctl enable NetworkManager-wait-online

[root@srv]# vi /lib/systemd/system/crond.service
  Requires=network.target
  After=syslog.target auditd.service systemd-user-sessions.service time-sync.target network.target mysqld.service

Da mysqldes immer noch auf dem alten basiert, das init.dich zum Erstellen eines systemdDienstes benötigt habe, wie hier vorgeschlagen, unterscheidet sich systemctl enable vom systemctl start :

[root@srv]# vi /lib/systemd/system/mysqld.service
  [Unit]
  Description=MySQL Server
  After=network.target
  [Service]
  Type=forking
  ExecStart=/etc/rc.d/init.d/mysql start
  ExecStop=/etc/rc.d/init.d/mysql stop
  [Install]
  WantedBy=multi-user.target

[root@srv]# systemctl daemon-reload
[root@srv]# chkconfig mysql off
[root@srv]# systemctl enable mysqld

Und schließlich den Apache-Dienst so einrichten, dass er nach MySQL gestartet wird:

[root@srv]# vi /lib/systemd/system/httpd.service
  Requires=mysqld.service
  After=network.target remote-fs.target nss-lookup.target mysqld.service

Das funktioniert zumindest bei mir.

Ich habe diese Befehle verwendet, um es anschließend zu überprüfen, wo ich deutlich sehen kann, dass das Netzwerk vor mindestens MySQL und Apache gestartet wurde. Ich kann das zwar crondnirgendwo sehen, aber ich kann sehen, dass es in meinen Skripten funktioniert:

[root@srv]# systemd-analyze critical-chain
  multi-user.target @10.510s
    + httpd.service @10.344s +165ms
      + mysqld.service @9.277s +1.065s
        + network.target @9.273s
          + network.service @8.917s +355ms
            + iptables.service @444ms +157ms
              + basic.target @443ms
                [CUT]

Einige andere nützliche Befehle, die ich verwendet habe, sind:

# See exactly what takes how long (who to blame for the delay)
[root@srv]# systemd-analyze blame

# Check available names that can be used in the service files
[root@srv]# systemctl list-unit-files

Wenn jemand einen besseren Weg sieht, dies zu tun, dann teile es bitte mit.

DHS
quelle
+1 für die Veröffentlichung der Befehle, mit denen Sie dies debuggt haben. Ich war in der Lage, eine wirklich schlimme Reihe von Problemen mit zu lösen systemd-analyze critical-chain. Ich werde das nicht nur oft benutzen, sondern bin plötzlich weiterverkauft systemd. Vielen Dank!
Brian Topping
Sie sollten keine Servicedateien ändern, die von Ihrem Distributionspaket-Manager verwaltet werden. Verwenden Sie stattdessen Drop-In-Konfigurationsdateien. Siehe die Antwort auf Wie überschreibe oder konfiguriere ich systemd-Dienste?
Ludovic Ronsin