Neon: Serverless PostgreSQL
Neon separates compute from storage, enabling scale-to-zero (pay nothing when idle) and instant database branching.
Key Features
- Scale to zero: Pause after inactivity, resume in ~500ms
- Branching: Create point-in-time database copies in seconds
- Autoscaling: 0.25 to 16 CUs automatically
- Read replicas: Instantly create read replicas
Connection
import { neon } from '@neondatabase/serverless'
// Direct connection (for edge/serverless)
const sql = neon(process.env.DATABASE_URL!)
const users = await sql`SELECT * FROM users LIMIT 10`
const user = await sql`SELECT * FROM users WHERE id = ${userId}`
// With transactions
const result = await sql.transaction([
sql`INSERT INTO orders (user_id, total) VALUES (${userId}, ${total})`,
sql`UPDATE users SET order_count = order_count + 1 WHERE id = ${userId}`,
])
// With pg (for connection pooling)
import { Pool } from 'pg'
import { neonConfig } from '@neondatabase/serverless'
import ws from 'ws'
neonConfig.webSocketConstructor = ws // Required for Node.js
const pool = new Pool({
connectionString: process.env.DATABASE_URL,
ssl: true,
})
Database Branching
# Install Neon CLI
npm install -g neonctl
# Create branch for feature development
neonctl branches create --name feature/new-schema --parent main
# Get connection string for branch
neonctl connection-string feature/new-schema
# Delete branch after merge
neonctl branches delete feature/new-schema
// Environment-aware branching in CI/CD
const DATABASE_URL = process.env.CI
? process.env.NEON_BRANCH_URL // Branch for this PR
: process.env.DATABASE_URL // Main database
Next.js App Router Integration
// lib/db.ts
import { neon } from '@neondatabase/serverless'
import { drizzle } from 'drizzle-orm/neon-http'
import * as schema from './schema'
const sql = neon(process.env.DATABASE_URL!)
export const db = drizzle(sql, { schema })
// app/api/users/route.ts
import { db } from '@/lib/db'
import { users } from '@/lib/schema'
export async function GET() {
const allUsers = await db.select().from(users).limit(20)
return Response.json(allUsers)
}
Cold Start Optimization
// Neon wakes up in ~500ms on first connection
// Use connection pooler URL (pooler.neon.tech) to maintain warm connections
const sql = neon(process.env.DATABASE_POOLER_URL!) // Use pooler endpoint
// Pre-warm: ping on app startup
await sql`SELECT 1`
Cost Model
| Usage | Cost |
|---|---|
| Compute (paused) | $0 |
| Compute (running) | $0.102/hour per CU |
| Storage | $0.000164/GiB-hour |
| Free tier | 0.5 CU, 3 GiB storage |
Perfect for: preview deployments, development, low-traffic projects.