Skip to main content
Back to Blog
VercelDeploymentDevOpsNext.jsCI/CDWeb DevelopmentHosting

Vercel Deployment Guide: From Local Development to Production in Minutes

Learn how to deploy web applications to Vercel with this comprehensive guide. Covers Next.js deployment, environment variables, custom domains, preview deployments, edge functions, and production optimization.

7 min read

Vercel has become the go-to platform for deploying modern web applications. Having deployed numerous projects including my portfolio and InsureSignal on Vercel, I've learned the ins and outs of getting the most from this powerful platform. This guide covers everything from your first deployment to advanced production configurations.

Why Vercel?

Before diving in, let's understand why Vercel stands out:

  • Zero configuration - Deploy Next.js apps without any setup
  • Global edge network - Content served from locations nearest to users
  • Preview deployments - Every PR gets its own URL
  • Instant rollbacks - One-click to revert problematic deployments
  • Serverless functions - Backend logic without managing servers
  • Built-in analytics - Performance insights out of the box

Your First Deployment

Method 1: Deploy from Git (Recommended)

The easiest way to deploy is connecting your Git repository:

  1. Go to vercel.com and sign up
  2. Click "Add New Project"
  3. Import your GitHub, GitLab, or Bitbucket repository
  4. Vercel auto-detects your framework and configures build settings
  5. Click "Deploy"

That's it. Your site is live in under a minute.

Method 2: Vercel CLI

For more control, use the Vercel CLI:

# Install globally
npm install -g vercel

# Login
vercel login

# Deploy from project directory
vercel

# Deploy to production
vercel --prod

The CLI is great for:

  • Deploying from CI/CD pipelines
  • Testing deployments before pushing to Git
  • Managing environment variables locally

Framework-Specific Configuration

Next.js (Optimized by Default)

Vercel built Next.js, so deployment is seamless:

// package.json
{
  "scripts": {
    "dev": "next dev",
    "build": "next build",
    "start": "next start"
  }
}

No vercel.json needed. Vercel automatically:

  • Configures Server Components
  • Sets up API routes as serverless functions
  • Enables ISR (Incremental Static Regeneration)
  • Optimizes images

React (Vite/Create React App)

// vercel.json
{
  "buildCommand": "npm run build",
  "outputDirectory": "dist",
  "framework": "vite"
}

For client-side routing:

{
  "rewrites": [
    { "source": "/(.*)", "destination": "/" }
  ]
}

Node.js API

// vercel.json
{
  "functions": {
    "api/**/*.ts": {
      "memory": 1024,
      "maxDuration": 30
    }
  }
}

Environment Variables

Adding Environment Variables

In the Vercel dashboard:

  1. Go to Project Settings > Environment Variables
  2. Add your variables
  3. Choose which environments: Production, Preview, Development
# Example variables
DATABASE_URL=postgresql://...
NEXT_PUBLIC_API_URL=https://api.example.com
STRIPE_SECRET_KEY=sk_live_...

Important: Variables prefixed with NEXT_PUBLIC_ are exposed to the browser.

Using the CLI

# Add a variable
vercel env add DATABASE_URL

# List all variables
vercel env ls

# Pull variables to .env.local
vercel env pull

Different Values Per Environment

Set different values for each environment:

| Variable | Production | Preview | Development | |----------|-----------|---------|-------------| | API_URL | api.example.com | staging-api.example.com | localhost:3001 |

Custom Domains

Adding a Domain

  1. Go to Project Settings > Domains
  2. Add your domain (e.g., example.com)
  3. Configure DNS at your registrar

DNS Configuration:

# For apex domain (example.com)
Type: A
Name: @
Value: 76.76.21.21

# For www subdomain
Type: CNAME
Name: www
Value: cname.vercel-dns.com

Multiple Domains

You can add multiple domains to one project:

  • example.com (primary)
  • www.example.com (redirects to primary)
  • app.example.com (separate subdomain)

Automatic HTTPS

Vercel provisions SSL certificates automatically. No configuration needed.

Preview Deployments

Every push to a non-production branch creates a preview deployment:

https://my-project-git-feature-branch-username.vercel.app

Customizing Preview URLs

// vercel.json
{
  "github": {
    "autoAlias": true
  }
}

Preview Comments

Enable GitHub comments on PRs with deployment previews:

  1. Install the Vercel GitHub app
  2. Enable "Deployment Comments" in project settings

Serverless Functions

Creating API Routes (Next.js)

// app/api/users/route.ts
import { NextResponse } from 'next/server';

export async function GET() {
  const users = await fetchUsers();
  return NextResponse.json(users);
}

export async function POST(request: Request) {
  const data = await request.json();
  const user = await createUser(data);
  return NextResponse.json(user, { status: 201 });
}

Standalone Functions

// api/hello.ts
import type { VercelRequest, VercelResponse } from '@vercel/node';

export default function handler(req: VercelRequest, res: VercelResponse) {
  res.json({ message: 'Hello from Vercel!' });
}

Function Configuration

// vercel.json
{
  "functions": {
    "api/heavy-task.ts": {
      "memory": 3008,
      "maxDuration": 60
    }
  }
}

Edge Functions

For ultra-low latency, use Edge Functions:

// app/api/geo/route.ts
import { NextResponse } from 'next/server';

export const runtime = 'edge';

export async function GET(request: Request) {
  const country = request.headers.get('x-vercel-ip-country') || 'Unknown';
  const city = request.headers.get('x-vercel-ip-city') || 'Unknown';

  return NextResponse.json({ country, city });
}

Edge Functions run at the edge, closest to your users, with:

  • Sub-millisecond cold starts
  • Global distribution
  • Limited runtime (standard Web APIs only)

Build Optimization

Caching Dependencies

Vercel automatically caches node_modules. Speed up builds further:

// vercel.json
{
  "installCommand": "npm ci",
  "buildCommand": "npm run build"
}

Ignoring Builds

Skip unnecessary builds for documentation changes:

// vercel.json
{
  "git": {
    "deploymentEnabled": {
      "main": true,
      "docs/*": false
    }
  }
}

Or use a script:

#!/bin/bash
# vercel-ignore-build.sh

if [[ "$VERCEL_GIT_COMMIT_MESSAGE" == *"[skip ci]"* ]]; then
  echo "Skipping build"
  exit 0
fi

exit 1

Monitoring and Analytics

Web Vitals

// app/layout.tsx
import { SpeedInsights } from '@vercel/speed-insights/next';
import { Analytics } from '@vercel/analytics/react';

export default function RootLayout({ children }) {
  return (
    <html>
      <body>
        {children}
        <Analytics />
        <SpeedInsights />
      </body>
    </html>
  );
}

Logs

View real-time logs in the dashboard or via CLI:

vercel logs your-project.vercel.app

Error Tracking

Integrate with Sentry for error tracking:

npm install @sentry/nextjs
npx @sentry/wizard -i nextjs

Advanced Configuration

Headers and Redirects

// vercel.json
{
  "headers": [
    {
      "source": "/api/(.*)",
      "headers": [
        { "key": "Access-Control-Allow-Origin", "value": "*" },
        { "key": "Cache-Control", "value": "no-store" }
      ]
    },
    {
      "source": "/(.*)",
      "headers": [
        { "key": "X-Frame-Options", "value": "DENY" },
        { "key": "X-Content-Type-Options", "value": "nosniff" }
      ]
    }
  ],
  "redirects": [
    {
      "source": "/old-blog/:slug",
      "destination": "/blog/:slug",
      "permanent": true
    }
  ],
  "rewrites": [
    {
      "source": "/api/:path*",
      "destination": "https://api.backend.com/:path*"
    }
  ]
}

Regional Deployment

Deploy functions to specific regions:

{
  "regions": ["iad1", "sfo1", "cdg1"]
}

Monorepo Support

// vercel.json in root
{
  "buildCommand": "cd packages/web && npm run build",
  "outputDirectory": "packages/web/dist",
  "installCommand": "npm install"
}

Production Checklist

Before going live, verify:

  • [ ] Environment variables set for production
  • [ ] Custom domain configured with SSL
  • [ ] Error pages (404, 500) customized
  • [ ] Analytics and monitoring enabled
  • [ ] Security headers configured
  • [ ] Redirects for old URLs set up
  • [ ] Performance tested with Lighthouse
  • [ ] Database connection pooling configured

Troubleshooting

Common Issues

Build fails with memory error:

{
  "functions": {
    "api/**/*.ts": {
      "memory": 3008
    }
  }
}

Environment variables not loading:

  • Ensure variable names match exactly
  • Redeploy after adding new variables
  • Check if the variable is available in the correct environment

Cold starts too slow:

  • Use Edge Functions for latency-sensitive routes
  • Keep functions small and focused
  • Use connection pooling for databases

Conclusion

Vercel makes deployment a joy rather than a chore. The platform handles the complexity of global distribution, SSL, CI/CD, and scaling while letting you focus on building great products.

I've deployed everything from simple landing pages to complex fintech applications on Vercel, and it consistently delivers excellent performance and developer experience. Start with the basics covered here, and you'll have production-grade deployments in no time.

For more DevOps and deployment content, check out my other blog posts or explore my projects to see Vercel deployments in action.