class GraphQL::Schema::Subscription
This class can be extended to create fields on your subscription root.
It provides hooks for the different parts of the subscription lifecycle:
-
authorized?: called before initial subscription and subsequent updates -
subscribe: called for the initial subscription -
update: called for subsequent update
Also, unsubscribe terminates the subscription.
Constants
- NO_UPDATE
Public Class Methods
# File lib/graphql/schema/subscription.rb, line 178 def self.subscription_scope(new_scope = NOT_CONFIGURED, optional: false) if new_scope != NOT_CONFIGURED @subscription_scope = new_scope @subscription_scope_optional = optional elsif defined?(@subscription_scope) @subscription_scope else find_inherited_value(:subscription_scope) end end
Call this method to provide a new subscription_scope; OR call it without an argument to get the subscription_scope
Parameters
-
new_scope(Symbol) -
optional(Boolean) β If true, then donβt requirescope:to be provided to updates to this subscription.
Returns
-
Symbol
# File lib/graphql/schema/subscription.rb, line 189 def self.subscription_scope_optional? if defined?(@subscription_scope_optional) @subscription_scope_optional else find_inherited_value(:subscription_scope_optional, false) end end
# File lib/graphql/schema/subscription.rb, line 222 def self.topic_for(arguments:, field:, scope:) Subscriptions::Serialize.dump_recursive([scope, field.graphql_name, arguments]) end
This is called during initial subscription to get a βnameβ for this subscription. Later, when .trigger is called, this will be called again to build another βnameβ. Any subscribers with matching topic will begin the update flow.
The default implementation creates a string using the field name, subscription scope, and argument keys and values. In that implementation, only .trigger calls with exact matches result in updates to subscribers.
To implement a filtered stream-type subscription flow, override this method to return a string with field name and subscription scope. Then, implement update to compare its arguments to the current object and return NO_UPDATE when an update should be filtered out.
See update for how to skip updates when an event comes with a matching topic.
Parameters
-
arguments(Hash<String => Object>) β The arguments for this topic, in GraphQL-style (camelized strings) -
field(GraphQL::Schema::Field) -
scope(Object, nil) β A value corresponding to.trigger(... scope:)(for updates) or thesubscription_scopefound incontext(for initial subscriptions).
Returns
-
Stringβ An identifier corresponding to a stream of updates
Public Instance Methods
# File lib/graphql/schema/subscription.rb, line 267 def event @event ||= begin if @original_arguments.nil? && @field_resolve_step @original_arguments, _errors = @field_resolve_step.arguments_without_loads end Subscriptions::Event.new( name: field.name, arguments: @original_arguments, context: context, field: field, ) end end
Returns
-
Subscriptions::Eventβ This object is used as a representation of this subscription for the backend
# File lib/graphql/schema/subscription.rb, line 134 def load_application_object_failed(err) if @mode == :update unsubscribe end super end
If an argument is flagged with loads: and no object is found for it, remove this subscription (assuming that the object was deleted in the meantime, or that it became inaccessible).
Source
# File lib/graphql/schema/subscription.rb, line 90 def resolve(**args) # Dispatch based on `@mode`, which will raise a `NoMethodError` if we ever # have an unexpected `@mode` public_send("resolve_#{@mode}", **args) end
Source
# File lib/graphql/schema/subscription.rb, line 109 def subscribe(args = {}) :no_response end
The default implementation returns nothing on subscribe. Override it to return an object or :no_response to (explicitly) return nothing.
# File lib/graphql/schema/subscription.rb, line 257 def subscription_written? @subscription_written end
Returns
-
Booleanβtrueif write subscription was called already
# File lib/graphql/schema/subscription.rb, line 153 def unsubscribe(update_value = nil) context.namespace(:subscriptions)[:unsubscribed] = true err = EarlyUnsubscribe.new err.unsubscribed_result = update_value raise err end
Call this to halt execution and remove this subscription from the system
Parameters
-
update_value(Object) β if present, deliver this update before unsubscribing
Returns
-
void
Source
# File lib/graphql/schema/subscription.rb, line 127 def update(args = {}) object end
The default implementation returns the root object. Override it to return NO_UPDATE if you want to skip updates sometimes. Or override it to return a different object.
Source
# File lib/graphql/schema/subscription.rb, line 241 def write_subscription if subscription_written? raise GraphQL::Error, "`write_subscription` was called but `#{self.class}#subscription_written?` is already true. Remove a call to `write subscription`." else @subscription_written = true context.schema.subscriptions.write_subscription(context.query, [event]) end nil end
Calls through to schema.subscriptions to register this subscription with the backend. This is automatically called by GraphQL-Ruby after a query finishes successfully, but if you need to commit the subscription during subscribe, you can call it there. (This method also sets a flag showing that this subscription was already written.)
If you call this method yourself, you may also need to unsubscribe or call subscriptions.delete_subscription to clean up the database if the query crashes with an error later in execution.
Returns
-
void