Self-Hosting
Self-Hosting
Section titled “Self-Hosting”Introduction
Section titled “Introduction”Self-hosting means running your Next.js application on your own infrastructure — a VPS, Docker container, or cloud platform like AWS or Google Cloud.
Why Self-Host?
Section titled “Why Self-Host?”- Full control over infrastructure
- No vendor lock-in
- Custom compliance requirements
- Lower costs at very high scale
Docker Deployment
Section titled “Docker Deployment”Requirement: This Dockerfile requires
output: 'standalone'innext.config.js. Without it, the.next/standalonefolder won’t exist.
Dockerfile
Section titled “Dockerfile”# DockerfileFROM node:20-alpine AS base
# Install dependenciesFROM base AS depsWORKDIR /appCOPY package.json package-lock.json ./RUN npm ci
# BuildFROM base AS builderWORKDIR /appCOPY --from=deps /app/node_modules ./node_modulesCOPY . .RUN npm run build
# ProductionFROM base AS runnerWORKDIR /appENV NODE_ENV=production
COPY --from=builder /app/public ./publicCOPY --from=builder /app/.next/standalone ./COPY --from=builder /app/.next/static ./.next/static
EXPOSE 3000CMD ["node", "server.js"]Docker Compose
Section titled “Docker Compose”version: '3'services: nextjs: build: . ports: - "3000:3000" environment: - DATABASE_URL=postgresql://postgres:password@db:5432/mydb depends_on: - db
db: image: postgres:16 environment: POSTGRES_DB: mydb POSTGRES_PASSWORD: password volumes: - postgres_data:/var/lib/postgresql/data
volumes: postgres_data:Output File Tracing
Section titled “Output File Tracing”For self-hosting, enable output file tracing to reduce deployment size:
module.exports = { output: 'standalone',}This creates a .next/standalone folder with only the files needed to run your app.
Node.js Server
Section titled “Node.js Server”# Buildnpm run build
# Start production servernpm start
# Or specify a portnpx next start -p 8080Reverse Proxy with Nginx
Section titled “Reverse Proxy with Nginx”server { listen 80; server_name example.com;
location / { proxy_pass http://127.0.0.1:3000; proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection 'upgrade'; proxy_set_header Host $host; proxy_cache_bypass $http_upgrade; }}Self-Hosting Flow
Section titled “Self-Hosting Flow”flowchart LR A[Build app] --> B[Generate standalone] B --> C{Docker?} C -->|Yes| D[Build Docker image] C -->|No| E[Copy to server] D --> F[Push to registry] F --> G[Pull on server] E --> G G --> H[Run with Node.js] H --> I[Configure reverse proxy] I --> J[Set up SSL]Common Mistakes
Section titled “Common Mistakes”- Not enabling
output: 'standalone'— Without it, the entirenode_modulesis needed on the server. - Running as root — Always use a non-root user in Docker for security.
- Hardcoding environment variables — Use runtime environment variables, not build-time.
- Not configuring reverse proxy — Without it, you lose features like SSL termination and load balancing.
Best Practices
Section titled “Best Practices”- Use Docker for consistent deployments across environments
- Enable
output: 'standalone'to reduce deployment size - Use a reverse proxy (Nginx, Caddy) for SSL and load balancing
- Set up health checks for container orchestration
- Use environment variables for runtime configuration
Summary
Section titled “Summary”Self-hosting gives you full control. Use Docker with output: 'standalone' for efficient deployments, a reverse proxy for SSL and routing, and environment variables for configuration. Docker Compose simplifies multi-service setups.