www/docs/server/adapters/aws-lambda.md
The AWS Lambda adapter is supported for API Gateway REST API(v1) and HTTP API(v2), and Lambda Function URL use cases.
httpBatchLinkrequires the router to work on a single API Gateway Resource (as shown in the example). If you'd like to have a Resource per procedure, you can use thehttpLinkinstead (more info).
yarn add @trpc/server
:::tip AI Agents If you use an AI coding agent, install tRPC skills for better code generation:
npx @tanstack/intent@latest install
:::
Implement your tRPC router. A sample router is given below:
import { initTRPC } from '@trpc/server';
import { z } from 'zod';
export const t = initTRPC.create();
const appRouter = t.router({
getUser: t.procedure.input(z.string()).query((opts) => {
opts.input; // string
return { id: opts.input, name: 'Bilbo' };
}),
});
// export type definition of API
export type AppRouter = typeof appRouter;
tRPC includes an adapter for API Gateway out of the box. This adapter lets you run your routes through the API Gateway handler.
// @filename: router.ts
import { initTRPC } from '@trpc/server';
const t = initTRPC.create();
export const appRouter = t.router({});
export type AppRouter = typeof appRouter;
// @filename: server.ts
// ---cut---
import type { APIGatewayProxyEventV2 } from 'aws-lambda';
import type { CreateAWSLambdaContextOptions } from '@trpc/server/adapters/aws-lambda';
import { awsLambdaRequestHandler } from '@trpc/server/adapters/aws-lambda';
import { appRouter } from './router';
// created for each request
const createContext = ({
event,
context,
}: CreateAWSLambdaContextOptions<APIGatewayProxyEventV2>) => ({}); // no context
type Context = Awaited<ReturnType<typeof createContext>>;
export const handler = awsLambdaRequestHandler({
router: appRouter,
createContext,
})
Build & deploy your code, now use your API Gateway URL to call your function.
| Endpoint | HTTP URI |
|---|---|
getUser | GET https://<execution-api-link>/getUser?input=INPUT |
where INPUT is a URI-encoded JSON string. |
API Gateway has two different event data formats when it invokes a Lambda. For REST APIs they should be version "1.0"(APIGatewayProxyEvent), but you can choose which for HTTP APIs by stating either version "1.0" or "2.0".
APIGatewayProxyEventAPIGatewayProxyEventV2To infer what version you might have, supply the context as following:
import type { APIGatewayProxyEvent } from 'aws-lambda';
import type { CreateAWSLambdaContextOptions } from '@trpc/server/adapters/aws-lambda';
// ---cut---
function createContext({
event,
context,
}: CreateAWSLambdaContextOptions<APIGatewayProxyEvent>) {
// ...
}
// CreateAWSLambdaContextOptions<APIGatewayProxyEvent> or CreateAWSLambdaContextOptions<APIGatewayProxyEventV2>
Read more here about payload format version
AWS Lambda supports streaming responses to clients with both Lambda Function URLs and API Gateway REST APIs.
Response streaming is supported for Lambda Function URLs and API Gateway REST APIs. For API Gateway REST APIs, you need to configure the integration with
responseTransferMode: STREAM. Read more about Lambda response streaming and API Gateway response streaming.
The signature of a streaming handler is different from the default handler. The streaming handler additionally receives a writable stream parameter, responseStream, besides the default node handler parameters, event and context. To indicate that Lambda should stream your responses, you must wrap your function handler with the awslambda.streamifyResponse() decorator.
Note that the
awslambdanamespace is automatically provided by the Lambda execution environment. You can import the types from@types/aws-lambdato augment the global namespace with theawslambdanamespace.
/// <reference types="aws-lambda" />
// @filename: router.ts
import { initTRPC } from '@trpc/server';
const t = initTRPC.create();
export const appRouter = t.router({
iterable: t.procedure.query(async function* () {
for (let i = 0; i < 10; i++) {
await new Promise((resolve) => setTimeout(resolve, 500));
yield i;
}
}),
});
// @filename: server.ts
// ---cut---
/// <reference types="aws-lambda" />
import type { APIGatewayProxyEventV2 } from 'aws-lambda';
import type { CreateAWSLambdaContextOptions } from '@trpc/server/adapters/aws-lambda';
import { awsLambdaStreamingRequestHandler } from '@trpc/server/adapters/aws-lambda';
import { appRouter } from './router';
// created for each request
const createContext = ({
event,
context,
}: CreateAWSLambdaContextOptions<APIGatewayProxyEventV2>) => ({
// your context
});
type Context = Awaited<ReturnType<typeof createContext>>;
export const handler = awslambda.streamifyResponse(
awsLambdaStreamingRequestHandler({
router: appRouter,
createContext,
}),
);