Stripe is a good default if you want the most familiar developer payment
workflow and full control over products, prices, and metadata.
What You Are Setting Up
For Stripe, you need four things:- a product or payment link in Stripe
- a checkout URL saved in your env vars
- a webhook endpoint in Stripe
- a way for the repo to understand what was purchased
Required Env Vars
Step 1: Create Your Stripe Products
In Stripe:- Open
Product catalog - Create a product for each thing you want to sell
- Add a price for each product
- Create a payment link or checkout flow you want to use in the app
- one Enterprise product
- one Small credits product
Step 2: Decide How Stripe Should Describe The Purchase
You have two good options.Option A: Put type In Metadata
This is the easiest to reason about.
Examples:
type=anotherwrapper-enterprisetype=credits-small
session.metadata.typeproduct.metadata.type
Option B: Use STRIPE_PRODUCT_MAP
If you prefer, keep the mapping in env:
Step 3: Add Your Checkout URL To The App
Paste the Stripe payment link into the matching env var in.env.local.
Examples:
Step 4: Add The Webhook In Stripe
In Stripe:- Open
Developers -> Webhooks - Add a new endpoint
- Use this URL:
- Enable at least:
checkout.session.completedcheckout.session.async_payment_succeeded
- Copy the signing secret into
STRIPE_WEBHOOK_SECRET
Step 5: Add Your Server Secret Key
Add your Stripe secret key too:How The Repo Processes A Successful Stripe Payment
Once Stripe sends a successful webhook:- the repo verifies the signature
- it loads the checkout session
- it resolves the purchase type from metadata or
STRIPE_PRODUCT_MAP - it stores the purchase in the database
- it updates the user’s credits or plan state
Verification Checklist
Your Stripe setup is working if:- the app opens the Stripe checkout page
- Stripe shows a successful webhook delivery
- a row appears in
purchases - a credits purchase increases the user’s credits
- a plan purchase updates the user’s purchase state
Common Stripe Mistakes
- using the publishable key instead of
STRIPE_SECRET_KEY - adding a checkout URL but forgetting the webhook
- not setting metadata and not setting
STRIPE_PRODUCT_MAP - using the wrong production domain in the webhook URL

