# Open SWE dashboard frontend (TanStack Start SPA) + scoped API proxy. # TEMPLATE: tokens (@@...@@) are rendered at first boot by user-data.sh. # # nginx is the SOLE ingress and security boundary (T5 OSWE-IAC-03): the backend # binds 127.0.0.1:2024 and is NOT network-reachable. nginx proxies exactly two # prefixes to it — /dashboard/api/* and /webhooks/* — and nothing else. The # unauthenticated LangGraph agent API (/threads, /runs, /assistants, /store) is # NEVER proxied; those paths return the SPA shell. # # Both ALB target groups (dashboard host + hooks host) point at this nginx :80, # not at :2024 directly, so there is no path to the raw control plane even from # inside the SG. Webhook signature verification still happens in the app (the raw # body + GitHub/Slack/Linear signature headers are passed through unmodified). server { listen 80 default_server; listen [::]:80 default_server; server_name @@SERVER_NAME@@; root @@WWW_ROOT@@; index _shell.html; # ALB target-group health check (dashboard TG). location = /healthz { default_type text/plain; return 200 "ok\n"; } # Dashboard API + OAuth callback -> backend webapp. location /dashboard/api/ { proxy_pass http://@@BACKEND_ADDR@@; proxy_http_version 1.1; 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 https; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_read_timeout 300s; } # Inbound webhooks (GitHub/Slack/Linear) -> backend webapp. Routed through # nginx so :2024 stays loopback-only (T5 OSWE-IAC-03). The raw request body + # signature headers pass through unmodified for in-app signature verification. location /webhooks/ { proxy_pass http://@@BACKEND_ADDR@@; proxy_http_version 1.1; 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 https; proxy_request_buffering off; proxy_read_timeout 300s; } # Static assets + SPA shell fallback (client-side routing). location / { try_files $uri $uri/ /_shell.html; } }