From 6f6a854337a7d28fc244d5c1aab97f52ded569b4 Mon Sep 17 00:00:00 2001 From: Ilia Denisov Date: Fri, 8 May 2026 11:04:00 +0200 Subject: [PATCH] local-dev: Vite proxy for same-origin requests + upstream gateway Dockerfile fix MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit vite.config.ts now proxies `/api` and `/galaxy.gateway.v1.EdgeGateway` to the gateway, so the browser sees only `localhost:5173` and never trips a cross-origin preflight. `.env.development` accordingly points `VITE_GATEWAY_BASE_URL` at the Vite origin. The proxy target is overridable via `VITE_DEV_PROXY_TARGET=...` for non-default gateways without touching the compose file. `gateway/Dockerfile` previously failed to build because gateway imports `galaxy/core` (replaced to `../ui/core` in `gateway/go.mod`) but the Dockerfile did not copy `ui/core/` into the build context nor declare the replace in the synthesised `go.work`. Adding both makes `docker build -f gateway/Dockerfile .` succeed; this is the same fix already shipped in `tools/local-dev/gateway.Dockerfile`, back-ported to upstream. Verified: - docker build -f gateway/Dockerfile . — builds cleanly - pnpm test 14/14, pnpm exec playwright test 44/44 (with CI=1 to force a fresh dev server; reuse keeps the previous startup env) - curl POST through localhost:5173/api/* and /galaxy.gateway.v1.* — reach the gateway, no CORS preflight on the browser side tools/local-dev/README.md updated with the new network map and the `VITE_DEV_PROXY_TARGET` override. Co-Authored-By: Claude Opus 4.7 --- gateway/Dockerfile | 9 +++++--- tools/local-dev/README.md | 42 +++++++++++++++++++++++------------- ui/frontend/.env.development | 10 +++++++-- ui/frontend/vite.config.ts | 27 +++++++++++++++++++++++ 4 files changed, 68 insertions(+), 20 deletions(-) diff --git a/gateway/Dockerfile b/gateway/Dockerfile index d0d4675..5f5f4b4 100644 --- a/gateway/Dockerfile +++ b/gateway/Dockerfile @@ -1,9 +1,9 @@ # syntax=docker/dockerfile:1.7 # Build context is the workspace root (galaxy/), not the gateway/ -# subdirectory, because the gateway module pulls galaxy/{backend,model, -# redisconn,transcoder} through the go.work replace directives. Build -# with: +# subdirectory, because the gateway module pulls +# galaxy/{backend,core,model,redisconn,transcoder} through the +# go.work replace directives. Build with: # # docker build -t galaxy/gateway:integration -f gateway/Dockerfile . @@ -23,6 +23,7 @@ COPY pkg/redisconn/ ./pkg/redisconn/ COPY pkg/schema/ ./pkg/schema/ COPY pkg/transcoder/ ./pkg/transcoder/ COPY pkg/util/ ./pkg/util/ +COPY ui/core/ ./ui/core/ COPY backend/ ./backend/ COPY gateway/ ./gateway/ @@ -41,6 +42,7 @@ use ( ./pkg/schema ./pkg/transcoder ./pkg/util + ./ui/core ) replace ( @@ -53,6 +55,7 @@ replace ( galaxy/schema v0.0.0 => ./pkg/schema galaxy/transcoder v0.0.0 => ./pkg/transcoder galaxy/util v0.0.0 => ./pkg/util + galaxy/core v0.0.0 => ./ui/core ) EOF diff --git a/tools/local-dev/README.md b/tools/local-dev/README.md index 682a6e0..4cad8fa 100644 --- a/tools/local-dev/README.md +++ b/tools/local-dev/README.md @@ -72,23 +72,35 @@ the backend with the new env). ## Network map ``` -host compose network "galaxy-local-dev-net" - ┌────────────────────────────┐ ┌──────────────────────────────┐ - │ pnpm dev localhost:5173 │──HMR──▶│ host (Vite) │ - │ browser localhost:8080 │──REST/Connect─▶│ gateway:8080 │ - │ browser localhost:8025 │─────▶│ mailpit:8025 (web UI) │ - │ psql localhost:5433 │─────▶│ postgres:5432 │ - │ redis-cli localhost:6380 │─────▶│ redis:6379 │ - └────────────────────────────┘ │ ↳ backend:8080 (HTTP) │ - │ ↳ backend:8081 (gRPC push) │ - │ ↳ mailpit:1025 (SMTP in) │ - └──────────────────────────────┘ +host compose network "galaxy-local-dev-net" + ┌────────────────────────────────┐ ┌──────────────────────────────┐ + │ browser localhost:5173 │── pnpm dev (Vite, host) ──┐ │ + │ ↳ /api/* proxied ───┼──────────────────────────▶│ gateway:8080 │ + │ ↳ /galaxy.gateway... ┼──────────────────────────▶│ │ + │ browser localhost:8025 │─────────────────────────▶│ mailpit:8025 │ + │ psql localhost:5433 │─────────────────────────▶│ postgres:5432 │ + │ redis-cli localhost:6380 │─────────────────────────▶│ redis:6379 │ + └────────────────────────────────┘ │ ↳ backend:8080 (HTTP) │ + │ ↳ backend:8081 (gRPC push) │ + │ ↳ mailpit:1025 (SMTP in) │ + └────────────────────────────────┘ ``` -Only the gateway public port (8080) and the mailpit web UI (8025) -are needed for normal UI work. Postgres (5433) and Redis (6380) are -exposed for direct inspection (`make psql`, `redis-cli -h localhost --p 6380 -a galaxy-dev`). +Vite's dev server proxies `/api` and `/galaxy.gateway.v1.EdgeGateway` +to the gateway, so every browser request stays same-origin (no CORS +preflight). The gateway is therefore reachable only through Vite at +, not at from the +browser tab. Direct curl/wget against still +works for diagnostic probes — only the browser-side requests are +proxied. + +Mailpit (8025), postgres (5433), and redis (6380) remain directly +reachable for diagnostics (`make psql`, `redis-cli -h localhost -p +6380 -a galaxy-dev`). + +To point the proxy at a non-local gateway, run +`VITE_DEV_PROXY_TARGET=http://gateway.host:8080 pnpm -C ui/frontend dev` +— no compose changes needed. ## Make targets diff --git a/ui/frontend/.env.development b/ui/frontend/.env.development index 6536944..93ddbbc 100644 --- a/ui/frontend/.env.development +++ b/ui/frontend/.env.development @@ -3,8 +3,14 @@ # brought up by `make -C tools/local-dev up`. Per-developer overrides # live in `.env.development.local` (gitignored by Vite convention). -# Gateway public REST + Connect-Web edge listener. -VITE_GATEWAY_BASE_URL=http://localhost:8080 +# Gateway public REST + Connect-Web edge listener. Points at the Vite +# dev server's own origin so the browser sees same-origin requests; +# Vite then proxies `/api` and `/galaxy.gateway.v1.EdgeGateway` to the +# real gateway at `http://localhost:8080`. See `vite.config.ts`. To +# work against a non-local gateway, override the proxy target via +# `VITE_DEV_PROXY_TARGET=http://gateway.host:8080 pnpm dev` (no UI +# rebuild needed). +VITE_GATEWAY_BASE_URL=http://localhost:5173 # Standard non-URL-safe base64 of the gateway response-signing public # key. Pairs with `tools/local-dev/keys/gateway-response.pem`. The pair diff --git a/ui/frontend/vite.config.ts b/ui/frontend/vite.config.ts index cba9f31..dc2f53b 100644 --- a/ui/frontend/vite.config.ts +++ b/ui/frontend/vite.config.ts @@ -10,9 +10,36 @@ const pkg = JSON.parse( ), ) as { version: string }; +// Default upstream gateway address used by the dev proxy. Override by +// pointing `VITE_DEV_PROXY_TARGET` at a different gateway when working +// with a remote stack instead of `tools/local-dev/`. +const DEV_PROXY_TARGET = + process.env.VITE_DEV_PROXY_TARGET ?? "http://localhost:8080"; + export default defineConfig({ plugins: [sveltekit()], define: { __APP_VERSION__: JSON.stringify(pkg.version), }, + server: { + // Same-origin proxy so the browser sees only `localhost:5173` + // and never trips a cross-origin preflight against the + // gateway's REST + Connect-Web surfaces. Production deployments + // serve the UI and the gateway behind a single host, so the + // proxy is purely a dev-time convenience. + proxy: { + "/api": { + target: DEV_PROXY_TARGET, + changeOrigin: false, + }, + "/galaxy.gateway.v1.EdgeGateway": { + target: DEV_PROXY_TARGET, + changeOrigin: false, + // Connect-Web server-streaming (`SubscribeEvents`) uses + // chunked HTTP responses; http-proxy passes them through + // transparently as long as buffering stays off, which is + // the default. + }, + }, + }, });