CtrlK
BlogDocsLog inGet started
Tessl Logo

ee-billing

Surface workflow for billing in Grida — Stripe (subscriptions) + Metronome (AI credit ledger). The stable contracts: `grida_billing.*` is not REST-exposed (views/RPCs only), `fn_billing_apply_*` are the single mutation points, webhook receivers are `GRIDA-SEC-001`, BYOK is the `GRIDA-SEC-003` carve-out. Use when touching `editor/lib/billing/`, `editor/scripts/billing/`, the `grida_billing` schema, the webhook receivers, or the entitlement gate. Companion to `ee`.

74

Quality

92%

Does it follow best practices?

Run evals on this skill

Adds up to 20 points to the overall score

View guide

SecuritybySnyk

Critical

Do not install without reviewing

SKILL.md
Quality
Evals
Security

ee-billing

This is the surface skill for billing — the workflow once the ee anchor has placed billing on the EE side and the contributor setup is done. Setup itself is documented; cite it, don't restate it:

  • docs/contributing/billing — local Stripe + Metronome sandbox, cloudflared tunnel, env vars, troubleshooting.
  • docs/wg/platform/billing/ — design notes: AI credits master plan, Metronome integration, known issues.
  • docs/platform/billing — user-facing copy.

Stable surface (the contract)

These shapes are locked. A change that breaks any of them must be intentional and called out in the PR description.

  • grida_billing.* schema — not REST-exposed. Public reads go through v_billing_* views; writes only through fn_billing_* RPCs. Don't add a new direct-access surface; add a view or an RPC. Schema discipline lives in database / supabase/AGENTS.md.
  • public.fn_billing_apply_stripe_event — the only place Stripe-driven subscription state mutates. Mutating from a new direction (UI form, ad-hoc RPC, hand-written migration) corrupts the projector model.
  • public.fn_billing_apply_metronome_event — same role for Metronome credit / alert / payment_gate events.
  • Webhook receivers/webhooks/stripe and /webhooks/metronome are the only billing ingress; both are signature-verified per GRIDA-SEC-001.
  • editor/lib/billing/metronome.ts — the service module surface: provisionOrg, addStripeChargedCommit, setAutoReload, getEntitlement, ingestUsageEvent. New billing actions go through this module, not adjacent to it.

Substrates

Two external clouds; both use per-contributor sandbox accounts. Credentials are never shared. Live keys are refused at boot.

  • Stripe — subscriptions + payment processing. Provision via pnpm tsx editor/scripts/billing/cli.ts setup:stripe. Idempotent; re-run after every supabase db reset (writes price IDs into the catalog).
  • Metronome — AI credit ledger. Provision via pnpm tsx editor/scripts/billing/cli.ts setup:metronome. Same idempotency / re-run rule.

editor/scripts/billing/cli.ts is the single entry point for every billing script; run without arguments for the full subcommand list. See editor/scripts/billing/README.md.

The seam: how OSS reads entitlement

OSS code that needs to gate on a paid plan, AI credit balance, or org entitlement does not import billing internals. The seam is getEntitlement (from editor/lib/billing/metronome.ts) and its typed wrappers. New gates go through this function so fail-closed and BYOK behavior stay centralized.

BYOK carve-out — GRIDA-SEC-003

If BYOK_OPENROUTER_API_KEY or BYOK_AI_GATEWAY_API_KEY is set in editor/.env.local, the AI-SDK text path routes through the contributor's provider and bypasses billing.

  • Auth is never bypassed. A resolvable org is still required.
  • Text/chat only. Image and audio still go through Replicate and still bill, even under BYOK.
  • Never set BYOK_* on a hosted or preview deploy. It disables billing and the org-id sanity gate for every org. See SECURITY.md (GRIDA-SEC-003).

Working on billing

  1. Read docs/contributing/billing for setup before the first change. Don't skip cloudflared if you need Metronome — webhook delivery requires public HTTPS.
  2. Tag every billing file with GRIDA-EE: billing per the ee skill.
  3. Webhook receivers also carry GRIDA-SEC-001 — the security review runs first.
  4. Don't mutate grida_billing.* outside fn_billing_apply_* or the migration that creates it.
  5. Run the E2E suite before opening the PR (refuses to start unless every channel is demonstrably test-mode): pnpm --filter editor vitest run lib/billing/__tests__/e2e.
  6. For schema changes, the database skill governs — grida_billing is a regular grida_* schema under that discipline.

Known issues

docs/wg/platform/billing/known-issues is the living register (KI-BILL-NNN). Add to it when you mitigate or accept an issue; don't quietly bake the mitigation into a PR without registering it.

See also: ee (the EE anchor), security (GRIDA-SEC-001, GRIDA-SEC-003), database (schema discipline for grida_billing).

Repository
gridaco/grida
Last updated
First committed

Is this your skill?

If you maintain this skill, you can claim it as your own. Once claimed, you can manage eval scenarios, bundle related skills, attach documentation or rules, and ensure cross-agent compatibility.