graphql-rails-resolver 0.1.3 → 0.1.4

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: daaae82f72286352c8b15b9c04ebe0f29cdb5c7d
4
- data.tar.gz: 8d6d288781cbe6643e005a7d618f174f96324833
3
+ metadata.gz: c3bd5d1d617b2c9a98b5c934e6338d121a3e1b9d
4
+ data.tar.gz: 52dcc208c579b92a5af7cb0b25e63ff756b48443
5
5
  SHA512:
6
- metadata.gz: a1d3162e913409721fb111794ec0cc2d325957852d126513123945683d97ab220fc16475ae391feea818014d02604f9e91a35fda4c8b12025f01e9c99adc4e78
7
- data.tar.gz: 2388a47c80fcfd9440322c14355587d6dd546866b95b9ff3402e3761c47faf459a517086c56470c3a850353f116736154bd75e22ce325cdff59f009021c9f152
6
+ metadata.gz: 7d6067d452c52d4b22492c36dd2317363cb73be52d0d9043dc446a5f756acdfe6221361aa39604e8319af882671525799c7b0f98076a72c26447d11e80789297
7
+ data.tar.gz: 61ec192ce50cfc125187eab6d212613f5036853fbf12376ec22e88f31e2d350b28bdd63d9a23d844968f956f979fa743d8a72826effacc4497f280d52196dce9
@@ -1,6 +1,10 @@
1
1
  # GraphQL::Rails::Resolver
2
2
  ## CHANGELOG
3
3
 
4
+ ### Version 0.1.4
5
+ Added `resolve` with parameters
6
+ Deprecates `resolve_where` and `resolve_scope`
7
+
4
8
  ### Version 0.1.3
5
9
  Added `resolve_scope` for resolving model scopes.
6
10
  Fixed `resolve_where` not being called and reworked class inheritance.
data/README.md CHANGED
@@ -88,43 +88,44 @@ Take the Resolver from the previous example. Using `GraphQL::Rails::Resolver`, w
88
88
  class Post < GraphQL::Rails::Resolver
89
89
  # ID argument is resolved in base class
90
90
 
91
- # Resolve :is_public to a class method
92
- resolve_method :is_public
93
-
94
91
  # Resolve :title, :created_at, :updated_at to Post.where() arguments
95
- resolve_where :title
96
- resolve_where :created_at
97
- resolve_where :updated_at
92
+ resolve :title
93
+ resolve :createdAt, :where => :created_at
94
+ resolve :updatedAt, :where => :updated_at
98
95
 
99
96
  # Resolve :featured argument with default test: if argument `featured` is present
100
- resolve_scope :featured
97
+ resolve :featured, :scope => :featured
101
98
 
102
99
  # Same resolution as the line above, but send the value to the scope function
103
- resolve_scope :featured, :with_value => true
100
+ resolve :featured, :scope => :featured, :with_value => true
104
101
 
105
- # Resolve :featured scope if it passes custom argument test
106
- resolve_scope :featured, -> (value) { value == :today }
102
+ # Resolve :featured scope to a dynamic scope name
103
+ resolve :is_public, :scope => -> (value) { value == true ? :is_public : :is_private}
107
104
 
108
- # Resolve :is_public argument with a different scope name
109
- resolve_scope :is_public, -> (value) { value != true }, :scope_name => :is_private
105
+ # Resolve :is_public to a class method
106
+ resolve :custom_arg, :custom_resolve_method
110
107
 
111
- def is_public(value)
112
- @result.is_public if value
113
- @result.is_private unless value
108
+ def custom_resolve_method(value)
109
+ ...
114
110
  end
115
111
 
112
+ # Resolve :is_public to a method on the model object
113
+ resolve :custom_arg, :model_obj_method
114
+
116
115
  end
117
116
  ```
118
117
 
119
- In the example above, there are three declarations:
118
+ In the examples above, the three primary arguments to `resolve` are:
119
+
120
+ `resolve :argument_name, ...`
120
121
 
121
- `resolve_where` is a declarative approach using `ActiveRecord.where` to resolve arguments.
122
+ `where` to specify another attribute.
122
123
 
123
- `resolve_scope` is an declarative way to call scopes on a model where a custom test for the argument can be specified with a closure.
124
+ `scope` to specify a scope on the model:
125
+ - `scope` accepts string/symbol "scope name" or a closure that returns a scope name or `nil`
124
126
  - Use `with_value` to send the argument value to the scope closure.
125
- - Use `scope_name` to map an argument to a scope by another name.
126
127
 
127
- `resolve_method` is an imperative approach that allows completely custom resolution.
128
+ Alternatively you can specify a symbol representing a method name: (ie: `resolve :arg_1, :custom_method`). The resolver will use it's own method if it exists, or else it will call the method on the object itself.
128
129
 
129
130
 
130
131
 
@@ -156,7 +157,7 @@ Resolvers::Post.new(Proc.new {
156
157
 
157
158
 
158
159
  # Needs Help
159
- I wanted to release this utility for the hopes of sparking interest in Rails integration with `graphql-ruby`. If you wish to contribute to this project, any pull request is warmly welcomed.
160
+ I wanted to release this utility for the hopes of sparking interest in Rails integration with `graphql-ruby`. If you wish to contribute to this project, any pull request is warmly welcomed.
160
161
 
161
162
  # Credits
162
163
  - Cole Turner ([@colepatrickturner](https://github.com/colepatrickturner))
@@ -1,7 +1,7 @@
1
1
  module GraphQL
2
2
  module Rails
3
3
  class Resolver
4
- VERSION = '0.1.3'
4
+ VERSION = '0.1.4'
5
5
 
6
6
  attr_accessor :resolvers
7
7
 
@@ -15,6 +15,7 @@ module GraphQL
15
15
  @args = nil
16
16
  @ctx = nil
17
17
  @resolvers = self.class.resolvers
18
+ @id_field = self.class.id_field
18
19
  end
19
20
 
20
21
  def call(obj, args, ctx)
@@ -25,13 +26,62 @@ module GraphQL
25
26
  @result = @callable.call(obj, args, ctx)
26
27
 
27
28
  # If there's an ID type, offer ID resolution_strategy
28
- if has_id_field and args.key? :id
29
- lookup_id(args[:id])
29
+ if has_id_argument and args.key? @id_field
30
+ lookup_id(args[@id_field])
30
31
  end
31
32
 
32
- @resolvers.each do |field,method|
33
+ @resolvers.each do |field,resolvers|
33
34
  if args.key? field
34
- @result = method.call(@result, args[field])
35
+ value = args[field]
36
+
37
+ resolvers.each do |method, params|
38
+ # Match scopes
39
+ if params.key? :scope
40
+ scope_name = params[:scope]
41
+ scope_name = scope_name.call(value) if scope_name.respond_to? :call
42
+
43
+ scope_args = []
44
+ scope_args.push(value) if params.key? :with_value && params[:with_value] == true
45
+
46
+ @result = @result.send(scope_name) unless scope_name.nil?
47
+ # Match custom methods
48
+ elsif params.key? :method
49
+ @result = send(params[:method], value)
50
+ elsif method.present?
51
+ # Match first param
52
+ if method.respond_to? :call
53
+ # Match implicit blocks
54
+ @result = method.call(value)
55
+ elsif self.respond_to? method
56
+ # Match method name to current resolver class
57
+ @result = send(method, value)
58
+ elsif @result.respond_to? method
59
+ # Match method name to object
60
+ @result = @result.send(method, value)
61
+ else
62
+ raise ArgumentError, "Unable to resolve parameter of type #{method.class} in #{self}"
63
+ end
64
+ elsif params.size < 1
65
+ if self.respond_to? field
66
+ @result = send(field, value)
67
+ elsif @result.method_defined? field and params[:where].present? == false
68
+ @result = @result.send(field, value)
69
+ else
70
+ attribute =
71
+ if params[:where].present?
72
+ params[:where]
73
+ else
74
+ field
75
+ end
76
+
77
+ hash = {}
78
+ hash[attribute] = value
79
+ @result = @result.where(hash)
80
+ end
81
+ else
82
+ raise ArgumentError, "Unable to resolve field #{field} in #{self}"
83
+ end
84
+ end
35
85
  end
36
86
  end
37
87
 
@@ -57,8 +107,22 @@ module GraphQL
57
107
  @ctx.ast_node.name
58
108
  end
59
109
 
110
+ def has_id_argument
111
+ @ctx.irep_node.definitions.any? do |type_defn, field_defn|
112
+ if field_defn.name === field_name
113
+ field_defn.arguments.any? do |k,v|
114
+ v.type == ::GraphQL::ID_TYPE or
115
+ (v.type.kind == ::GraphQL::TypeKinds::LIST and v.type.of_type == ::GraphQL::ID_TYPE)
116
+ end
117
+ else
118
+ false
119
+ end
120
+ end
121
+ end
122
+
60
123
  def has_id_field
61
- @ctx.irep_node.children.any? {|x| x[1].return_type == GraphQL::ID_TYPE }
124
+ warn "[DEPRECATION] `has_id_field` is deprecated. Please use `has_id_argument` instead."
125
+ has_id_argument
62
126
  end
63
127
 
64
128
  def connection?
@@ -77,62 +141,63 @@ module GraphQL
77
141
  "::#{self.class.name.demodulize}".constantize
78
142
  end
79
143
 
80
- def lookup_id(value)
144
+ def to_model_id(value)
81
145
  if is_global_id(value)
82
146
  type_name, id = NodeIdentification.from_global_id(value)
83
147
  constantized = "::#{type_name}".constantize
84
148
 
85
149
  if constantized == model
86
- @result = @result.where(:id => id)
150
+ id
87
151
  else
88
152
  nil
89
153
  end
90
154
  else
91
- @result = @result.where(:id => value)
155
+ value
156
+ end
157
+ end
158
+
159
+ def lookup_id(value)
160
+ if value.kind_of? Array
161
+ value = value.map { |v| to_model_id(v) }.compact
92
162
  end
163
+
164
+ @result = @result.where(:id => value)
93
165
  end
94
166
 
95
167
  class << self
168
+ @@id_field = :id
169
+
170
+ def id_field
171
+ @@id_field
172
+ end
96
173
 
97
174
  def resolvers
98
175
  @resolvers ||= {}
99
176
  @resolvers
100
177
  end
101
178
 
102
- def resolve(field, method)
179
+ def resolve(field, definition=nil, **otherArgs)
103
180
  @resolvers ||= {}
104
- @resolvers[field] = method
181
+ @resolvers[field] ||= []
182
+ @resolvers[field].push([definition, otherArgs])
105
183
  end
106
184
 
107
185
  def resolve_where(field)
108
- resolve(field, lambda { |obj, value|
109
- where = {}
110
- where[field] = value
111
-
112
- obj.where(where)
113
- })
186
+ warn "[DEPRECATION] `resolve_where` is deprecated. Please use `resolve` instead."
187
+ resolve(field)
114
188
  end
115
189
 
116
190
  def resolve_scope(field, test=nil, scope_name: nil, with_value: false)
191
+ warn "[DEPRECATION] `resolve_scope` is deprecated. Please use `resolve` instead."
117
192
  test = lambda { |value| value.present? } if test.nil?
118
193
  scope_name = field if scope_name.nil?
119
194
 
120
- resolve(field, lambda { |obj, value|
121
- args = []
122
- args.push(value) if with_value
123
-
124
- if test.call(value)
125
- obj.send(scope_name, *args)
126
- else
127
- obj
128
- end
129
- })
195
+ resolve(field, :scope => -> (value) { test.call(value) ? scope_name : nil }, :with_value => with_value)
130
196
  end
131
197
 
132
198
  def resolve_method(field)
133
- resolve(field, lambda { |obj, value|
134
- obj.send(field, value)
135
- })
199
+ warn "[DEPRECATION] `resolve_method` is deprecated. Please use `resolve` instead."
200
+ resolve(field)
136
201
  end
137
202
  end
138
203
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: graphql-rails-resolver
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.3
4
+ version: 0.1.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Cole Turner
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-09-28 00:00:00.000000000 Z
11
+ date: 2016-09-29 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: graphql