Docs
Stripe Integration Flow
Stripe Integration Flow
Modular subscription management and payment processing with Stripe
Overview
Handles subscription management, payment processing, and billing operations using a modular architecture with Stripe. The system is organized into clear layers: types, repositories, clients, and services, providing better maintainability and testability. Supports multiple subscription tiers with monthly/yearly billing cycles and webhook-based subscription lifecycle management.
Main libraries/services:
stripe- Payment processing and subscription management@stripe/stripe-js- Client-side Stripe integration- Webhook endpoints for real-time subscription updates
- Kysely + raw SQL for subscription data persistence
- Modular architecture with separated concerns
File Map
š types/subscriptions.ts - Centralized TypeScript interfaces
š lib/stripe.ts - Stripe client configuration
š config/subscriptions.ts - Pricing plans and tier definitions
š repositories/subscriptions/ - Data access layer
āāā index.ts - Repository exports
āāā find.ts - Database queries for subscriptions
āāā create.ts - Subscription creation operations
āāā update.ts - Subscription update operations
āāā cancel.ts - Subscription cancellation operations
š clients/stripe/ - Stripe API integration layer
āāā index.ts - Client exports
āāā subscription.ts - Stripe subscription operations
āāā invoices.ts - Stripe invoice operations
š services/subscriptions/ - Business logic layer
āāā index.ts - Service exports
āāā helpers.ts - Pure utility functions
āāā get-plan.ts - Subscription plan retrieval
āāā create.ts - Subscription creation logic
āāā update.ts - Subscription update logic
āāā cancel.ts - Subscription cancellation logic
āāā webhooks.ts - Webhook event processing
š actions/generate-user-stripe.ts - Server action for checkout/billing portal
š app/api/webhooks/stripe/route.ts - Webhook endpoint (simplified)
š components/forms/billing-form-button.tsx - Billing UI components
š components/pricing/ - Pricing page components
š app/(protected)/dashboard/billing/page.tsx - Billing dashboard
š app/(marketing)/pricing/page.tsx - Public pricing page
Step-by-Step Flow
New Subscription Creation
- User clicks "Upgrade" button on pricing page
generateUserStripeaction is triggered with priceId- User authentication is verified via
auth() - Service Layer:
getUserSubscriptionPlanservice fetches current subscription status - If user is on free plan:
- Client Layer:
createCheckoutSessioncreates Stripe checkout session - User metadata (userId) is attached to session
- User is redirected to Stripe checkout
- Client Layer:
- User completes payment on Stripe
- Stripe webhook
checkout.session.completedis triggered - Webhook Processing:
- Webhook signature verified in API route
handleWebhookEventservice processes the eventhandleCheckoutCompletedservice handles the specific event- Client Layer:
retrieveSubscriptiongets subscription details from Stripe - Repository Layer:
updateUserOnSubscriptionCreateupdates database
Subscription Management (Existing Customers)
- User clicks "Manage Billing" button
- Service Layer:
getUserSubscriptionPlanchecks current subscription status - If user is on paid plan:
- Client Layer:
createBillingPortalSessioncreates Stripe portal session - User is redirected to Stripe customer portal
- Client Layer:
- User can update payment methods, cancel, or change plans
- Changes trigger webhook events for real-time updates
Webhook Event Processing (Modular Architecture)
- Stripe sends webhook to
/api/webhooks/stripe - API Route: Webhook signature is verified using
STRIPE_WEBHOOK_SECRET - Service Layer:
handleWebhookEventservice processes the event - Event routing based on type:
checkout.session.completed: CallshandleCheckoutCompletedserviceinvoice.payment_succeeded: CallshandlePaymentSucceededservice
- Service Layer: Business logic validation and orchestration
- Client Layer: Stripe API calls for data retrieval
- Repository Layer: Database operations for data persistence
- Response: Success/error response sent back to Stripe
Subscription Plan Detection (Service Layer)
- Service Layer:
getUserSubscriptionPlanorchestrates the process - Repository Layer:
findUserSubscriptionfetches user data from database - Helper Functions:
isSubscriptionActivechecks plan validity - Helper Functions:
findPlanByPriceIdmatches pricing data - Helper Functions:
determinePlanIntervaldetermines billing cycle - Client Layer:
retrieveSubscriptiongets cancellation status from Stripe - Helper Functions:
formatSubscriptionPlanformats final response - UI components use this data for conditional rendering
Data Flow Diagram
flowchart TD
A[Pricing Page] --> B[Server Action]
B --> C[Service Layer]
C --> D[Client Layer]
D --> E[Stripe API]
E --> F[Stripe Payment]
F --> G[Webhook]
G --> H[API Route]
H --> I[Service Layer]
I --> J[Client Layer]
J --> K[Repository Layer]
K --> L[Database Update]
M[User Dashboard] --> N[Service Layer]
N --> O[Repository Layer]
O --> P[Database Query]
P --> Q[Helper Functions]
Q --> R[Client Layer]
R --> S[Stripe API]
S --> T[Subscription Status]
U[Billing Portal] --> V[Service Layer]
V --> W[Client Layer]
W --> X[Stripe Portal]
X --> Y[Plan Changes]
Y --> Z[Webhook]
Z --> AA[Database Update]Architecture Layers
Types Layer
- Purpose: Centralized TypeScript interfaces
- Files:
types/subscriptions.ts - Responsibilities: Type definitions, interfaces, data contracts
Repository Layer
- Purpose: Data access and persistence
- Files:
repositories/subscriptions/* - Responsibilities: Database queries, data transformation, error handling
Client Layer
- Purpose: External API integration
- Files:
clients/stripe/* - Responsibilities: Stripe API calls, request/response handling
Service Layer
- Purpose: Business logic and orchestration
- Files:
services/subscriptions/* - Responsibilities: Business rules, validation, coordination between layers
Subscription Tiers
- Starter: Free tier (no Stripe integration)
- Pro: $15/month or $144/year
- Business: $30/month or $300/year
Dependencies & Contracts
Core Types
SubscriptionData: Core subscription information from StripeUserSubscriptionRecord: Database representation of user subscriptionSubscriptionServiceResponse: Standardized service response formatCheckoutSessionData: Data required for creating checkout sessionsUpdateSubscriptionData: Data for subscription updates
Service Contracts
getUserSubscriptionPlan(userId: string): Retrieves formatted subscription plancreateSubscription(userId: string, priceId: string): Creates new subscriptionupdateSubscription(subscriptionId: string, priceId: string): Updates existing subscriptioncancelSubscription(subscriptionId: string): Cancels subscriptionhandleWebhookEvent(event: Stripe.Event): Processes webhook events
Repository Contracts
findUserSubscription(userId: string): Finds user subscription datacreateUserSubscription(data: CreateSubscriptionData): Creates subscription recordupdateUserSubscription(userId: string, data: UpdateSubscriptionData): Updates subscriptioncancelUserSubscription(userId: string): Marks subscription as canceled
Client Contracts
createCheckoutSession(data: CheckoutSessionData): Creates Stripe checkout sessioncreateBillingPortalSession(customerId: string, returnUrl: string): Creates billing portalretrieveSubscription(subscriptionId: string): Gets subscription from StripeupdateSubscription(subscriptionId: string, data: UpdateSubscriptionData): Updates in Stripe
Known Limitations
- Webhook events are processed synchronously (no retry mechanism)
- No support for subscription proration when changing plans
- Limited error handling for Stripe API failures
- No subscription analytics or reporting
- Single currency support (USD only)
- No support for usage-based billing
Notes and TODOs
ā Completed Features
- ā Modular architecture with separated concerns
- ā Checkout session creation for new subscriptions
- ā Billing portal integration for existing customers
- ā Webhook handling for subscription lifecycle events
- ā Multi-tier pricing with monthly/yearly options
- ā Subscription status detection and plan matching
- ā Type-safe interfaces throughout the system
- ā Pure utility functions for business logic
- ā Centralized error handling patterns
š In Progress
- š Add comprehensive error handling and retry mechanisms
- š Implement subscription analytics and reporting
- š Add support for multiple currencies
š Future Enhancements
- š Add support for proration when changing plans
- š Implement subscription cancellation grace periods
- š Add usage-based billing for higher tiers
- š Consider adding trial periods for new users
- š Add subscription metrics and monitoring
- š Implement subscription pause/resume functionality
- š Add support for subscription add-ons and upgrades