Hub as portal, OAuth, and the service catalog

Partially superseded (2026-06-09) — two halves, different fates

This document merged two architectural threads. They have diverged since:

Current ownership rules: parachute-patterns/patterns/hub-module-boundary.md Modular-UI shift: parachute-patterns/design/2026-06-09-modular-ui-architecture.md

Date: 2026-04-20 (launch week — launch target 2026-04-23) Context: Aaron is out walking, has two related architectural thoughts that converge.

The two threads that converged

Thread 1: Hub click-through is dead for API-only services

Aaron clicks the Vault card on the hub and lands on a raw API response. Not useful for humans. Notes has a real UI; Vault doesn't. He wants the hub to do more — become a configuration surface for the whole ecosystem so users don't have to use the CLI for every setting.

Thread 2: OAuth architecture — where should it live?

Originally proposed: vault as ecosystem identity provider (vault already has OAuth 2.1 + PKCE + DCR — just reuse it). Aaron pushed back: that conflates data service with identity. The hub is the front door; identity belongs at the front door. His proposal: hub-as-OAuth-issuer, vault and other services accept hub-issued tokens.

Aaron is right. Vault-as-IDP was expedient, not clean. Extracting identity from the data layer is the architecturally correct move. Services shouldn't inherit auth from a sibling; they should inherit from a shared source above them.

Core design

Hub is the ecosystem front door. It owns three things:

  1. The landing page and service directory (exists today)
  2. The OAuth issuer surface (/.well-known/oauth-authorization-server, /oauth/authorize, /oauth/token, /oauth/register)
  3. The configuration portal (future — phase 2+)

Vault, Notes, Scribe, and future services are OAuth clients of the hub. Services accept hub-issued tokens, validate scopes.

Scopes per service: vault:read, vault:write, scribe:transcribe, hub:admin, channel:send. Clients declare what they need at authorization; hub consent UI shows "Notes wants: read your vault, write notes, transcribe audio."

Token response carries the service catalog (ecosystem extension):

{
  "access_token": "...",
  "scopes": ["vault:read", "vault:write"],
  "services": {
    "vault": { "url": "https://parachute.x.ts.net/vault/default", "version": "0.3.0" },
    "scribe": { "url": "https://parachute.x.ts.net/scribe", "version": "0.2.0" }
  }
}

Notes never asks the user for a vault URL. It does OAuth against the hub, gets a token + the service catalog, auto-populates everything.

Step-up permissions: Notes initially requests vault:read. User tries voice memo. Notes requests scribe:transcribe + vault:write via refresh; hub re-prompts consent for new scopes. No full re-login.

Phasing

Phase 0 — launch seam (pre-2026-04-23)

Small PR, low risk:

Net effect: clients from launch day onward never know vault is the auth implementation. When we later extract or rewrite auth, zero client changes.

Phase 1 — catalog in token response (post-launch, 1–2 weeks)

Phase 2 — real scope enforcement (post-launch, 2–6 weeks)

Phase 3 — full extraction (post-launch, open-ended)

Hub as config portal (Thread 1 resolution)

Orthogonal to OAuth but benefits from it:

Why this shape is right

  1. Separation of concerns: identity is cross-cutting, data services are data services. Don't conflate.
  2. Front door UX: "Log into Parachute" (via hub) is more natural than "log into your vault." Users see one door.
  3. Single sign-on, automatically: one OAuth flow against the hub grants access to every installed service. No per-service login.
  4. Auto-discovery: services learn about each other through the token response. Notes stops asking for vault URLs. New services plug in without clients being reconfigured.
  5. Scope-based permissions: users can grant fine-grained access per client app. Notes gets read; some future AI agent gets read-only; an admin tool gets full.
  6. Clean extraction path: auth implementation can move (vault → hub → dedicated service) without ever breaking a client, because the client only sees the hub as the issuer.

Open questions

Decisions made

Why this note exists

We're 3 days from launch. This is a significant architectural direction that we can't fully build pre-launch but whose public shape matters from day one. The launch Phase 0 seam is the commitment that keeps the post-launch door open without painting us into a corner.

Revisit this note when starting Phase 1 work — likely within 2 weeks of launch.