BoilerplateHub

Next.js + Turso + Better Auth + Lemon Squeezy

Next.js with Turso, Better Auth and Lemon Squeezy is the licence-key configuration. Lemon Squeezy issues and validates keys, Turso stores activations, and Better Auth provides the account wrapped around them. It suits a paid developer tool, desktop app or API sold to individuals rather than to companies.

Next.js TursoBetter AuthLemon Squeezy

Database

Turso

This is the lightest schema in the set. Turso holds Better Auth's tables and an activation table, and for a downloadable tool or a modest hosted app one database is plenty before per-tenant splitting becomes worth the operational cost. SQLite's simplicity is a genuine asset when the whole billing model reduces to a row stating that this key is valid until this date, refreshed by webhook.

Authentication

Better Auth

Better Auth on SQLite runs the same code path it does on Postgres, so nothing about identity changes; what changes is that the file behind it is small enough to keep as a local replica beside your server. Session validation then resolves without a network hop, which suits a deployment on a long-lived host rather than on functions. The user ID goes into the Lemon Squeezy checkout as custom data exactly as it would anywhere else.

Payments

Lemon Squeezy

Lemon Squeezy's licence key feature is the specific reason to pair it with this database. Keys are issued, activated and deactivated on their side, and Turso stores only the activation record your product checks. For a command line tool, a desktop app or an API sold to individuals, that removes an entire licensing subsystem along with the registrations that come with selling to individuals across many countries.

What to watch out for

Embedded replicas read locally and push writes upstream, so at the instant a webhook grants a licence the local copy in another region can still say no. Someone who pays and immediately presses activate sees a failure. Send access-gating reads to the primary, or sync before checking, and accept that the latency you carefully removed is the latency you need back at precisely this moment.

Boilerplates close to this stack

Matched on Next.js plus the parts of this stack our catalog tags. Each card shows which pieces actually line up, so you can see how much you would still wire yourself.

A CLAUDE.md for this stack

The rules that matter for this combination specifically, including who owns entitlement state. Adapt the commands to your repository before committing it.

CLAUDE.md
# CLAUDE.md

This project is a Next.js SaaS on Turso, Better Auth and Lemon Squeezy.

## Stack

- Framework: Next.js
- Database: Turso
- Auth: Better Auth
- Payments: Lemon Squeezy

## Boundaries

- Never edit a migration that has already run. Write a new one.
- Never hardcode Lemon Squeezy price or product identifiers in components. They belong in config.
- Never trust a client-supplied user id. Read the session from Better Auth on the server.
- Treat webhook handlers as idempotent. The same event will arrive twice.

## Entitlements

- Lemon Squeezy is the source of truth for what a customer paid for.
- The database mirrors that state; it never decides it.
- Any check for "can this user do X" reads the mirrored entitlement, not a live API call.

## Before you say a change is done

- The app builds.
- Tests pass.
- No secret, key or webhook signing secret appears in a committed file.

Related stacks