feat(cli): carry plan-gate entitlement on machine-mode errors by pamelachia · Pull Request #7271 · supabase/cli · GitHub
Skip to content

feat(cli): carry plan-gate entitlement on machine-mode errors - #7271

Draft
pamelachia wants to merge 5 commits into
developfrom
pamela/growth-1050-entitlement-json-errors
Draft

pamelachia wants to merge 5 commits into
developfrom
pamela/growth-1050-entitlement-json-errors

Conversation

@pamelachia

@pamelachia pamelachia commented Oct 21, 2026 •

Copy link
Copy Markdown
Contributor

Plan-gated Management API denials already return { error: { code: "entitlement_required", feature, upgrade_url } }. In --output-format json and stream-json that signal only survives as escaped text inside error.message, so an agent has to parse prose to learn that an upgrade is needed and where. This adds a structured entitlement to the machine-mode error object for every command whose status errors go through mapHttpError.

{"_tag":"Error","error":{"code":"DomainsUnexpectedStatusError","message":"...","entitlement":{"feature":"custom_domain","upgrade_url":"https://supabase.com/dashboard/org/<slug>/billing"}}}

Changed:

  • Machine-mode errors carry the plan gate: on a 4xx, mapHttpError decodes the untruncated body and, when it is the plan-gate envelope, attaches entitlement: { feature, upgrade_url } to the status error. normalizeCliError passes it into the json and stream-json error object, so commands with no per-command upgrade wiring (branches unpause) get it too.
  • Handlers that rebuild a mapped error keep it: branches create/update and vanity-subdomains activate/check-availability forward the field.
  • Envelope values are validated in one place: I moved the parser into http-errors.ts and suggestUpgrade reuses it. feature must be a plain key and upgrade_url an http(s) URL without credentials, emitted as the parsed URL so control and bidi characters arrive percent-encoded; anything else counts as no envelope.

Note: text output and cli_upgrade_suggested are unchanged for well-formed envelopes. The per-command text hint stays until I move the hint and the event onto the same central path in a follow-up.

Linear

  • part of GROWTH-1050

@pamelachia pamelachia self-assigned this Oct 21, 2026

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant