From 4df01f6285ba4a3ca670e172c26c5cd150436020 Mon Sep 17 00:00:00 2001 From: Robert Mosolgo Date: Mon, 20 Jun 2022 11:07:43 -0400 Subject: [PATCH] Fix subscription inheritance/override --- lib/graphql/schema.rb | 8 +++++++- lib/graphql/subscriptions.rb | 2 +- spec/graphql/schema_spec.rb | 15 ++++++++++++--- 3 files changed, 20 insertions(+), 5 deletions(-) diff --git a/lib/graphql/schema.rb b/lib/graphql/schema.rb index c954790cc9..bc44611ed1 100644 --- a/lib/graphql/schema.rb +++ b/lib/graphql/schema.rb @@ -132,7 +132,13 @@ def deprecated_graphql_definition end # @return [GraphQL::Subscriptions] - attr_accessor :subscriptions + def subscriptions(inherited: true) + defined?(@subscriptions) ? @subscriptions : (inherited ? find_inherited_value(:subscriptions, nil) : nil) + end + + def subscriptions=(new_implementation) + @subscriptions = new_implementation + end # Returns the JSON response of {Introspection::INTROSPECTION_QUERY}. # @see {#as_json} diff --git a/lib/graphql/subscriptions.rb b/lib/graphql/subscriptions.rb index b81b814bfc..0bbeb698c9 100644 --- a/lib/graphql/subscriptions.rb +++ b/lib/graphql/subscriptions.rb @@ -26,7 +26,7 @@ class SubscriptionScopeMissingError < GraphQL::Error def self.use(defn, options = {}) schema = defn.is_a?(Class) ? defn : defn.target - if schema.subscriptions + if schema.subscriptions(inherited: false) raise ArgumentError, "Can't reinstall subscriptions. #{schema} is using #{schema.subscriptions}, can't also add #{self}" end diff --git a/spec/graphql/schema_spec.rb b/spec/graphql/schema_spec.rb index 3e7873fbd6..08bbf28d6b 100644 --- a/spec/graphql/schema_spec.rb +++ b/spec/graphql/schema_spec.rb @@ -23,6 +23,9 @@ class Subscription < GraphQL::Schema::Object field :some_field, String end + class CustomSubscriptions < GraphQL::Subscriptions::ActionCableSubscriptions + end + let(:base_schema) do Class.new(GraphQL::Schema) do query Query @@ -47,6 +50,7 @@ class Subscription < GraphQL::Schema::Object multiplex_analyzer Object.new rescue_from(StandardError) { } use GraphQL::Backtrace + use GraphQL::Subscriptions::ActionCableSubscriptions, action_cable: nil, action_cable_coder: JSON end end @@ -73,11 +77,15 @@ class Subscription < GraphQL::Schema::Object assert_equal base_schema.query_analyzers, schema.query_analyzers assert_equal base_schema.multiplex_analyzers, schema.multiplex_analyzers assert_equal base_schema.disable_introspection_entry_points?, schema.disable_introspection_entry_points? - assert_equal [GraphQL::Backtrace], schema.plugins.map(&:first) + assert_equal [GraphQL::Backtrace, GraphQL::Subscriptions::ActionCableSubscriptions], schema.plugins.map(&:first) + assert_instance_of GraphQL::Subscriptions::ActionCableSubscriptions, schema.subscriptions end it "can override configuration from its superclass" do - schema = Class.new(base_schema) + schema = Class.new(base_schema) do + use CustomSubscriptions, action_cable: nil, action_cable_coder: JSON + end + query = Class.new(GraphQL::Schema::Object) do graphql_name 'Query' field :some_field, String @@ -141,9 +149,10 @@ class Subscription < GraphQL::Schema::Object assert_equal schema.directives, GraphQL::Schema.default_directives.merge(DummyFeature1.graphql_name => DummyFeature1, DummyFeature2.graphql_name => DummyFeature2) assert_equal base_schema.query_analyzers + [query_analyzer], schema.query_analyzers assert_equal base_schema.multiplex_analyzers + [multiplex_analyzer], schema.multiplex_analyzers - assert_equal [GraphQL::Backtrace], schema.plugins.map(&:first) + assert_equal [GraphQL::Backtrace, GraphQL::Subscriptions::ActionCableSubscriptions, CustomSubscriptions], schema.plugins.map(&:first) assert_equal [GraphQL::Tracing::DataDogTracing, GraphQL::Backtrace::Tracer], base_schema.tracers assert_equal [GraphQL::Tracing::DataDogTracing, GraphQL::Backtrace::Tracer, GraphQL::Tracing::NewRelicTracing], schema.tracers + assert_instance_of CustomSubscriptions, schema.subscriptions end end