BackVolver al blog

Next.js 13

Next.js 13 introduce diseños (layouts), Componentes del Servidor de React y streaming en el directorio app, además de Turbopack, un componente de imagen mejorado y el nuevo componente de fuentes.

Como anunciamos en Next.js Conf, Next.js 13 (estable) sienta las bases para ser dinámico sin límites:

Next.js 13 y el directorio pages son estables y listos para producción. Actualiza hoy ejecutando:

Terminal
npm i next@latest react@latest react-dom@latest eslint-config-next@latest

Nuevo directorio app (Beta)

Hoy mejoramos la experiencia de enrutamiento y diseños en Next.js alineándonos con el futuro de React mediante la introducción del directorio app. Esto es un seguimiento al RFC de Layouts publicado previamente para recibir comentarios de la comunidad.

El directorio app está actualmente en beta y no recomendamos usarlo en producción todavía. Puedes usar Next.js 13 con el directorio pages con funciones estables como los componentes mejorados next/image y next/link, y adoptar el directorio app a tu propio ritmo. El directorio pages seguirá siendo compatible en el futuro previsible.

El directorio app incluye soporte para:

  • Diseños (Layouts): Comparte UI entre rutas manteniendo el estado y evitando re-renderizados costosos.
  • Componentes del Servidor: Haciendo que "servidor-primero" sea el predeterminado para aplicaciones dinámicas.
  • Streaming: Muestra estados de carga instantáneos y transmite unidades de UI según se renderizan.
  • Soporte para obtención de datos: Componentes del Servidor async y API fetch extendida permiten obtención de datos a nivel de componente.

El directorio app puede adoptarse incrementalmente desde tu directorio pages/ existente.

El directorio app puede adoptarse incrementalmente desde tu directorio pages/ existente.

Diseños (Layouts)

El directorio app/ facilita la creación de interfaces complejas que mantienen estado entre navegaciones, evitan re-renderizados costosos y permiten patrones de enrutamiento avanzados. Además, puedes anidar diseños y colocar código de la aplicación junto a tus rutas, como componentes, tests y estilos.

El directorio app/ puede adoptarse incrementalmente desde tu directorio pages/ existente.

El directorio app/ puede adoptarse incrementalmente desde tu directorio pages/ existente.

Crear rutas dentro de app/ requiere un solo archivo, page.js:

app/page.js
// Este archivo corresponde a la ruta índice (/)
export default function Page() {
  return <h1>¡Hola, Next.js!</h1>;
}

Luego puedes definir diseños mediante el sistema de archivos. Los diseños comparten UI entre múltiples páginas. En la navegación, los diseños preservan el estado, permanecen interactivos y no se re-renderizan.

app/blog/layout.js
export default function BlogLayout({ children }) {
  return <section>{children}</section>;
}

Aprende más sobre diseños y páginas o implementa un ejemplo para probarlo.

Componentes del Servidor

El directorio app/ introduce soporte para la nueva arquitectura de Componentes del Servidor de React. Los Componentes del Servidor y Componentes del Cliente usan el servidor y el cliente para lo que cada uno hace mejor - permitiéndote construir aplicaciones rápidas y altamente interactivas con un único modelo de programación que ofrece una gran experiencia de desarrollo.

Con Componentes del Servidor, sentamos las bases para construir interfaces complejas reduciendo la cantidad de JavaScript enviado al cliente, permitiendo cargas iniciales de página más rápidas.

Cuando se carga una ruta, el tiempo de ejecución de Next.js y React se cargará, el cual es almacenable en caché y de tamaño predecible. Este tiempo de ejecución no aumenta de tamaño a medida que crece tu aplicación. Además, el tiempo de ejecución se carga de forma asíncrona, permitiendo que tu HTML del servidor se mejore progresivamente en el cliente.

Aprende más sobre Componentes del Servidor o implementa un ejemplo para probarlo.

Streaming

El directorio app/ introduce la capacidad de renderizar progresivamente y transmitir incrementalmente unidades renderizadas de la UI al cliente.

Con Componentes del Servidor y diseños anidados en Next.js, puedes renderizar instantáneamente partes de la página que no requieren datos específicamente, y mostrar un estado de carga para partes de la página que están obteniendo datos. Con este enfoque, el usuario no tiene que esperar a que se cargue toda la página antes de poder interactuar con ella.

Puedes colocar tu código de aplicación, como componentes, tests y estilos, junto a tus rutas.

Puedes colocar tu código de aplicación, como componentes, tests y estilos, junto a tus rutas.

Cuando se implementa en Vercel, las aplicaciones Next.js 13 que usan el directorio app/ transmitirán respuestas por defecto tanto en los entornos de ejecución Node.js como Edge para mejorar el rendimiento.

Aprende más sobre streaming o implementa un ejemplo para probarlo.

Obtención de datos

El reciente RFC de Soporte para Promesas de React introduce una nueva y poderosa forma de obtener datos y manejar promesas dentro de componentes:

app/page.js
async function getData() {
  const res = await fetch('https://api.example.com/...');
  // El valor de retorno *no* está serializado
  // Puedes retornar Date, Map, Set, etc.
  return res.json();
}
 
// Este es un Componente del Servidor async
export default async function Page() {
  const data = await getData();
 
  return <main>{/* ... */}</main>;
}

La API nativa fetch también se ha extendido en React y Next.js. Deduplica automáticamente solicitudes fetch y proporciona una forma flexible de obtener, almacenar en caché y revalidar datos a nivel de componente. Esto significa que todos los beneficios de Generación de Sitios Estáticos (SSG), Renderizado del Lado del Servidor (SSR) y Regeneración Estática Incremental (ISR) están ahora disponibles a través de una sola API:

// Esta solicitud debe almacenarse en caché hasta invalidarse manualmente.
// Similar a `getStaticProps`.
// `force-cache` es el predeterminado y puede omitirse.
fetch(URL, { cache: 'force-cache' });
 
// Esta solicitud debe reobtenerse en cada solicitud.
// Similar a `getServerSideProps`.
fetch(URL, { cache: 'no-store' });
 
// Esta solicitud debe almacenarse en caché con un tiempo de vida de 10 segundos.
// Similar a `getStaticProps` con la opción `revalidate`.
fetch(URL, { next: { revalidate: 10 } });

En el directorio app, puedes obtener datos dentro de diseños, páginas y componentes - incluyendo soporte para respuestas en streaming desde el servidor.

Estamos habilitando formas ergonómicas de manejar estados de carga y error, y transmitir UI según se renderiza. En una futura versión, también mejoraremos y simplificaremos las mutaciones de datos.

Con el directorio app/, puedes usar un nuevo archivo especial loading.js para crear automáticamente UI de Carga Instantánea con límites Suspense.

Con el directorio app/, puedes usar un nuevo archivo especial loading.js para crear automáticamente UI de Carga Instantánea con límites Suspense.

Estamos emocionados de trabajar con la comunidad de código abierto, mantenedores de paquetes y otras empresas que contribuyen al ecosistema React para construir esta nueva era de React y Next.js. La capacidad de colocar la obtención de datos dentro de componentes y enviar menos JavaScript al cliente fueron dos piezas importantes de retroalimentación de la comunidad que estamos emocionados de incluir con el directorio app/.

Aprende más sobre obtención de datos o implementa un ejemplo para probarlo.

Introduciendo Turbopack (Alpha)

Next.js 13 incluye Turbopack, el nuevo sucesor de Webpack basado en Rust.

Webpack ha sido descargado más de 3 mil millones de veces. Si bien ha sido una parte integral de la construcción de la Web, hemos alcanzado los límites del rendimiento máximo posible con herramientas basadas en JavaScript.

En Next.js 12, comenzamos nuestra transición a herramientas nativas basadas en Rust. Comenzamos migrando de Babel, lo que resultó en una transpilación 17x más rápida. Luego, reemplazamos Terser, lo que resultó en una minificación 6x más rápida. Es hora de ir todo a nativo para el empaquetado.

Usar Turbopack alpha con Next.js 13 resulta en:

  • 700x más rápido que Webpack en actualizaciones
  • 10x más rápido que Vite en actualizaciones
  • 4x más rápido que Webpack en arranques en frío

Turbopack es nuestro sucesor de Webpack basado en Rust, con HMR 700x más rápido para aplicaciones grandes.

Turbopack es nuestro sucesor de Webpack basado en Rust, con HMR 700x más rápido para aplicaciones grandes.

Turbopack solo empaqueta los activos mínimos requeridos en desarrollo, por lo que el tiempo de inicio es extremadamente rápido. En una aplicación con 3,000 módulos, Turbopack tarda 1.8 segundos en arrancar. Vite tarda 11.4 segundos y Webpack tarda 16.5 segundos.

Turbopack tiene soporte listo para usar para Componentes del Servidor, TypeScript, JSX, CSS y más. Durante la alpha, muchas características aún no son compatibles. Nos encantaría escuchar tus comentarios sobre usar Turbopack para acelerar tus iteraciones locales.

Nota: Turbopack en Next.js actualmente solo soporta next dev. Consulta las características soportadas. También estamos trabajando para agregar soporte para next build a través de Turbopack.

Prueba Turbopack alpha hoy en Next.js 13 con next dev --turbo.

next/image

Next.js 13 introduce un nuevo y potente componente Image, permitiéndote mostrar imágenes fácilmente sin cambios de diseño y optimizar archivos bajo demanda para mayor rendimiento.

Durante la Encuesta de la Comunidad Next.js, 70% de los encuestados nos dijeron que usaban el componente Image de Next.js en producción, y a su vez, vieron mejoras en Core Web Vitals. Con Next.js 13, estamos mejorando next/image aún más.

El nuevo componente Image:

  • Envía menos JavaScript del lado del cliente
  • Más fácil de estilizar y configurar
  • Más accesible al requerir etiquetas alt por defecto
  • Se alinea con la plataforma Web
  • Más rápido porque la carga diferida nativa no requiere hidratación
app/page.js
import Image from 'next/image';
import avatar from './lee.png';
 
export default function Home() {
  // "alt" ahora es requerido para mejor accesibilidad
  // opcional: archivos de imagen pueden colocarse dentro del directorio app/
  return <Image alt="leeerob" src={avatar} placeholder="blur" />;
}

Aprende más sobre el componente Image o implementa un ejemplo para probarlo.

Actualizando next/image a Next.js 13

El antiguo componente Image fue renombrado a next/legacy/image. Hemos proporcionado un codemod que actualizará automáticamente tu uso existente de next/image a next/legacy/image. Por ejemplo, este comando ejecutaría el codemod en tu directorio ./pages cuando se ejecute desde la raíz:

Terminal
npx @next/codemod next-image-to-legacy-image ./pages

Aprende más sobre el codemod.

@next/font

Next.js 13 introduce un nuevo sistema de fuentes que:

  • Optimiza automáticamente tus fuentes, incluyendo fuentes personalizadas
  • Elimina solicitudes de red externas para mejorar privacidad y rendimiento
  • Autoalojamiento incorporado para cualquier archivo de fuente
  • Cero cambios de diseño automáticamente usando la propiedad CSS size-adjust

Este nuevo sistema de fuentes te permite usar convenientemente todas las Google Fonts con rendimiento y privacidad en mente. Los archivos CSS y de fuentes se descargan en tiempo de compilación y se autoalojan con el resto de tus activos estáticos. No se envían solicitudes a Google desde el navegador.

app/layout.js / pages/_app.js
import { Inter } from '@next/font/google';
 
const inter = Inter();
 
<html className={inter.className}></html>;

También se admiten fuentes personalizadas, incluyendo soporte para autoalojamiento automático, almacenamiento en caché y precarga de archivos de fuentes.

app/layout.js / pages/_app.js
import localFont from '@next/font/local';
 
const myFont = localFont({ src: './my-font.woff2' });
 
<html className={myFont.className}></html>;

Puedes personalizar cada parte de la experiencia de carga de fuentes mientras garantizas un gran rendimiento y sin cambios de diseño, incluyendo font-display, precarga, fallbacks y más.

Aprende más sobre el nuevo componente Font o implementa un ejemplo para probarlo.

next/link ya no requiere agregar manualmente <a> como hijo.

Esto se agregó como una opción experimental en 12.2 y ahora es el predeterminado. En Next.js 13, <Link> siempre renderiza un <a> y te permite reenviar props a la etiqueta subyacente. Por ejemplo:

import Link from 'next/link'
 
// Next.js 12: `<a>` debe anidarse de lo contrario se excluye
<Link href="/about">
  <a>About</a>
</Link>
 
// Next.js 13: `<Link>` siempre renderiza `<a>`
<Link href="/about">
  About
</Link>

Aprende más sobre el componente Link mejorado o implementa un ejemplo para probarlo.

Para actualizar sus enlaces a Next.js 13, hemos proporcionado un codemod que actualizará automáticamente su base de código. Por ejemplo, este comando ejecutaría el codemod en su directorio ./pages cuando se ejecute desde la raíz:

Terminal
npx @next/codemod new-link ./pages

Obtenga más información sobre el codemod o consulte la documentación.

Generación de imágenes OG

Las tarjetas sociales, también conocidas como imágenes de gráficos abiertos (open graph), pueden aumentar masivamente la tasa de participación en los clics de su contenido, con algunos experimentos que muestran hasta un 40% mejor en conversiones.

Las tarjetas sociales estáticas consumen mucho tiempo, son propensas a errores y difíciles de mantener. Por esto, a menudo faltan o incluso se omiten. Hasta hoy, las tarjetas sociales dinámicas que necesitan personalizarse y calcularse sobre la marcha eran difíciles y costosas.

Hemos creado una nueva biblioteca @vercel/og que funciona perfectamente con Next.js para generar tarjetas sociales dinámicas.

pages/api/og.jsx
import { ImageResponse } from '@vercel/og';
 
export const config = {
  runtime: 'experimental-edge',
};
 
export default function () {
  return new ImageResponse(
    (
      <div
        style={{
          display: 'flex',
          fontSize: 128,
          background: 'white',
          width: '100%',
          height: '100%',
        }}
      >
        Hello, World!
      </div>
    ),
  );
}

Este enfoque es 5 veces más rápido que las soluciones existentes al utilizar Vercel Edge Functions, WebAssembly y una nueva biblioteca central para convertir HTML y CSS en imágenes, aprovechando la abstracción de componentes de React.

Obtenga más información sobre la generación de imágenes OG o implemente un ejemplo para probarlo.

Actualizaciones de la API de Middleware

En Next.js 12, introdujimos Middleware para permitir una flexibilidad total con el enrutador de Next.js. Hemos escuchado sus comentarios sobre el diseño inicial de la API y hemos agregado algunas adiciones para mejorar la experiencia del desarrollador y añadir funcionalidades nuevas y potentes.

Ahora puede configurar más fácilmente encabezados en la solicitud:

middleware.ts
import { NextResponse } from 'next/server';
import type { NextRequest } from 'next/server';
 
export function middleware(request: NextRequest) {
  // Clonar los encabezados de la solicitud y establecer un nuevo encabezado `x-version`
  const requestHeaders = new Headers(request.headers);
  requestHeaders.set('x-version', '13');
 
  // También puede establecer encabezados de solicitud en NextResponse.rewrite
  const response = NextResponse.next({
    request: {
      // Nuevos encabezados de solicitud
      headers: requestHeaders,
    },
  });
 
  // Establecer un nuevo encabezado de respuesta `x-version`
  response.headers.set('x-version', '13');
  return response;
}

También puede ahora proporcionar una respuesta directamente desde Middleware, sin tener que usar rewrite o redirect.

middleware.ts
import { NextRequest, NextResponse } from 'next/server';
import { isAuthenticated } from '@lib/auth';
 
// Limitar el middleware a rutas que comienzan con `/api/`
export const config = {
  matcher: '/api/:function*',
};
 
export function middleware(request: NextRequest) {
  // Llamar a nuestra función de autenticación para verificar la solicitud
  if (!isAuthenticated(request)) {
    // Responder con JSON indicando un mensaje de error
    return NextResponse.json(
      {
        success: false,
        message: 'Auth failed',
      },
      {
        status: 401,
      },
    );
  }
}

Enviar respuestas desde Middleware actualmente requiere la opción de configuración experimental.allowMiddlewareResponseBody dentro de next.config.js.

Cambios importantes

  • La versión mínima de React ha aumentado de 17.0.2 a 18.2.0.
  • La versión mínima de Node.js ha aumentado de 12.22.0 a 14.6.0, ya que la versión 12.x ha llegado al fin de su vida útil (PR).
  • La propiedad de configuración swcMinify cambió de false a true. Consulte Next.js Compiler para más información.
  • La importación next/image se renombró a next/legacy/image. La importación next/future/image se renombró a next/image. Hay un codemod disponible para renombrar sus importaciones de manera segura y automática.
  • El hijo de next/link ya no puede ser <a>. Agregue la propiedad legacyBehavior para usar el comportamiento heredado o elimine el <a> para actualizar. Hay un codemod disponible para actualizar automáticamente su código.
  • Las rutas ya no se prefetch cuando el User-Agent es un bot.
  • Se ha eliminado la opción obsoleta target de next.config.js.
  • Los navegadores compatibles han cambiado para eliminar Internet Explorer y enfocarse en navegadores modernos. Aún puede usar Browserslist para cambiar los navegadores objetivo.
    • Chrome 64+
    • Edge 79+
    • Firefox 67+
    • Opera 51+
    • Safari 12+

Para obtener más información, consulte la guía de actualización.

Comunidad

Hace seis años, lanzamos Next.js al público. Nos propusimos construir un framework de React de configuración cero que simplifique su experiencia como desarrollador. Mirando atrás, es increíble ver cómo ha crecido la comunidad y lo que hemos podido lanzar juntos. Sigamos adelante.

Next.js es el resultado del trabajo combinado de más de 2,400 desarrolladores individuales, socios de la industria como Google y Meta, y nuestro equipo central. Con más de 3 millones de descargas de npm por semana y 94,000 estrellas en GitHub, Next.js es una de las formas más populares de construir la Web.

Un agradecimiento especial al equipo Aurora de Google Chrome que ayudó con la investigación y los experimentos fundamentales que llevaron a este lanzamiento.

Este lanzamiento fue posible gracias a las contribuciones de: @ijjk, @huozhi, @HaNdTriX, @iKethavel, @timneutkens, @shuding, @rishabhpoddar, @hanneslund, @balazsorban44, @devknoll, @anthonyshew, @TomerAberbach, @philippbosch, @styfle, @mauriciomutte, @hayitsdavid, @abdennor, @Kikobeats, @cjdunteman, @Mr-Afonso, @kdy1, @jaril, @abdallah-nour, @North15, @feedthejim, @brunocrosier, @Schniz, @sedlukha, @hashlash, @Ethan-Arrowood, @fireairforce, @migueloller, @leerob, @janicklas-ralph, @Trystanr, @atilafassina, @nramkissoon, @kasperadk, @valcosmos, @henriqueholtz, @nip10, @jesstelford, @lorensr, @AviAvinav, @SukkaW, @jaycedotbin, @saurabhburade, @notrab, @kwonoj, @sanruiz, @angeloashmore, @falsepopsky, @fmontes, @Gebov, @UltiRequiem, @p13lgst, @Simek, @mrkldshv, @thomasballinger, @kyliau, @AdarshKonchady, @endymion1818, @pedro757, @perkinsjr, @gnoff, @jridgewell, @silvioprog, @mabels, @nialexsan, @feugy, @jackromo888, @crazyurus, @EarlGeorge, @MariaSolOs, @lforst, @maximbaz, @maxam2017, @teobler, @Nutlope, @sunwoo0706, @WestonThayer, @Brooooooklyn, @Nsttt, @charlypoly, @aprendendofelipe, @sviridoff, @jackton1, @nuta, @Rpaudel379, @marcialca, @MarDi66, @ismaelrumzan, @javivelasco, @eltociear, y @hiro0218.