Skip to content

dev: --auto-port — auto-pick free pg + module ports, register dynamic local_url over WSS #28

Description

@I-am-nothing

Goal

`mirrorstack dev --auto-port` (or `--auto`) picks free ports for both the bundled pg and the module's HTTP listener at startup, then sends the chosen `local_url` to dispatch in the WSS `register` frame so Leaf 1 routing always 302s to the correct port — even when ports shift between runs.

This is the runtime-flexible cousin of #27 (which only fixes the scaffold-time default). #27 nicens the first run; #28 makes every run port-collision-proof.

Why this matters

Currently `--local-url` is a static flag (`http://localhost:8080\` default). If port 8080 is taken at `dev` startup, the SDK fails to bind. Even if we solve that, the registered URL goes stale across runs. With `--auto-port`:

  • pg port: scan upward from 5433, write the chosen one into compose + `MS_LOCAL_DB_URL`
  • module port: scan upward from 8080, set via `MS_HTTP_PORT` (env the SDK already reads, OR a new env we add)
  • `local_url` for the register frame: built from the chosen module port (`http://localhost:`)
  • Tunnel session carries the dynamic URL → dispatch's Leaf 1 302s to it correctly

Sketch

```rust
let pg_port = pick_free_port(5433)?;
let app_port = pick_free_port(8080)?;
let local_url = format!("http://localhost:{app_port}\");

// Render compose with chosen pg_port (re-bootstrap or in-memory only)
// Set MS_HTTP_PORT=<app_port> when spawning go run .
// Pass local_url to tunnel::open(... register: RegisterPayload { local_url: &local_url, ... })
```

Open questions

  1. Compose file: re-bootstrap with new port, or use `docker compose up` with a port override env? Override is less surprising (devs may have edited their compose).
  2. Module port: does the SDK honor `MS_HTTP_PORT` already, or do we need a new env / a new wiring?
  3. Re-registration: if `--auto-port` shifts between runs, does the platform see two stale registrations? Sessions store TTL is 24h, so until #69 (or whatever shipped Phase 1's session lifecycle), there's drift. Probably fine — old registration just expires.

Deps

Acceptance

  • `mirrorstack dev --auto-port` scans pg + module ports, surfaces them in startup output ("pg :5434, module :8081")
  • WSS register frame carries the chosen `local_url` (verifiable on the dispatch side once #113-116 + IaC ship)
  • Browser hit to `/m/<module_id>/foo` 302s to the correct localhost port

Estimate

~120 LoC. Mostly straightforward; the SDK port wiring is the one unknown.

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions