If you’ve been thinking of building a full-stack web app that’s scalable, fast, and modern, this tech stack trio is the dream team:
Next.js + Supabase + Stripe.
In this guide, I’ll walk you through how to build a full-stack application using these tools — even if you’re just getting started.
Whether you're building a SaaS product, an e-commerce platform, or a subscription-based app, this stack covers it all.
Let’s build something awesome:
Step 1: Set Up the Project
npx create-next-app@latest fullstack-app
cd fullstack-app
npm install
Then install Supabase and Stripe SDKs:
npm install @supabase/supabase-js stripe
Step 2: Connect to Supabase
Create a Supabase project at supabase.com.
Inside the dashboard:
- Create a table (e.g. users or products)
- Enable Auth (Email/Password or OAuth)
Now create a .env.local file in your Next.js app:
NEXT_PUBLIC_SUPABASE_URL=your_supabase_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_supabase_anon_key
And initialize it:
// lib/supabase.js
import { createClient } from '@supabase/supabase-js'
const supabase = createClient(
process.env.NEXT_PUBLIC_SUPABASE_URL,
process.env.NEXT_PUBLIC_SUPABASE_ANON_KEY
)
export default supabase
Step 3: Set Up Auth in Next.js
Create a simple sign-up/login page:
// pages/auth.js
import supabase from '../lib/supabase'
export default function Auth() {
const handleLogin = async () => {
const { user, error } = await supabase.auth.signInWithPassword({
email: '[email protected]',
password: 'password123'
})
console.log(user, error)
}
return Login
}
Step 4: Integrate Stripe Payments
Go to Stripe Dashboard and get your API keys.
Add them to .env.local:
STRIPE_SECRET_KEY=your_stripe_secret
NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY=your_publishable_key
Install stripe on the server:
npm install stripe
Create an API route in pages/api/create-checkout-session.js:
import Stripe from 'stripe'
const stripe = new Stripe(process.env.STRIPE_SECRET_KEY)
export default async function handler(req, res) {
const session = await stripe.checkout.sessions.create({
payment_method_types: ['card'],
line_items: [{
price_data: {
currency: 'usd',
product_data: { name: 'Pro Plan' },
unit_amount: 1000,
},
quantity: 1,
}],
mode: 'payment',
success_url: `${req.headers.origin}/success`,
cancel_url: `${req.headers.origin}/cancel`,
})
res.status(200).json({ id: session.id })
}
Then trigger checkout from your client:
// pages/checkout.js
import { loadStripe } from '@stripe/stripe-js'
const stripePromise = loadStripe(process.env.NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY)
export default function Checkout() {
const handleClick = async () => {
const res = await fetch('/api/create-checkout-session', { method: 'POST' })
const { id } = await res.json()
const stripe = await stripePromise
stripe.redirectToCheckout({ sessionId: id })
}
return Buy Now
}
Final Thoughts
With just a few tools — Next.js, Supabase, and Stripe — you’ve got a full-stack app that can handle:
- Frontend UI & routing
- Authentication & database storage
- Payments & subscriptions
You can scale this into a full SaaS or marketplace with confidence. If you're short on time or want a pro to handle it all, you can always hire full stack developers to bring your vision to life.