← back to Watches

infrastructure/nginx-omega-watches.conf

216 lines

# ============================================================================
# OMEGA WATCHES - NGINX CONFIGURATION
# Production-grade reverse proxy with load balancing and SSL
# ============================================================================

# Upstream configuration for load balancing
upstream omega_watches_backend {
    least_conn;  # Use least connections load balancing

    # Primary instance
    server 127.0.0.1:7500 weight=3 max_fails=3 fail_timeout=30s;

    # Backup instances (uncomment when scaling)
    # server 127.0.0.1:7501 weight=2 max_fails=3 fail_timeout=30s;
    # server 127.0.0.1:7502 weight=2 max_fails=3 fail_timeout=30s;

    # Health check
    keepalive 32;
}

# Rate limiting zones
limit_req_zone $binary_remote_addr zone=general:10m rate=10r/s;
limit_req_zone $binary_remote_addr zone=api:10m rate=30r/s;
limit_conn_zone $binary_remote_addr zone=conn_limit:10m;

# Cache configuration
proxy_cache_path /var/cache/nginx/omega-watches
    levels=1:2
    keys_zone=omega_cache:10m
    max_size=1g
    inactive=60m
    use_temp_path=off;

# ============================================================================
# HTTP Server - Redirect to HTTPS (uncomment when SSL is configured)
# ============================================================================
# server {
#     listen 80;
#     server_name omega-watches.example.com;
#     return 301 https://$server_name$request_uri;
# }

# ============================================================================
# MAIN SERVER BLOCK
# ============================================================================
server {
    listen 80;
    listen [::]:80;

    # Enable when SSL is configured
    # listen 443 ssl http2;
    # listen [::]:443 ssl http2;

    server_name omega-watches.local 45.61.58.125;

    # SSL Configuration (uncomment when certificates are ready)
    # ssl_certificate /etc/ssl/certs/omega-watches.crt;
    # ssl_certificate_key /etc/ssl/private/omega-watches.key;
    # ssl_protocols TLSv1.2 TLSv1.3;
    # ssl_ciphers HIGH:!aNULL:!MD5;
    # ssl_prefer_server_ciphers on;
    # ssl_session_cache shared:SSL:10m;
    # ssl_session_timeout 10m;

    # Security headers
    add_header X-Frame-Options "SAMEORIGIN" always;
    add_header X-Content-Type-Options "nosniff" always;
    add_header X-XSS-Protection "1; mode=block" always;
    add_header Referrer-Policy "no-referrer-when-downgrade" always;

    # Logging
    access_log /var/log/nginx/omega-watches-access.log combined;
    error_log /var/log/nginx/omega-watches-error.log warn;

    # Gzip compression
    gzip on;
    gzip_vary on;
    gzip_min_length 1024;
    gzip_types text/plain text/css text/xml text/javascript
               application/x-javascript application/xml+rss
               application/json application/javascript;

    # Client body size limit
    client_max_body_size 10M;

    # Rate limiting
    limit_req zone=general burst=20 nodelay;
    limit_conn conn_limit 10;

    # Root location
    location / {
        proxy_pass http://omega_watches_backend;

        # Proxy headers
        proxy_set_header Host $host;
        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;

        # Timeouts
        proxy_connect_timeout 60s;
        proxy_send_timeout 60s;
        proxy_read_timeout 60s;

        # Buffering
        proxy_buffering on;
        proxy_buffer_size 4k;
        proxy_buffers 8 4k;

        # WebSocket support
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
    }

    # API endpoints with higher rate limit
    location /api/ {
        limit_req zone=api burst=50 nodelay;

        proxy_pass http://omega_watches_backend;
        proxy_set_header Host $host;
        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;

        # Cache API responses
        proxy_cache omega_cache;
        proxy_cache_valid 200 5m;
        proxy_cache_valid 404 1m;
        proxy_cache_key "$scheme$request_method$host$request_uri";
        add_header X-Cache-Status $upstream_cache_status;
    }

    # Static files with aggressive caching
    location ~* \.(jpg|jpeg|png|gif|ico|css|js|svg|woff|woff2|ttf|eot)$ {
        proxy_pass http://omega_watches_backend;
        proxy_cache omega_cache;
        proxy_cache_valid 200 7d;
        expires 7d;
        add_header Cache-Control "public, immutable";
        add_header X-Cache-Status $upstream_cache_status;
    }

    # Health check endpoint (no caching, no rate limiting)
    location /api/health {
        limit_req off;
        limit_conn off;

        proxy_pass http://omega_watches_backend;
        proxy_set_header Host $host;
        access_log off;
    }

    # Nginx status for monitoring
    location /nginx-status {
        stub_status on;
        access_log off;
        allow 127.0.0.1;
        deny all;
    }

    # Deny access to sensitive files
    location ~ /\. {
        deny all;
        access_log off;
        log_not_found off;
    }

    # Robots.txt
    location = /robots.txt {
        proxy_pass http://omega_watches_backend;
        access_log off;
    }

    # Sitemap
    location = /sitemap.xml {
        proxy_pass http://omega_watches_backend;
        proxy_cache omega_cache;
        proxy_cache_valid 200 1d;
    }
}

# ============================================================================
# MONITORING DASHBOARD (Grafana)
# ============================================================================
server {
    listen 80;
    server_name grafana.omega-watches.local;

    location / {
        proxy_pass http://127.0.0.1:7511;
        proxy_set_header Host $host;
        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;
    }
}

# ============================================================================
# PROMETHEUS METRICS
# ============================================================================
server {
    listen 80;
    server_name prometheus.omega-watches.local;

    # Basic auth for security
    # auth_basic "Prometheus Metrics";
    # auth_basic_user_file /etc/nginx/.htpasswd;

    location / {
        proxy_pass http://127.0.0.1:7510;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}