From a31399f32f2f7a63aa9261f6679e551553e3ddb3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Artur=20Ku=C5=9B?= Date: Mon, 18 Aug 2025 16:57:04 +0200 Subject: [PATCH] Prepare to cache in nginx --- deploy-this/deploy-dc.yml | 63 +++++++++++-------- nginx-config/https-cache/nginx-cache.conf | 15 +++++ .../conf.d/caching.conf | 8 +++ .../conf.d/rate-limiting.conf | 1 + .../sites-available/http-for-letsencrypt.conf | 13 ++++ .../https-angular-arti24-eu.conf | 19 ++++++ .../sites-available/https-api-arti24-eu.conf | 19 ++++++ .../sites-available/https-arti24.eu.conf | 30 +++++++++ .../sites-available/https-artiks.tk.conf | 30 +++++++++ .../sites-available/https-bodypainter.eu.conf | 30 +++++++++ .../https-subdomains-themself-eu.conf | 47 ++++++++++++++ .../sites-available/https-themself.eu.conf | 30 +++++++++ .../snippets/image-cache.conf | 10 +++ .../snippets/proxy-headers.conf | 6 ++ .../snippets/proxy-optimization.conf | 9 +++ .../snippets/security-headers.conf | 6 ++ .../snippets/ssl-params.conf | 10 +++ .../snippets/static-cache.conf | 10 +++ 18 files changed, 330 insertions(+), 26 deletions(-) create mode 100644 nginx-config/https-cache/nginx-cache.conf create mode 100644 nginx-config/https-prepare-to-cache/conf.d/caching.conf create mode 100644 nginx-config/https-prepare-to-cache/conf.d/rate-limiting.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/http-for-letsencrypt.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-angular-arti24-eu.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-api-arti24-eu.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-arti24.eu.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-artiks.tk.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-bodypainter.eu.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-subdomains-themself-eu.conf create mode 100644 nginx-config/https-prepare-to-cache/sites-available/https-themself.eu.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/image-cache.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/proxy-headers.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/proxy-optimization.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/security-headers.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/ssl-params.conf create mode 100644 nginx-config/https-prepare-to-cache/snippets/static-cache.conf diff --git a/deploy-this/deploy-dc.yml b/deploy-this/deploy-dc.yml index 4af919b..6bd0d74 100755 --- a/deploy-this/deploy-dc.yml +++ b/deploy-this/deploy-dc.yml @@ -1,37 +1,48 @@ services: - proxy-nginx: - image: nginx-with-tools container_name: proxy-nginx - restart: always - - + restart: unless-stopped networks: - - proxy-net + - proxy-net environment: - TZ: Europe/Warsaw - - ports: - - 80:80 - - 443:443 - - volumes: - # Nginx configuration - - apps-data:/etc/nginx/conf.d + TZ: Europe/Warsaw + NGINX_ENVSUBST_TEMPLATE_DIR: /etc/nginx/templates + NGINX_ENVSUBST_OUTPUT_DIR: /etc/nginx/conf.d - - # Lets encrypt for https - - ${DOCKER_DATA}/letsencrypt:/letsencrypt:rw - - ${DOCKER_DATA}/letsencrypt-tmp:/var/www/certbot/:rw + ports: + - "80:80" + - "443:443" + + volumes: + # Konfiguracja Nginx + - apps-data:/etc/nginx/conf.d:ro + # Cache + - type: tmpfs + target: /var/cache/nginx + tmpfs: + size: 2147483648 # 2GB w bajtach + + # Certyfikaty SSL + - ${DOCKER_DATA}/letsencrypt:/etc/letsencrypt:ro + - ${DOCKER_DATA}/letsencrypt-tmp:/var/www/certbot:rw + + # Logi + - ${DOCKER_DATA}/nginx-logs:/var/log/nginx:rw + + healthcheck: + test: ["CMD", "nginx", "-t"] + interval: 30s + timeout: 10s + retries: 3 + volumes: - apps-data: - external: true - + apps-data: + external: true + networks: - proxy-net: - name: proxy-net - external: false -# docker compose --profile base --profile base-dv --profile production --file 3.jenkins-with-docker-compose.yml --env-file artik-docker.env up --detach + proxy-net: + name: proxy-net + driver: bridge \ No newline at end of file diff --git a/nginx-config/https-cache/nginx-cache.conf b/nginx-config/https-cache/nginx-cache.conf new file mode 100644 index 0000000..8a82466 --- /dev/null +++ b/nginx-config/https-cache/nginx-cache.conf @@ -0,0 +1,15 @@ +http { + proxy_cache_path /var/cache/nginx/static levels=1:2 keys_zone=STATIC:50m max_size=500m; + proxy_cache_path /var/cache/nginx/media levels=1:2 keys_zone=MEDIA:100m max_size=2g; + + server { + location ~* \.(jpg|jpeg|png|gif|ico|css|js)$ { + proxy_cache STATIC; + proxy_cache_valid 200 1d; + proxy_cache_use_stale error timeout updating; + add_header X-Cache-Status $upstream_cache_status; + expires 30d; + access_log off; + } + } +} \ No newline at end of file diff --git a/nginx-config/https-prepare-to-cache/conf.d/caching.conf b/nginx-config/https-prepare-to-cache/conf.d/caching.conf new file mode 100644 index 0000000..6e66f09 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/conf.d/caching.conf @@ -0,0 +1,8 @@ +proxy_cache_path /var/cache/nginx levels=1:2 keys_zone=static_cache:100m inactive=7d use_temp_path=off; +proxy_cache_path /var/cache/nginx/img levels=1:2 keys_zone=img_cache:200m inactive=30d use_temp_path=off; +map $request_uri $cache_type { + default "none"; + ~*\.(jpg|jpeg|png|gif|ico|webp)$ "img"; + ~*\.(css|js|woff2?|ttf|eot|svg)$ "static"; +} +add_header X-Cache-Status $upstream_cache_status; diff --git a/nginx-config/https-prepare-to-cache/conf.d/rate-limiting.conf b/nginx-config/https-prepare-to-cache/conf.d/rate-limiting.conf new file mode 100644 index 0000000..e6481ea --- /dev/null +++ b/nginx-config/https-prepare-to-cache/conf.d/rate-limiting.conf @@ -0,0 +1 @@ +limit_req_zone $binary_remote_addr zone=ip_limit:10m rate=2r/s; diff --git a/nginx-config/https-prepare-to-cache/sites-available/http-for-letsencrypt.conf b/nginx-config/https-prepare-to-cache/sites-available/http-for-letsencrypt.conf new file mode 100644 index 0000000..2039bc8 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/http-for-letsencrypt.conf @@ -0,0 +1,13 @@ +server { + listen 80 default_server; + server_name _; + server_tokens off; + + location /.well-known/acme-challenge/ { + root /var/www/certbot; + } + + location / { + return 301 https://$host$request_uri; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-angular-arti24-eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-angular-arti24-eu.conf new file mode 100644 index 0000000..f355bd2 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-angular-arti24-eu.conf @@ -0,0 +1,19 @@ +server { + listen 443 ssl http2; + server_name angular.arti24.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://arti24-container:3003; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } + + # Angular SPA fallback + location ~ ^/(?!.*\.(js|css|png|jpg|jpeg|gif|ico|svg|woff2|ttf|eot)) { + try_files \$uri \$uri/ /index.html; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-api-arti24-eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-api-arti24-eu.conf new file mode 100644 index 0000000..530a1eb --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-api-arti24-eu.conf @@ -0,0 +1,19 @@ +server { + listen 443 ssl http2; + server_name api.arti24.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=10 nodelay; + proxy_pass http://angular-services:8800; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + + # Specjalne nagłówki dla API + add_header 'Access-Control-Allow-Origin' '*' always; + add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS' always; + add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range' always; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-arti24.eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-arti24.eu.conf new file mode 100644 index 0000000..a4ceb49 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-arti24.eu.conf @@ -0,0 +1,30 @@ +server { + listen 443 ssl http2; + server_name www.arti24.eu; + server_tokens off; + include snippets/ssl-params.conf; + return 301 https://arti24.eu$request_uri; +} + +server { + listen 443 ssl http2; + server_name arti24.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://arti24-eu-container:${PORT:-3000}; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } + + location ~* \.(?:jpg|jpeg|png|gif|ico|css|js|svg|webp|woff2)$ { + include snippets/static-cache.conf; + } + + location ~ ^/(images|gallery|photos)/ { + include snippets/image-cache.conf; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-artiks.tk.conf b/nginx-config/https-prepare-to-cache/sites-available/https-artiks.tk.conf new file mode 100644 index 0000000..bd733a1 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-artiks.tk.conf @@ -0,0 +1,30 @@ +server { + listen 443 ssl http2; + server_name www.artiks.tk; + server_tokens off; + include snippets/ssl-params.conf; + return 301 https://artiks.tk$request_uri; +} + +server { + listen 443 ssl http2; + server_name artiks.tk; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://artiks-tk-container:${PORT:-3000}; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } + + location ~* \.(?:jpg|jpeg|png|gif|ico|css|js|svg|webp|woff2)$ { + include snippets/static-cache.conf; + } + + location ~ ^/(images|gallery|photos)/ { + include snippets/image-cache.conf; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-bodypainter.eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-bodypainter.eu.conf new file mode 100644 index 0000000..5c6ab1f --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-bodypainter.eu.conf @@ -0,0 +1,30 @@ +server { + listen 443 ssl http2; + server_name www.bodypainter.eu; + server_tokens off; + include snippets/ssl-params.conf; + return 301 https://bodypainter.eu$request_uri; +} + +server { + listen 443 ssl http2; + server_name bodypainter.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://bodypainter-eu-container:${PORT:-3000}; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } + + location ~* \.(?:jpg|jpeg|png|gif|ico|css|js|svg|webp|woff2)$ { + include snippets/static-cache.conf; + } + + location ~ ^/(images|gallery|photos)/ { + include snippets/image-cache.conf; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-subdomains-themself-eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-subdomains-themself-eu.conf new file mode 100644 index 0000000..600cde1 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-subdomains-themself-eu.conf @@ -0,0 +1,47 @@ +# Massage subdomain +server { + listen 443 ssl http2; + server_name massage.themself.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://arti24-container:3334; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } +} + +# Kopama subdomain +server { + listen 443 ssl http2; + server_name kopama.themself.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://arti24-container:3335; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } +} + +# Driving subdomain +server { + listen 443 ssl http2; + server_name driving.themself.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://arti24-container:3336; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } +} diff --git a/nginx-config/https-prepare-to-cache/sites-available/https-themself.eu.conf b/nginx-config/https-prepare-to-cache/sites-available/https-themself.eu.conf new file mode 100644 index 0000000..370d533 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/sites-available/https-themself.eu.conf @@ -0,0 +1,30 @@ +server { + listen 443 ssl http2; + server_name www.themself.eu; + server_tokens off; + include snippets/ssl-params.conf; + return 301 https://themself.eu$request_uri; +} + +server { + listen 443 ssl http2; + server_name themself.eu; + server_tokens off; + include snippets/ssl-params.conf; + include snippets/security-headers.conf; + + location / { + limit_req zone=ip_limit burst=20 nodelay; + proxy_pass http://themself-eu-container:${PORT:-3000}; + include snippets/proxy-headers.conf; + include snippets/proxy-optimization.conf; + } + + location ~* \.(?:jpg|jpeg|png|gif|ico|css|js|svg|webp|woff2)$ { + include snippets/static-cache.conf; + } + + location ~ ^/(images|gallery|photos)/ { + include snippets/image-cache.conf; + } +} diff --git a/nginx-config/https-prepare-to-cache/snippets/image-cache.conf b/nginx-config/https-prepare-to-cache/snippets/image-cache.conf new file mode 100644 index 0000000..8eb865f --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/image-cache.conf @@ -0,0 +1,10 @@ +proxy_cache img_cache; +proxy_cache_key "$scheme://$host$request_uri$is_args$args"; +proxy_cache_valid 200 301 302 30d; +proxy_cache_valid 404 1h; +proxy_cache_use_stale error timeout updating; +proxy_cache_lock on; +proxy_cache_background_update on; +expires max; +access_log off; +add_header Cache-Control "public, immutable"; diff --git a/nginx-config/https-prepare-to-cache/snippets/proxy-headers.conf b/nginx-config/https-prepare-to-cache/snippets/proxy-headers.conf new file mode 100644 index 0000000..02efb86 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/proxy-headers.conf @@ -0,0 +1,6 @@ +proxy_set_header X-Real-IP $remote_addr; +proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; +proxy_set_header X-Forwarded-Proto $scheme; +proxy_set_header Host $host; +proxy_set_header X-Forwarded-Host $host; +proxy_set_header X-Forwarded-Port $server_port; diff --git a/nginx-config/https-prepare-to-cache/snippets/proxy-optimization.conf b/nginx-config/https-prepare-to-cache/snippets/proxy-optimization.conf new file mode 100644 index 0000000..4aa35e9 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/proxy-optimization.conf @@ -0,0 +1,9 @@ +proxy_http_version 1.1; +proxy_set_header Connection ""; +proxy_cache_bypass $http_upgrade; +proxy_read_timeout 300s; +proxy_connect_timeout 75s; +proxy_buffering on; +proxy_buffer_size 4k; +proxy_buffers 8 16k; +proxy_busy_buffers_size 32k; diff --git a/nginx-config/https-prepare-to-cache/snippets/security-headers.conf b/nginx-config/https-prepare-to-cache/snippets/security-headers.conf new file mode 100644 index 0000000..07ba95a --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/security-headers.conf @@ -0,0 +1,6 @@ +add_header X-Frame-Options "SAMEORIGIN" always; +add_header X-Content-Type-Options "nosniff" always; +add_header Referrer-Policy "strict-origin-when-cross-origin" always; +add_header Strict-Transport-Security "max-age=63072000; includeSubDomains; preload" always; +add_header Permissions-Policy "geolocation=(), midi=(), camera=(), microphone=(), fullscreen=(self)" always; +add_header Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' https:; style-src 'self' 'unsafe-inline' https:; img-src 'self' data: https:; font-src 'self' https:; connect-src 'self' https:; frame-src 'self' https:; object-src 'none';" always; diff --git a/nginx-config/https-prepare-to-cache/snippets/ssl-params.conf b/nginx-config/https-prepare-to-cache/snippets/ssl-params.conf new file mode 100644 index 0000000..b8c1174 --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/ssl-params.conf @@ -0,0 +1,10 @@ +ssl_certificate /letsencrypt/live/$ssl_server_name/fullchain.pem; +ssl_certificate_key /letsencrypt/live/$ssl_server_name/privkey.pem; +ssl_protocols TLSv1.2 TLSv1.3; +ssl_ciphers 'ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384'; +ssl_prefer_server_ciphers on; +ssl_session_cache shared:SSL:10m; +ssl_session_timeout 1d; +ssl_session_tickets off; +ssl_dhparam /etc/nginx/dhparam.pem; +ssl_buffer_size 4k; diff --git a/nginx-config/https-prepare-to-cache/snippets/static-cache.conf b/nginx-config/https-prepare-to-cache/snippets/static-cache.conf new file mode 100644 index 0000000..b6778aa --- /dev/null +++ b/nginx-config/https-prepare-to-cache/snippets/static-cache.conf @@ -0,0 +1,10 @@ +proxy_cache static_cache; +proxy_cache_key "$scheme://$host$request_uri"; +proxy_cache_valid 200 301 302 7d; +proxy_cache_valid 404 1m; +proxy_cache_use_stale error timeout updating; +proxy_cache_lock on; +proxy_cache_revalidate on; +expires 1y; +access_log off; +add_header Cache-Control "public, immutable";