Router Customizations

Extend your router with custom functionality


You can create customizations for the GraphOS Router or Apollo Router Core to add functionality that isn't available via built-in configuration options. For example, you can make an external call to fetch authentication data for each incoming request.

Customization types

The GraphOS Router supports the following customization types:

  • Rhai scripts

    • The Rhai scripting language lets you add functionality directly to your stock router binary by hooking into different phases of the router's request lifecycle.

  • External co-processing (Enterprise feature)

    • If your organization has a GraphOS Enterprise plan, you can write custom request-handling code in any language. This code can run in the same container as your router or separately.

    • The router calls your custom code via HTTP, passing it the details of each incoming client request.

The Apollo Router Core supports customization only through Rhai scripts.

Because Rhai scripts are easier to deploy, we recommend using them if they support your use case. Use external co-processing if your customization needs to do any of the following (which Rhai scripts don't support):

  • Read or write to disk

  • Make network requests

  • Use libraries from a particular language or framework

Customizations along the request lifecycle

Customizations intervene at specific points of the request lifecycle, depending on the task you want to perform. Each point is represented by a specific service with its own request and response objects.

tip
Understand the entire request lifecycle by following flowcharts of its request path and response path, starting from a client request to your subgraphs, and all the way back from subgraph responses to a client response.

Request lifecycle plugins

Each service can have a set of plugins. For requests, the router executes plugins before the service.

For responses, the router executes the plugins after the service.

Each request and response object contains a Context object, which is carried throughout the entire process. Each request's Context object is unique. You can use it to store plugin-specific information between the request and response or to communicate between different hook points. (A plugin can be called at multiple steps of the request lifecycle.)

Request and response buffering

note
This guidance applies if you are:
  • Modifying the router
  • Creating a native Rust plugin
  • Creating a custom binary

The router expects to execute on a stream of data. In order to work correctly and provide high performance, the following expectations must be met:

  • Request Path: No buffering before the end of the router_service processing step

  • Response Path: No buffering

tip
In general, it's best to avoid buffering where possible. If necessary, it is ok to do so on the request path once the router_service step is complete.

Creating customizations

To learn how to hook into the various lifecycle stages, including examples customizations, refer to the Rhai scripts and external coprocessing docs.

Feedback

Edit on GitHub

Forums