¿Por qué Vercel para Next.js?
Vercel es la plataforma creada por el mismo equipo detrás de Next.js, lo que garantiza una integración de primera clase. No es la única opción para desplegar aplicaciones Next.js, pero sí la que ofrece la experiencia más fluida y optimizada.
Estas son las razones principales por las que Vercel destaca para proyectos Next.js 16:
- Zero-config deployment: Conecta tu repositorio y Vercel detecta automáticamente que es un proyecto Next.js, configurando el build sin intervención manual.
- Edge Network global: Tu contenido se sirve desde más de 100 puntos de presencia (PoPs) en todo el mundo, minimizando la latencia.
- Soporte nativo para ISR: La Incremental Static Regeneration funciona de forma transparente, incluyendo la revalidación on-demand.
- Preview Deployments: Cada pull request genera un entorno de preview único con su propia URL.
- Edge Functions y Middleware: Ejecuta lógica en el edge sin cold starts, ideal para detección de locale, A/B testing y más.
- Analytics integrado: Monitoriza Web Vitals y rendimiento real de usuarios sin herramientas externas.
Nota: Aunque esta guía se centra en Vercel, Next.js 16 también puede desplegarse en otras plataformas como AWS Amplify, Netlify, Cloudflare Pages o servidores propios con Node.js.
Configuración del proyecto
Antes del primer despliegue, es buena práctica configurar algunos aspectos del proyecto. Aunque Vercel funciona sin archivo de configuración, puedes crear un vercel.json para ajustes específicos:
// vercel.json
{
"framework": "nextjs",
"buildCommand": "npm run build",
"installCommand": "npm install",
"regions": ["cdg1"],
"headers": [
{
"source": "/(.*)",
"headers": [
{
"key": "X-Content-Type-Options",
"value": "nosniff"
},
{
"key": "X-Frame-Options",
"value": "DENY"
},
{
"key": "X-XSS-Protection",
"value": "1; mode=block"
},
{
"key": "Referrer-Policy",
"value": "strict-origin-when-cross-origin"
}
]
},
{
"source": "/(.*)\.(js|css|woff2|png|jpg|svg|ico)",
"headers": [
{
"key": "Cache-Control",
"value": "public, max-age=31536000, immutable"
}
]
}
],
"redirects": [
{
"source": "/old-page",
"destination": "/new-page",
"statusCode": 301
}
]
}
La opción regions te permite elegir la región principal donde se ejecutan tus Serverless Functions. Para un sitio orientado a España y Europa, cdg1 (París) es una excelente elección.
Configuración de Next.js para producción
Asegúrate de que tu next.config.ts está optimizado para producción:
// next.config.ts
import createNextIntlPlugin from "next-intl/plugin";
const withNextIntl = createNextIntlPlugin();
const nextConfig = {
// Optimización de imágenes
images: {
remotePatterns: [
{
protocol: "https",
hostname: "**.example.com",
},
],
formats: ["image/avif", "image/webp"],
},
// Headers de seguridad
async headers() {
return [
{
source: "/(.*)",
headers: [
{
key: "Strict-Transport-Security",
value: "max-age=63072000; includeSubDomains; preload",
},
],
},
];
},
// Compresión y optimización
compress: true,
poweredByHeader: false,
// Análisis de bundle (solo desarrollo)
...(process.env.ANALYZE === "true" && {
experimental: {
bundlePagesExternals: true,
},
}),
};
export default withNextIntl(nextConfig);Primer despliegue
El proceso de primer despliegue en Vercel es sorprendentemente sencillo. Puedes hacerlo desde la interfaz web o desde la CLI:
Desde la interfaz web
- Crea una cuenta en vercel.com (puedes usar tu cuenta de GitHub).
- Haz clic en Add New Project.
- Importa tu repositorio de GitHub, GitLab o Bitbucket.
- Vercel detectará automáticamente que es un proyecto Next.js.
- Configura las variables de entorno necesarias.
- Haz clic en Deploy.
Desde la CLI
La CLI de Vercel te permite desplegar directamente desde tu terminal:
# Instalar la CLI de Vercel
npm install -g vercel
# Iniciar sesión
vercel login
# Primer despliegue (te guiará con preguntas interactivas)
vercel
# Despliegue a producción
vercel --prod
# Ver el estado del despliegue
vercel lsEn el primer despliegue, la CLI te preguntará por el nombre del proyecto, el directorio raíz y si quieres vincular a un proyecto existente o crear uno nuevo.
Configurar un dominio personalizado
Una vez desplegado, puedes añadir tu dominio personalizado:
# Añadir dominio
vercel domains add tusitio.com
# Verificar la configuración DNS
vercel domains inspect tusitio.comVercel genera automáticamente certificados SSL con Let's Encrypt y los renueva sin intervención. También configura la redirección de HTTP a HTTPS y de www a non-www (o viceversa) según tu preferencia.
ISR y revalidación
La Incremental Static Regeneration (ISR) es una de las funcionalidades más potentes de Next.js en Vercel. Permite servir páginas estáticas que se regeneran en segundo plano después de un intervalo configurable.
ISR basado en tiempo
Configura la revalidación en tu página o layout exportando la constante revalidate:
// app/[locale]/page.tsx
export const revalidate = 86400; // Revalidar cada 24 horas (en segundos)
export default async function HomePage() {
const data = await fetchHomeData();
return (
<main>
<h1>{data.title}</h1>
{/* contenido */}
</main>
);
}Con esta configuración, la primera petición después de 24 horas activará una regeneración en segundo plano. Los usuarios siempre ven la versión cacheada mientras se genera la nueva versión.
Revalidación on-demand
Para casos donde necesitas actualizar el contenido inmediatamente (por ejemplo, al publicar un nuevo artículo desde un CMS), usa la revalidación on-demand:
// app/api/revalidate/route.ts
import { revalidatePath, revalidateTag } from "next/cache";
import { NextRequest, NextResponse } from "next/server";
export async function POST(request: NextRequest) {
const { searchParams } = request.nextUrl;
const secret = searchParams.get("secret");
// Verificar el secreto de revalidación
if (secret !== process.env.REVALIDATION_SECRET) {
return NextResponse.json(
{ error: "Token de revalidación inválido" },
{ status: 401 }
);
}
const path = searchParams.get("path");
const tag = searchParams.get("tag");
try {
if (tag) {
// Revalidar por tag (recomendado)
revalidateTag(tag);
return NextResponse.json({ revalidated: true, tag });
}
if (path) {
// Revalidar por ruta
revalidatePath(path);
return NextResponse.json({ revalidated: true, path });
}
return NextResponse.json(
{ error: "Especifica un path o tag" },
{ status: 400 }
);
} catch (error) {
return NextResponse.json(
{ error: "Error al revalidar" },
{ status: 500 }
);
}
}# Revalidar una ruta específica
curl -X POST "https://tusitio.com/api/revalidate?secret=tu-secreto&path=/es/blog"
# Revalidar por tag
curl -X POST "https://tusitio.com/api/revalidate?secret=tu-secreto&tag=blog-posts"Edge Functions y Middleware
Las Edge Functions de Vercel ejecutan código en el edge de la CDN, lo más cerca posible del usuario. El middleware de Next.js se ejecuta como una Edge Function automáticamente.
Casos de uso ideales para Edge Functions y Middleware:
- Detección de locale: Redirigir al usuario al idioma correcto basándose en su ubicación o cabecera
Accept-Language. - Autenticación: Verificar tokens JWT o cookies de sesión antes de servir contenido protegido.
- A/B testing: Asignar variantes de experimentos sin latencia adicional.
- Rate limiting: Limitar el número de peticiones por IP.
- Geolocalización: Personalizar contenido según la ubicación del usuario.
// middleware.ts — Ejemplo con detección de locale y geolocalización
import createMiddleware from "next-intl/middleware";
import { NextRequest, NextResponse } from "next/server";
import { routing } from "./i18n/routing";
const intlMiddleware = createMiddleware(routing);
export default function middleware(request: NextRequest) {
// Acceder a datos de geolocalización de Vercel
const country = request.geo?.country || "ES";
const city = request.geo?.city || "Unknown";
// Log de analytics en el edge
console.log(`Request from ${city}, ${country}`);
// Bloquear regiones específicas si es necesario
const blockedCountries = ["XX"];
if (blockedCountries.includes(country)) {
return new NextResponse("Access denied", { status: 403 });
}
// Añadir headers personalizados
const response = intlMiddleware(request);
response.headers.set("X-User-Country", country);
return response;
}
export const config = {
matcher: ["/((?!api|_next|_vercel|.*\..*).*)", "/"],
};Importante: Las Edge Functions tienen restricciones: no pueden usar APIs de Node.js completas (como
fs) y tienen un límite de ejecución de 30 segundos. Para operaciones pesadas, usa Serverless Functions estándar.
Optimización de imágenes
El componente next/image se integra con el servicio de optimización de imágenes de Vercel de forma transparente. Las imágenes se optimizan automáticamente en formato WebP o AVIF, se redimensionan al tamaño correcto y se sirven desde la CDN.
// Ejemplo de uso optimizado de next/image
import Image from "next/image";
export default function ProjectCard({
title,
image,
}: {
title: string;
image: string;
}) {
return (
<article className="group relative overflow-hidden rounded-xl">
<Image
src={image}
alt={title}
width={800}
height={450}
className="object-cover transition-transform duration-300
group-hover:scale-105"
sizes="(max-width: 768px) 100vw, (max-width: 1200px) 50vw, 33vw"
placeholder="blur"
blurDataURL="data:image/png;base64,iVBORw0KGgoAAAANSUhEUg..."
quality={85}
/>
<div className="absolute inset-0 bg-gradient-to-t from-black/60">
<h3 className="absolute bottom-4 left-4 text-white text-xl font-bold">
{title}
</h3>
</div>
</article>
);
}Consejos para la optimización de imágenes en Vercel:
- Usa siempre
sizes: Indica al navegador qué tamaño de imagen necesita en cada breakpoint, evitando descargar imágenes más grandes de lo necesario. - Prioriza las imágenes above-fold: Añade
prioritya las imágenes visibles sin scroll (hero, logo, banner principal). - Usa placeholder blur: Genera un blur data URL para mostrar una vista previa mientras se carga la imagen real.
- Configura formatos modernos: En
next.config.ts, habilita AVIF además de WebP para navegadores compatibles. - Establece un
qualityrazonable: Un valor entre 75 y 85 ofrece el mejor balance entre calidad visual y tamaño del archivo.
// next.config.ts — Configuración avanzada de imágenes
const nextConfig = {
images: {
formats: ["image/avif", "image/webp"],
deviceSizes: [640, 750, 828, 1080, 1200, 1920, 2048],
imageSizes: [16, 32, 48, 64, 96, 128, 256, 384],
minimumCacheTTL: 60 * 60 * 24 * 30, // 30 días
remotePatterns: [
{
protocol: "https",
hostname: "images.unsplash.com",
},
{
protocol: "https",
hostname: "**.cloudinary.com",
},
],
},
};Analytics y Web Vitals
Vercel ofrece un sistema de analytics integrado que monitoriza las Core Web Vitals de tu sitio con datos reales de usuarios (RUM - Real User Monitoring).
Instalar Vercel Analytics
npm install @vercel/analytics @vercel/speed-insights// app/[locale]/layout.tsx
import { Analytics } from "@vercel/analytics/react";
import { SpeedInsights } from "@vercel/speed-insights/next";
export default async function LocaleLayout({
children,
params,
}: {
children: React.ReactNode;
params: Promise<{ locale: string }>;
}) {
const { locale } = await params;
return (
<html lang={locale}>
<body>
{children}
<Analytics />
<SpeedInsights />
</body>
</html>
);
}Las métricas que monitoriza Vercel Analytics incluyen:
- LCP (Largest Contentful Paint): Tiempo de carga del contenido principal. Objetivo: < 2.5s.
- FID (First Input Delay): Tiempo de respuesta a la primera interacción. Objetivo: < 100ms.
- CLS (Cumulative Layout Shift): Estabilidad visual durante la carga. Objetivo: < 0.1.
- INP (Interaction to Next Paint): Latencia de interacciones. Objetivo: < 200ms.
- TTFB (Time to First Byte): Tiempo de respuesta del servidor. Objetivo: < 800ms.
Eventos personalizados
Además de las métricas automáticas, puedes enviar eventos personalizados:
"use client";
import { track } from "@vercel/analytics";
export default function CTAButton() {
return (
<button
onClick={() => {
track("cta_clicked", {
location: "hero",
variant: "primary",
});
}}
className="bg-sky-900 text-white px-8 py-4 rounded-lg"
>
Ver proyectos
</button>
);
}Variables de entorno
Vercel ofrece un sistema robusto para gestionar variables de entorno con tres scopes diferentes:
- Production: Solo se aplican al despliegue de producción (rama main/master).
- Preview: Se aplican a todos los despliegues de preview (pull requests, ramas).
- Development: Se descargan con
vercel env pullpara desarrollo local.
# Añadir una variable de entorno
vercel env add MAILJET_API_KEY production
# Listar variables configuradas
vercel env ls
# Descargar variables de desarrollo a .env.local
vercel env pull .env.localBuenas prácticas para variables de entorno en Vercel:
- Nunca expongas secretos al cliente: Solo las variables con prefijo
NEXT_PUBLIC_son accesibles desde el navegador. Las claves API, secretos de webhook y credenciales deben ser variables de servidor. - Usa valores diferentes por entorno: Configura claves de test para Preview y claves de producción para Production.
- Rotación de secretos: Vercel permite actualizar variables sin redesplegar. Los cambios se aplican en el siguiente despliegue o revalidación.
- Variables sensibles: Vercel cifra las variables de entorno y las inyecta en el entorno de ejecución de forma segura.
// environment.d.ts — Tipar las variables de entorno
declare namespace NodeJS {
interface ProcessEnv {
// Variables de servidor (secretas)
MAILJET_API_KEY: string;
MAILJET_API_SECRET: string;
MAILJET_SENDER_EMAIL: string;
REVALIDATION_SECRET: string;
// Variables de cliente (públicas)
NEXT_PUBLIC_ENABLE_CONTACT_FORM: string;
NEXT_PUBLIC_GA_MEASUREMENT_ID: string;
}
}Preview Deployments
Una de las funcionalidades más valiosas de Vercel es el sistema de Preview Deployments. Cada vez que abres un pull request o haces push a una rama, Vercel genera automáticamente un despliegue de preview con una URL única.
Ventajas de los Preview Deployments:
- URL única por commit: Cada push genera una nueva URL, lo que permite comparar versiones.
- Comentarios en PR: El bot de Vercel añade un comentario al PR con la URL de preview y el estado del build.
- Variables de entorno separadas: Los previews usan variables de entorno de Preview, no de Production.
- Protección con contraseña: Puedes proteger los previews con autenticación para proyectos privados.
- Checks de GitHub: El estado del despliegue aparece como un check en el PR.
# Desplegar una rama específica como preview
vercel
# Promover un preview a producción
vercel promote [deployment-url]
# Inspeccionar un despliegue
vercel inspect [deployment-url]Proteger Preview Deployments
Para proyectos que manejan datos sensibles, puedes configurar Vercel Authentication en los previews:
// vercel.json
{
"vercelAuthentication": {
"deployment": "standard-protection"
}
}Esto requiere que los usuarios inicien sesión con su cuenta de Vercel para acceder a los previews, asegurando que solo los miembros del equipo puedan ver el contenido antes de publicarlo.
Checklist de producción
Antes de lanzar tu aplicación Next.js 16 en Vercel, revisa esta checklist completa:
Rendimiento
- Ejecuta
npm run buildlocalmente y verifica que no hay errores ni warnings. - Verifica las Core Web Vitals con Lighthouse y asegúrate de que todas están en verde.
- Comprueba que las imágenes above-fold tienen el atributo
priority. - Revisa que el bundle size es razonable con
@next/bundle-analyzer. - Confirma que las páginas estáticas están marcadas con
force-staticorevalidate.
Seguridad
- Verifica que las variables de entorno sensibles no tienen prefijo
NEXT_PUBLIC_. - Comprueba que los headers de seguridad están configurados (HSTS, X-Frame-Options, CSP).
- Valida que los formularios sanitizan inputs en el servidor.
- Confirma que las API routes validan y autentican correctamente.
- Revisa que
.envestá en.gitignore.
SEO y accesibilidad
- Verifica los metadatos de cada página (title, description, Open Graph).
- Comprueba que las etiquetas
hreflangestán configuradas para cada idioma. - Genera el
sitemap.xmlyrobots.txt. - Ejecuta un audit de accesibilidad con axe DevTools.
- Verifica la navegación por teclado en todos los componentes interactivos.
Monitorización
- Configura
@vercel/analyticsy@vercel/speed-insights. - Configura alertas para errores en producción.
- Establece un baseline de rendimiento y monitoriza las regresiones.
- Configura Google Search Console para cada dominio/idioma.
Despliegue
- Configura el dominio personalizado con certificado SSL.
- Verifica los redirects de www y HTTP a HTTPS.
- Configura las variables de entorno de producción en Vercel.
- Haz un despliegue final y verifica la URL de producción.
- Comprueba que los webhooks y APIs externas apuntan a la URL de producción.
Consejo final: Vercel hace que desplegar Next.js sea casi trivial, pero no subestimes la importancia de la configuración correcta. Invierte tiempo en optimizar imágenes, configurar ISR apropiadamente y monitorizar el rendimiento real. Un despliegue rápido no garantiza una experiencia rápida para tus usuarios.