Files
ArchiTools/nginx/tile-cache.conf
T
AI Assistant 9bab9db4df feat(geoportal): N8N webhook on sync completion + tile cache monitoring
- weekend-deep-sync.ts: fire webhook to N8N_WEBHOOK_URL after each sync cycle
  (N8N triggers tippecanoe PMTiles rebuild via SSH on host)
- nginx tile-cache: add stub_status at /status, custom log format with cache status
- Add tile-cache-stats.sh: shows HIT/MISS ratio, cache size, slow tiles
- docker-compose: add N8N_WEBHOOK_URL env var

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-03-28 09:44:38 +02:00

86 lines
2.7 KiB
Plaintext

# nginx tile cache for Martin vector tile server
# Proxy-cache layer: 10-100x faster on repeat requests, zero PostGIS load for cached tiles
proxy_cache_path /var/cache/nginx/tiles
levels=1:2
keys_zone=tiles:64m
max_size=2g
inactive=7d
use_temp_path=off;
# Log format with cache status for monitoring (docker logs tile-cache | grep HIT/MISS)
log_format tiles '$remote_addr [$time_local] "$request" $status '
'cache=$upstream_cache_status size=$body_bytes_sent '
'time=$request_time';
server {
access_log /var/log/nginx/access.log tiles;
listen 80;
server_name _;
# Health check
location = /health {
access_log off;
return 200 "ok\n";
add_header Content-Type text/plain;
}
# nginx status (active connections, request counts) — for monitoring
location = /status {
access_log off;
stub_status on;
}
# Martin catalog endpoint (no cache)
location = /catalog {
proxy_pass http://martin:3000/catalog;
proxy_set_header Host $host;
}
# Tile requests — cache aggressively
location / {
proxy_pass http://martin:3000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
# Cache config — tiles change only on sync (weekly), long TTL is safe
proxy_cache tiles;
proxy_cache_key "$request_uri";
proxy_cache_valid 200 7d;
proxy_cache_valid 204 1h;
proxy_cache_valid 404 1m;
proxy_cache_use_stale error timeout updating http_500 http_502 http_503 http_504;
proxy_cache_lock on;
proxy_cache_lock_timeout 5s;
# Browser caching — tiles are immutable between syncs
add_header Cache-Control "public, max-age=86400, stale-while-revalidate=604800" always;
# Pass cache status header (useful for debugging)
add_header X-Cache-Status $upstream_cache_status always;
# CORS headers for tile requests
add_header Access-Control-Allow-Origin "*" always;
add_header Access-Control-Allow-Methods "GET, HEAD, OPTIONS" always;
add_header Access-Control-Allow-Headers "Range, If-None-Match, Accept-Encoding" always;
add_header Access-Control-Expose-Headers "Content-Range, Content-Length, ETag, X-Cache-Status" always;
# Handle preflight
if ($request_method = OPTIONS) {
add_header Access-Control-Allow-Origin "*";
add_header Access-Control-Allow-Methods "GET, HEAD, OPTIONS";
add_header Access-Control-Max-Age 86400;
add_header Content-Length 0;
return 204;
}
# Let Martin gzip natively — pass compressed response through to client and cache
gzip off;
# Timeouts (Martin can be slow on low-zoom tiles)
proxy_connect_timeout 10s;
proxy_read_timeout 120s;
proxy_send_timeout 30s;
}
}