Billing
Ampout uses Stripe for subscriptions. Every account has an associated Stripe customer (created at signup when STRIPE_SECRET_KEY is configured). Plan changes happen in Stripe Checkout / Customer Portal; the Stripe webhook handler flips account.plan automatically when subscription events fire.
Get current subscription
Section titled “Get current subscription”GET /billing/subscriptionAuthorization: Bearer <key>{ "plan": { "slug": "hobby", "name": "Hobby", "tier": 1, "monthly_limit": 5000 }, "current_period": { "start": "2026-04-01T00:00:00Z", "end": "2026-04-30T23:59:59Z", "sends_count": 1842 }, "stripe_subscription_id": "sub_...", "stripe_customer_id": "cus_..."}Period boundaries come from the Stripe subscription when one is active; otherwise they fall back to calendar months.
Get usage history
Section titled “Get usage history”GET /billing/usageAuthorization: Bearer <key>{ "monthly_limit": 5000, "current": { "period_start": "2026-04-01T00:00:00Z", "period_end": "2026-04-30T23:59:59Z", "sends_count": 1842 }, "history": [ { "period_start": "2026-03-01T00:00:00Z", "period_end": "2026-03-31T23:59:59Z", "sends_count": 4923 } ]}Returns the last 12 monthly UsageRecords plus the current period’s running total.
Open a Stripe Checkout Session (upgrade)
Section titled “Open a Stripe Checkout Session (upgrade)”POST /billing/checkoutAuthorization: Bearer <key>Content-Type: application/jsonIdempotency-Key: optional-stable-key
{ "plan_slug": "hobby" }{ "url": "https://checkout.stripe.com/c/pay/cs_test_..." }Redirect the user to url. On successful payment, Stripe redirects back to BILLING_RETURN_URL?status=success and the inbound webhook flips the account’s plan automatically.
Validates that the requested plan is public, non-archived, and paid (has stripe_price_id). Free / private / archived plans return 422.
Open a Stripe Customer Portal session
Section titled “Open a Stripe Customer Portal session”POST /billing/portalAuthorization: Bearer <key>Content-Type: application/jsonIdempotency-Key: optional-stable-key{ "url": "https://billing.stripe.com/p/session/test_..." }The Customer Portal lets users update payment methods, view invoices, and cancel/downgrade their subscription. Requires the account to have a stripe_customer_id (created at signup when Stripe is configured).
Errors
Section titled “Errors”| Status | Code | When |
|---|---|---|
| 404 | plan_not_found | checkout with unknown plan_slug. |
| 422 | plan_not_purchasable | checkout for a free, private, or archived plan. |
| 422 | no_stripe_customer | Account has no stripe_customer_id (signed up before Stripe was wired). |
Soft-cap behavior
Section titled “Soft-cap behavior”When current.sends_count >= monthly_limit, POST /campaigns/:id/dispatch returns 402 plan_limit_reached before enqueuing any new SendEmailJobs. Already-scheduled SendEmailJobs (e.g., step 2/3 fires from earlier dispatches) still fire — soft-cap applies to new dispatch only.