1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104
|
---
layout: guide
doc_stub: false
search: true
title: Object Identification
section: Schema
desc: Working with unique global IDs
index: 8
---
Some GraphQL features use unique IDs to load objects:
- the `node(id:)` field looks up objects by ID
- any arguments with `loads:` configurations look up objects by ID
To use these features, you must provide a function for generating UUIDs and fetching objects with them. In your schema, define `self.id_from_object` and `self.object_from_id`:
```ruby
class MySchema < GraphQL::Schema
def self.id_from_object(object, type_definition, query_ctx)
# Generate a unique string ID for `object` here
# For example, use Rails' GlobalID library (https://github.com/rails/globalid):
object.to_gid_param
end
def self.object_from_id(global_id, query_ctx)
# For example, use Rails' GlobalID library (https://github.com/rails/globalid):
GlobalID.find(global_id)
end
end
```
## Node interface
One requirement for Relay's object management is implementing the `"Node"` interface.
To implement the node interface, add {{ "GraphQL::Types::Relay::Node" | api_doc }} to your definition:
```ruby
class Types::PostType < GraphQL::Schema::Object
# Implement the "Node" interface for Relay
implements GraphQL::Types::Relay::Node
# ...
end
```
To tell GraphQL how to resolve members of the `Node` interface, you must also define `Schema.resolve_type`:
```ruby
class MySchema < GraphQL::Schema
# You'll also need to define `resolve_type` for
# telling the schema what type Relay `Node` objects are
def self.resolve_type(type, obj, ctx)
case obj
when Post
Types::PostType
when Comment
Types::CommentType
else
raise("Unexpected object: #{obj}")
end
end
end
```
## UUID fields
Nodes must have a field named `"id"` which returns a globally unique ID.
To add a UUID field named `"id"`, implement the {{ "GraphQL::Types::Relay::Node" | api_doc }} interface::
```ruby
class Types::PostType < GraphQL::Schema::Object
implements GraphQL::Types::Relay::Node
end
```
This field will call the previously-defined `id_from_object` class method.
## `node` field (find-by-UUID)
You should also provide a root-level `node` field so that Relay can refetch objects from your schema. You can attach it like this:
```ruby
class Types::QueryType < GraphQL::Schema::Object
# Used by Relay to lookup objects by UUID:
# Add `node(id: ID!)
include GraphQL::Types::Relay::HasNodeField
# ...
end
```
## `nodes` field
You can also provide a root-level `nodes` field so that Relay can refetch objects by IDs:
```ruby
class Types::QueryType < GraphQL::Schema::Object
# Fetches a list of objects given a list of IDs
# Add `nodes(ids: [ID!]!)`
include GraphQL::Types::Relay::HasNodesField
# ...
end
```
|