fix(billing): public plans listing only returns products tagged with metadata.planId - #4124
Conversation
…w id fallback fetchPlansFromStripe fell back to the raw Stripe product id when metadata.planId was missing, so any active Stripe product (a one-time pack, a recurring product sold outside the plans catalogue via a Payment Link) advertised itself as a public plan on GET /api/billing/plans, often with a null price id. Now only products carrying metadata.planId are returned. Subscription and webhook plan resolution (billing.planResolver.js, billing.webhook.service.js, billing.admin.service.js) are untouched: a recurring product sold outside the plans catalogue still resolves and works, it just no longer appears in the public listing. Fixes #4113 Claude-Session: https://claude.ai/code/session_01ARSKGeyDyVFv3UzGH1LBn6
The two tests covering "no metadata" and "metadata without planId key" exercised the identical guard clause and assertion; one test with both product shapes gives the same coverage with less duplication. Claude-Session: https://claude.ai/code/session_01ARSKGeyDyVFv3UzGH1LBn6
|
Warning Review limit reachedNext included review available in 54 minutes. View limit detailsLimit details: You’ve used the included review currently available. You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository. Review configuration: ⚙️ Run configurationConfiguration used: Repository: pierreb-devkit/Node/.coderabbit.yaml Review profile: ASSERTIVE Plan: Advanced Run ID: 📒 Files selected for processing (4)
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. Comment |
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## master #4124 +/- ##
=======================================
Coverage 94.36% 94.36%
=======================================
Files 173 173
Lines 6012 6016 +4
Branches 1936 1937 +1
=======================================
+ Hits 5673 5677 +4
Misses 276 276
Partials 63 63
Flags with carried forward coverage won't be shown. Click here to find out more. Continue to review full report in Codecov by Harness.
🚀 New features to boost your workflow:
|
Summary
GET /api/billing/plansis public and returned every active Stripe product as a plan: a product withoutmetadata.planIdfell back to its raw Stripe id, so one-time packs (and anything else active in the account) showed up as plans withmonthlyPrice: 0and a null price id.fetchPlansFromStripenow keeps only products tagged withmetadata.planId; the raw-id fallback is gone.createCheckoutvalidatespriceIdagainst the same listing, so self-serve checkout also accepts only prices of tagged plans.[billing.plans]warning instead of a silent empty listing.billing.planResolver.js, webhook, admin sync) — a recurring product sold outside the catalogue (e.g. a Payment Link) keeps working, it just is not listed.Verification
test:coverage: 235 suites / 3158 tests pass, thresholds unchanged; the plans unit suite adds a mixed-catalogue case and the untagged-catalogue warning cases.Closes #4113
https://claude.ai/code/session_01ARSKGeyDyVFv3UzGH1LBn6