pundit-matchers 1.9.0 → 2.1.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 836bd12c848b5a4d68608155884e87515ab4f73926d064e6da1881369e1abb27
4
- data.tar.gz: b8346711d3bbfdee77779c8607e0dde827f2dec9c34dc3e58491c4aaa659a9f8
3
+ metadata.gz: ca57a9d5fc96cbacd89c5af52106a126fa6cf01d72654c677fa5e1a7a957e139
4
+ data.tar.gz: 5dd3c52dcf6cc289a76ba40947ff1d46fad538e5b6bfcec5484ba1d87b2092b9
5
5
  SHA512:
6
- metadata.gz: 7069911c4cbd5886ca4ace96a2417b9c1a1afe45c410ac0f1a5bfbf24866478491b8f9c135e4f98b25e2f8eb6113dc72f7dc03abd63b25ebe98e38f3dff84859
7
- data.tar.gz: 9ad39f93ad83169107df878f85c71bc75bc4478ab3d6e59ced4338bfd05accbedb646476772f2c32868bbf5272edee0e833c9e30c4a29d2b9b740bc6b02ea936
6
+ metadata.gz: e965e471adca0f06d4ab84e1d03f426902d5ac79bb69644afc88be3b158defb27bcd36d9170c6f47fbb3cbf7d832884a9b8f1e65bc3e7e0587d4ede6d75f9de5
7
+ data.tar.gz: e8c47b1311ab7afc3d119714ee12d605d0063dc315f38a70e7fc0b5761e99432cd6f3fceb109a504e82b4c61621147197291dbd59f5d1dceb434e7f6ec346d80
@@ -14,7 +14,7 @@ module Pundit
14
14
  module ErrorMessageFormatter
15
15
  def message
16
16
  "#{policy_name} expected to have all actions #{expected_kind}, " \
17
- "but #{mismatches_are(missed_expected_actions)} #{opposite_kind}"
17
+ "but #{mismatches_are(missed_expected_actions)} #{opposite_kind}"
18
18
  end
19
19
 
20
20
  private
@@ -0,0 +1,39 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pundit
4
+ module Matchers
5
+ module Utils
6
+ module OnlyActions
7
+ # Parent class for specific only_action matcher. Should not be used directly.
8
+ #
9
+ # Expects methods in child class:
10
+ # * actual_actions - list of actions which actually matches expected type.
11
+ class ActionsMatcher
12
+ attr_reader :policy_info, :expected_actions
13
+
14
+ def initialize(policy, expected_actions)
15
+ @policy_info = PolicyInfo.new(policy)
16
+ @expected_actions = expected_actions
17
+ end
18
+
19
+ def match?
20
+ missed_expected_actions.empty? &&
21
+ actual_actions.sort == expected_actions.sort
22
+ end
23
+
24
+ def unexpected_actions
25
+ @unexpected_actions ||= actual_actions - expected_actions
26
+ end
27
+
28
+ def missed_expected_actions
29
+ @missed_expected_actions ||= expected_actions - actual_actions
30
+ end
31
+
32
+ def policy
33
+ policy_info.policy
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,54 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Pundit
4
+ module Matchers
5
+ module Utils
6
+ module OnlyActions
7
+ # Adds #message method which generates failed assertion message
8
+ # for *_only_actions matchers.
9
+ #
10
+ # Expects methods to be defined:
11
+ # * matcher - instance which has `OnlyActions::ActionsMatcher` as a parent class
12
+ # * expected_kind - string with expected actions type (can be "forbidden" or "permitted")
13
+ # * opposite_kind - string with oposite then expected actions type (can be "permitted" or "forbidden")
14
+ module ErrorMessageFormatter
15
+ def message
16
+ "#{policy_name} expected to have only actions #{matcher.expected_actions} #{expected_kind}, but " \
17
+ "#{unless missed_expected_actions.empty?
18
+ "#{mismatches_are(missed_expected_actions)} #{opposite_kind} and "
19
+ end}" \
20
+ "#{mismatches_are(unexpected_actions)} #{expected_kind} too"
21
+ end
22
+
23
+ private
24
+
25
+ attr_reader :matcher, :expected_kind, :opposite_kind
26
+
27
+ def policy
28
+ matcher.policy
29
+ end
30
+
31
+ def unexpected_actions
32
+ matcher.unexpected_actions
33
+ end
34
+
35
+ def missed_expected_actions
36
+ matcher.missed_expected_actions
37
+ end
38
+
39
+ def policy_name
40
+ policy.class.name
41
+ end
42
+
43
+ def mismatches_are(mismatches)
44
+ if mismatches.count == 1
45
+ "#{mismatches} is"
46
+ else
47
+ "#{mismatches} are"
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end
53
+ end
54
+ end
@@ -0,0 +1,26 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'error_message_formatter'
4
+
5
+ module Pundit
6
+ module Matchers
7
+ module Utils
8
+ module OnlyActions
9
+ # Error message formatter for `forbid_only_actions` matcher.
10
+ class ForbiddenActionsErrorFormatter
11
+ include OnlyActions::ErrorMessageFormatter
12
+
13
+ def initialize(matcher)
14
+ @expected_kind = 'forbidden'
15
+ @opposite_kind = 'permitted'
16
+ @matcher = matcher
17
+ end
18
+
19
+ private
20
+
21
+ attr_reader :matcher, :expected_kind, :opposite_kind
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'actions_matcher'
4
+
5
+ module Pundit
6
+ module Matchers
7
+ module Utils
8
+ module OnlyActions
9
+ # Handles all the checks in `forbid_only_actions` matcher.
10
+ class ForbiddenActionsMatcher < OnlyActions::ActionsMatcher
11
+ private
12
+
13
+ def actual_actions
14
+ policy_info.forbidden_actions
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,26 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'error_message_formatter'
4
+
5
+ module Pundit
6
+ module Matchers
7
+ module Utils
8
+ module OnlyActions
9
+ # Error message formatter for `permit_only_actions` matcher.
10
+ class PermittedActionsErrorFormatter
11
+ include OnlyActions::ErrorMessageFormatter
12
+
13
+ def initialize(matcher)
14
+ @expected_kind = 'permitted'
15
+ @opposite_kind = 'forbidden'
16
+ @matcher = matcher
17
+ end
18
+
19
+ private
20
+
21
+ attr_reader :matcher, :expected_kind, :opposite_kind
22
+ end
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'actions_matcher'
4
+
5
+ module Pundit
6
+ module Matchers
7
+ module Utils
8
+ module OnlyActions
9
+ # Handles all the checks in `permit_only_actions` matcher.
10
+ class PermittedActionsMatcher < OnlyActions::ActionsMatcher
11
+ private
12
+
13
+ def actual_actions
14
+ policy_info.permitted_actions
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
@@ -8,6 +8,11 @@ module Pundit
8
8
  require_relative 'matchers/utils/all_actions/permitted_actions_error_formatter'
9
9
  require_relative 'matchers/utils/all_actions/permitted_actions_matcher'
10
10
 
11
+ require_relative 'matchers/utils/only_actions/forbidden_actions_error_formatter'
12
+ require_relative 'matchers/utils/only_actions/forbidden_actions_matcher'
13
+ require_relative 'matchers/utils/only_actions/permitted_actions_error_formatter'
14
+ require_relative 'matchers/utils/only_actions/permitted_actions_matcher'
15
+
11
16
  class Configuration
12
17
  attr_accessor :user_alias
13
18
 
@@ -26,12 +31,12 @@ module Pundit
26
31
  end
27
32
  end
28
33
 
29
- RSpec::Matchers.define :forbid_action do |action, *args|
34
+ RSpec::Matchers.define :forbid_action do |action, *args, **kwargs|
30
35
  match do |policy|
31
36
  if args.any?
32
- !policy.public_send("#{action}?", *args)
37
+ !policy.public_send("#{action}?", *args, **kwargs)
33
38
  else
34
- !policy.public_send("#{action}?")
39
+ !policy.public_send("#{action}?", **kwargs)
35
40
  end
36
41
  end
37
42
 
@@ -53,6 +58,7 @@ module Pundit
53
58
  actions.flatten!
54
59
  match do |policy|
55
60
  return false if actions.count < 1
61
+
56
62
  @allowed_actions = actions.select do |action|
57
63
  policy.public_send("#{action}?")
58
64
  end
@@ -62,14 +68,14 @@ module Pundit
62
68
  attr_reader :allowed_actions
63
69
 
64
70
  zero_actions_failure_message = 'At least one action must be ' \
65
- 'specified when using the forbid_actions matcher.'
71
+ 'specified when using the forbid_actions matcher.'
66
72
 
67
73
  failure_message do |policy|
68
74
  if actions.count.zero?
69
75
  zero_actions_failure_message
70
76
  else
71
77
  "#{policy.class} expected to forbid #{actions}, but allowed " \
72
- "#{allowed_actions} for " +
78
+ "#{allowed_actions} for " +
73
79
  policy.public_send(Pundit::Matchers.configuration.user_alias)
74
80
  .inspect + '.'
75
81
  end
@@ -80,7 +86,7 @@ module Pundit
80
86
  zero_actions_failure_message
81
87
  else
82
88
  "#{policy.class} expected to permit #{actions}, but forbade " \
83
- "#{allowed_actions} for " +
89
+ "#{allowed_actions} for " +
84
90
  policy.public_send(Pundit::Matchers.configuration.user_alias)
85
91
  .inspect + '.'
86
92
  end
@@ -107,7 +113,7 @@ module Pundit
107
113
 
108
114
  RSpec::Matchers.define :forbid_mass_assignment_of do |attributes|
109
115
  # Map single object argument to an array, if necessary
110
- attributes = attributes.is_a?(Array) ? attributes : [attributes]
116
+ attributes = [attributes] unless attributes.is_a?(Array)
111
117
 
112
118
  match do |policy|
113
119
  return false if attributes.count < 1
@@ -130,22 +136,22 @@ module Pundit
130
136
  end
131
137
 
132
138
  zero_attributes_failure_message = 'At least one attribute must be ' \
133
- 'specified when using the forbid_mass_assignment_of matcher.'
139
+ 'specified when using the forbid_mass_assignment_of matcher.'
134
140
 
135
141
  failure_message do |policy|
136
142
  if attributes.count.zero?
137
143
  zero_attributes_failure_message
138
144
  elsif defined? @action
139
145
  "#{policy.class} expected to forbid the mass assignment of the " \
140
- "attributes #{attributes} when authorising the #{@action} action, " \
141
- 'but allowed the mass assignment of the attributes ' \
142
- "#{allowed_attributes} for " +
146
+ "attributes #{attributes} when authorising the #{@action} action, " \
147
+ 'but allowed the mass assignment of the attributes ' \
148
+ "#{allowed_attributes} for " +
143
149
  policy.public_send(Pundit::Matchers.configuration.user_alias)
144
150
  .inspect + '.'
145
151
  else
146
152
  "#{policy.class} expected to forbid the mass assignment of the " \
147
- "attributes #{attributes}, but allowed the mass assignment of " \
148
- "the attributes #{allowed_attributes} for " +
153
+ "attributes #{attributes}, but allowed the mass assignment of " \
154
+ "the attributes #{allowed_attributes} for " +
149
155
  policy.public_send(Pundit::Matchers.configuration.user_alias)
150
156
  .inspect + '.'
151
157
  end
@@ -156,15 +162,15 @@ module Pundit
156
162
  zero_attributes_failure_message
157
163
  elsif defined? @action
158
164
  "#{policy.class} expected to permit the mass assignment of the " \
159
- "attributes #{attributes} when authorising the #{@action} action, " \
160
- 'but permitted the mass assignment of the attributes ' \
161
- "#{allowed_attributes} for " +
165
+ "attributes #{attributes} when authorising the #{@action} action, " \
166
+ 'but permitted the mass assignment of the attributes ' \
167
+ "#{allowed_attributes} for " +
162
168
  policy.public_send(Pundit::Matchers.configuration.user_alias)
163
169
  .inspect + '.'
164
170
  else
165
171
  "#{policy.class} expected to permit the mass assignment of the " \
166
- "attributes #{attributes}, but permitted the mass assignment of " \
167
- "the attributes #{allowed_attributes} for " +
172
+ "attributes #{attributes}, but permitted the mass assignment of " \
173
+ "the attributes #{allowed_attributes} for " +
168
174
  policy.public_send(Pundit::Matchers.configuration.user_alias)
169
175
  .inspect + '.'
170
176
  end
@@ -189,12 +195,12 @@ module Pundit
189
195
  end
190
196
  end
191
197
 
192
- RSpec::Matchers.define :permit_action do |action, *args|
198
+ RSpec::Matchers.define :permit_action do |action, *args, **kwargs|
193
199
  match do |policy|
194
200
  if args.any?
195
- policy.public_send("#{action}?", *args)
201
+ policy.public_send("#{action}?", *args, **kwargs)
196
202
  else
197
- policy.public_send("#{action}?")
203
+ policy.public_send("#{action}?", **kwargs)
198
204
  end
199
205
  end
200
206
 
@@ -215,6 +221,7 @@ module Pundit
215
221
  actions.flatten!
216
222
  match do |policy|
217
223
  return false if actions.count < 1
224
+
218
225
  @forbidden_actions = actions.reject do |action|
219
226
  policy.public_send("#{action}?")
220
227
  end
@@ -235,6 +242,7 @@ module Pundit
235
242
  tests would pass.'
236
243
 
237
244
  return true if actions.count < 1
245
+
238
246
  @forbidden_actions = actions.reject do |action|
239
247
  policy.public_send("#{action}?")
240
248
  end
@@ -244,14 +252,14 @@ module Pundit
244
252
  attr_reader :forbidden_actions
245
253
 
246
254
  zero_actions_failure_message = 'At least one action must be specified ' \
247
- 'when using the permit_actions matcher.'
255
+ 'when using the permit_actions matcher.'
248
256
 
249
257
  failure_message do |policy|
250
258
  if actions.count.zero?
251
259
  zero_actions_failure_message
252
260
  else
253
261
  "#{policy.class} expected to permit #{actions}, but forbade " \
254
- "#{forbidden_actions} for " +
262
+ "#{forbidden_actions} for " +
255
263
  policy.public_send(Pundit::Matchers.configuration.user_alias)
256
264
  .inspect + '.'
257
265
  end
@@ -262,7 +270,7 @@ module Pundit
262
270
  zero_actions_failure_message
263
271
  else
264
272
  "#{policy.class} expected to forbid #{actions}, but allowed " \
265
- "#{forbidden_actions} for " +
273
+ "#{forbidden_actions} for " +
266
274
  policy.public_send(Pundit::Matchers.configuration.user_alias)
267
275
  .inspect + '.'
268
276
  end
@@ -289,7 +297,7 @@ module Pundit
289
297
 
290
298
  RSpec::Matchers.define :permit_mass_assignment_of do |attributes|
291
299
  # Map single object argument to an array, if necessary
292
- attributes = attributes.is_a?(Array) ? attributes : [attributes]
300
+ attributes = [attributes] unless attributes.is_a?(Array)
293
301
 
294
302
  match do |policy|
295
303
  return false if attributes.count < 1
@@ -312,22 +320,22 @@ module Pundit
312
320
  end
313
321
 
314
322
  zero_attributes_failure_message = 'At least one attribute must be ' \
315
- 'specified when using the permit_mass_assignment_of matcher.'
323
+ 'specified when using the permit_mass_assignment_of matcher.'
316
324
 
317
325
  failure_message do |policy|
318
326
  if attributes.count.zero?
319
327
  zero_attributes_failure_message
320
328
  elsif defined? @action
321
329
  "#{policy.class} expected to permit the mass assignment of the " \
322
- "attributes #{attributes} when authorising the #{@action} action, " \
323
- 'but forbade the mass assignment of the attributes ' \
324
- "#{forbidden_attributes} for " +
330
+ "attributes #{attributes} when authorising the #{@action} action, " \
331
+ 'but forbade the mass assignment of the attributes ' \
332
+ "#{forbidden_attributes} for " +
325
333
  policy.public_send(Pundit::Matchers.configuration.user_alias)
326
334
  .inspect + '.'
327
335
  else
328
336
  "#{policy.class} expected to permit the mass assignment of the " \
329
- "attributes #{attributes}, but forbade the mass assignment of the " \
330
- "attributes #{forbidden_attributes} for " +
337
+ "attributes #{attributes}, but forbade the mass assignment of the " \
338
+ "attributes #{forbidden_attributes} for " +
331
339
  policy.public_send(Pundit::Matchers.configuration.user_alias)
332
340
  .inspect + '.'
333
341
  end
@@ -338,15 +346,15 @@ module Pundit
338
346
  zero_attributes_failure_message
339
347
  elsif defined? @action
340
348
  "#{policy.class} expected to forbid the mass assignment of the " \
341
- "attributes #{attributes} when authorising the #{@action} action, " \
342
- 'but forbade the mass assignment of the attributes ' \
343
- "#{forbidden_attributes} for " +
349
+ "attributes #{attributes} when authorising the #{@action} action, " \
350
+ 'but forbade the mass assignment of the attributes ' \
351
+ "#{forbidden_attributes} for " +
344
352
  policy.public_send(Pundit::Matchers.configuration.user_alias)
345
353
  .inspect + '.'
346
354
  else
347
355
  "#{policy.class} expected to forbid the mass assignment of the " \
348
- "attributes #{attributes}, but forbade the mass assignment of the " \
349
- "attributes #{forbidden_attributes} for " +
356
+ "attributes #{attributes}, but forbade the mass assignment of the " \
357
+ "attributes #{forbidden_attributes} for " +
350
358
  policy.public_send(Pundit::Matchers.configuration.user_alias)
351
359
  .inspect + '.'
352
360
  end
@@ -383,6 +391,18 @@ module Pundit
383
391
  end
384
392
  end
385
393
 
394
+ RSpec::Matchers.define :permit_only_actions do |actions|
395
+ match do |policy|
396
+ @matcher = Pundit::Matchers::Utils::OnlyActions::PermittedActionsMatcher.new(policy, actions)
397
+ @matcher.match?
398
+ end
399
+
400
+ failure_message do
401
+ formatter = Pundit::Matchers::Utils::OnlyActions::PermittedActionsErrorFormatter.new(@matcher)
402
+ formatter.message
403
+ end
404
+ end
405
+
386
406
  RSpec::Matchers.define :forbid_all_actions do
387
407
  match do |policy|
388
408
  @matcher = Pundit::Matchers::Utils::AllActions::ForbiddenActionsMatcher.new(policy)
@@ -394,6 +414,18 @@ module Pundit
394
414
  formatter.message
395
415
  end
396
416
  end
417
+
418
+ RSpec::Matchers.define :forbid_only_actions do |actions|
419
+ match do |policy|
420
+ @matcher = Pundit::Matchers::Utils::OnlyActions::ForbiddenActionsMatcher.new(policy, actions)
421
+ @matcher.match?
422
+ end
423
+
424
+ failure_message do
425
+ formatter = Pundit::Matchers::Utils::OnlyActions::ForbiddenActionsErrorFormatter.new(@matcher)
426
+ formatter.message
427
+ end
428
+ end
397
429
  end
398
430
 
399
431
  if defined?(Pundit)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pundit-matchers
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.9.0
4
+ version: 2.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Chris Alley
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-04-16 00:00:00.000000000 Z
11
+ date: 2023-04-28 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rspec-rails
@@ -57,11 +57,18 @@ files:
57
57
  - lib/pundit/matchers/utils/all_actions/forbidden_actions_matcher.rb
58
58
  - lib/pundit/matchers/utils/all_actions/permitted_actions_error_formatter.rb
59
59
  - lib/pundit/matchers/utils/all_actions/permitted_actions_matcher.rb
60
+ - lib/pundit/matchers/utils/only_actions/actions_matcher.rb
61
+ - lib/pundit/matchers/utils/only_actions/error_message_formatter.rb
62
+ - lib/pundit/matchers/utils/only_actions/forbidden_actions_error_formatter.rb
63
+ - lib/pundit/matchers/utils/only_actions/forbidden_actions_matcher.rb
64
+ - lib/pundit/matchers/utils/only_actions/permitted_actions_error_formatter.rb
65
+ - lib/pundit/matchers/utils/only_actions/permitted_actions_matcher.rb
60
66
  - lib/pundit/matchers/utils/policy_info.rb
61
67
  homepage: http://github.com/punditcommunity/pundit-matchers
62
68
  licenses:
63
69
  - MIT
64
- metadata: {}
70
+ metadata:
71
+ rubygems_mfa_required: 'true'
65
72
  post_install_message:
66
73
  rdoc_options: []
67
74
  require_paths:
@@ -70,7 +77,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
70
77
  requirements:
71
78
  - - ">="
72
79
  - !ruby/object:Gem::Version
73
- version: '0'
80
+ version: '3.0'
74
81
  required_rubygems_version: !ruby/object:Gem::Requirement
75
82
  requirements:
76
83
  - - ">="