Module: GraphQLIncludable
- Extended by:
- ActiveSupport::Concern
- Defined in:
- lib/graphql_includable.rb
Defined Under Namespace
Modules: ClassMethods
Class Method Summary collapse
-
.find_association(return_model, child_name) ⇒ Object
find a valid association on return_model, following method delegation.
- .find_child_node_matching_model_name(node, model_name) ⇒ Object
- .generate_includes_from_graphql(query_context, model_name) ⇒ Object
- .includes_from_irep_node(node) ⇒ Object
- .node_has_active_record_children(node) ⇒ Object
- .node_return_class(node) ⇒ Object
- .node_returns_active_record?(node) ⇒ Boolean
-
.suggested_association_name(name, node) ⇒ Object
find the association to look for based on a field definition precedence is
includeskey, thenpropertykey, then the field name. -
.unwrapped_type(node) ⇒ Object
unwrap GraphQL ListType and NonNullType wrappers.
-
.wrap_delegate(contents, delegate, delegate_key = delegate) ⇒ Object
return raw contents, or contents wrapped in a hash (for delegated associations).
Class Method Details
.find_association(return_model, child_name) ⇒ Object
find a valid association on return_model, following method delegation
112 113 114 115 116 117 118 |
# File 'lib/graphql_includable.rb', line 112 def self.find_association(return_model, child_name) delegated_model = return_model.instance_variable_get('@delegate_cache').try(:[], child_name.to_sym) association_model = delegated_model ? return_model.reflect_on_association(delegated_model).klass : return_model association = association_model.reflect_on_association(child_name) [association, delegated_model] end |
.find_child_node_matching_model_name(node, model_name) ⇒ Object
35 36 37 38 39 40 41 42 43 44 45 46 47 |
# File 'lib/graphql_includable.rb', line 35 def self.find_child_node_matching_model_name(node, model_name) matching_node = nil return_type = unwrapped_type(node) if return_type.to_s == model_name matching_node = node elsif node.respond_to? :scoped_children node.scoped_children[return_type].each do |child_name, child_node| matching_node = find_child_node_matching_model_name(child_node, model_name) break if matching_node end end matching_node end |
.generate_includes_from_graphql(query_context, model_name) ⇒ Object
30 31 32 33 |
# File 'lib/graphql_includable.rb', line 30 def self.generate_includes_from_graphql(query_context, model_name) matching_node = GraphQLIncludable.find_child_node_matching_model_name(query_context.irep_node, model_name) GraphQLIncludable.includes_from_irep_node(matching_node) end |
.includes_from_irep_node(node) ⇒ Object
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 |
# File 'lib/graphql_includable.rb', line 49 def self.includes_from_irep_node(node) includes = [] nested_includes = {} return_type = unwrapped_type(node) return_model = node_return_class(node) return [] unless node && return_type && return_model node.scoped_children[return_type].each do |child_name, child_node| child_association_name, explicit_includes = suggested_association_name(child_name, child_node) association, delegated_model_name = find_association(return_model, child_association_name) if association child_includes = includes_from_irep_node(child_node) if node_has_active_record_children(child_node) && child_includes.size > 0 nested_includes[delegated_model_name || child_association_name] = wrap_delegate(child_includes, delegated_model_name, child_association_name) else includes << wrap_delegate(child_association_name, delegated_model_name) end elsif explicit_includes includes << explicit_includes end end includes << nested_includes if nested_includes.size > 0 includes end |
.node_has_active_record_children(node) ⇒ Object
77 78 79 80 81 |
# File 'lib/graphql_includable.rb', line 77 def self.node_has_active_record_children(node) node.scoped_children[unwrapped_type(node)].each do |child_return_name, child_node| node_returns_active_record?(child_node) end end |
.node_return_class(node) ⇒ Object
83 84 85 86 87 88 |
# File 'lib/graphql_includable.rb', line 83 def self.node_return_class(node) begin Object.const_get(unwrapped_type(node).name) rescue NameError end end |
.node_returns_active_record?(node) ⇒ Boolean
90 91 92 93 |
# File 'lib/graphql_includable.rb', line 90 def self.node_returns_active_record?(node) klass = node_return_class(node) klass && klass < ActiveRecord::Base end |
.suggested_association_name(name, node) ⇒ Object
find the association to look for based on a field definition precedence is includes key, then property key, then the field name
122 123 124 125 126 127 128 129 |
# File 'lib/graphql_includable.rb', line 122 def self.suggested_association_name(name, node) = node.definitions[0].[:includes] assoc_name = node.definitions[0].property || name assoc_name = if && .is_a?(Symbol) [assoc_name.to_sym, ] end |
.unwrapped_type(node) ⇒ Object
unwrap GraphQL ListType and NonNullType wrappers
105 106 107 108 109 |
# File 'lib/graphql_includable.rb', line 105 def self.unwrapped_type(node) type = node.return_type type = type.of_type while type.respond_to? :of_type type end |
.wrap_delegate(contents, delegate, delegate_key = delegate) ⇒ Object
return raw contents, or contents wrapped in a hash (for delegated associations)
96 97 98 99 100 101 102 |
# File 'lib/graphql_includable.rb', line 96 def self.wrap_delegate(contents, delegate, delegate_key = delegate) return contents unless delegate obj = {} obj[delegate_key] = contents obj end |