Skip to content

[STUB-deploy] Register C0 stub as a resolvable BillingProvider — DO NOT MERGE#380

Draft
seanhanca wants to merge 1 commit into
preview/phase-2-integrationfrom
feat/stub-provider-deploy
Draft

[STUB-deploy] Register C0 stub as a resolvable BillingProvider — DO NOT MERGE#380
seanhanca wants to merge 1 commit into
preview/phase-2-integrationfrom
feat/stub-provider-deploy

Conversation

@seanhanca

Copy link
Copy Markdown
Contributor

🚫 DO NOT MERGE — Phase-2 generalization artifact. Based on preview/phase-2-integration (the consolidated integration vehicle), not main.

Coordination

Plan PR ID:   STUB-deploy
Repo:         NaaP (livepeer/naap)
Base:         preview/phase-2-integration
Depends-on:   C0, NAAP-A (+ NAAP-A-db, NAAP-B/C/1 for the resolve path)
Blocks:       INT-G
Feature flag: NAAP_ENABLE_STUB_PROVIDER (env, default OFF); catalog enabled:false
Merge-safety: stub is catalog-disabled + adapter is in-process only ⇒ no prod
              behavior change; migrations expand-only (adapterType already added
              by NAAP-A-db); INV-1 green.

What

Stand up the C0 in-memory stub as a first-class, registered BillingProvider alongside pymthouse, so the NAAP-C front door can resolve a naap_ key against BOTH providers — proving the seam is provider-agnostic (generalization E8, enforced by INT-G).

  • BillingProvider{slug:"stub", adapterType:"stub", enabled:false} added to the catalog; adapterType now persisted in all three upsert paths (web-next seed, packages/database seed, sync-plugin-registry).
  • enabled:false keeps the stub out of the production provider picker; binding a team's billingAccountRef.providerSlug to "stub" is an explicit, opt-in action. The stub carries no secrets and needs no provisioning (contrast pymthouse's OIDC/M2M env).
  • src/lib/billing/stub-provider-config.ts: registration/resolution helpers, NAAP_ENABLE_STUB_PROVIDER env gate (default OFF), and structured deploy-status logging (no secrets/PII).

Self-review

  • The static registry (registry.ts) and the DB registry (registry-db.ts, NAAP-A-db) both resolve "stub" → StubAdapter; DB resolution falls back to static on any miss so it stays resolvable even before the catalog row is seeded.
  • No live secrets — stub is in-memory only. Structured logs assert no secret-bearing keys.

Guardrail tests (added)

  • catalog registers stub + pymthouse (≥2 providers);
  • static + DB registries resolve "stub";
  • deploy gate defaults OFF;
  • structured log line contains no secret|token|password.

DoD

  • Registry resolves ≥2 providers (pymthouse + stub)
  • No prod behavior change (catalog-disabled, env gate OFF) — INV-1 green
  • No secrets; stub in-memory only
  • DO NOT MERGE (intentional)

Made with Cursor

Stand up the C0 in-memory stub provider as a first-class, registered
BillingProvider alongside pymthouse so the NAAP-C front door can resolve a
naap_ key against BOTH providers — proving the seam is provider-agnostic
(generalization E8, enforced by INT-G).

- Add BillingProvider{slug:"stub", adapterType:"stub", enabled:false} to the
  catalog; persist adapterType in all three upsert paths (web-next seed,
  packages/database seed, sync-plugin-registry). enabled:false keeps it out of
  the production provider picker; binding a team's billingAccountRef to "stub"
  is explicit/opt-in. The stub carries no secrets and needs no provisioning.
- src/lib/billing/stub-provider-config.ts: registration/resolution helpers +
  NAAP_ENABLE_STUB_PROVIDER env gate (default OFF) + structured deploy-status
  logging (no secrets/PII).
- Tests: catalog registers stub (≥2 providers); static + DB (NAAP-A-db)
  registries resolve "stub" → StubAdapter; deploy gate defaults OFF; structured
  log carries no secret-bearing keys.

Flag/catalog default keeps prod behavior unchanged (INV-1 green).

Co-authored-by: Cursor <cursoragent@cursor.com>
@vercel

vercel Bot commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
naap-platform Ready Ready Preview Jun 17, 2026 9:32pm

Request Review

@github-actions github-actions Bot added the size/L Large PR (201-500 lines) label Jun 17, 2026
@github-actions

Copy link
Copy Markdown

⚠️ This PR is large (250 lines changed). Consider splitting it into smaller PRs for easier review.

@github-actions github-actions Bot added scope/shell Shell app changes scope/packages Shared package changes scope/infra Infrastructure changes labels Jun 17, 2026
@coderabbitai

coderabbitai Bot commented Jun 17, 2026

Copy link
Copy Markdown

Important

Review skipped

Draft detected.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 1ecfce49-c6fe-41a0-a26f-20f72b538cd4

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/stub-provider-deploy

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@seanhanca

Copy link
Copy Markdown
Contributor Author

🔎 Self code-review (STUB-deploy)

Correctness

  • adapterType is persisted in all three upsert paths (web-next seed, packages/database seed, sync-plugin-registry) so the catalog row and the DB-driven registry (NAAP-A-db) agree. DB resolution falls back to the static slug map on any miss, so the stub stays resolvable even before the row is seeded — no chicken-and-egg.
  • Front-door resolution keys off billingAccountRef.providerSlug → adapter, which is independent of the catalog enabled flag, so enabled:false does not block a stub-backed team (intended).

Safety / invariants

  • enabled:false + NAAP_ENABLE_STUB_PROVIDER default OFF ⇒ the stub never surfaces in the production provider picker and prod behavior is unchanged (INV-1).
  • Stub is in-memory; no secrets, no external calls, no provisioning. Structured deploy-status log asserts it carries no secret|token|password keys.
  • Migration: none new — adapterType was added expand-only by NAAP-A-db.

Risks considered

  • Could the new catalog row leak into a provider dropdown? Guarded by enabled:false; if a UI ignores enabled, that's a UI bug to fix there, not here.
  • Generality: this PR adds a second BPP provider without NaaP importing it directly — the registry/adapter seam is the only coupling. ✅

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

Labels

scope/infra Infrastructure changes scope/packages Shared package changes scope/shell Shell app changes size/L Large PR (201-500 lines)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant