Skip to content
oRPC
Esc
navigateopen⌘Jpreview
On this page

Timeout Plugin

Abort requests that exceed a timeout on the client or the server, using a static value or a per-request dynamic timeout.

Client

Use TimeoutLinkPlugin to abort requests that exceed the timeout with an AbortError:

import { TimeoutLinkPlugin } from '@orpc/client/plugins'

const link = new RPCLink({
  plugins: [
    new TimeoutLinkPlugin({
      timeout: 10_000, // 10 seconds
    }),
  ],
})

Server

Use TimeoutHandlerPlugin to abort the request signal with an AbortError when handling exceeds the timeout. A procedure that honors the signal stops early, and logging treats the abort as a cancellation rather than a failure. The plugin never preempts the procedure, so real errors are never masked:

import { TimeoutHandlerPlugin } from '@orpc/server/plugins'

const handler = new RPCHandler(router, {
  plugins: [
    new TimeoutHandlerPlugin({
      timeout: 10_000, // 10 seconds
    }),
  ],
})

Streaming Responses

The timeout option only covers producing the response, so streaming responses can outlive it. Use the separate streamingTimeout option, usually higher than timeout, to limit the full duration of streaming response bodies:

const handler = new RPCHandler(router, {
  plugins: [
    new TimeoutHandlerPlugin({
      timeout: 10_000, // 10 seconds to produce the response
      streamingTimeout: 300_000, // 5 minutes for the full stream
    }),
  ],
})

When streamingTimeout is exceeded, the request signal is aborted and the body ends once its producer honors the signal, for example an async iterator object body ends with an error event.

Dynamic Timeout

The timeout and streamingTimeout options also accept a function, so you can resolve the timeout per request from the interceptor options. On the client these include the procedure path and the client context, on the server the matched procedure and the handler context:

const link = new RPCLink({
  plugins: [
    new TimeoutLinkPlugin({
      timeout: ({ context, path }) => context.timeout ?? 10_000,
    }),
  ],
})
const handler = new RPCHandler(router, {
  plugins: [
    new TimeoutHandlerPlugin({
      timeout: ({ path }) => path[0] === 'reports' ? 60_000 : 10_000,
    }),
  ],
})

Learn More

For implementation details, see the TimeoutLinkPlugin source code or the TimeoutHandlerPlugin source code.

Last updated on August 14, 2026

Was this page helpful?