Skip to main content
A hybrid billing model combining subscriptions with usage credits and one-time top-ups. Common for AI generation platforms.
View the complete source code on GitHub.

Prerequisites

  • Flowglad account with API key
  • TanStack Start project with authentication (this example uses Better Auth)
  • Node.js 21+ or Bun

Project Structure

├── src/
│   ├── lib/
│   │   ├── flowglad.ts
│   │   └── billing-helpers.ts
│   └── routes/
│       ├── index.tsx
│       └── pricing.tsx
├── pricing.yaml
└── package.json

Key Concepts

This pricing model combines three billing mechanisms:
  1. Subscription tiers - Monthly plans at fixed prices ($10, $30, $60/mo)
  2. Usage credit grants - Each tier includes credits that renew each billing period (200, 360, 750 generations)
  3. One-time top-ups - Customers can purchase additional credits when they run out
This model works well when you want predictable recurring revenue while giving customers flexibility to exceed their plan limits. Customers who find themselves consistently purchasing top-ups can choose to upgrade to a higher tier for better value.

Implementation

Pricing Configuration

The pricing.yaml file defines subscription tiers, credit allocations, and top-up products. See the full configuration in the repository. Pricing model diagram showing usage meters, subscription tiers, and top-ups The key distinction in pricing.yaml is renewalFrequency: use "every_billing_period" for subscription credits that reset monthly, and "once" for top-up credits that are consumed permanently.

Checking Usage Balance

Use checkUsageBalance to display remaining credits and gate access to generation features.
src/routes/index.tsx
const billing = useBilling();
const balance = billing.checkUsageBalance('fast_generations');

// balance.availableBalance - credits remaining
The balance includes both subscription credits and any purchased top-ups. Flowglad automatically draws from credits when you register a usage event.

Recording Usage

When a customer generates content, record the usage event. This decrements their credit balance. The SDK’s createUsageEvent method on the useBilling() hook handles the server communication automatically.
src/routes/index.tsx
const billing = useBilling();

const result = await billing.createUsageEvent({
  usageMeterSlug: 'fast_generations',
  amount: 3,
});

if ('error' in result) {
  throw new Error(result.error.json?.error || 'Failed to create usage event');
}
The SDK auto-resolves the subscriptionId from the customer’s current subscription.

Checking Feature Access

Toggle features let you differentiate plans beyond just credit amounts. Use checkFeatureAccess to check if a user has access to gated premium features.
src/routes/index.tsx
const hasRelaxMode = billing.checkFeatureAccess('unlimited_relaxed_images');
This returns true if the customer’s current subscription includes the feature, false otherwise.

Purchasing Top-Up Credits

When customers run low on credits, let them purchase additional credits without changing their subscription.
src/routes/index.tsx
const price = billing.getPrice('fast_generation_top_up');

await billing.createCheckoutSession({
  priceId: price.id,
  successUrl: window.location.href,
  cancelUrl: window.location.href,
  quantity: 1,
  autoRedirect: true,
});
This opens a checkout for the top-up product. On successful payment, the credits are immediately added to the customer’s balance.

Next Steps