From 5fc00a3285f4184a59085295d147d6b0865d2abc Mon Sep 17 00:00:00 2001 From: Ivan Gabaldon Date: Fri, 14 Feb 2025 10:27:41 +0100 Subject: [PATCH] Rework Caddyfile (#255) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * rework Caddyfile * fix missing "public" directive * features cleanup Since this header is attached to each outgoing request the overall size is slightly increased by 300 bytes, we don't care if the site is allowed to play media in the background, so with the vast majority of features that have been added (and those that were already present) * restore encode directive Caddyserver actually did passthrough the precompressed resources served by uWSGI (Oops) * merge upstream changes * fix typo --------- Co-authored-by: Émilien (perso) <4016501+unixfox@users.noreply.github.com> --- Caddyfile | 176 +++++++++++++++++++++----------------------- docker-compose.yaml | 3 +- 2 files changed, 85 insertions(+), 94 deletions(-) diff --git a/Caddyfile b/Caddyfile index dea6806..e200946 100644 --- a/Caddyfile +++ b/Caddyfile @@ -1,99 +1,91 @@ { - admin off + admin off + + log { + output stderr + format filter { + # Preserves first 8 bits from IPv4 and 32 bits from IPv6 + request>remote_ip ip_mask 8 32 + request>client_ip ip_mask 8 32 + + # Remove identificable information + request>remote_port delete + request>headers delete + request>uri query { + delete url + delete h + delete q + } + } + } } -{$SEARXNG_HOSTNAME} { - log { - output discard - } +{$SEARXNG_HOSTNAME:http://localhost} - tls {$SEARXNG_TLS} +tls {$SEARXNG_TLS:internal} - @api { - path /config - path /healthz - path /stats/errors - path /stats/checker - } - - @static { - path /static/* - } - - @notstatic { - not path /static/* - } - - @imageproxy { - path /image_proxy - } - - @notimageproxy { - not path /image_proxy - } - - header { - # Enable HTTP Strict Transport Security (HSTS) to force clients to always connect via HTTPS - Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" - - # Enable cross-site filter (XSS) and tell browser to block detected attacks - X-XSS-Protection "1; mode=block" - - # Prevent some browsers from MIME-sniffing a response away from the declared Content-Type - X-Content-Type-Options "nosniff" - - # Disable some features - Permissions-Policy "accelerometer=(),ambient-light-sensor=(),autoplay=(),camera=(),encrypted-media=(),focus-without-user-activation=(),geolocation=(),gyroscope=(),magnetometer=(),microphone=(),midi=(),payment=(),picture-in-picture=(),speaker=(),sync-xhr=(),usb=(),vr=()" - - # Disable some features (legacy) - Feature-Policy "accelerometer 'none';ambient-light-sensor 'none'; autoplay 'none';camera 'none';encrypted-media 'none';focus-without-user-activation 'none'; geolocation 'none';gyroscope 'none';magnetometer 'none';microphone 'none';midi 'none';payment 'none';picture-in-picture 'none'; speaker 'none';sync-xhr 'none';usb 'none';vr 'none'" - - # Referer - Referrer-Policy "no-referrer" - - # X-Robots-Tag - X-Robots-Tag "noindex, noarchive, nofollow" - - # Remove Server header - -Server - } - - header @api { - Access-Control-Allow-Methods "GET, OPTIONS" - Access-Control-Allow-Origin "*" - } - - # Cache - header @static { - # Cache - Cache-Control "public, max-age=31536000" - defer - } - - header @notstatic { - # No Cache - Cache-Control "no-cache, no-store" - Pragma "no-cache" - } - - # CSP (see http://content-security-policy.com/ ) - header @imageproxy { - Content-Security-Policy "default-src 'none'; img-src 'self' data:" - } - - header @notimageproxy { - Content-Security-Policy "upgrade-insecure-requests; default-src 'none'; script-src 'self'; style-src 'self' 'unsafe-inline'; form-action 'self' https://github.com/searxng/searxng/issues/new; font-src 'self'; frame-ancestors 'self'; base-uri 'self'; connect-src 'self' https://overpass-api.de; img-src 'self' data: https://*.tile.openstreetmap.org; frame-src https://www.youtube-nocookie.com https://player.vimeo.com https://www.dailymotion.com https://www.deezer.com https://www.mixcloud.com https://w.soundcloud.com https://embed.spotify.com" - } - - # SearXNG - handle { - encode zstd gzip - - reverse_proxy localhost:8080 { - header_up X-Forwarded-Port {http.request.port} - header_up X-Forwarded-Proto {http.request.scheme} - header_up X-Real-IP {remote_host} - } - } +encode zstd gzip +@api { + path /config + path /healthz + path /stats/errors + path /stats/checker +} + +@search { + path /search +} + +@imageproxy { + path /image_proxy +} + +@static { + path /static/* +} + +header { + # CSP (https://content-security-policy.com) + Content-Security-Policy "upgrade-insecure-requests; default-src 'none'; script-src 'self'; style-src 'self' 'unsafe-inline'; form-action 'self' https://github.com/searxng/searxng/issues/new; font-src 'self'; frame-ancestors 'self'; base-uri 'self'; connect-src 'self' https://overpass-api.de; img-src * data:; frame-src https://www.youtube-nocookie.com https://player.vimeo.com https://www.dailymotion.com https://www.deezer.com https://www.mixcloud.com https://w.soundcloud.com https://embed.spotify.com;" + + # Disable some browser features + Permissions-Policy "accelerometer=(),camera=(),geolocation=(),gyroscope=(),magnetometer=(),microphone=(),payment=(),usb=()" + + # Set referrer policy + Referrer-Policy "no-referrer" + + # Force clients to use HTTPS + Strict-Transport-Security "max-age=31536000" + + # Prevent MIME type sniffing from the declared Content-Type + X-Content-Type-Options "nosniff" + + # X-Robots-Tag (comment to allow site indexing) + X-Robots-Tag "noindex, noarchive, nofollow" + + # Remove "Server" header + -Server +} + +header @api { + Access-Control-Allow-Methods "GET, OPTIONS" + Access-Control-Allow-Origin "*" +} + +route { + # Cache policy + header Cache-Control "max-age=0, no-store" + header @search Cache-Control "max-age=5, private" + header @imageproxy Cache-Control "max-age=604800, public" + header @static Cache-Control "max-age=31536000, public, immutable" +} + +# SearXNG (uWSGI) +reverse_proxy localhost:8080 { + header_up X-Forwarded-Port {http.request.port} + header_up X-Real-IP {http.request.remote.host} + + # https://github.com/searx/searx-docker/issues/24 + header_up Connection "close" } diff --git a/docker-compose.yaml b/docker-compose.yaml index b42926a..0ee2a4e 100644 --- a/docker-compose.yaml +++ b/docker-compose.yaml @@ -11,8 +11,7 @@ services: - caddy-data:/data:rw - caddy-config:/config:rw environment: - - SEARXNG_HOSTNAME=${SEARXNG_HOSTNAME:-http://localhost:80} - - SEARXNG_TLS=${LETSENCRYPT_EMAIL:-internal} + - SEARXNG_TLS=${LETSENCRYPT_EMAIL} cap_drop: - ALL cap_add: