Docs
Launch GraphOS Studio

Deferring query response data with GraphOS

Using the @defer directive


With , your 's can defer returning data for certain in your schema. This enables a client to receive non-deferred data more quickly, because the can return it immediately instead of waiting for all response data to be ready:

RouterClientRouterClientResolves non-deferredfieldsResolves deferredfieldsSends a query thatdefers some fieldsReturns data fornon-deferred fieldsReturns data fordeferred fields

Both cloud supergraphs and self-hosted supergraphs support deferring with the . Additionally, this feature is compatible with all supported subgraph libraries, because the logic resides entirely within the !

How do I defer fields in a query?

NOTE

Deferring requires a defer-compatible client library. These libraries support receiving query data incrementally via multipart HTTP responses.

Defer support is currently available in for Web and Kotlin (experimental).

If you're using a defer-compatible client, you apply the @defer to in your queries to specify which you want to defer:

query GetTopProductsAndReviews {
topProducts {
id
name
# You always apply @defer to a fragment, not to individual fields
... @defer {
reviews {
score
}
}
}
}

When your 's receives this , it defers every in these that it's able to.

Which fields can my router defer?

Your 's can defer the following in your schema:

  • Root of the Query type (along with their sub)
  • of any type (along with their subfields)
    • Deferring is extremely powerful but requires some setup if you aren't using entities already. This is covered in more detail below.

See below for more information on each of these.

Query fields

Your can defer any of your schema's Query type, along with any sub of those fields:

query GetUsersAndDeferProducts {
users {
id
}
... @defer {
products {
id
}
}
}

With the above, the first returns a list of User IDs, then later completes the response with a list of Product IDs.

Entity fields

Your supports deferring of the special in your called entities.

Entities are that often define their across multiple (but they don't have to). You can identify an by its use of the @key . In the example below, the Product type is an :

Products subgraph
type Product @key(fields: "id") {
id: ID!
name: String!
price: Int!
}
type Query {
topProducts: [Product!]!
}
Reviews subgraph
type Product @key(fields: "id") {
id: ID!
reviews: [Review!]!
}
type Review {
score: Int!
}

Entities are entry points into your , and this is what enables your to defer their : the router can send a followup query to a subgraph to fetch any fields that it doesn't fetch initially.

Here's an example that defers using the above:

query GetProductsAndDeferReviews {
topProducts {
id
name
... @defer {
reviews {
score
}
}
}
}

To handle this , the first resolves and returns a list of Product objects with their IDs and names. Later, the completes the response by returning review scores for each of those products.

NOTE

It doesn't matter which defines a particular ! Queries can defer entity fields that are defined across any number of different subgraphs.

Defining entities in your subgraphs

If your don't yet include any entities, you need to define some before clients can start deferring their in queries.

To learn about creating entities, see this article.

Requirements for @defer

To use @defer successfully, your and its clients must meet the requirements listed below. These requirements are divided between general requirements (requirements for using @defer at all) and entity-specific requirements (additional requirements for using @defer with ).

General requirements

Entity-specific requirements

Previous
Safelisting with persisted queries
Next
GraphQL subscriptions
Edit on GitHubEditForumsDiscord

© 2024 Apollo Graph Inc.

Privacy Policy

Company