Helpers para el lado del servidor
Esta página fue traducida por PageTurner AI (beta). No está respaldada oficialmente por el proyecto. ¿Encontraste un error? Reportar problema →
Los helpers para el lado del servidor te proporcionan un conjunto de funciones auxiliares que puedes usar para precargar consultas en el servidor. Esto es útil para SSG (Static Site Generation), pero también para SSR (Server-Side Rendering) si optas por no usar ssr: true.
La precarga mediante estos helpers permite poblar la caché de consultas en el servidor, lo que significa que estas consultas no tendrán que ejecutarse inicialmente en el cliente.
Hay 2 formas de usar los helpers para el lado del servidor
1. Router interno
Este método se usa cuando tienes acceso directo a tu router tRPC. Por ejemplo, cuando desarrollas una aplicación monolítica con Next.js.
Usar estos helpers hace que tRPC llame a tus procedimientos directamente en el servidor sin una solicitud HTTP, similar a las llamadas en el lado del servidor.
Esto también significa que no tendrás a mano la solicitud y la respuesta como sueles hacer. Asegúrate de instanciar los helpers con un contexto sin req y res, que normalmente se completan mediante la creación del contexto. Recomendamos el concepto de contexto "interno" y "externo" en ese escenario.
tsimport { createServerSideHelpers } from '@trpc/react-query/server';import { createContext } from '~/server/context';import superjson from 'superjson';const helpers = createServerSideHelpers({router: appRouter,ctx: await createContext(),transformer: superjson, // optional - adds superjson serialization});
tsimport { createServerSideHelpers } from '@trpc/react-query/server';import { createContext } from '~/server/context';import superjson from 'superjson';const helpers = createServerSideHelpers({router: appRouter,ctx: await createContext(),transformer: superjson, // optional - adds superjson serialization});
2. Router externo
Este método se usa cuando no tienes acceso directo a tu router tRPC. Por ejemplo, cuando desarrollas una aplicación Next.js con una API independiente alojada por separado.
tsimport { createTRPCProxyClient } from '@trpc/client';import { createServerSideHelpers } from '@trpc/react-query/server';import superjson from 'superjson';const proxyClient = createTRPCProxyClient<AppRouter>({links: [httpBatchLink({url: 'http://localhost:3000/api/trpc',}),],transformer: superjson,});const helpers = createServerSideHelpers({client: proxyClient,});
tsimport { createTRPCProxyClient } from '@trpc/client';import { createServerSideHelpers } from '@trpc/react-query/server';import superjson from 'superjson';const proxyClient = createTRPCProxyClient<AppRouter>({links: [httpBatchLink({url: 'http://localhost:3000/api/trpc',}),],transformer: superjson,});const helpers = createServerSideHelpers({client: proxyClient,});
Uso de los helpers
Los métodos de estos helpers devuelven un objeto similar al cliente tRPC, con todos tus routers como claves. Sin embargo, en lugar de useQuery y useMutation, obtienes funciones prefetch, fetch, prefetchInfinite y fetchInfinite.
La diferencia principal entre prefetch y fetch es que fetch actúa como una llamada de función normal, devolviendo el resultado de la consulta, mientras que prefetch no devuelve el resultado y nunca lanza errores - si necesitas ese comportamiento, usa fetch en su lugar. En cambio, prefetch agregará la consulta a la caché, que luego deshidratas y envías al cliente.
tsreturn {props: {// very important - use `trpcState` as the keytrpcState: helpers.dehydrate(),},};
tsreturn {props: {// very important - use `trpcState` as the keytrpcState: helpers.dehydrate(),},};
La regla general es: usa prefetch para consultas que sabes que necesitarás en el cliente, y fetch para consultas cuyo resultado quieras usar en el servidor.
Todas las funciones son wrappers alrededor de las funciones de react-query. Por favor, consulta su documentación para aprender más sobre ellas en detalle.
Para un ejemplo completo, consult nuestro ejemplo de prueba E2E SSG
Ejemplo con Next.js
pages/posts/[id].tsxtsximport { createServerSideHelpers } from '@trpc/react-query/server';import { GetServerSidePropsContext, InferGetServerSidePropsType } from 'next';import { appRouter } from 'server/routers/_app';import superjson from 'superjson';import { trpc } from 'utils/trpc';export async function getServerSideProps(context: GetServerSidePropsContext<{ id: string }>,) {const helpers = createServerSideHelpers({router: appRouter,ctx: {},transformer: superjson,});const id = context.params?.id as string;/** Prefetching the `post.byId` query.* `prefetch` does not return the result and never throws - if you need that behavior, use `fetch` instead.*/await helpers.post.byId.prefetch({ id });// Make sure to return { props: { trpcState: helpers.dehydrate() } }return {props: {trpcState: helpers.dehydrate(),id,},};}export default function PostViewPage(props: InferGetServerSidePropsType<typeof getServerSideProps>,) {const { id } = props;const postQuery = trpc.post.byId.useQuery({ id });if (postQuery.status !== 'success') {// won't happen since the query has been prefetchedreturn <>Loading...</>;}const { data } = postQuery;return (<><h1>{data.title}</h1><em>Created {data.createdAt.toLocaleDateString()}</em><p>{data.text}</p><h2>Raw data:</h2><pre>{JSON.stringify(data, null, 4)}</pre></>);}
pages/posts/[id].tsxtsximport { createServerSideHelpers } from '@trpc/react-query/server';import { GetServerSidePropsContext, InferGetServerSidePropsType } from 'next';import { appRouter } from 'server/routers/_app';import superjson from 'superjson';import { trpc } from 'utils/trpc';export async function getServerSideProps(context: GetServerSidePropsContext<{ id: string }>,) {const helpers = createServerSideHelpers({router: appRouter,ctx: {},transformer: superjson,});const id = context.params?.id as string;/** Prefetching the `post.byId` query.* `prefetch` does not return the result and never throws - if you need that behavior, use `fetch` instead.*/await helpers.post.byId.prefetch({ id });// Make sure to return { props: { trpcState: helpers.dehydrate() } }return {props: {trpcState: helpers.dehydrate(),id,},};}export default function PostViewPage(props: InferGetServerSidePropsType<typeof getServerSideProps>,) {const { id } = props;const postQuery = trpc.post.byId.useQuery({ id });if (postQuery.status !== 'success') {// won't happen since the query has been prefetchedreturn <>Loading...</>;}const { data } = postQuery;return (<><h1>{data.title}</h1><em>Created {data.createdAt.toLocaleDateString()}</em><p>{data.text}</p><h2>Raw data:</h2><pre>{JSON.stringify(data, null, 4)}</pre></>);}