Class: GraphQL::Stitching::Request
- Inherits:
-
Object
- Object
- GraphQL::Stitching::Request
- Defined in:
- lib/graphql/stitching/request.rb,
lib/graphql/stitching/request/skip_include.rb
Overview
Request combines a supergraph, GraphQL document, variables, variable/fragment definitions, and the selected operation. It provides the lifecycle of validating, preparing, planning, and executing upon these inputs.
Defined Under Namespace
Classes: SkipInclude
Constant Summary collapse
- SKIP_INCLUDE_DIRECTIVE =
/@(?:skip|include)/
Instance Attribute Summary collapse
-
#context ⇒ Hash
readonly
Contextual object passed through resolver flows.
-
#query ⇒ GraphQL::Query
readonly
Query object defining the request.
-
#supergraph ⇒ Supergraph
readonly
Supergraph instance that resolves the request.
Instance Method Summary collapse
-
#digest ⇒ String
A digest of the original document string.
-
#execute(raw: false) ⇒ Hash
Executes the request and returns the rendered response.
-
#fragment_definitions ⇒ Hash<String, GraphQL::Language::Nodes::FragmentDefinition>
Map of fragment names to their AST definitions.
-
#initialize(supergraph, source, operation_name: nil, variables: nil, context: nil) ⇒ Request
constructor
Creates a new supergraph request.
-
#mutation? ⇒ Boolean
True if operation type is a mutation.
-
#normalized_digest ⇒ String
A digest of the normalized document string.
-
#normalized_string ⇒ String
A print of the parsed AST document with consistent whitespace.
-
#operation ⇒ GraphQL::Language::Nodes::OperationDefinition
The selected root operation for the request.
-
#operation_directives ⇒ String
A string of directives applied to the root operation.
- #operation_name ⇒ Object
- #original_document ⇒ Object
-
#plan(new_plan = nil) ⇒ Plan
Gets and sets the query plan for the request.
-
#query? ⇒ Boolean
True if operation type is a query.
-
#string ⇒ String
The original document string, or a print of the parsed AST document.
-
#subscription? ⇒ Boolean
True if operation type is a subscription.
-
#validate ⇒ Array<GraphQL::ExecutionError>
Validates the request using the combined supergraph schema.
-
#variable_definitions ⇒ Hash<String, GraphQL::Language::Nodes::AbstractNode>
Map of variable names to AST type definitions.
-
#variables ⇒ Hash<String, Any>
Provided variables hash filled in with default values from definitions.
Constructor Details
#initialize(supergraph, source, operation_name: nil, variables: nil, context: nil) ⇒ Request
Creates a new supergraph request.
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 |
# File 'lib/graphql/stitching/request.rb', line 29 def initialize(supergraph, source, operation_name: nil, variables: nil, context: nil) @supergraph = supergraph @prepared_document = nil @string = nil @digest = nil @normalized_string = nil @normalized_digest = nil @operation = nil @operation_directives = nil @variable_definitions = nil @fragment_definitions = nil @plan = nil params = { operation_name: operation_name, variables: variables, context: context, } if source.is_a?(String) @string = source params[:query] = source else params[:document] = source end @query = GraphQL::Query.new(@supergraph.schema, **params) @context = @query.context @context[:request] = self end |
Instance Attribute Details
#context ⇒ Hash (readonly)
Returns contextual object passed through resolver flows.
21 22 23 |
# File 'lib/graphql/stitching/request.rb', line 21 def context @context end |
#query ⇒ GraphQL::Query (readonly)
Returns query object defining the request.
18 19 20 |
# File 'lib/graphql/stitching/request.rb', line 18 def query @query end |
#supergraph ⇒ Supergraph (readonly)
Returns supergraph instance that resolves the request.
15 16 17 |
# File 'lib/graphql/stitching/request.rb', line 15 def supergraph @supergraph end |
Instance Method Details
#digest ⇒ String
Returns a digest of the original document string. Generally faster but less consistent.
75 76 77 |
# File 'lib/graphql/stitching/request.rb', line 75 def digest @digest ||= Stitching.digest.call("#{Stitching::VERSION}/#{string}") end |
#execute(raw: false) ⇒ Hash
Executes the request and returns the rendered response.
175 176 177 178 |
# File 'lib/graphql/stitching/request.rb', line 175 def execute(raw: false) add_subscription_update_handler if subscription? Executor.new(self).perform(raw: raw) end |
#fragment_definitions ⇒ Hash<String, GraphQL::Language::Nodes::FragmentDefinition>
Returns map of fragment names to their AST definitions.
138 139 140 141 142 |
# File 'lib/graphql/stitching/request.rb', line 138 def fragment_definitions @fragment_definitions ||= prepared_document.definitions.each_with_object({}) do |d, memo| memo[d.name] = d if d.is_a?(GraphQL::Language::Nodes::FragmentDefinition) end end |
#mutation? ⇒ Boolean
Returns true if operation type is a mutation.
116 117 118 |
# File 'lib/graphql/stitching/request.rb', line 116 def mutation? @query.mutation? end |
#normalized_digest ⇒ String
Returns a digest of the normalized document string. Slower but more consistent.
80 81 82 |
# File 'lib/graphql/stitching/request.rb', line 80 def normalized_digest @normalized_digest ||= Stitching.digest.call("#{Stitching::VERSION}/#{normalized_string}") end |
#normalized_string ⇒ String
Returns a print of the parsed AST document with consistent whitespace.
70 71 72 |
# File 'lib/graphql/stitching/request.rb', line 70 def normalized_string @normalized_string ||= prepared_document.to_query_string end |
#operation ⇒ GraphQL::Language::Nodes::OperationDefinition
Returns The selected root operation for the request.
85 86 87 88 89 90 91 92 93 94 95 96 |
# File 'lib/graphql/stitching/request.rb', line 85 def operation @operation ||= with_prepared_document do selected_op = @query.selected_operation raise GraphQL::ExecutionError, "No operation selected" unless selected_op @prepared_document.definitions.find do |d| next unless d.is_a?(GraphQL::Language::Nodes::OperationDefinition) selected_op.name.nil? || d.name == selected_op.name end end end |
#operation_directives ⇒ String
Returns A string of directives applied to the root operation. These are passed through in all subgraph requests.
103 104 105 106 107 108 |
# File 'lib/graphql/stitching/request.rb', line 103 def operation_directives @operation_directives ||= if operation.directives.any? printer = GraphQL::Language::Printer.new operation.directives.map { printer.print(_1) }.join(" ") end end |
#operation_name ⇒ Object
98 99 100 |
# File 'lib/graphql/stitching/request.rb', line 98 def operation_name operation.name end |
#original_document ⇒ Object
60 61 62 |
# File 'lib/graphql/stitching/request.rb', line 60 def original_document @query.document end |
#plan(new_plan = nil) ⇒ Plan
Gets and sets the query plan for the request. Assigned query plans may pull from a cache, which is useful for redundant GraphQL documents (commonly sent by frontend clients).
if cached_plan = $cache.get(request.digest)
plan = GraphQL::Stitching::Plan.from_json(JSON.parse(cached_plan))
request.plan(plan)
else
plan = request.plan
$cache.set(request.digest, JSON.generate(plan.as_json))
end
163 164 165 166 167 168 169 170 |
# File 'lib/graphql/stitching/request.rb', line 163 def plan(new_plan = nil) if new_plan raise StitchingError, "Plan must be a `GraphQL::Stitching::Plan`." unless new_plan.is_a?(Plan) @plan = new_plan else @plan ||= Planner.new(self).perform end end |
#query? ⇒ Boolean
Returns true if operation type is a query.
111 112 113 |
# File 'lib/graphql/stitching/request.rb', line 111 def query? @query.query? end |
#string ⇒ String
Returns the original document string, or a print of the parsed AST document.
65 66 67 |
# File 'lib/graphql/stitching/request.rb', line 65 def string with_prepared_document { @string || normalized_string } end |
#subscription? ⇒ Boolean
Returns true if operation type is a subscription.
121 122 123 |
# File 'lib/graphql/stitching/request.rb', line 121 def subscription? @query.subscription? end |
#validate ⇒ Array<GraphQL::ExecutionError>
Validates the request using the combined supergraph schema.
146 147 148 |
# File 'lib/graphql/stitching/request.rb', line 146 def validate @query.static_errors end |
#variable_definitions ⇒ Hash<String, GraphQL::Language::Nodes::AbstractNode>
Returns map of variable names to AST type definitions.
131 132 133 134 135 |
# File 'lib/graphql/stitching/request.rb', line 131 def variable_definitions @variable_definitions ||= operation.variables.each_with_object({}) do |v, memo| memo[v.name] = v.type end end |
#variables ⇒ Hash<String, Any>
Returns provided variables hash filled in with default values from definitions.
126 127 128 |
# File 'lib/graphql/stitching/request.rb', line 126 def variables @variables || with_prepared_document { @variables } end |