Hier werde ich beschreiben, wie man einen Reverse Proxy mit einer Web Application Firewall (WAF) basierend auf Apache2 installiert.
Dies geschieht mit ModSecurity und dem OWASP Core Rule Set (CRS), das sicherheitskritische Angriffe erkennt und blockiert. Der Artikel führt durch die Installation und Konfiguration von Apache2, SSL, ModSecurity und dem OWASP-Regelwerk

Installation

Starte zunächst mit der Installation der notwendigen Pakete. Aktualisiere die Paketquellen und installiere Apache2, ModSecurity, Git und Certbot.

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
apt update
apt install apache2 libapache2-mod-security2 git certbot python3-certbot-apache -y
apt update apt install apache2 libapache2-mod-security2 git certbot python3-certbot-apache -y
apt update
apt install apache2 libapache2-mod-security2 git certbot python3-certbot-apache -y

SSL-Zertifikat mit Certbot einrichten

Um SSL zu aktivieren, führen wir die Certbot-Konfiguration aus, die automatisch ein Zertifikat für den Webserver erstellt und einrichtet. Wenn du ein Wildcard-Zertifikat verwenden möchtest, kannst du dies mit der manuellen DNS-Validierung einrichten.

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
certbot --apache
certbot --apache
certbot --apache

Für Wildcard-Zertifikate (z. B. *.stangneth.com) kannst du den folgenden Befehl nutzen. Certbot fordert eine DNS-Challenge an, bei der ein TXT-Eintrag zum DNS hinzugefügt werden muss.

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
certbot certonly --manual --preferred-challenges=dns --server https://acme-v02.api.letsencrypt.org/directory -d *.stangneth.com
certbot certonly --manual --preferred-challenges=dns --server https://acme-v02.api.letsencrypt.org/directory -d *.stangneth.com
certbot certonly --manual --preferred-challenges=dns --server https://acme-v02.api.letsencrypt.org/directory -d *.stangneth.com

Befolge die Anweisungen von Certbot, um den TXT-Eintrag in den DNS-Einstellungen deines Domain-Anbieters hinzuzufügen. Sobald das Zertifikat eingerichtet ist, speichert Certbot es unter /etc/letsencrypt/live/.

Apache2-Module aktivieren und Default-Sites deaktivieren

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
a2enmod security2 proxy proxy_http rewrite ssl
a2enmod security2 proxy proxy_http rewrite ssl
a2enmod security2 proxy proxy_http rewrite ssl

Deaktiviere dann die Standard-Websites, um den Server für deine spezifische Konfiguration vorzubereiten:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
a2dissite 000-default.conf
a2dissite default-ssl.conf
a2dissite 000-default.conf a2dissite default-ssl.conf
a2dissite 000-default.conf
a2dissite default-ssl.conf

OWASP Core Rule Set (CRS) herunterladen und einrichten

Lade das OWASP Core Rule Set (CRS) herunter und platziere es im empfohlenen Verzeichnis /etc/crs4:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
git clone https://github.com/coreruleset/coreruleset /etc/crs4
cd /etc/crs4
cp crs-setup.conf.example crs-setup.conf
git clone https://github.com/coreruleset/coreruleset /etc/crs4 cd /etc/crs4 cp crs-setup.conf.example crs-setup.conf
git clone https://github.com/coreruleset/coreruleset /etc/crs4
cd /etc/crs4
cp crs-setup.conf.example crs-setup.conf

ModSecurity konfigurieren

Passe die ModSecurity-Konfigurationsdatei an, indem du die empfohlene Konfigurationsdatei kopierst und SecRuleEngine aktivierst:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
cp /usr/share/modsecurity-crs/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf
cp /usr/share/modsecurity-crs/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf
cp /usr/share/modsecurity-crs/modsecurity.conf-recommended /etc/modsecurity/modsecurity.conf

Öffne die Datei und setze SecRuleEngine auf On:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
nano /etc/modsecurity/modsecurity.conf
nano /etc/modsecurity/modsecurity.conf
nano /etc/modsecurity/modsecurity.conf

ModSecurity-Regeln in Apache einbinden

Bearbeite die Datei /etc/apache2/mods-enabled/security2.conf, um die CRS-Regeln einzubinden:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
nano /etc/apache2/mods-enabled/security2.conf
nano /etc/apache2/mods-enabled/security2.conf
nano /etc/apache2/mods-enabled/security2.conf

Füge folgende Zeilen hinzu, um das CRS-Regelwerk zu laden:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
IncludeOptional /etc/crs4/crs-setup.conf
IncludeOptional /etc/crs4/rules/*.conf
IncludeOptional /etc/crs4/crs-setup.conf IncludeOptional /etc/crs4/rules/*.conf
IncludeOptional /etc/crs4/crs-setup.conf
IncludeOptional /etc/crs4/rules/*.conf

Apache-Konfiguration als Reverse Proxy

Erstelle eine neue Konfigurationsdatei für den VirtualHost in /etc/apache2/sites-available. Verwende diese Konfiguration für example.stangneth.com und ersetze die IP-Adresse 172.16.254.3 und den Port 5151 mit den Werten deines Web-Servers.

Erstelle die Datei und füge die Konfiguration hinzu:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
nano /etc/apache2/sites-available/001-example.stangneth.com.conf
nano /etc/apache2/sites-available/001-example.stangneth.com.conf
nano /etc/apache2/sites-available/001-example.stangneth.com.conf
Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
<VirtualHost *:80>
ServerName example.stangneth.com
RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>
<VirtualHost *:443>
ServerName example.stangneth.com
SSLProxyEngine On
SSLProxyVerify none
SSLProxyCheckPeerCN off
SSLProxyCheckPeerName off
SSLProxyCheckPeerExpire off
ProxyPreserveHost off
# Globale ModSecurity-Ausnahmen
SecRuleRemoveById 949110
# Proxy-Konfiguration
ProxyPass / http://172.16.254.3:5151/
ProxyPassReverse / http://172.16.254.3:5151/
# SSL-Zertifikate
Include /etc/letsencrypt/options-ssl-apache.conf
SSLCertificateFile /etc/letsencrypt/live/stangneth.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/stangneth.com/privkey.pem
</VirtualHost>
<VirtualHost *:80> ServerName example.stangneth.com RewriteEngine On RewriteCond %{HTTPS} off RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [END,NE,R=permanent] </VirtualHost> <VirtualHost *:443> ServerName example.stangneth.com SSLProxyEngine On SSLProxyVerify none SSLProxyCheckPeerCN off SSLProxyCheckPeerName off SSLProxyCheckPeerExpire off ProxyPreserveHost off # Globale ModSecurity-Ausnahmen SecRuleRemoveById 949110 # Proxy-Konfiguration ProxyPass / http://172.16.254.3:5151/ ProxyPassReverse / http://172.16.254.3:5151/ # SSL-Zertifikate Include /etc/letsencrypt/options-ssl-apache.conf SSLCertificateFile /etc/letsencrypt/live/stangneth.com/fullchain.pem SSLCertificateKeyFile /etc/letsencrypt/live/stangneth.com/privkey.pem </VirtualHost>
<VirtualHost *:80>
    ServerName example.stangneth.com

    RewriteEngine On
    RewriteCond %{HTTPS} off
    RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

<VirtualHost *:443>
    ServerName example.stangneth.com

    SSLProxyEngine On
    SSLProxyVerify none
    SSLProxyCheckPeerCN off
    SSLProxyCheckPeerName off
    SSLProxyCheckPeerExpire off
    ProxyPreserveHost off

    # Globale ModSecurity-Ausnahmen
    SecRuleRemoveById 949110

    # Proxy-Konfiguration
    ProxyPass / http://172.16.254.3:5151/
    ProxyPassReverse / http://172.16.254.3:5151/

    # SSL-Zertifikate
    Include /etc/letsencrypt/options-ssl-apache.conf
    SSLCertificateFile /etc/letsencrypt/live/stangneth.com/fullchain.pem
    SSLCertificateKeyFile /etc/letsencrypt/live/stangneth.com/privkey.pem
</VirtualHost>

Aktiviere die neue Seite und starte Apache2 neu, um die Änderungen zu übernehmen:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
a2ensite 001-example.stangneth.com.conf
systemctl restart apache2
a2ensite 001-example.stangneth.com.conf systemctl restart apache2
a2ensite 001-example.stangneth.com.conf
systemctl restart apache2

Überprüfung der Logs

Um sicherzustellen, dass alles wie gewünscht funktioniert und ModSecurity keine Probleme verursacht, prüfe das Apache-Fehlerprotokoll:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
tail -f /var/log/apache2/error.log
tail -f /var/log/apache2/error.log
tail -f /var/log/apache2/error.log

Ein Ausgabe könnte wie folgt aussehen:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
2023/01/12 14:38:39 [error] 1155#1155: *18 [client 172.16.0.123] ModSecurity: Access denied with code 403 (phase 2). Matched "Operator `Ge' with parameter `5' against variable `TX:ANOMALY_SCORE' (Value: `5' ) [file "/usr/local/src/owasp-modsecurity-crs-3.0.2/rules/REQUEST-949-BLOCKING-EVALUATION.conf"] [line "44"] [id "949110"] [rev ""] [msg "Inbound Anomaly Score Exceeded (Total Score: 5)"] [data ""] [severity "2"] [ver ""] [maturity "0"] [accuracy "0"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [hostname "172.16.0.18"] [uri "/api/v1/tickets/14"] [unique_id "167188911882.664343"] [ref ""], client: 172.16.0.123, server: example.stangneth.com, request: "PUT /api/v1/tickets/14?all=true HTTP/1.1", host: "example.stangneth.com", referrer: "https://example.stangneth.com/"
2023/01/12 14:38:39 [error] 1155#1155: *18 [client 172.16.0.123] ModSecurity: Access denied with code 403 (phase 2). Matched "Operator `Ge' with parameter `5' against variable `TX:ANOMALY_SCORE' (Value: `5' ) [file "/usr/local/src/owasp-modsecurity-crs-3.0.2/rules/REQUEST-949-BLOCKING-EVALUATION.conf"] [line "44"] [id "949110"] [rev ""] [msg "Inbound Anomaly Score Exceeded (Total Score: 5)"] [data ""] [severity "2"] [ver ""] [maturity "0"] [accuracy "0"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [hostname "172.16.0.18"] [uri "/api/v1/tickets/14"] [unique_id "167188911882.664343"] [ref ""], client: 172.16.0.123, server: example.stangneth.com, request: "PUT /api/v1/tickets/14?all=true HTTP/1.1", host: "example.stangneth.com", referrer: "https://example.stangneth.com/"
2023/01/12 14:38:39 [error] 1155#1155: *18 [client 172.16.0.123] ModSecurity: Access denied with code 403 (phase 2). Matched "Operator `Ge' with parameter `5' against variable `TX:ANOMALY_SCORE' (Value: `5' ) [file "/usr/local/src/owasp-modsecurity-crs-3.0.2/rules/REQUEST-949-BLOCKING-EVALUATION.conf"] [line "44"] [id "949110"] [rev ""] [msg "Inbound Anomaly Score Exceeded (Total Score: 5)"] [data ""] [severity "2"] [ver ""] [maturity "0"] [accuracy "0"] [tag "application-multi"] [tag "language-multi"] [tag "platform-multi"] [tag "attack-generic"] [hostname "172.16.0.18"] [uri "/api/v1/tickets/14"] [unique_id "167188911882.664343"] [ref ""], client: 172.16.0.123, server: example.stangneth.com, request: "PUT /api/v1/tickets/14?all=true HTTP/1.1", host: "example.stangneth.com", referrer: "https://example.stangneth.com/"

In diesem Fall war es erforderlich, die Regel [id „949110“] aus der Konfiguration für DIESE Website zu entfernen (alle anderen Seiten können diese Regel verwenden, aber möglicherweise andere nicht. Überprüfen muss man dies für jede einzelne Webseite!). Spezifischen Seitenkonfiguration aufrufen:

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
nano /etc/apache2/sites-available/001-example.stangneth.com.conf
nano /etc/apache2/sites-available/001-example.stangneth.com.conf
nano /etc/apache2/sites-available/001-example.stangneth.com.conf

Und nun fügt man die folgende Zeile zur Konfiguration für *:443 hinzu (In obiger Beispielconfig schon geschehen):

Plain text
Copy to clipboard
Open code in new window
EnlighterJS 3 Syntax Highlighter
SecRuleRemoveById 949110
SecRuleRemoveById 949110
SecRuleRemoveById 949110

Disclaimer

Diese Anleitung dient als Orientierung und sollte an die jeweilige Umgebung angepasst werden. Die Artikel sind ausschließlich zu Testzwecken gedacht, und ich übernehme keine Haftung für eventuelle Schäden oder Fehlfunktionen. Ich empfehle, jede Konfiguration gründlich zu prüfen und in einer sicheren Testumgebung auszuprobieren. Gerne stehe ich Ihnen für eine individuelle Beratung und Umsetzung zur Verfügung.