graphql-pundit2 0.9.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.codeclimate.yml +16 -0
- data/.gitignore +15 -0
- data/.hound.yml +7 -0
- data/.rspec +3 -0
- data/.rubocop.yml +95 -0
- data/.ruby-version +1 -0
- data/.stickler.yml +7 -0
- data/.travis.yml +19 -0
- data/Gemfile +6 -0
- data/LICENSE.txt +21 -0
- data/README.md +368 -0
- data/Rakefile +8 -0
- data/bin/console +15 -0
- data/bin/setup +8 -0
- data/changelog.md +13 -0
- data/graphql-pundit2.gemspec +40 -0
- data/lib/graphql-pundit/authorization.rb +93 -0
- data/lib/graphql-pundit/common.rb +34 -0
- data/lib/graphql-pundit/field.rb +17 -0
- data/lib/graphql-pundit/instrumenter.rb +34 -0
- data/lib/graphql-pundit/instrumenters/after_scope.rb +24 -0
- data/lib/graphql-pundit/instrumenters/authorization.rb +77 -0
- data/lib/graphql-pundit/instrumenters/before_scope.rb +30 -0
- data/lib/graphql-pundit/instrumenters/scope.rb +90 -0
- data/lib/graphql-pundit/scope.rb +62 -0
- data/lib/graphql-pundit/version.rb +7 -0
- data/lib/graphql-pundit2.rb +53 -0
- metadata +258 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 66b36277a450b0c70ea3b33b8446da7657b789a1fa78c17bfa464309a23f4561
|
4
|
+
data.tar.gz: d0be03c7b35198615b5072c4ac39425d603671dd08bd339446fbb5146e7726e3
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 89f1d751d29daf813605d7ee026d4c9d01e9fd646d19f9ec2cce3cbd164405ec566a3a7ee47345ad2dcaeb0ae4f9792c8bb40562bfee8b0eff867ea670e834cc
|
7
|
+
data.tar.gz: c2aaa8e6d4d41f5f2925251f44c7714699d14900db465ee542054296185e6e37bcf61e84190ceaf0ddb633725755920f66a50848dfc77680f8fe3611d096db3c
|
data/.codeclimate.yml
ADDED
data/.gitignore
ADDED
data/.hound.yml
ADDED
data/.rspec
ADDED
data/.rubocop.yml
ADDED
@@ -0,0 +1,95 @@
|
|
1
|
+
AllCops:
|
2
|
+
TargetRubyVersion: 2.4
|
3
|
+
NewCops: enable
|
4
|
+
|
5
|
+
CacheRootDirectory: /tmp
|
6
|
+
AllowSymlinksInCacheRootDirectory: true
|
7
|
+
|
8
|
+
Exclude:
|
9
|
+
- 'apidoc/**/*'
|
10
|
+
- 'bin/bundle'
|
11
|
+
- 'bin/rails'
|
12
|
+
- 'bin/rake'
|
13
|
+
- 'bin/setup'
|
14
|
+
- 'bin/spring'
|
15
|
+
- 'bin/update'
|
16
|
+
- 'config/deploy/*.rb'
|
17
|
+
- 'config/mixins/applications/*.rb'
|
18
|
+
- 'data/**/*'
|
19
|
+
- 'db/schema.rb'
|
20
|
+
- 'node_modules/**/*'
|
21
|
+
- 'spec/dummy/**/*'
|
22
|
+
- 'vendor/**/*'
|
23
|
+
- 'repositories/**/*'
|
24
|
+
- 'repos/**/*'
|
25
|
+
- 'tmp/**/*'
|
26
|
+
|
27
|
+
Layout/ParameterAlignment:
|
28
|
+
Enabled: false
|
29
|
+
|
30
|
+
Layout/MultilineMethodCallIndentation:
|
31
|
+
EnforcedStyle: indented
|
32
|
+
|
33
|
+
Metrics/BlockLength:
|
34
|
+
Exclude:
|
35
|
+
- 'app/graphql/**/*'
|
36
|
+
- 'config/routes.rb'
|
37
|
+
- 'config/environments/**/*'
|
38
|
+
- 'config/initializers/devise.rb'
|
39
|
+
- 'lib/tasks/**/*.rake'
|
40
|
+
- 'spec/**/*'
|
41
|
+
- 'db/migrate/*'
|
42
|
+
- '*.gemspec'
|
43
|
+
|
44
|
+
Layout/LineLength:
|
45
|
+
Exclude:
|
46
|
+
- 'app/graphql/**/*_enum.rb'
|
47
|
+
- 'config/initializers/devise.rb'
|
48
|
+
|
49
|
+
Naming/FileName:
|
50
|
+
Exclude:
|
51
|
+
- config/deploy/*.rb
|
52
|
+
- config/mixins/applications/*.rb
|
53
|
+
- lib/git-shell.rb
|
54
|
+
- lib/graphql-pundit.rb
|
55
|
+
- lib/hets-agent.rb
|
56
|
+
- lib/ontohub-models.rb
|
57
|
+
- spec/lib/git-shell_spec.rb
|
58
|
+
|
59
|
+
Style/OptionalBooleanParameter:
|
60
|
+
Enabled: false
|
61
|
+
|
62
|
+
Naming/MethodParameterName:
|
63
|
+
Exclude:
|
64
|
+
- 'spec/**/*'
|
65
|
+
|
66
|
+
Style/Documentation:
|
67
|
+
Enabled: false
|
68
|
+
|
69
|
+
Style/DoubleNegation:
|
70
|
+
Enabled: false
|
71
|
+
|
72
|
+
Style/FormatStringToken:
|
73
|
+
Enabled: false
|
74
|
+
|
75
|
+
Style/NumericLiterals:
|
76
|
+
Enabled: false
|
77
|
+
|
78
|
+
Style/PercentLiteralDelimiters:
|
79
|
+
PreferredDelimiters:
|
80
|
+
default: ()
|
81
|
+
'%i': '()'
|
82
|
+
'%I': '()'
|
83
|
+
'%r': '{}'
|
84
|
+
'%w': '()'
|
85
|
+
'%W': '()'
|
86
|
+
|
87
|
+
Style/SymbolArray:
|
88
|
+
Exclude:
|
89
|
+
- 'db/migrate/**'
|
90
|
+
|
91
|
+
Style/TrailingCommaInArrayLiteral:
|
92
|
+
EnforcedStyleForMultiline: comma
|
93
|
+
|
94
|
+
Style/TrailingCommaInHashLiteral:
|
95
|
+
EnforcedStyleForMultiline: comma
|
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
2.7.2
|
data/.stickler.yml
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2017 Tom Gehrke
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in
|
13
|
+
all copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
21
|
+
THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,368 @@
|
|
1
|
+
[](https://travis-ci.com/lubosch/graphql-pundit)
|
2
|
+
[](https://codecov.io/gh/lubosch/graphql-pundit)
|
3
|
+
|
4
|
+
# GraphQL::Pundit
|
5
|
+
|
6
|
+
Original repository has been archived so I am continuing working on it,
|
7
|
+
fixing bugs and adding new features if requested.
|
8
|
+
|
9
|
+
## Installation
|
10
|
+
|
11
|
+
Add this line to your application's Gemfile:
|
12
|
+
|
13
|
+
```ruby
|
14
|
+
gem 'graphql-pundit2'
|
15
|
+
```
|
16
|
+
|
17
|
+
And then execute:
|
18
|
+
|
19
|
+
```bash
|
20
|
+
$ bundle
|
21
|
+
```
|
22
|
+
|
23
|
+
## Upgrading notes
|
24
|
+
|
25
|
+
# If you are coming from ontobot
|
26
|
+
|
27
|
+
Add this to your schema definition:
|
28
|
+
|
29
|
+
```
|
30
|
+
use GraphQL::Execution::Interpreter
|
31
|
+
use GraphQL::Analysis::AST
|
32
|
+
```
|
33
|
+
|
34
|
+
## Usage
|
35
|
+
|
36
|
+
### Class based API (`graphql-ruby >= 1.8`)
|
37
|
+
|
38
|
+
To use `graphql-pundit` with the class based API introduced in `graphql`
|
39
|
+
version 1.8, the used `Field` class must be changed:
|
40
|
+
|
41
|
+
It is recommended to have application-specific base classes, from which the
|
42
|
+
other types inherit (similar to having an `ApplicationController` from which
|
43
|
+
all other controllers inherit). That base class can be used to define a
|
44
|
+
custom field class, on which the new `graphql-pundit` API builds.
|
45
|
+
|
46
|
+
```ruby
|
47
|
+
class BaseObject < GraphQL::Schema::Object
|
48
|
+
field_class GraphQL::Pundit::Field
|
49
|
+
end
|
50
|
+
```
|
51
|
+
|
52
|
+
All other object types now inherit from `BaseObject`, and that is all that is
|
53
|
+
needed to get `graphql-pundit` working with the class based API.
|
54
|
+
|
55
|
+
In case you already use a custom field type, or if you want to use a context
|
56
|
+
key other than `:current_user` to make your current user available, you can
|
57
|
+
include `graphql-pundit`'s functionality into your field type:
|
58
|
+
|
59
|
+
```ruby
|
60
|
+
class MyFieldType < GraphQL::Schema::Field
|
61
|
+
prepend GraphQL::Pundit::Scope
|
62
|
+
prepend GraphQL::Pundit::Authorization
|
63
|
+
|
64
|
+
current_user :me # if the current_user is passed in as context[:me]
|
65
|
+
end
|
66
|
+
```
|
67
|
+
|
68
|
+
When using this, make sure the order of `prepend`s is correct, as you usually want the authorization to happen **first**, which means that it needs to be `prepend`ed **after** the scopes (if you need them).
|
69
|
+
|
70
|
+
#### Usage
|
71
|
+
|
72
|
+
```ruby
|
73
|
+
class Car < BaseObject
|
74
|
+
field :trunk, CarContent, null: true,
|
75
|
+
authorize: true
|
76
|
+
end
|
77
|
+
```
|
78
|
+
|
79
|
+
The above example shows the most basic usage of this gem. The example would
|
80
|
+
use `CarPolicy#trunk?` for authorizing access to the field, passing in the
|
81
|
+
parent object (in this case probably a `Car` model).
|
82
|
+
|
83
|
+
##### Options
|
84
|
+
|
85
|
+
Two styles of declaring fields is supported:
|
86
|
+
|
87
|
+
1. the inline style, passing all the options as a hash to the field method
|
88
|
+
2. the block style
|
89
|
+
|
90
|
+
Both styles are presented below side by side.
|
91
|
+
|
92
|
+
###### `authorize` and `authorize!`
|
93
|
+
|
94
|
+
To use authorization on a field, you **must** pass either the `authorize` or
|
95
|
+
`authorize!` option. Both options will cause the field to return `nil` if the
|
96
|
+
access is unauthorized, but `authorize!` will also add an error message (e.g.
|
97
|
+
for usage with mutations).
|
98
|
+
|
99
|
+
`authorize` and `authorize!` can be passed three different things:
|
100
|
+
|
101
|
+
```ruby
|
102
|
+
class User < BaseObject
|
103
|
+
# will use the `UserPolicy#display_name?` method
|
104
|
+
field :display_name, ..., authorize: true
|
105
|
+
field :display_name, ... do
|
106
|
+
authorize
|
107
|
+
end
|
108
|
+
|
109
|
+
# will use the passed lambda instead of a policy method
|
110
|
+
field :password_hash, ..., authorize: ->(obj, args, ctx) { ... }
|
111
|
+
field :password_hash, ... do
|
112
|
+
authorize ->(obj, args, ctx) { ... }
|
113
|
+
end
|
114
|
+
|
115
|
+
# will use the `UserPolicy#personal_info?` method
|
116
|
+
field :email, ..., authorize: :personal_info
|
117
|
+
field :email, ... do
|
118
|
+
authorize :personal_info
|
119
|
+
end
|
120
|
+
end
|
121
|
+
```
|
122
|
+
|
123
|
+
- `true` will trigger the inference mechanism, meaning that the method that will be called on the policy class will be inferred from the (snake_case) field name.
|
124
|
+
- a lambda function that will be called with the parent object, the arguments of the field and the context object; if the lambda returns a truthy value, authorization succeeds; otherwise (including thrown exceptions), authorization fails
|
125
|
+
- a string or a symbol that corresponds to the policy method that should be called **minus the "?"**
|
126
|
+
|
127
|
+
###### `policy`
|
128
|
+
|
129
|
+
`policy` is an optional argument that can also be passed three different values:
|
130
|
+
|
131
|
+
```ruby
|
132
|
+
class User < BaseObject
|
133
|
+
# will use the `UserPolicy#display_name?` method (default inference)
|
134
|
+
field :display_name, ..., authorize: true, policy: nil
|
135
|
+
field :display_name do
|
136
|
+
authorize policy: nil
|
137
|
+
end
|
138
|
+
|
139
|
+
# will use OtherUserPolicy#password_hash?
|
140
|
+
field :password_hash, ...,
|
141
|
+
authorize: true,
|
142
|
+
policy: ->(obj, args, ctx) { OtherUserPolicy }
|
143
|
+
field :password_hash, ... do
|
144
|
+
authorize policy: ->(obj, args, ctx) { OtherUserPolicy }
|
145
|
+
end
|
146
|
+
|
147
|
+
# will use MemberPolicy#email?
|
148
|
+
field :email, ..., authorize: true, policy: MemberPolicy
|
149
|
+
field :email, ... do
|
150
|
+
authorize policy: MemberPolicy
|
151
|
+
end
|
152
|
+
end
|
153
|
+
```
|
154
|
+
|
155
|
+
- `nil` is the default behavior and results in inferring the policy class from the record (see below)
|
156
|
+
- a lambda function that will be called with the parent object, the arguments of the field and the context object; the return value of this function will be used as the policy class
|
157
|
+
- an actual policy class
|
158
|
+
|
159
|
+
###### `record`
|
160
|
+
|
161
|
+
`record` can be used to pass a different value to the policy. Like `policy`,
|
162
|
+
this argument also can receive three different values:
|
163
|
+
|
164
|
+
```ruby
|
165
|
+
class User < BaseObject
|
166
|
+
# will use the parent object
|
167
|
+
field :display_name, ..., authorize: true, record: nil
|
168
|
+
field :display_name do
|
169
|
+
authorize record: nil
|
170
|
+
end
|
171
|
+
|
172
|
+
# will use the current user as the record
|
173
|
+
field :password_hash, ...,
|
174
|
+
authorize: true,
|
175
|
+
record: ->(obj, args, ctx) { ctx[:current_user] }
|
176
|
+
field :password_hash, ... do
|
177
|
+
authorize record: ->(obj, args, ctx) { ctx[:current_user] }
|
178
|
+
end
|
179
|
+
|
180
|
+
# will use AccountPolicy#email? with the first account as the record (the policy was inferred from the record class)
|
181
|
+
field :email, ..., authorize: true, record: Account.first
|
182
|
+
field :email, ... do
|
183
|
+
authorize record: Account.first
|
184
|
+
end
|
185
|
+
end
|
186
|
+
```
|
187
|
+
|
188
|
+
- `nil` is again used for the inference; in this case, the parent object is used
|
189
|
+
- a lambda function, again called with the parent object, the field arguments and the context object; the result will be used as the record
|
190
|
+
- any other value that will be used as the record
|
191
|
+
|
192
|
+
Using `record` can be helpful for e.g. mutations, where you need a value to
|
193
|
+
initialize the policy with, but for mutations there is no parent object.
|
194
|
+
|
195
|
+
###### `before_scope` and `after_scope`
|
196
|
+
|
197
|
+
`before_scope` and `after_scope` can be used to apply Pundit scopes to the
|
198
|
+
fields. Both options can be combined freely within one field. The result of
|
199
|
+
`before_scope` is passed to the resolver as the "parent object", while the
|
200
|
+
result of `after_scope` is returned as the result of the field.
|
201
|
+
|
202
|
+
```ruby
|
203
|
+
class User < BaseObject
|
204
|
+
# will use the `PostPolicy::Scope` before the resolver
|
205
|
+
field :posts, ..., before_scope: true
|
206
|
+
field :posts, ... do
|
207
|
+
before_scope
|
208
|
+
end
|
209
|
+
|
210
|
+
# will use the passed lambda after the resolver
|
211
|
+
field :comments, ..., after_scope: ->(comments, args, ctx) { ... }
|
212
|
+
field :comments, ... do
|
213
|
+
after_scope ->(comments, args, ctx) { ... }
|
214
|
+
end
|
215
|
+
|
216
|
+
# will use the `FriendPolicy::Scope`
|
217
|
+
field :friends, ..., after_scope: FriendPolicy
|
218
|
+
field :friends, ... do
|
219
|
+
after_scope FriendPolicy
|
220
|
+
end
|
221
|
+
end
|
222
|
+
```
|
223
|
+
|
224
|
+
- `true` will trigger the inference mechanism, where the policy class, which contains the scope class, is inferred based on either the parent object (for `before_scope`) or the result of the resolver (for `after_scope`).
|
225
|
+
- a lambda function, that will be called with the parent object (for `before_scope`) or the result of the resolver (for `after_scope`), the field arguments and the context
|
226
|
+
- a policy class that contains a `Scope` class (this does not actually have to be a policy class, but could also be a module containing a `Scope` class)
|
227
|
+
|
228
|
+
###### Combining options
|
229
|
+
|
230
|
+
All options can be combined with one another (except `authorize` and `authorize!`; please don't do that). Examples:
|
231
|
+
|
232
|
+
```ruby
|
233
|
+
# MemberPolicy#name? initialized with the parent
|
234
|
+
field :display_name, ..., authorize: :name,
|
235
|
+
policy: MemberPolicy
|
236
|
+
|
237
|
+
# UserPolicy#display_name? initialized with user.account_data
|
238
|
+
field :display_name, ..., do
|
239
|
+
authorize policy: UserPolicy,
|
240
|
+
record: ->(obj, args, ctx) { obj.account_data }
|
241
|
+
end
|
242
|
+
```
|
243
|
+
|
244
|
+
### Legacy `define` API
|
245
|
+
|
246
|
+
The legacy `define` based API will be supported until it is removed from the
|
247
|
+
`graphql` gem (as planned for version 1.10).
|
248
|
+
|
249
|
+
#### Add the authorization middleware
|
250
|
+
|
251
|
+
Add the following to your GraphQL schema:
|
252
|
+
|
253
|
+
```ruby
|
254
|
+
MySchema = GraphQL::Schema.define do
|
255
|
+
...
|
256
|
+
instrument(:field, GraphQL::Pundit::Instrumenter.new)
|
257
|
+
...
|
258
|
+
end
|
259
|
+
```
|
260
|
+
|
261
|
+
By default, `ctx[:current_user]` will be used as the user to authorize. To change that behavior, pass a symbol to `GraphQL::Pundit::Instrumenter`.
|
262
|
+
|
263
|
+
```ruby
|
264
|
+
GraphQL::Pundit::Instrumenter.new(:me) # will use ctx[:me]
|
265
|
+
```
|
266
|
+
|
267
|
+
#### Authorize fields
|
268
|
+
|
269
|
+
For each field you want to authorize via Pundit, add the following code to the field definition:
|
270
|
+
|
271
|
+
```ruby
|
272
|
+
field :email do
|
273
|
+
authorize # will use UserPolicy#email?
|
274
|
+
resolve ...
|
275
|
+
end
|
276
|
+
```
|
277
|
+
|
278
|
+
By default, this will use the Policy for the parent object (the first argument passed to the resolve proc), checking for `:email?` for the current user. Sometimes, the field name will differ from the policy method name, in which case you can specify it explicitly:
|
279
|
+
|
280
|
+
```ruby
|
281
|
+
field :email do
|
282
|
+
authorize :read_email # will use UserPolicy#read_email?
|
283
|
+
resolve ...
|
284
|
+
end
|
285
|
+
```
|
286
|
+
|
287
|
+
Now, in some cases you'll want to use a different policy, or in case of mutations, the passed object might be `nil`:
|
288
|
+
|
289
|
+
```ruby
|
290
|
+
field :createUser
|
291
|
+
authorize! :create, policy: User # or User.new; will use UserPolicy#create?
|
292
|
+
resolve ...
|
293
|
+
end
|
294
|
+
```
|
295
|
+
|
296
|
+
This will use the `:create?` method of the `UserPolicy`. You can also pass in objects instead of a class (or symbol), if you wish to authorize the user for the specific object.
|
297
|
+
|
298
|
+
If you want to pass a different value to the policy, you can use the keyword argument `record`:
|
299
|
+
|
300
|
+
```ruby
|
301
|
+
field :createUser
|
302
|
+
authorize! :create, record: User.new # or User.new; will use UserPolicy#create?
|
303
|
+
resolve ...
|
304
|
+
end
|
305
|
+
```
|
306
|
+
|
307
|
+
You can also pass a `lambda` as a record. This receives the usual three arguments (parent value, arguments, context) and returns the value to be used as a record.
|
308
|
+
|
309
|
+
You might have also noticed the use of `authorize!` instead of `authorize` in this example. The difference between the two is this:
|
310
|
+
|
311
|
+
- `authorize` will set the field to `nil` if authorization fails
|
312
|
+
- `authorize!` will set the field to `nil` and add an error to the response if authorization fails
|
313
|
+
|
314
|
+
You would normally want to use `authorize` for fields in queries, that only e.g. the owner of something can see, while `authorize!` would be usually used in mutations, where you want to communicate to the client that the operation failed because the user is unauthorized.
|
315
|
+
|
316
|
+
If you still need more control over how policies are called, you can pass a lambda to `authorize`:
|
317
|
+
|
318
|
+
```ruby
|
319
|
+
field :email
|
320
|
+
authorize ->(obj, args, ctx) { UserPolicy.new(obj, ctx[:me]).private_data?(:email) }
|
321
|
+
resolve ...
|
322
|
+
end
|
323
|
+
```
|
324
|
+
|
325
|
+
If the lambda returns a falsy value or raises a `Pundit::UnauthorizedError` the field will resolve to `nil`, if it returns a truthy value, control will be passed to the resolve function. Of course, this can be used with `authorize!` as well.
|
326
|
+
|
327
|
+
#### Scopes
|
328
|
+
|
329
|
+
Pundit scopes are supported by using `before_scope` and `after_scope` in the field definition
|
330
|
+
|
331
|
+
```ruby
|
332
|
+
field :posts
|
333
|
+
after_scope
|
334
|
+
resolve ...
|
335
|
+
end
|
336
|
+
```
|
337
|
+
|
338
|
+
Passing no arguments to `after_scope` and `before_scope` will infer the policy to use from the value it is passed: `before_scope` is run before `resolve` and will receive the parent object, `after_scope` will be run after `resolve` and receives the output of `resolve`. You can also pass a proc or a policy class to both `_scope`s:
|
339
|
+
|
340
|
+
```ruby
|
341
|
+
field :posts
|
342
|
+
before_scope ->(_root, _args, ctx) { Post.where(owner: ctx[:current_user]) }
|
343
|
+
resolve ->(posts, args, ctx) { ... }
|
344
|
+
end
|
345
|
+
```
|
346
|
+
|
347
|
+
```ruby
|
348
|
+
field :posts
|
349
|
+
after_scope PostablePolicy
|
350
|
+
resolve ...
|
351
|
+
end
|
352
|
+
```
|
353
|
+
|
354
|
+
## Development
|
355
|
+
|
356
|
+
After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
357
|
+
|
358
|
+
To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
|
359
|
+
|
360
|
+
## Contributing
|
361
|
+
|
362
|
+
Bug reports and pull requests are welcome on GitHub at https://github.com/lubosch/graphql-pundit.
|
363
|
+
|
364
|
+
|
365
|
+
## License
|
366
|
+
|
367
|
+
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
|
368
|
+
|
data/Rakefile
ADDED
data/bin/console
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
#!/usr/bin/env ruby
|
3
|
+
|
4
|
+
require 'bundler/setup'
|
5
|
+
require 'graphql/pundit'
|
6
|
+
|
7
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
8
|
+
# with your gem easier. You can also use a different console, if you like.
|
9
|
+
|
10
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
11
|
+
# require "pry"
|
12
|
+
# Pry.start
|
13
|
+
|
14
|
+
require 'irb'
|
15
|
+
IRB.start(__FILE__)
|
data/bin/setup
ADDED
data/changelog.md
ADDED
@@ -0,0 +1,40 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
lib = File.expand_path('lib', __dir__)
|
4
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
5
|
+
require 'graphql-pundit/version'
|
6
|
+
|
7
|
+
Gem::Specification.new do |spec|
|
8
|
+
spec.name = 'graphql-pundit2'
|
9
|
+
spec.version = GraphQL::Pundit::VERSION
|
10
|
+
spec.authors = ['Lubomir Vnenk']
|
11
|
+
spec.email = ['lubomir.vnenk@zoho.com']
|
12
|
+
|
13
|
+
spec.summary = 'Pundit authorization support for new graphql interpreter'
|
14
|
+
spec.description = spec.summary
|
15
|
+
spec.homepage = 'https://github.com/lubosch/graphql-pundit'
|
16
|
+
spec.license = 'MIT'
|
17
|
+
spec.required_ruby_version = Gem::Requirement.new('>= 2.4.0')
|
18
|
+
|
19
|
+
spec.files = `git ls-files -z`.split("\x0").reject do |f|
|
20
|
+
f.match(%r{^(test|spec|features)/})
|
21
|
+
end
|
22
|
+
spec.bindir = 'exe'
|
23
|
+
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
24
|
+
spec.require_paths = ['lib']
|
25
|
+
|
26
|
+
spec.add_dependency 'graphql', '>= 1.6.4', '< 1.13.0'
|
27
|
+
spec.add_dependency 'pundit', '~> 2.1.0'
|
28
|
+
|
29
|
+
spec.add_development_dependency 'bundler', '~> 2.0'
|
30
|
+
spec.add_development_dependency 'codecov', '~> 0.1.10'
|
31
|
+
spec.add_development_dependency 'fuubar', '~> 2.5.0'
|
32
|
+
spec.add_development_dependency 'pry', '~> 0.13.1'
|
33
|
+
spec.add_development_dependency 'pry-byebug', '~> 3.9.0'
|
34
|
+
spec.add_development_dependency 'pry-rescue', '~> 1.5.0'
|
35
|
+
spec.add_development_dependency 'pry-stack_explorer', '~> 0.4.9.2'
|
36
|
+
spec.add_development_dependency 'rake', '~> 13.0'
|
37
|
+
spec.add_development_dependency 'rspec', '~> 3.6'
|
38
|
+
spec.add_development_dependency 'rubocop', '>= 0.83.0'
|
39
|
+
spec.add_development_dependency 'simplecov', '~> 0.18.5'
|
40
|
+
end
|