Anatomie einer sicheren Apache2-Konfigurationsdatei

Einige Vorschläge

Zuerst möchte ich vorschlagen, dass Sie Ihre Konfigurationsdateien aufteilen und dann jede Site (und andere wichtige Konfigurationstypen) in die Hauptserverkonfiguration aufnehmen. Ihre Konfigurationsdatei mit serverweiten Einstellungen wird aufgerufen apache2.confoder manchmal httpd.conf und befindet sich normalerweise in der
/etc/apache2/ Verzeichnis. Unter diesem Hauptkonfigurationsverzeichnis von Apache2 werden Sie wahrscheinlich auch einige andere Verzeichnisse sehen, und diese werden später aus Ihrer primären Konfigurationsdatei hinzugefügt. Die drei, die wir heute verwenden werden, werden sein mods-available / mods-enabled, sites-available /sites-enabledund conf-available / conf-enabled. Jetzt können Sie das alles wirklich so organisieren, wie Sie es möchten, solange Sie alles richtig einfügen. Aber ich schlage vor, das Standardschema zu verwenden, da die meisten Leute sowie die Dokumentation diesem Setup folgen.

Die primäre Konfigurationsdatei

Jetzt, da das aus dem Weg ist, werden wir einen Blick auf die aktuelle Konfiguration werfen, wenn Sie gerade Apache2 von Ihrem Paketmanager installiert haben, wird es sehr generisch aussehen, so wie hier (außer mit viel Dokumentation auskommentiert, ich werde weglassen):

Hinweis: Sie können Ihre eigene Konfiguration beliebig dokumentieren, indem Sie eine Raute „#” Zeichen vor, woran Sie sich selbst oder jemand anderen erinnern möchten!

ServerRoot "/etc/apache2"
Mutex file:${APACHE_LOCK_DIR} default
PidFile ${APACHE_PID_FILE}
Timeout 300
KeepAlive On
MaxKeepAliveRequests 100
KeepAliveTimeout 5
User ${APACHE_RUN_USER}
Group ${APACHE_RUN_GROUP}
HostnameLookups Off
ErrorLog ${APACHE_LOG_DIR}/error.log
LogLevel warn
IncludeOptional mods-enabled/*.load
IncludeOptional mods-enabled/*.conf
Include ports.conf
<Directory />
  Options FollowSymLinks
  AllowOverride None
  Require all denied
</Directory>
<Directory /usr/share>
  AllowOverride None
  Require all granted
</Directory>
<Directory /var/www/>
  Options Indexes FollowSymLinks
  AllowOverride None
  Require all granted
</Directory>
AccessFileName .htaccess
<FilesMatch "^\.ht">
  Require all denied
</FilesMatch>
LogFormat "%v:%p %h %l %u %t \"%r\" %>s %O \"%{Referer}i\" \"%{User-Agent}i\"" vhost_combined
LogFormat "%h %l %u %t \"%r\" %>s %O \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %O" common
LogFormat "%{Referer}i -> %U" referer
LogFormat "%{User-agent}i" agent
IncludeOptional conf-enabled/*.conf
IncludeOptional sites-enabled/*.conf

Die meisten dieser Dinge sollten drin bleiben und können unverändert bleiben.

Also die erste Zeile ServerRoot "/etc/apache2" sagt uns nur, in welchem ​​Verzeichnis all unsere Konfigurationsdinge untergebracht werden. Es sollte niemals einen nachgestellten Schrägstrich haben.

Unser erstes Sicherheitsmerkmal ist das User und Group Deklarationen, die der Apache2-Binärdatei mitteilen, unter welchen Berechtigungen sie laufen soll. Dies ist wichtig, denn wenn der Server tut zufällig pwnt bekommen, dann bekommt der Angreifer keine höheren Privilegien als die hier aufgelisteten.

Warnung: Stellen Sie NIEMALS einen dieser beiden auf root oder Ihren eigenen persönlichen Kontobenutzer ein.

Ihre nächsten beiden wichtigen Sicherheitstypanweisungen sind ErrorLog und LogLevel. Ich würde empfehlen, diese gleich zu lassen, außer wenn Sie Probleme haben, können Sie die Protokollebene gerne auf irgendetwas von trace1 bis trace8 ändern, sowie debug, info, notice, warn, error, crit, alert, emerg. Dadurch erhalten Sie einige Debugging-Ausgaben. Achten Sie darauf, die Debugging-Ausgabe nicht in der Produktion eingeschaltet zu lassen, da dies wahrscheinlich zu Leistungsproblemen unter Last führen wird.

Deine nächsten drei wichtigen Dinge sind deine Single Include Dateien und Ihre IncludeOptional Verzeichnisse, jedes mit Dateien, die in die erste Ebene aufgenommen werden sollen. Diese werden später wichtig.

Jetzt das einzige Directory Direktive, die ich in meinen Prod-Servern hinterlasse, lautet:

<Directory />
  Options FollowSymLinks
  AllowOverride None
  Require all denied
</Directory>

Damit auf keinen Fall auf das Root-Verzeichnis unseres Servers zugegriffen werden kann. Wir weisen es zuerst an, jedem Simlink darunter zu folgen, und verbieten dann explizit das Lesen dieses Verzeichnisses durch irgendetwas auf der Client-Seite und lassen keine Möglichkeit der .htaccess-Überschreibung zu.

Wir verbieten dann auch das clientseitige Laden von Dateien, die mit .ht beginnen. Dies ist ein Verweis auf .htaccess und .htpasswdfalls diese irgendwo sind, die derzeit bedient werden, und im Fall von .htaccesses wird sein.

Sie haben auch Ihre LogFormat-Anweisungen, die dem Server mitteilen, wie er Ihre generieren soll error.log und access.log. Sofern nicht anders angegeben, erscheinen diese in /var/log/apache2/.

Jetzt einige sicherheitsorientierte Ergänzungen

Ich werde eine etwas redigierte Version von einem meiner eigenen teilen apache2.conf Dateien. Einige dieser Dinge müssen möglicherweise für Ihren beabsichtigten Anwendungsfall angepasst werden, bitte kopieren Sie sie nicht einfach und fügen Sie sie ein.

DefaultRuntimeDir ${APACHE_RUN_DIR}
PidFile ${APACHE_PID_FILE}
Timeout 300
KeepAlive On
MaxKeepAliveRequests 100
KeepAliveTimeout 5
User ${APACHE_RUN_USER}
Group ${APACHE_RUN_GROUP}
HostnameLookups Off
IncludeOptional mods-enabled/*.load
IncludeOptional mods-enabled/*.conf
IncludeOptional conf-enabled/*.conf
IncludeOptional sites-enabled/*.conf
Include ports.conf
SetEnv SERVER_ADMIN youremail@yoursite.com
SetEnv TZ America/New_York
DefaultLanguage en-US
LoadModule headers_module modules/mod_headers.so
Header always set X-XSS-Protection "1; mode=block"
Header always append X-Frame-Options deny
Header always set X-Content-Type-Options "nosniff"
Header always set Content-Security-Policy "default-src 'self' data: blob: cdn.jsdelivr.net;"
Header always set Content-Security-Policy "style-src 'self' *.google.com googleapis.com;"
Header always set Content-Security-Policy "script-src 'self' nonce-76dbe9426bd20a5ffbe536edc407958201af3a03 *.google.com;"
Header always set Content-Security-Policy "frame-src: 'self' feed.mikle.com;"
Header always set Permissions-Policy "geolocation=(),midi=(),sync-xhr=(),microphone=(),camera=(),magnetometer=(),gyroscope=(),fullscreen=(self),payment=()"
Header always set Referrer-Policy "no-referrer-when-downgrade"
Header edit Set-Cookie ^(.*)$ $1;HttpOnly;Secure;SameSite=None
SSLProtocol all -SSLv2 -SSLv3 -TLSv1 -TLSv1.1
ServerSignature Off
ServerTokens Prod
AccessFileName .htaccess
TraceEnable Off
ErrorLog ${APACHE_LOG_DIR}/error.log
LogLevel warn
LogFormat "%v:%p %h %l %u %t \"%r\" %>s %O \"%{Referer}i\" \"%{User-Agent}i\"" vhost_combined
LogFormat "%h %l %u %t \"%r\" %>s %O \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" detailed
LogFormat "%h %l %u %t \"%r\" %>s %O" common
LogFormat "%{Referer}i -> %U" referer
LogFormat "%{User-agent}i" agent
<Directory />
  Options +FollowSymLinks
  AllowOverride None
  Require all denied
</Directory>

<FilesMatch "^\.ht">
  Require all denied
</FilesMatch>

Notiz: Sie können die nächsten paar Dinge hinzufügen, über die ich spreche /etc/apache2/conf-enabled/security.confoder bewahren Sie sie alle an einem Ort auf, wenn Sie möchten!

Vieles davon ist also dasselbe mit einigen geringfügigen Änderungen, aber ich werde auf Dinge eingehen, die Sie hinzufügen sollten.

Erstens sollten Sie im Falle unerwarteter Fehler Ihre E-Mail-Adresse in die Serverkonfiguration aufnehmen, damit ein Benutzer Sie im Falle eines Dienstausfalls kontaktieren kann. Das machen wir mit der SetEnv SERVER_ADMIN Server-Umgebungsvariable.

Wir sollten auch die Inline-Header-Hinzufügung und -Änderung für die nächsten paar Zeilen aktivieren, wir werden dies tunLoadModule headers_module modules/mod_headers.so. Als Ergebnis können wir jetzt Dinge wie den serverseitigen XSS-Schutz einstellen mit:Header always set X-XSS-Protection "1; mode=block" und seine Companion-Optionen: Header always append X-Frame-Options deny undHeader always set X-Content-Type-Options "nosniff". Wir tun dies über Header, da einige davon unsere Clients, die Webbrowser, anweisen müssen, wie sie mit einigen der Daten interagieren sollen, die wir mit ihnen teilen.

Eine andere Sache, die wir mit Header-Hinzufügung erreichen können, ist die Verwendung unserer CSP oder Content Security Policy, die im Grunde über den Server anweist, was der Client-Browser von einer externen Quelle abrufen und auf der Seite verwenden kann und wo genau er es abrufen kann. Wir machen das mitHeader always set Content-Security-Policy. Wenn ich sage, dass ich extern gehostetes Javascript von js.google.com oder script.google.com ausführen wollte, könnten wir es so einstellen: Header always set Content-Security-Policy "script-src 'self' *.google.com;". Wie Sie sehen können, gibt es verschiedene Typen für Javascript, Iframes, CSS usw.

Wir können auch unseren Referrer-Policy-Header setzen, was wichtig ist, wenn andere unsichere Websites herausfinden, auf welcher Seite unsere Kunden zuletzt waren. Für meine Zwecke habe ich meine auf eingestellt no-referrer-when-downgrade, aber Sie können auch eine Reihe anderer festlegen, darunter: „no-referrer“, „no-referrer-when-downgrade“, „same-origin“, „origin“, „strict-origin“, „origin-when- Cross-Origin“, „Strict-Origin-When-Cross-Origin“ und „Unsafe-URL“. Jede hat ihr eigenes Tempo, und Sie können mehr über jede Richtlinie im Einzelnen lesen hier.

Unser Permissions-Policy Header sollte auch auf den meisten modernen Webservern gesetzt sein. Dies bestimmt, welche Rechte unser Server hat, um auf den Computer des Client-Browsers zuzugreifen, wie z. B. eine Kamera oder deren genauen Standort. Ihre Website und wofür Sie den Browser verwenden, wird Ihnen sagen, welche Berechtigungen Sie benötigen, also verschiebe ich mich hier auf ein nettes Berechtigungsrichtlinien-Generator Ich habe nützliche gefunden, die diese Zeichenfolge automatisch ohne Fehler für Sie generieren können. Ich schlage vor, nur nach dem zu fragen, was Sie wirklich brauchen, da die Frage nach zu vielen „ungenutzten“ Berechtigungen eine großartige Möglichkeit ist, einen Benutzer abzuwehren.

Eine coole Sache, die wir mit dem machen können Header edit Anweisung ist, Dinge wie ein Cookie inline zu bearbeiten, bevor es an den Benutzer gesendet wird, also sagen wir, wir wollen alle Cookies anstoßen Httponly;Secure; Wir würden den regulären Ausdruck verwenden: Header edit Set-Cookie ^(.*)$ $1;HttpOnly;Secure; als Sammelsurium.

Normalerweise entferne ich auch den Zugriff auf unsichere SSL-Protokolle, wenn ich mich mit meinem Server verbinde. Es gibt nichts Schlimmeres, als zu denken, dass Ihre Verbindung sicher ist, obwohl dies nicht der Fall ist. Sie können dies tun, indem Sie die SSLProtocol-Direktive verwenden und sie nach Ihren Wünschen einstellen. Ich habe meine eingestellt:SSLProtocol all -SSLv2 -SSLv3 -TLSv1 -TLSv1.1 für ein gutes Maß.

Es ist wichtig sicherzustellen, dass unser jetzt gesicherter Server keine internen Serverinformationen preisgibt, wenn ein Angreifer darauf herumstochert und Fehlercodes generiert. Jetzt, da unser Server festgezogen ist, sollten wir uns einrichten TraceEnable Off, ServerSignature Off und schlussendlich ServerTokens Prod. Jetzt sollten unsere Fehler gelesen und von einem Endbenutzer als Fehler angesehen werden können, aber keine wichtigen serverseitigen Informationen wie IP-Adressen und Serverversionen preisgeben. Als zukünftige Referenz sollte Trace auf einem mit dem Internet verbundenen Produktionsserver immer deaktiviert werden, da es sich um eine unsichere HTTP-Methode handelt.

Der Standort

Jetzt können wir hinübergehen /etc/apache2/sites-available und erstellen Sie Ihre Website. Ich gehe davon aus, dass Sie bereits SSL/HTTPS eingerichtet haben und für Ihre Website arbeiten, wo es mit LetsEncrypt oder etwas anderem ist. Ich gehe auch davon aus, dass Sie eine funktionierende Site mit mindestens einer Hauptseite und einem Unterverzeichnis mit etwas darin haben.

Ich zeige Ihnen eine einfache Konfiguration einer meiner Seiten, bei der einige sensiblere Dinge entfernt wurden.

Also rein /etc/apache2/sites-available Ich habe folgende Datei namens site.com-ssl.conf. Es sollte auch einen symbolischen Link geben, der auf diese Datei verweist/etc/apache2/sites-enabled damit die Daten von Apache2 geparst und dann bedient werden.

<IfModule mod_ssl.c>
<VirtualHost *:443>
Header always set Strict-Transport-Security "max-age=63072000; includeSubDomains"
  ServerAdmin marshall@site.com
  DocumentRoot /var/www/site.com
  ErrorLog ${APACHE_LOG_DIR}/error.log
  CustomLog ${APACHE_LOG_DIR}/access.log combined
  ServerName site.com
  ServerAlias site.com
  Include /etc/letsencrypt/options-ssl-apache.conf
  SSLCertificateFile /etc/letsencrypt/live/site.com/fullchain.pem
  SSLCertificateKeyFile /etc/letsencrypt/live/site.com/privkey.pem
</VirtualHost>
</IfModule>
<Directory "/var/www/site.com/">
  Options -Indexes +FollowSymLinks -ExecCGI
  AllowOverride all
  Require all granted
  Header always set Access-Control-Allow-Origin "*"
  RewriteEngine on
  ErrorDocument 403 
  ErrorDocument 404 
  RewriteCond %{REQUEST_METHOD} !^(GET|HEAD|POST|OPTIONS)$ [NC]
  RewriteRule .? - [F,NS,L]
  RewriteCond %{THE_REQUEST} !^[A-Z]{3,9}\ .+\ HTTP/(0\.9|1\.0|1\.1) [NC]
  RewriteRule .? - [F,NS,L]
</Directory>
<Location "/code/">
  AddType text/plain .txt .cpp .c .pl .sh .py
  Options +Indexes +FollowSymLinks -ExecCGI
  require all granted
  AllowOverride None
</Location>

Wie Sie sehen können, ein eher generisches Apache2-Setup mit ein paar Ergänzungen.

Sie benötigen eine DocumentRoot mindestens auf das niedrigste Verzeichnis zeigen, das Sie für diese Site bereitstellen möchten.

Unsere Verzeichnis-Tags verweisen auf einen Ort auf der Dateisystem die wir um die beiliegenden Richtlinien ergänzen möchten. Die Standort-Tags schließen einen Standort ein, der von dem Webserver bedient wird, dem wir die Anweisungen hinzufügen möchten. Dies ist eine wichtige Unterscheidung.

Wenn wir in diesem Verzeichnis kein CGI (wie Perl oder PHP) verwenden, stellen Sie sicher, dass Sie es hinzufügen -ExecCGI zur Optionsrichtlinie. Sie können auch hinzufügen oder weglassen Indexes, entweder mit Plus oder Minus, um ihm mitzuteilen, ob wir eine Verzeichnisliste in untergeordneten Verzeichnissen wünschen oder nicht. Ich lasse das hier weg.

Angenommen, wir haben unsere Header-Modifikationen aktiviert, können wir dies tun Header always set Access-Control-Allow-Origin "*" Für die Zugriffskontrolle können Sie, wenn Sie nichts anderes verwenden, dies nur für Ihre Site festlegen, um sie ein wenig zu straffen.

Wir möchten, dass unsere URL-Rewrite-Engine eingeschaltet ist, damit wir ihr mitteilen können, dass sie NUR sichere HTTP-Methoden zulassen sollRewriteCond %{REQUEST_METHOD} !^(GET|HEAD|POST|OPTIONS)$ [NC] und dann RewriteRule .? - [F,NS,L]und wir möchten, dass nur gültige HTTP-Anforderungen durchkommen, daher die nächste Anweisung RewriteCond %{THE_REQUEST} !^[A-Z]{3,9}\ .+\ HTTP/(0\.9|1\.0|1\.1) [NC] und RewriteRule .? - [F,NS,L].

Zum Abschluss können wir optional einen HTTP-Server sowie unseren HTTPS-Server ausführen und einfach das HTTP verwenden, um mit einer Umschreibung auf HTTPS umzusteigen. Wenn Sie dies also tun möchten, erstellen Sie eine Datei namens site.com.conf das sieht in etwa so aus:

<VirtualHost *:80>
  ServerAdmin marshall@site.org
  ErrorLog ${APACHE_LOG_DIR}/error.log
  CustomLog ${APACHE_LOG_DIR}/access.log combined
  RewriteEngine on
  RewriteCond %{SERVER_NAME} =site.com
  RewriteRule ^  [END,NE,R=permanent]
</VirtualHost>

Fazit

Jetzt musst du nur noch laufen systemctl restart apache2 um den Server mit Ihren neuen Einstellungen neu zu starten. Jetzt, da wir es verschärft haben, haben Sie vielleicht etwas mehr Sicherheit gegen Hacker. Stellen Sie jedoch immer sicher, dass Sie Ihre Protokolle auf verdächtigen Code überprüfen.

Fühlen Sie sich frei, mir mit Kommentaren und Vorschlägen eine E-Mail zu senden!

Viel Spaß beim Servieren!

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *