Payments
Set up Stripe, Polar, or Dodo Payments via Better Auth plugins to handle one-time and subscription payments.
Setup
Stripe
- Sign up at Stripe and create an account.
- Create a Product in the Stripe Dashboard.
- Add pricing plans (e.g. Monthly $10, Yearly $60).
- Copy the Price IDs (they look like
price_xxx).
- Copy your Secret Key and Webhook Secret from the Stripe Dashboard (Developers > API Keys and Webhooks).
- Set the following environment variables:
.env
STRIPE_SECRET_KEY="your-stripe-secret-key" STRIPE_WEBHOOK_SECRET="your-stripe-webhook-secret" - Update pricing plans in your config:
shared/config.ts
pricing: { paymentProvider: enums.paymentProvider.stripe, // Set paymentProvider Stripe successUrlPath: '/payment-success', // Redirect after successful payment failedUrlPath: '/payment-failed', // Redirect after failed payment plans: { pro: { enable: true, // Is show Pro Plan key: 'pro', monthly: { key: 'pro-monthly', priceId: 'price_monthly', // Set Stripe Price ID for monthly subscription mode: 'subscription', // Payment is subscription }, yearly: { key: 'pro-yearly', priceId: 'price_yearly', // Set Stripe Price ID for yearly subscription mode: 'subscription', // Payment is subscription }, }, lifetime: { enable: true, // Is show Lifetime Plan key: 'lifetime', priceId: 'price_lifetime', // Set Stripe Price ID for one-time payment promoCodeId: '', // Optional - Set Stripe Promo ID for any promo/coupon to discount mode: 'payment', // Payment is one-time }, }, }, - Set up a webhook:
- Local: Use Stripe CLICopy the Webhook Secret intoTerminal
stripe listen --forward-to localhost:3000/api/auth/stripe/webhook.env. - Production: Add a webhook endpoint in Stripe Dashboard pointing to:
Select events like
https://your-site.com/api/auth/stripe/webhookcheckout.session.completed,customer.subscription.created,customer.subscription.updated, andcustomer.subscription.deleted.
- Local: Use Stripe CLI
Polar
- Sign up at Polar and create an account.
- Create a Product in the Polar Dashboard.
- Add pricing plans (e.g. Monthly $10, Yearly $60).
- Copy the Product IDs (found in the product details/API settings).
- Generate a Personal Access Token (or Organization Token) and configure a Webhook in the Polar Dashboard (Settings > Developers).
- Set the following environment variables:
.env
POLAR_ACCESS_TOKEN="your-polar-access-token" POLAR_WEBHOOK_SECRET="your-polar-webhook-secret" - Update pricing plans in your config:
shared/config.ts
pricing: { paymentProvider: enums.paymentProvider.polar, // Set paymentProvider Polar successUrlPath: '/payment-success', // Redirect after successful payment failedUrlPath: '/payment-failed', // Redirect after failed payment plans: { pro: { enable: true, // Is show Pro Plan key: 'pro', monthly: { key: 'pro-monthly', priceId: 'price_monthly', // Set Polar Product ID for monthly subscription mode: 'subscription', // Payment is subscription }, yearly: { key: 'pro-yearly', priceId: 'price_yearly', // Set Polar Product ID for yearly subscription mode: 'subscription', // Payment is subscription }, }, lifetime: { enable: true, // Is show Lifetime Plan key: 'lifetime', priceId: 'price_lifetime', // Set Polar Product ID for one-time payment mode: 'payment', // Payment is one-time }, }, }, - Set up a webhook:
- Local: Use a tunneling service (like ngrok) or Polar's CLI if available to forward events to your local environment. Copy the Webhook Secret into
.env. - Production: Add a webhook endpoint in Polar Dashboard pointing to:
Select at least the following events like
https://your-site.com/api/auth/polar/webhooksorder.created,subscription.created,subscription.updated,subscription.canceled.
- Local: Use a tunneling service (like ngrok) or Polar's CLI if available to forward events to your local environment. Copy the Webhook Secret into
Dodo Payments
- Sign up at Dodo Payments and create an account.
- Create a Product and its associated pricing plans in the Dodo Payments Dashboard.
- Copy the Product IDs (they typically start with
pdt_) for each unique plan/interval.
- Copy the Product IDs (they typically start with
- Copy your API Key and Webhook Secret from the Dodo Payments Dashboard (Developer > API Keys and Webhooks).
- Set the following environment variables:
.env
DODO_PAYMENTS_API_KEY="your-dodo-api-key" DODO_PAYMENTS_WEBHOOK_SECRET="your-dodo-webhook-secret" - Update pricing plans in your config:
shared/config.ts
pricing: { paymentProvider: enums.paymentProvider.dodo, // Set paymentProvider Dodo successUrlPath: '/payment-success', // Redirect after successful payment failedUrlPath: '/payment-failed', // Redirect after failed payment plans: { pro: { enable: true, // Is show Pro Plan key: 'pro', monthly: { key: 'pro-monthly', priceId: 'price_monthly', // Set Dodo Product ID for monthly subscription mode: 'subscription', // Payment is subscription }, yearly: { key: 'pro-yearly', priceId: 'price_yearly', // Set Dodo Product ID for yearly subscription mode: 'subscription', // Payment is subscription }, }, lifetime: { enable: true, // Is show Lifetime Plan key: 'lifetime', priceId: 'price_lifetime', // Set Dodo Product ID for one-time payment mode: 'payment', // Payment is one-time }, }, }, - Set up a webhook:
- Local: Use a tunneling service (like ngrok) to expose your local development server.
Copy the resulting URL and add /api/payment/dodo/webhook to it for the Dodo Webhook configuration.terminal
# Example using ngrok to tunnel to your app's port ngrok http 3000 - Production: Add a webhook endpoint in Dodo Payments Dashboard pointing to:
Select at lease the following events like
https://your-site.com/api/payment/dodo/webhookpayment.succeeded,payment.failed,subscription.active,subscription.updated,subscription.renewed,subscription.cancelled,subscription.on_hold, andsubscription.failed.
- Local: Use a tunneling service (like ngrok) to expose your local development server.
Usage
- Handle Webhooks: Plugin automatically updates subscription status on payment events.
- Verify Payments: Check transactions and subscriptions in the plugin dashboard.
- Initiate Checkout: Use the
paymentCheckoutfunction to start a payment.Users are redirected to payment's checkout page, then back toconst { payment } = useAuth(); payment.paymentCheckout(appConfig.pricing.plans.lifetime.key, locale.value);successUrlPathorfailedUrlPath - Customer Portal: Let users manage subscriptions, invoices, and payment methods:
const { payment } = useAuth(); payment.toCustomerPortal();
Authentication
Set up authentication in your ShipAhead app with Better Auth. Configure sign-in methods, user sessions, and account management for your SaaS product.
Admin Panel
Configure the ShipAhead admin dashboard to manage users, revenue, and subscriptions. Learn how to set up admin access and monitor your SaaS business.