G DATA XDR
Traffic-Reduzierung durch Update-Caching mit HAProxy
Einleitung
Dieser Artikel beschreibt, wie Sie den Netzwerk-Traffic zwischen den G DATA Agenten und dem G DATA Backend reduzieren. Dazu speichert ein lokal betriebener HAProxy die eigentlichen Datei-Downloads von Updates zwischen (Caching) über Port 80. Der vorgelagerte Abgleich von Dateiliste und Hashsummen ist davon nicht betroffen, dieser wird über Port 443 unabhängig durchgeführt und nicht gecacht.
Ein Caching-Proxy bringt den Vorteil, dass die Downloadmenge auf Kundenseite sinkt. Updates werden nur einmal aus dem Internet geladen und danach lokal an alle Agenten im Netzwerk verteilt.
|
Dieser Artikel richtet sich vor allem an Administratoren mit Linux- und Netzwerk-Kenntnissen. Technische Fachbegriffe werden zusätzlich kurz erklärt. So können auch Leser ohne tiefes IT-Hintergrundwissen dem Ablauf folgen. |
Hintergrundwissen: Was ist HAProxy und was macht ein Caching-Proxy?
Wenn viele G DATA Agenten im selben Netzwerk laufen, lädt normalerweise jeder Agent einzeln die Signatur- und Programm-Updates direkt aus dem Internet vom G DATA Update-Server herunter. Bei hundert Endpunkten bedeutet das hundert identische Downloads über Ihre Internetleitung.
Ein Proxy ist ein Vermittler zwischen den G DATA Agenten und dem G DATA Backend. Ein Cache ist ein Zwischenspeicher. Die erste Anfrage nach einer Update-Datei wird normal ins Internet weitergeleitet. Die Antwort wird zusätzlich lokal gespeichert. Jede weitere Anfrage nach derselben Datei wird direkt aus diesem lokalen Speicher beantwortet. Das Internet wird dabei nicht erneut belastet.
HAProxy ist eine weit verbreitete, quelloffene Software. Sie übernimmt diese Aufgabe zuverlässig als TCP/HTTP-Proxy mit Caching-Funktion.
Voraussetzungen
-
Ein Linux-Server (z. B. Debian/Ubuntu) im Netzwerk. Alle G DATA Agenten müssen diesen Server erreichen können.
-
Root- bzw. sudo-Rechte auf diesem Server.
-
Ein gültiges TLS-Zertifikat, inklusive Zertifikatskette. Es gilt für den Hostnamen, unter dem die Agenten den Proxy per HTTPS ansprechen (Index- und Metadaten-Anfragen).
-
Netzwerkfreigaben:
-
Der Proxy-Server muss den G DATA Update-Server agent-update-server.gdatasecurity.de erreichen können. Dafür sind zwei Ports nötig: HTTPS Port 443 und HTTP Port 80.
-
Die G DATA Agenten müssen den Proxy-Server ebenfalls über HTTPS Port 443 und HTTP Port 80 erreichen können.
-
-
Grundkenntnisse im Umgang mit HAProxy-Konfigurationsdateien sind hilfreich, auch wenn diese Dokumentation eine fertige Vorlage bereitstellt.
Erreichbarkeit der G DATA Cloud
Zur Sicherstellung des der zuverlässigen und zeitnahen Meldung von Ereignissen und Vorfällen muss die G DATA Cloud erreichbar sein und darf nicht durch eine Firewall blockiert werden. Dafür sind folgend aufgeführten Einstellungen notwendig. Es muss sichergestellt werden, dass *.gdatasecurity.de und *.gdatasoftware.com aufgelöst werden können und erreichbar sind.
-
Portfreigaben
-
Die G DATA Agenten auf den Endpunkten müssen die IPs unserer Backend-Server über Port TCP/443, IP-Range 194.156.84.0/22 (194.156.84.0 - 194.156.87.255) erreichen können.
-
-
Protokolle
-
Die Systeme müssen über die Protokolle HTTPS:// sowie auch WSS:// kommunizieren können.
-
-
TLS
-
Eingesetzte Proxyserver müssen mindestens TLS 1.2 unterstützen.
-
Es darf keine SSL Inspection oder Deep Packet Inspection vorhanden sein.
-
Es muss eine TLS-verschlüsselte Verbindung mit chess.gdatasecurity.de aufgebaut werden können. Dafür muss ein entsprechendes Root-Zertifikat vorhanden sein.
-
Einrichtung des HAProxys
Schritt 1: HAProxy installieren
Installieren Sie HAProxy über den Paketmanager Ihrer Linux-Distribution, zum Beispiel unter Debian/Ubuntu:
sudo apt update
sudo apt install haproxy
Schritt 2: Zertifikat vorbereiten
HAProxy terminiert die TLS-Verbindung der Agenten. Dafür benötigt es ein Zertifikat samt zugehörigem privaten Schlüssel.
|
HAProxy erwartet Zertifikat, Zertifikatskette und privaten Schlüssel in einer einzigen PEM-Datei, kombiniert in dieser Reihenfolge. Die einzelnen Bestandteile sind: |
| Reihenfolge | Bestandteil |
|---|---|
1 |
Das eigentliche Zertifikat (Server-Zertifikat). |
2 |
Die Zwischenzertifikate, auch Bundle oder Chain genannt. |
3 |
Das Root-CA-Zertifikat, sofern separat vorhanden. |
4 |
Der private Schlüssel. |
Fügen Sie die Dateien in genau dieser Reihenfolge zu einer PEM-Datei zusammen. Beispiel:
cat server.crt intermediate.crt root-ca.crt server.key > /etc/haproxy/certs/haproxy-cache.pem
chmod 640 /etc/haproxy/certs/haproxy-cache.pem
chown root:haproxy /etc/haproxy/certs/haproxy-cache.pem
Schritt 3: HAProxy-Konfiguration erstellen
Legen Sie die Konfigurationsdatei haproxy.cfg unter /etc/haproxy/ an. Nutzen Sie dafür die unten stehende Vorlage (siehe Vollständige Beispielkonfiguration). Ersetzen Sie eine bestehende Datei durch diese Vorlage.
Passen Sie dabei folgende Platzhalter an:
| Platzhalter | Bedeutung |
|---|---|
{{ haproxy_caching_bind }} |
Die IP-Adresse, auf der HAProxy lauscht. Das ist die IP, unter der die Agenten den Proxy erreichen. |
{{ haproxy_caching_server_cert }} |
Der vollständige Pfad zur PEM-Zertifikatsdatei aus Schritt 2, z. B. /etc/haproxy/certs/haproxy-cache.pem. |
{{ haproxy_caching_server }} |
Der interne Hostname, unter dem die Agenten den Caching-Server ansprechen. Dieser Name wird im Host-Header erwartet. |
Schritt 4: HAProxy (neu) starten
Starten Sie den Dienst neu, nachdem Sie die Konfiguration erstellt oder geändert haben:
sudo systemctl restart haproxy
sudo systemctl enable haproxy
Schritt 5 (optional): Konfiguration prüfen
Prüfen Sie die Syntax der Konfigurationsdatei, bevor Sie HAProxy neu starten. So erkennen Sie Tippfehler frühzeitig:
haproxy -c -f /etc/haproxy/haproxy.cfg
Eine fehlerfreie Prüfung meldet Configuration file is valid.
Vollständige Beispielkonfiguration
Die folgende Datei haproxy.cfg dient als Vorlage. Ersetzen Sie die drei Platzhalter. Die Bedeutung der Platzhalter steht in Einrichtung des HAProxys.
global
log /dev/log sample 1:10 local0
log /dev/log sample 1:10 local1 notice
chroot /var/lib/haproxy
stats socket /run/haproxy/admin.sock mode 660 level admin expose-fd listeners
stats timeout 30s
user haproxy
group haproxy
daemon
maxconn 256000
hard-stop-after 15m
tune.ssl.default-dh-param 2048
defaults
log global
mode http
option httplog
option dontlognull
option http-keep-alive
option forwardfor
timeout http-request 10s
timeout queue 1m
timeout connect 10s
timeout client 20s
timeout server 20s
timeout http-keep-alive 10s
timeout check 10s
errorfile 400 /etc/haproxy/errors/400.http
errorfile 403 /etc/haproxy/errors/403.http
errorfile 408 /etc/haproxy/errors/408.http
errorfile 500 /etc/haproxy/errors/500.http
errorfile 502 /etc/haproxy/errors/502.http
errorfile 503 /etc/haproxy/errors/503.http
errorfile 504 /etc/haproxy/errors/504.http
frontend stats
bind {{ haproxy_caching_bind }}:8404 ssl crt {{ haproxy_caching_server_cert }} alpn h2,http/1.1
stats enable
stats uri /
stats refresh 10s
http-request set-log-level silent
http-request use-service prometheus-exporter if { path /metrics }
# ---------------------------------------------------------------------------
# Port 80 (HTTP): eigentlicher Datei-Download - HIER findet das Caching statt.
# ---------------------------------------------------------------------------
frontend http_update_server
bind {{ haproxy_caching_bind }}:80
acl is_update_download path_beg /api/v2/update/download/
acl is_caching_host req.hdr(host) -i {{ haproxy_caching_server }}
http-request set-header X-Forwarded-Host %[req.hdr(Host)]
http-request set-header Host %[req.hdr(Host)]
# Nur Download-Anfragen an den bekannten Hostnamen werden gecacht bedient.
use_backend http_update_server_backend if is_update_download is_caching_host
# Alle anderen Anfragen auf Port 80 sicherheitshalber auf HTTPS umleiten.
http-request redirect scheme https code 301 unless is_update_download
default_backend nomatch
# ---------------------------------------------------------------------------
# Port 443 (HTTPS): Index-/Hash-Abgleich - reiner Pass-through OHNE Caching.
# Diese Antworten sind klein, ändern sich häufig und werden von G DATA
# bewusst nicht für das Caching vorgesehen.
# ---------------------------------------------------------------------------
frontend https_update_server
bind {{ haproxy_caching_bind }}:443 ssl crt {{ haproxy_caching_server_cert }} alpn h2,http/1.1
http-request set-header X-Forwarded-Host %[req.hdr(Host)]
http-request set-header Host %[req.hdr(Host)]
use_backend https_update_server_backend if { req.hdr(host) -i {{ haproxy_caching_server }} }
default_backend nomatch
cache objectcache_update_server
total-max-size 3000
max-object-size 200000000
max-age 86400
backend http_update_server_backend
balance roundrobin
http-request set-header Connection keep-alive
http-request set-header Host agent-update-server.gdatasecurity.de
http-request set-header X-Forwarded-Proto http
http-request cache-use objectcache_update_server if { path_beg /api/v2/update/download/ }
http-response cache-store objectcache_update_server
option httpchk GET /api/status
http-check send hdr Host agent-update-server.gdatasecurity.de
http-check expect status 200
server agent-update-server.gdatasecurity.de agent-update-server.gdatasecurity.de:80 check inter 10s
backend https_update_server_backend
balance roundrobin
http-request set-header Connection keep-alive
http-request set-header Host agent-update-server.gdatasecurity.de
http-request set-header X-Forwarded-Proto https
option httpchk GET /api/status
http-check send hdr Host agent-update-server.gdatasecurity.de
http-check expect status 200
server agent-update-server.gdatasecurity.de agent-update-server.gdatasecurity.de:443 check inter 10s check-sni agent-update-server.gdatasecurity.de sni str(agent-update-server.gdatasecurity.de) ssl verify required ca-file /etc/ssl/certs/ca-certificates.crt
backend nomatch
errorfile 503 /etc/haproxy/errors/503.http
Erläuterung der Konfiguration
Die wichtigsten Abschnitte werden hier einzeln erklärt. So können auch Leser mit weniger HAProxy-Erfahrung die Konfiguration nachvollziehen.
| Abschnitt | Erläuterung |
|---|---|
global / defaults |
Grundlegende Prozess- und Verbindungseinstellungen. Beispiele: Logging, maximale Anzahl gleichzeitiger Verbindungen (maxconn), Standard-Timeouts. Diese Werte müssen Sie in der Regel nicht anpassen. |
frontend stats |
Stellt eine Statusseite auf Port 8404 bereit. Über diese Seite können Sie den Zustand von HAProxy beobachten, unter anderem im Prometheus-Format (/metrics). |
frontend http_update_server |
Der Eingangspunkt für die eigentlichen Datei-Downloads auf Port 80. Nur Anfragen unterhalb von /api/v2/update/download/ an den bekannten Hostnamen gehen an das cachende Backend. Alle anderen Anfragen auf Port 80 werden sicherheitshalber auf HTTPS umgeleitet. |
frontend https_update_server |
Der Eingangspunkt für die Index- und Hash-Abgleiche auf Port 443 (TLS). Hier prüft HAProxy, ob der angefragte Hostname ({{ haproxy_caching_server }}) zum Update-Backend passt. Nur dann leitet HAProxy die Anfrage weiter. Andernfalls landet die Anfrage im Backend nomatch und erhält den Fehler 503. An dieser Stelle findet kein Caching statt. |
cache objectcache_update_server |
Definiert den Zwischenspeicher. Drei Werte sind wichtig: die maximale Gesamtgröße des Caches (total-max-size, in MB), die maximale Größe einer einzelnen Datei (max-object-size, in Byte) und die maximale Verweildauer eines Objekts im Cache (max-age, in Sekunden). Die Vorlage nutzt rund 3 GB Gesamtgröße, bis zu 200 MB pro Datei und 24 Stunden Gültigkeit. Nur das HTTP-Backend nutzt diesen Cache. |
backend http_update_server_backend |
Leitet die Download-Anfragen unverschlüsselt (Port 80) an agent-update-server.gdatasecurity.de weiter. Die Zeile http-request cache-use … if { path_beg /api/v2/update/download/ } sorgt dafür, dass nur dieser Pfad gecacht wird. Der http-check prüft laufend, ob der G DATA Server erreichbar ist. |
backend https_update_server_backend |
Leitet die Index- und Hash-Anfragen verschlüsselt (Port 443, mit Zertifikatsprüfung) an denselben G DATA Server weiter. Dieses Backend enthält weder cache-use noch cache-store. Die Antworten werden durchgereicht, aber nicht gespeichert. |
backend nomatch |
Fängt alle Anfragen ab, die zu keinem bekannten Host passen. Diese Anfragen erhalten den Fehler 503. So verhindert die Konfiguration Missbrauch als offener Proxy. |
|
HAProxy speichert nur Anfragen unterhalb des Pfads /api/v2/update/download/ über HTTP. Die Index- und Hash-Anfragen über HTTPS laufen unverändert weiter. Andere Kommunikationswege der Agenten, zum Beispiel Telemetrie oder Meldungen an das XDR-Backend, sind vom Caching nicht betroffen. |
Agenten auf den Caching-Server umstellen
Wenn Sie die G DATA Agenten bereits auf den Endpunkten installiert haben, kontaktieren Sie den technischen Support unter der Telefonnummer +49 234 9762-901. Die Kollegen des Support werden Ihre G DATA Agenten gerne umstellen.
Haben Sie noch keine G DATA Agenten ausgerollt, erstellen Sie eine Setup-Konfiguration mit der Angabe der Proxy-Adresse. Alle Endpunkte, die mit der dazugehörigen SetupID installiert werden, erhalten Ihre Updates über Ihren Proxy.
|
Prüfen Sie unbedingt, ob die Konfiguration funktioniert. Endpunkte, die keine Updates erhalten, stellen ein Sicherheitsrisiko dar. Lassen Sie in der Konfiguration den Fallbackserver unbedingt an (er sollte nur in begründeten Ausnahmefällen abgeschaltet werden). Mit eingeschaltetem Fallbackserver erhalten Ihre Endpunkte auch Updates, wenn sie das Netzwerk verlassen (zum Beispiel Laptops) oder wenn Ihr Reverse-Proxyserver ausfällt. |
Fehlersuche
| Symptom | Vorgehen |
|---|---|
HAProxy startet nicht |
Prüfen Sie die Konfiguration mit haproxy -c -f /etc/haproxy/haproxy.cfg. Kontrollieren Sie zusätzlich den Dienststatus mit systemctl status haproxy und journalctl -u haproxy. |
Agenten erhalten Zertifikatsfehler |
Prüfen Sie zwei Dinge: Enthält die PEM-Datei Zertifikat, Zwischenzertifikate und privaten Schlüssel in der korrekten Reihenfolge? Passt der Hostname im Zertifikat zu {{ haproxy_caching_server }}? |
Kein Rückgang des Internet-Traffics erkennbar |
Prüfen Sie über die Statusseite (frontend stats, Port 8404), ob die Download-Anfragen über das Backend http_update_server_backend laufen und ob dort Cache-Treffer entstehen. Das Backend https_update_server_backend cacht bewusst nicht. |
Anfragen landen im Backend nomatch |
Der Host-Header der eingehenden Anfrage stimmt nicht mit {{ haproxy_caching_server }} überein. Prüfen Sie die Agenten-Konfiguration und die DNS-Auflösung. |