Skip to content

Shadow discovery

Sooner or later, somebody points an agent at Quayside without telling the registry it exists. Quayside’s response is strict reject, but log the attempt.

What happens

  1. Caller hits the proxy with x-api-key: qsk_<jwt> whose class_slug claim is wat/rogue-bot.
  2. The proxy decodes the JWT, gets the slug, asks the registry to resolve it.
  3. The registry doesn’t have a class with that slug → raises NotFound.
  4. The proxy catches the NotFound, records a shadow attempt for (slug, principal_id), and re-raises so the caller still gets 404.

The caller cannot tell from the response whether they’ve been logged. The operator can see exactly who tried what.

What’s in the shadow log

FieldNotes
idUUID
slugThe unknown class slug
principal_idWho tried
tenantWhich tenant context they tried in
first_seen_atFirst attempt
last_seen_atLatest attempt (bumped on repeat)
attempt_countBumped on (slug, principal_id) repeat

The unique constraint is on (slug, principal_id) so the same person retrying the same slug just bumps the count.

What the operator does

Open /shadow in the dashboard. Each entry shows:

  • the slug
  • the principal who tried
  • how many times they’ve tried
  • when they last tried

Two actions per entry:

  • Clear — the entry is dismissed. If the principal tries again, a new row is created.
  • Register — open the registry’s register-class form pre-filled with the slug. After registration, future calls from that principal succeed.

Via HTTP

Terminal window
# List
curl http://localhost:8000/api/v1/registry/shadow
# Clear one
curl -X DELETE http://localhost:8000/api/v1/registry/shadow/<entry_id>

Why strict-reject

Two alternatives Quayside deliberately rejected:

  • Auto-register on first sight — too lenient. An attacker can name a class whatever they want and it suddenly exists in your registry. Strict-reject means every new class goes through a human.
  • 404 with no record — too thin. Without the log, you can’t see who is doing what, and the dashboard has nothing to surface.

The shadow log is the discovery queue — a queue of decisions waiting for a registrar.

What this isn’t

It isn’t an alert. It isn’t a block list. It’s an inbox for the person responsible for class registration. They get to decide.