How to add a cart and checkout to an existing Next.js site
- Type
- Applies to
- Medusa v2.x
- Updated
Short answer
To add a cart and checkout to an existing Next.js site and keep your own design, connect it to a commerce backend such as Medusa. Medusa runs as a separate Node.js app with PostgreSQL, which Medusa Cloud hosts from $29/month. Your Next.js app calls it through the @medusajs/js-sdk package for carts, shipping, Stripe payments, and orders.
Three ways to add a cart and checkout to a Next.js site
You have three realistic options when you have a Next.js site for your brand and want to sell about 50 products while keeping your own design: a drop-in cart (Snipcart or the Shopify Buy Button), payments only (Stripe Checkout), or a commerce backend such as Medusa. They differ in who owns the checkout UI and who stores products, stock, and orders.
Do I need a separate backend to sell from Next.js with Medusa?
Yes. Medusa is a separate Node.js application backed by a PostgreSQL database, and your Next.js app talks to it over HTTP through the Store API. Medusa only supports PostgreSQL as its database, according to the architecture docs.
You don't have to run that backend yourself. Medusa Cloud hosts the Medusa server, admin dashboard, PostgreSQL, and file storage on every plan, adds managed Redis from the Launch plan, and can also host a Next.js storefront kept in the same monorepo. Plans start at $29/month (Develop), with Launch at $99 and Scale at $299, and every plan has a 0% GMV fee. If your Next.js app stays on another host, it calls the Medusa backend by URL.
Before you start
- A Next.js app (App Router works with server actions).
- A Medusa application, created on Medusa Cloud or locally with Copy to clipboard
npx create-medusa-app@latest. - A Stripe account with secret and publishable keys.
1. Create the Medusa backend and add products
Create a project on Medusa Cloud, or install Medusa locally. Then add your products, a region with its currency, and shipping options in the Medusa Admin. For about 50 products, entering them in the admin or importing a CSV is enough.
2. Install the JS SDK in your Next.js app
The Copy to clipboard@medusajs/js-sdk package wraps Medusa's Store API. Store requests need a publishable API key, which you create in the Medusa Admin and which scopes requests to a sales channel. Add your Next.js origin to the backend's Copy to clipboardSTORE_CORS setting.
1234567// lib/sdk.ts (npm install @medusajs/js-sdk @medusajs/types)import Medusa from "@medusajs/js-sdk"export const sdk = new Medusa({baseUrl: process.env.NEXT_PUBLIC_MEDUSA_BACKEND_URL!,publishableKey: process.env.NEXT_PUBLIC_MEDUSA_PUBLISHABLE_KEY,})
3. Add cart server actions
Next.js server actions keep cart logic on the server. Medusa's Next.js Starter Storefront uses the same pattern, storing the cart ID in a cookie. Create the cart with Copy to clipboardsdk.store.cart.create({ region_id }), then add items:
12345678910"use server"import { sdk } from "@/lib/sdk"export async function addToCart(cartId: string, variantId: string) {const { cart } = await sdk.store.cart.createLineItem(cartId, {variant_id: variantId,quantity: 1,})return cart}
4. Build the checkout steps
Medusa's checkout runs on the cart: set the email and addresses with Copy to clipboardsdk.store.cart.update, list shipping options with Copy to clipboardsdk.store.fulfillment.listCartOptions, and pick one with Copy to clipboardsdk.store.cart.addShippingMethod. Each step is a form in your own design. The checkout guides cover each call.
5. Take payment with Stripe and place the order
Register the Stripe Module Provider in Copy to clipboardmedusa-config.ts and enable it in your region. In the storefront, call Copy to clipboardsdk.store.payment.initiatePaymentSession(cart, { provider_id: "pp_stripe_stripe" }), render Stripe's card form with the returned client secret, then call Copy to clipboardsdk.store.cart.complete(cart.id). A response with Copy to clipboardtype: "order" means the order was placed. The Stripe storefront guide has the full component.
When Medusa is not the right choice
- You have no developer and want to start selling this week: a drop-in cart or the Shopify Buy Button needs no backend.
- You sell a few digital products or one subscription: Stripe Checkout alone may cover it.
- You want zero hosting cost at very low volume: a Medusa backend is an extra service, even on Medusa Cloud.
Medusa fits when you want your own checkout design, plan to grow past a simple catalog, or need inventory, promotions, returns, and multiple regions without per-transaction platform fees.
Common questions
Do I need a separate backend to use Medusa with Next.js?
Yes. Medusa is a separate Node.js application that uses PostgreSQL as its database, and your Next.js app calls its Store API. Medusa Cloud hosts the backend, admin, and database for you, adds managed Redis from the Launch plan, and can host a Next.js storefront kept in the same monorepo.
Does Medusa work with the Next.js App Router and server actions?
Yes. Medusa's Next.js Starter Storefront calls the JS SDK from server actions in a "use server" file, for example to create carts, add line items, and complete the cart.
Is Medusa a Snipcart alternative?
Medusa covers the same need differently. Snipcart adds its own cart UI through a script tag and charges 2% per transaction, while Medusa is a commerce backend with no transaction fee where you build the cart and checkout UI yourself.
Can I start from a template instead of my existing Next.js app?
Yes. Running npx create-medusa-app@latest --with-nextjs-starter installs a Medusa backend and the Next.js Starter Storefront in one monorepo. Medusa Cloud also offers starters with a Next.js storefront.