Tại sao nên quản lý subscription và billing với Supabase và Stripe
Trong thời đại phần mềm SaaS, subscription và billing không chỉ là tính năng phụ - chúng là xương sống của mô hình kinh doanh. Tuy nhiên, nhiều startup thường gặp khó khăn khi phải tự xây dựng hệ thống thanh toán từ đầu, dẫn đến lãng phí thời gian và tiềm ẩn rủi ro bảo mật. Giải pháp tối ưu là kết hợp Supabase - nền tảng backend mạnh mẽ - với Stripe - công cụ thanh toán toàn cầu, giúp triển khai nhanh chóng và an toàn.
Các thành phần cốt lõi của hệ thống
Supabase: Backend linh hoạt và bảo mật
Supabase cung cấp cơ sở dữ liệu PostgreSQL, xác thực người dùng, và API REST/Realtime. Với khả năng mở rộng và tích hợp sẵn Row Level Security (RLS), bạn có thể kiểm soát chặt chẽ ai được xem hay thay đổi dữ liệu subscription.
Stripe: Nền tảng thanh toán toàn cầu
Stripe xử lý mọi khâu từ tạo subscription, quản lý khách hàng, đến thanh toán định kỳ. API mạnh mẽ và dashboard trực quan giúp bạn dễ dàng theo dõi doanh thu và trạng thái thanh toán.
Tích hợp webhook: Cầu nối giữa hai hệ thống
Webhook là chìa khóa để đồng bộ dữ liệu giữa Stripe và Supabase. Mỗi khi có sự kiện thanh toán (thành công, thất bại, gia hạn), Stripe sẽ gửi webhook tới backend của bạn, từ đó cập nhật trạng thái subscription trong database.
Triển khai từng bước
1. Thiết lập database và bảng subscription
Đầu tiên, tạo bảng subscriptions trong Supabase với các cột cần thiết:
- id (khóa chính)
- user_id (liên kết với người dùng)
- stripe_subscription_id (để đồng bộ với Stripe)
- status (active, canceled, past_due)
- plan (gói dịch vụ)
- current_period_end (thời điểm kết thúc kỳ thanh toán hiện tại)
CREATE TABLE subscriptions (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
user_id UUID REFERENCES auth.users NOT NULL,
stripe_subscription_id TEXT UNIQUE,
status TEXT,
plan TEXT,
current_period_end BIGINT,
created_at TIMESTAMP DEFAULT NOW(),
updated_at TIMESTAMP DEFAULT NOW()
);
2. Cấu hình webhook trong Stripe
Trong dashboard Stripe, tạo endpoint webhook trỏ về URL của Supabase (ví dụ: https://your-project.supabase.co/webhooks/stripe). Chọn các sự kiện cần xử lý như:
- invoice.paid
- invoice.payment_failed
- customer.subscription.deleted
- customer.subscription.updated
3. Viết Cloud Function để xử lý webhook
Supabase cho phép viết Cloud Function bằng JavaScript/TypeScript. Function này sẽ lắng nghe webhook, xác thực chữ ký từ Stripe, và cập nhật database:
import { createClient } from '@supabase/supabase-js';
import { stripe } from 'stripe';
const supabase = createClient(process.env.SUPABASE_URL, process.env.SUPABASE_KEY);
const stripe = new stripe(process.env.STRIPE_SECRET_KEY);
export default async function (req, res) {
const sig = req.headers['stripe-signature'];
let event;
try {
event = stripe.webhooks.constructEvent(req.body, sig, process.env.STRIPE_WEBHOOK_SECRET);
} catch (err) {
console.log(err.message);
return res.status(400).send();
}
Quảng cáo
300x250 In-Content Advertisement
switch (event.type) {
case 'invoice.paid':
// Cập nhật subscription thành active
break;
case 'invoice.payment_failed':
// Đánh dấu là past_due
break;
case 'customer.subscription.deleted':
// Cập nhật status thành canceled
break;
// ... các trường hợp khác
}
res.json({ received: true });
}
4. Tích hợp vào frontend
Sử dụng Supabase Auth để xác thực người dùng, và Stripe.js để tạo checkout session. Khi người dùng chọn gói dịch vụ, tạo session và redirect họ tới trang thanh toán của Stripe.
Xử lý lỗi và bảo mật
Xác thực webhook
Luôn xác thực chữ ký webhook từ Stripe để tránh giả mạo. Sử dụng stripe.webhooks.constructEvent với secret key đã cấu hình.
Row Level Security (RLS)
Kích hoạt RLS trong Supabase và viết policy để đảm bảo người dùng chỉ có thể xem subscription của chính họ:
CREATE POLICY "Users can view their own subscriptions" ON subscriptions
FOR SELECT USING (auth.uid() = user_id);
Retry logic cho webhook
Webhook có thể thất bại do mạng hay lỗi logic. Stripe sẽ tự động retry trong 3 ngày, nhưng bạn nên log lại mỗi sự kiện để dễ debug và có thể trigger lại thủ công nếu cần.
Mẹo tối ưu và mở rộng
Dùng Stripe Billing
Nếu có nhiều gói dịch vụ, hãy tận dụng Stripe Billing để tự động tạo và quản lý subscription, giảm thiểu code thủ công.
Đồng bộ offline
Với ứng dụng mobile, lưu trữ subscription status trên local storage và đồng bộ khi online để tránh gián đoạn trải nghiệm.
Dashboard analytics
Tạo dashboard trong Supabase để theo dõi doanh thu, tỷ lệ churn, và trạng thái subscription theo thời gian thực.
Kết luận
Kết hợp Supabase và Stripe giúp bạn xây dựng hệ thống subscription và billing nhanh chóng, bảo mật, và dễ mở rộng. Thay vì mất hàng tháng để tự phát triển, bạn có thể triển khai chỉ trong vài tuần và tập trung vào việc phát triển sản phẩm cốt lõi. Điều quan trọng là luôn xử lý lỗi một cách chủ động và bảo mật dữ liệu người dùng ở mức cao nhất.