Skip to content

Commit

Permalink
update documentation.
Browse files Browse the repository at this point in the history
  • Loading branch information
gmac committed May 31, 2024
1 parent 4fce9b9 commit f4ca186
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 23 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -153,15 +153,15 @@ type Query {
* The `@stitch` directive is applied to a root query where the merged type may be accessed. The merged type identity is inferred from the field return.
* The `key: "id"` parameter indicates that an `{ id }` must be selected from prior locations so it may be submitted as an argument to this query. The query argument used to send the key is inferred when possible ([more on arguments](#multiple-query-arguments) later).

Each location that provides a unique variant of a type must provide at least one resolver query for the type. The exception to this requirement are [foreign key types](./docs/mechanics.md##modeling-foreign-keys-for-stitching) that contain only a single key field:
Each location that provides a unique variant of a type must provide at least one resolver query for the type. The exception to this requirement are [outbound-only types](./docs/mechanics.md#outbound-only-merged-types) and/or [foreign key types](./docs/mechanics.md##modeling-foreign-keys-for-stitching) that contain no exclusive data:

```graphql
type Product {
id: ID!
}
```

The above representation of a `Product` type provides no unique data beyond a key that is available in other locations. Thus, this representation will never require an inbound request to fetch it, and its resolver query may be omitted.
The above representation of a `Product` type contains nothing but a key that is available in other locations. Therefore, this representation will never require an inbound request to fetch it, and its resolver query may be omitted.

#### List queries

Expand Down
42 changes: 42 additions & 0 deletions docs/mechanics.md
Original file line number Diff line number Diff line change
Expand Up @@ -303,3 +303,45 @@ And produces this result:
```

Location B is allowed to return `null` here because its one unique field, `rating`, is nullable (the `id` field can be provided by Location A). If `rating` were non-null, then null bubbling would invalidate the response data.

### Outbound-only merged types

Merged types do not always require a resolver query. For example:

```graphql
# -- Location A

type Widget {
id: ID!
name: String
}

type Query {
widgetA(id: ID!): Widget @stitch(key: "id")
}

# -- Location B

type Widget {
id: ID!
size: Float
}

type Query {
widgetB(id: ID!): Widget @stitch(key: "id")
}

# -- Location C

type Widget {
id: ID!
name: String
size: Float
}

type Query {
featuredWidget: Widget
}
```

In this graph, `Widget` is a merged type without a resolver query in location C. This works because all of its fields are resolvable in other locations; that means location C can provide outbound representations of this type without ever needing to resolve inbound requests for it. Outbound types do still require a key field (such as `id` above) that allow them to join with data in other resolver locations.
21 changes: 0 additions & 21 deletions test/graphql/stitching/supergraph_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -290,27 +290,6 @@ def test_route_type_to_locations_favors_longer_paths_through_necessary_locations
assert routes.none? { |_key, path| path.any? { _1["location"] == "e" } }
end

# def test_route_type_to_locations_returns_nil_for_unreachable_locations
# a = %|
# type T { upc:ID! }
# type Query { a(upc:ID!):T @stitch(key: "upc") }
# |
# b = %|
# type T { id:ID! }
# type Query { b(id:ID!):T @stitch(key: "id") }
# |
# c = %|
# type T { id:ID! }
# type Query { c(id:ID!):T @stitch(key: "id") }
# |

# supergraph = compose_definitions({ "a" => a, "b" => b, "c" => c })

# routes = supergraph.route_type_to_locations("T", "b", ["a", "c"])
# assert_equal ["c"], routes["c"].map { _1["location"] }
# assert_nil routes["a"]
# end

describe "#to_definition / #from_definition" do
def setup
alpha = %|
Expand Down

0 comments on commit f4ca186

Please sign in to comment.