oRPC
website·Indexed 34 days ago
https://orpc.dev/A framework for building end-to-end typesafe APIs with built-in OpenAPI support. oRPC provides a wide range of adapters for environments including Next.js, Hono, Express, Fastify, Cloudflare Workers, AWS Lambda, Electron, and various browser and worker-based communication methods.
What's inside oRPC
- Contract-first development in oRPC splits API creation into two steps: defining a contract (a description of procedures, inputs, and outputs without logic) and implementing that contract. This approach is recommended when you need to agree on API design before coding, when the client and server live in different repositories/teams, or when you need a strict source of truth to prevent implementation drift.
Integrate Valibot schemas with oRPC
Because Valibot implements the Standard Schema specification, oRPC procedures accept Valibot schemas directly without requiring a converter. A converter is only necessary for tools that specifically consume JSON Schema, such as OpenAPI generation or Smart Coercion.Run oRPC in Expo (General Setup)
Expo is the supported environment for running oRPC in React Native. To ensure features like JSON calls,
AsyncIteratorObject, and streamed downloads work, you need Web Streams (ReadableStream,WritableStream,TransformStream) and a streamingfetchimplementation.- SDK 56+: Everything works out of the box as
expo/fetchreplaces the globalfetchon Android and iOS. - SDK 53 to 55: These versions provide native globals for Web Streams, but you must explicitly pass
expo/fetchto your oRPC link because the default React Nativefetchdoes not support streaming.
- SDK 56+: Everything works out of the box as
Update Event Iterator to AsyncIteratorObject
The 'Event Iterator' concept has been renamed toAsyncIteratorObject. While v1 names remain as deprecated aliases, developers should migrate to the new naming convention.import { asyncIteratorObject } from '@orpc/server' const streaming = os .output(asyncIteratorObject(z.object({ message: z.string() }))) .handler(async function* () { yield { message: 'Hello' } })Integrate ArkType with oRPC
ArkType implements Standard Schema, allowing oRPC procedures to accept ArkType types directly without requiring a converter. A converter is only necessary for tools that specifically consume JSON Schema, such as Smart Coercion or OpenAPI generation.Use oRPC built-in feature packages
oRPC offers several specialized utility packages for common backend requirements:
@orpc/publisher: Pub/Sub functionality with memory, Redis, and Upstash adapters.@orpc/ratelimit: Rate limiting with memory, Redis, and Upstash adapters.@orpc/experimental-lock: Distributed locking with memory, Redis, and Upstash adapters.@orpc/hibernation: Support for Hibernation APIs (e.g., Cloudflare WebSocket Hibernation).@orpc/json-schema: Provides smart coercion for OpenAPI requests.
Compare oRPC, tRPC, and Hono for TypeScript APIs
oRPC, tRPC, and Hono all provide end-to-end typesafe APIs in TypeScript but differ in focus:
- oRPC: Combines typesafe RPC with first-class, native OpenAPI support and a wide range of first-party integrations.
- tRPC: Focuses primarily on RPC for full-stack TypeScript applications.
- Hono: A general-purpose web framework that includes an RPC feature.
oRPC Core packages overview
The core of oRPC is split into four primary packages:@orpc/contractfor defining the API contract as the single source of truth;@orpc/serverfor building APIs and implementing those contracts;@orpc/clientfor consuming APIs with end-to-end type safety; and@orpc/openapifor adding OpenAPI compatibility to APIs.Prevent CSRF attacks on GET methods using GetMethodCsrfProtectionHandlerPlugin
The
GetMethodCsrfProtectionHandlerPlugincloses a security gap where browsers attachSameSite=Laxcookies to safe methods likeGETduring top-level navigations (e.g., link clicks, redirects, or address bar entries).It uses Fetch Metadata headers to reject requests with a
403status ifSec-Fetch-Siteiscross-siteornonewhileSec-Fetch-ModeisnavigateandSec-Fetch-Destisdocument.Behavior Summary:
- Rejected: Link clicks, redirects,
window.open, GET forms, bookmarks, and links from emails/native apps from another site. - Allowed:
fetch,XMLHttpRequest,<img>,<script>, media, prefetch, and non-top-level elements like<iframe>. - Ignored: Any method other than
GET. - Always Allowed: Requests from the same site (including sibling subdomains).
Only requests that match a defined procedure are judged; unmatched requests (e.g., those falling through to a static site) are not affected.
- Rejected: Link clicks, redirects,
Create an oRPC client
UsecreateORPCClientto instantiate a client. You must provide a link (such as an RPC Link or OpenAPI Link) that defines the communication method. Depending on your architecture, you can use either a contract-first approach withRouterContractClientor a normal approach withRouterClient.import { createORPCClient } from '@orpc/client' import { RouterContractClient } from '@orpc/contract' import { RouterClient } from '@orpc/server' // Contract-first approach const contractClient: RouterContractClient<typeof contract> = createORPCClient(link) // Normal approach const normalClient: RouterClient<typeof router> = createORPCClient(link)Configure observability for oRPC
To implement logging and tracing in oRPC, use the following observability packages:
@orpc/opentelemetry: For distributed tracing using OpenTelemetry.@orpc/pino: For logging via Pino.@orpc/evlog: For logging via Evlog.
Access oRPC interactive playgrounds
oRPC provides pre-configured playgrounds for different environments to help developers explore the library. These are available as interactive StackBlitz projects or as source code on GitHub.