be9-acl9 0.9.1 → 0.9.2

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,119 @@
1
+ require File.join(File.dirname(__FILE__), 'dsl_base')
2
+
3
+ module Acl9
4
+ class AccessDenied < StandardError; end
5
+ class FilterSyntaxError < StandardError; end
6
+
7
+ module Dsl
8
+ module Generators
9
+ class BaseGenerator < Acl9::Dsl::Base
10
+ def initialize(*args)
11
+ @subject_method = args[0]
12
+
13
+ super
14
+ end
15
+
16
+ protected
17
+
18
+ def _access_denied
19
+ "raise Acl9::AccessDenied"
20
+ end
21
+
22
+ def _subject_ref
23
+ "#{_controller_ref}send(:#{@subject_method})"
24
+ end
25
+
26
+ def _object_ref(object)
27
+ "#{_controller_ref}instance_variable_get('@#{object}')"
28
+ end
29
+
30
+ def _action_ref
31
+ "#{_controller_ref}action_name"
32
+ end
33
+
34
+ def _controller_ref
35
+ @controller ? "#{@controller}." : ''
36
+ end
37
+ end
38
+
39
+ class FilterLambda < BaseGenerator
40
+ def initialize(subject_method)
41
+ super
42
+
43
+ @controller = 'controller'
44
+ end
45
+
46
+ def install_on(controller_class, options)
47
+ controller_class.send(:before_filter, options, &self.to_proc)
48
+ end
49
+
50
+ def to_proc
51
+ code = <<-RUBY
52
+ lambda do |controller|
53
+ unless #{allowance_expression}
54
+ #{_access_denied}
55
+ end
56
+ end
57
+ RUBY
58
+
59
+ self.instance_eval(code, __FILE__, __LINE__)
60
+ rescue SyntaxError
61
+ raise FilterSyntaxError, code
62
+ end
63
+ end
64
+
65
+ class FilterMethod < BaseGenerator
66
+ def initialize(subject_method, method_name)
67
+ super
68
+
69
+ @method_name = method_name
70
+ @controller = nil
71
+ end
72
+
73
+ def install_on(controller_class, options)
74
+ _add_method(controller_class)
75
+ controller_class.send(:before_filter, @method_name, options)
76
+ end
77
+
78
+ protected
79
+
80
+ def _add_method(controller_class)
81
+ code = self.to_method_code
82
+ controller_class.send(:class_eval, code, __FILE__, __LINE__)
83
+ rescue SyntaxError
84
+ raise FilterSyntaxError, code
85
+ end
86
+
87
+ def to_method_code
88
+ <<-RUBY
89
+ def #{@method_name}
90
+ unless #{allowance_expression}
91
+ #{_access_denied}
92
+ end
93
+ end
94
+ RUBY
95
+ end
96
+ end
97
+
98
+ class BooleanMethod < FilterMethod
99
+ def install_on(controller_class, *_)
100
+ _add_method(controller_class)
101
+ end
102
+
103
+ protected
104
+
105
+ def to_method_code
106
+ <<-RUBY
107
+ def #{@method_name}(options = {})
108
+ #{allowance_expression}
109
+ end
110
+ RUBY
111
+ end
112
+
113
+ def _object_ref(object)
114
+ "(options[:#{object}] || #{super})"
115
+ end
116
+ end
117
+ end
118
+ end
119
+ end
@@ -44,7 +44,7 @@ module Acl9 # :nodoc:
44
44
 
45
45
  MAJOR = 0
46
46
  MINOR = 9
47
- TINY = 1
47
+ TINY = 2
48
48
 
49
49
  # The current version as a Version instance
50
50
  CURRENT = new(MAJOR, MINOR, TINY)
@@ -26,28 +26,35 @@ end
26
26
 
27
27
  # all these controllers behave the same way
28
28
 
29
- class AccessControllingController1 < EmptyController
29
+ class ACLBlock < EmptyController
30
30
  access_control do
31
31
  allow all, :to => [:index, :show]
32
32
  allow :admin
33
33
  end
34
34
  end
35
35
 
36
- class AccessControllingController2 < EmptyController
36
+ class ACLMethod < EmptyController
37
37
  access_control :as_method => :acl do
38
38
  allow all, :to => [:index, :show]
39
39
  allow :admin, :except => [:index, :show]
40
40
  end
41
41
  end
42
42
 
43
- class AccessControllingController3 < EmptyController
43
+ class ACLMethod2 < EmptyController
44
+ access_control :acl do
45
+ allow all, :to => [:index, :show]
46
+ allow :admin, :except => [:index, :show]
47
+ end
48
+ end
49
+
50
+ class ACLArguments < EmptyController
44
51
  access_control :except => [:index, :show] do
45
52
  allow :admin
46
53
  end
47
54
  end
48
55
 
49
- class AccessControllingController4 < EmptyController
50
- access_control :as_method => :acl, :filter => false do
56
+ class ACLBooleanMethod < EmptyController
57
+ access_control :acl, :filter => false do
51
58
  allow all, :to => [:index, :show]
52
59
  allow :admin
53
60
  end
@@ -85,11 +92,19 @@ describe "permit anonymous to index and show and admin everywhere else", :shared
85
92
  end
86
93
  end
87
94
 
88
- describe AccessControllingController1, :type => :controller do
95
+ describe ACLBlock, :type => :controller do
96
+ it_should_behave_like "permit anonymous to index and show and admin everywhere else"
97
+ end
98
+
99
+ describe ACLMethod, :type => :controller do
100
+ it "should add :acl as a method" do
101
+ controller.should respond_to(:acl)
102
+ end
103
+
89
104
  it_should_behave_like "permit anonymous to index and show and admin everywhere else"
90
105
  end
91
106
 
92
- describe AccessControllingController2, :type => :controller do
107
+ describe ACLMethod2, :type => :controller do
93
108
  it "should add :acl as a method" do
94
109
  controller.should respond_to(:acl)
95
110
  end
@@ -97,11 +112,11 @@ describe AccessControllingController2, :type => :controller do
97
112
  it_should_behave_like "permit anonymous to index and show and admin everywhere else"
98
113
  end
99
114
 
100
- describe AccessControllingController3, :type => :controller do
115
+ describe ACLArguments, :type => :controller do
101
116
  it_should_behave_like "permit anonymous to index and show and admin everywhere else"
102
117
  end
103
118
 
104
- describe AccessControllingController4, :type => :controller do
119
+ describe ACLBooleanMethod, :type => :controller do
105
120
  it_should_behave_like "permit anonymous to index and show and admin everywhere else"
106
121
  end
107
122
 
@@ -111,7 +126,7 @@ end
111
126
 
112
127
  class VenerableBar; end
113
128
 
114
- class AccessControllingController5 < EmptyController
129
+ class ACLIvars < EmptyController
115
130
  before_filter :set_ivars
116
131
 
117
132
  access_control do
@@ -128,7 +143,7 @@ class AccessControllingController5 < EmptyController
128
143
  end
129
144
  end
130
145
 
131
- describe AccessControllingController5, :type => :controller do
146
+ describe ACLIvars, :type => :controller do
132
147
  class OwnerOfFoo
133
148
  def has_role?(role, obj)
134
149
  role == 'owner' && obj == MyDearFoo.instance
@@ -158,7 +173,7 @@ class TheOnlyUser
158
173
  end
159
174
  end
160
175
 
161
- class AccessControllingController6 < ActionController::Base
176
+ class ACLSubjectMethod < ActionController::Base
162
177
  access_control :subject_method => :the_only_user do
163
178
  allow :the_only_one
164
179
  end
@@ -172,7 +187,7 @@ class AccessControllingController6 < ActionController::Base
172
187
  end
173
188
  end
174
189
 
175
- describe AccessControllingController6, :type => :controller do
190
+ describe ACLSubjectMethod, :type => :controller do
176
191
  it "should allow the only user to index" do
177
192
  get :index, :user => TheOnlyUser.instance
178
193
  end
@@ -183,3 +198,62 @@ describe AccessControllingController6, :type => :controller do
183
198
  end.should raise_error(Acl9::AccessDenied)
184
199
  end
185
200
  end
201
+
202
+ class ACLObjectsHash < ActionController::Base
203
+ access_control :allowed?, :filter => false do
204
+ allow :owner, :of => :foo
205
+ end
206
+
207
+ def allow
208
+ @foo = nil
209
+ raise unless allowed?(:foo => MyDearFoo.instance)
210
+ end
211
+
212
+ def current_user
213
+ params[:user]
214
+ end
215
+ end
216
+
217
+ describe ACLObjectsHash, :type => :controller do
218
+ class FooOwner
219
+ def has_role?(role_name, obj)
220
+ role_name == 'owner' && obj == MyDearFoo.instance
221
+ end
222
+ end
223
+
224
+ it "should consider objects hash and prefer it to @ivar" do
225
+ get :allow, :user => FooOwner.new
226
+ end
227
+ end
228
+
229
+ describe "Argument checking" do
230
+ def arg_err(&block)
231
+ lambda do
232
+ block.call
233
+ end.should raise_error(ArgumentError)
234
+ end
235
+
236
+ it "should raise ArgumentError without a block" do
237
+ arg_err do
238
+ class FailureController < ActionController::Base
239
+ access_control
240
+ end
241
+ end
242
+ end
243
+
244
+ it "should raise ArgumentError with 1st argument which is not a symbol" do
245
+ arg_err do
246
+ class FailureController < ActionController::Base
247
+ access_control 123 do end
248
+ end
249
+ end
250
+ end
251
+
252
+ it "should raise ArgumentError with more than 1 positional argument" do
253
+ arg_err do
254
+ class FailureController < ActionController::Base
255
+ access_control :foo, :bar do end
256
+ end
257
+ end
258
+ end
259
+ end
@@ -0,0 +1,703 @@
1
+ require File.join(File.dirname(__FILE__), 'spec_helper')
2
+ require File.join(File.dirname(__FILE__), '..', 'lib', 'acl9', 'controller_extensions', 'dsl_base')
3
+
4
+ class FakeUser
5
+ def initialize
6
+ @roles = {}
7
+ end
8
+
9
+ def has_role?(role, object = nil)
10
+ @roles.include?([role.to_s, object])
11
+ end
12
+
13
+ def <<(role)
14
+ role = [role] unless role.is_a? Array
15
+
16
+ role << nil if role.size == 1
17
+ raise unless role[0]
18
+
19
+ role[0] = role[0].to_s
20
+
21
+ @roles[role] = true
22
+ end
23
+ end
24
+
25
+ class DslTester < Acl9::Dsl::Base
26
+ def initialize
27
+ super
28
+
29
+ @_subject = nil
30
+ @_objects = {}
31
+ @_current_action = nil
32
+ end
33
+
34
+ def permit(user, *args)
35
+ check_allowance(user, *args).should == true
36
+
37
+ self
38
+ end
39
+
40
+ def forbid(user, *args)
41
+ check_allowance(user, *args).should == false
42
+
43
+ self
44
+ end
45
+
46
+ def show_code
47
+ puts "\n", allowance_expression
48
+ self
49
+ end
50
+
51
+ protected
52
+
53
+ def check_allowance(subject, *args)
54
+ @_subject = subject
55
+ @_current_action = (args[0] || 'index').to_s
56
+ @_objects = args.last.is_a?(Hash) ? args.last : {}
57
+
58
+ instance_eval(allowance_expression)
59
+ end
60
+
61
+ def _subject_ref
62
+ "@_subject"
63
+ end
64
+
65
+ def _object_ref(object)
66
+ "@_objects[:#{object.to_s}]"
67
+ end
68
+
69
+ def _action_ref
70
+ "@_current_action"
71
+ end
72
+ end
73
+
74
+ describe Acl9::Dsl::Base do
75
+ class Foo; end
76
+ class Bar; end
77
+
78
+ def arg_err(&block)
79
+ lambda do
80
+ acl(&block)
81
+ end.should raise_error(ArgumentError)
82
+ end
83
+
84
+ def acl(&block)
85
+ tester = DslTester.new
86
+ tester.acl_block!(&block)
87
+
88
+ tester
89
+ end
90
+
91
+ def permit_some(tester, user, actions, vars = {})
92
+ actions.each { |act| tester.permit(user, act, vars) }
93
+ (@all_actions - actions).each { |act| tester.forbid(user, act, vars) }
94
+ end
95
+
96
+ before do
97
+ @user = FakeUser.new
98
+ @user2 = FakeUser.new
99
+ @user3 = FakeUser.new
100
+ @foo = Foo.new
101
+ @foo2 = Foo.new
102
+ @foo3 = Foo.new
103
+ end
104
+
105
+ describe "default" do
106
+ it "should set default action to deny if none specified" do
107
+ acl do end.default_action.should == :deny
108
+ end
109
+
110
+ it "should set default action to allow" do
111
+ acl do
112
+ default :allow
113
+ end.default_action.should == :allow
114
+ end
115
+
116
+ it "should set default action to deny" do
117
+ acl do
118
+ default :deny
119
+ end.default_action.should == :deny
120
+ end
121
+
122
+ it "should raise ArgumentError with unknown default_action" do
123
+ arg_err do
124
+ default 123
125
+ end
126
+ end
127
+
128
+ it "should raise ArgumentError when default is called more than once" do
129
+ arg_err do
130
+ default :deny
131
+ default :deny
132
+ end
133
+ end
134
+ end
135
+
136
+ describe "empty blocks" do
137
+ it "should deny everyone with default deny" do
138
+ acl do
139
+ end.forbid(nil).forbid(@user)
140
+ end
141
+
142
+ it "should allow everyone with default allow" do
143
+ acl do
144
+ default :allow
145
+ end.permit(nil).permit(@user)
146
+ end
147
+ end
148
+
149
+ describe "empty" do
150
+ it "allow should raise an ArgumentError" do
151
+ arg_err { allow }
152
+ end
153
+
154
+ it "deny should raise an ArgumentError" do
155
+ arg_err { deny }
156
+ end
157
+ end
158
+
159
+ describe "anonymous" do
160
+ it "'allow nil' should allow anonymous, but not logged in" do
161
+ acl do
162
+ allow nil
163
+ end.permit(nil).forbid(@user)
164
+ end
165
+
166
+ it "'allow anonymous' should allow anonymous, but not logged in" do
167
+ acl do
168
+ allow anonymous
169
+ end.permit(nil).forbid(@user)
170
+ end
171
+
172
+ it "'deny nil' should deny anonymous, but not logged in" do
173
+ acl do
174
+ default :allow
175
+ deny nil
176
+ end.forbid(nil).permit(@user)
177
+ end
178
+
179
+ it "'deny anonymous' should deny anonymous, but not logged in" do
180
+ acl do
181
+ default :allow
182
+ deny anonymous
183
+ end.forbid(nil).permit(@user)
184
+ end
185
+ end
186
+
187
+ describe "all" do
188
+ it "'allow all' should allow all" do
189
+ acl do
190
+ allow all
191
+ end.permit(nil).permit(@user)
192
+ end
193
+
194
+ it "'deny all' should deny all" do
195
+ acl do
196
+ default :allow
197
+ deny all
198
+ end.forbid(nil).forbid(@user)
199
+ end
200
+ end
201
+
202
+ describe "default :allow" do
203
+ it "should allow when neither allow nor deny conditions are matched" do
204
+ acl do
205
+ default :allow
206
+ allow :blah
207
+ deny :bzz
208
+ end.permit(nil).permit(@user)
209
+ end
210
+
211
+ it "should deny when deny is matched, but allow is not" do
212
+ acl do
213
+ default :allow
214
+ deny all
215
+ allow :blah
216
+ end.forbid(nil).forbid(@user)
217
+ end
218
+
219
+ it "should allow when allow is matched, but deny is not" do
220
+ @user << :cool
221
+ acl do
222
+ default :allow
223
+ deny nil
224
+ allow :cool
225
+ end.permit(@user)
226
+ end
227
+
228
+ it "should allow both allow and deny conditions are matched" do
229
+ @user << :cool
230
+ acl do
231
+ default :allow
232
+ deny :cool
233
+ allow :cool
234
+ end.permit(@user)
235
+
236
+ acl do
237
+ default :allow
238
+ deny all
239
+ allow all
240
+ end.permit(@user).permit(nil).permit(@user2)
241
+ end
242
+ end
243
+
244
+ describe "logged_in" do
245
+ it "'allow logged_in' should allow logged in, but not anonymous" do
246
+ acl do
247
+ allow logged_in
248
+ end.forbid(nil).permit(@user)
249
+ end
250
+
251
+ it "'allow logged_in' should deny logged in, but not anonymous" do
252
+ acl do
253
+ default :allow
254
+ deny logged_in
255
+ end.permit(nil).forbid(@user)
256
+ end
257
+ end
258
+
259
+ describe "default :deny" do
260
+ it "should deny when neither allow nor deny conditions are matched" do
261
+ acl do
262
+ default :deny
263
+ allow :blah
264
+ deny :bzz
265
+ end.forbid(nil).forbid(@user)
266
+ end
267
+
268
+ it "should deny when deny is matched, but allow is not" do
269
+ acl do
270
+ default :deny
271
+ deny all
272
+ allow :blah
273
+ end.forbid(nil).forbid(@user)
274
+ end
275
+
276
+ it "should allow when allow is matched, but deny is not" do
277
+ @user << :cool
278
+ acl do
279
+ default :deny
280
+ deny nil
281
+ allow :cool
282
+ end.permit(@user)
283
+ end
284
+
285
+ it "should deny both allow and deny conditions are matched" do
286
+ @user << :cool
287
+ acl do
288
+ default :deny
289
+ deny :cool
290
+ allow :cool
291
+ end.forbid(@user)
292
+
293
+ acl do
294
+ default :deny
295
+ deny all
296
+ allow all
297
+ end.forbid(@user).forbid(nil).forbid(@user2)
298
+ end
299
+ end
300
+
301
+ describe "global roles" do
302
+ it "#allow with role" do
303
+ @user << :admin
304
+
305
+ acl { allow :admin }.permit(@user).forbid(nil).forbid(@user2)
306
+ end
307
+
308
+ it "#allow with plural role name" do
309
+ @user << :mouse
310
+
311
+ acl do
312
+ allow :mice
313
+ end.permit(@user).forbid(nil).forbid(@user2)
314
+ end
315
+
316
+ it "#allow with several roles" do
317
+ @user << :admin
318
+ @user << :cool
319
+
320
+ @user2 << :cool
321
+
322
+ @user3 << :super
323
+
324
+ acl do
325
+ allow :admin
326
+ allow :cool
327
+ end.permit(@user).permit(@user2).forbid(nil).forbid(@user3)
328
+ end
329
+
330
+ it "#deny with role" do
331
+ @user << :foo
332
+
333
+ acl { default :allow; deny :foo }.forbid(@user).permit(nil).permit(@user2)
334
+ end
335
+
336
+ it "#deny with plural role name" do
337
+ @user << :mouse
338
+
339
+ acl do
340
+ default :allow
341
+ deny :mice
342
+ end.forbid(@user).permit(nil).permit(@user2)
343
+ end
344
+
345
+ it "#deny with several roles" do
346
+ @user << :admin
347
+ @user << :cool
348
+
349
+ @user2 << :cool
350
+
351
+ @user3 << :super
352
+
353
+ acl do
354
+ default :allow
355
+ deny :admin
356
+ deny :cool
357
+ end.forbid(@user).forbid(@user2).permit(nil).permit(@user3)
358
+ end
359
+ end
360
+
361
+ describe "prepositions" do
362
+ [:of, :for, :in, :on, :at, :by].each do |prep|
363
+ it "#allow with object role (:#{prep}) should check controller's ivar" do
364
+ @user << [:manager, @foo]
365
+
366
+ acl do
367
+ allow :manager, prep => :foo
368
+ end.
369
+ permit(@user, :foo => @foo).
370
+ forbid(@user, :foo => @foo2).
371
+ forbid(@user, :foo => Foo).
372
+ forbid(nil, :foo => @foo).
373
+ forbid(@user2, :foo => @foo)
374
+ end
375
+
376
+ it "#allow with invalid value for preposition should raise an ArgumentError" do
377
+ arg_err do
378
+ allow :hom, :by => 1
379
+ end
380
+ end
381
+ end
382
+
383
+ it "#allow with a class role should verify this role against a class" do
384
+ @user << [:owner, Foo]
385
+
386
+ acl do
387
+ allow :owner, :of => Foo
388
+ end.permit(@user).forbid(nil).forbid(@user2)
389
+ end
390
+
391
+ [:of, :for, :in, :on, :at, :by].each do |prep|
392
+ it "#deny with object role (:#{prep}) should check controller's ivar" do
393
+ @user << [:bastard, @foo]
394
+
395
+ acl do
396
+ default :allow
397
+ deny :bastard, prep => :foo
398
+ end.
399
+ forbid(@user, :foo => @foo).
400
+ permit(@user, :foo => @foo2).
401
+ permit(@user, :foo => Foo).
402
+ permit(nil, :foo => @foo).
403
+ permit(@user2, :foo => @foo)
404
+ end
405
+
406
+ it "#deny with invalid value for preposition should raise an ArgumentError" do
407
+ arg_err do
408
+ deny :her, :for => "him"
409
+ end
410
+ end
411
+ end
412
+
413
+ it "#deny with a class role should verify this role against a class" do
414
+ @user << [:ignorant, Foo]
415
+
416
+ acl do
417
+ default :allow
418
+ deny :ignorant, :of => Foo
419
+ end.forbid(@user).permit(nil).permit(@user2)
420
+ end
421
+
422
+ it "#allow with several prepositions should raise an ArgumentError" do
423
+ arg_err do
424
+ allow :some, :by => :one, :for => :another
425
+ end
426
+ end
427
+
428
+ it "#deny with several prepositions should raise an ArgumentError" do
429
+ arg_err do
430
+ deny :some, :in => :here, :on => :today
431
+ end
432
+ end
433
+ end
434
+
435
+ describe ":to and :except" do
436
+ it "should raise an ArgumentError when both :to and :except are specified" do
437
+ arg_err do
438
+ allow all, :to => :index, :except => ['show', 'edit']
439
+ end
440
+ end
441
+
442
+ describe do
443
+ after do
444
+ %w(index show).each { |act| @list.permit(nil, act) }
445
+ %w(edit update delete destroy).each { |act| @list.forbid(nil, act) }
446
+
447
+ %w(index show edit update).each { |act| @list.permit(@user, act) }
448
+ %w(delete destroy).each { |act| @list.forbid(@user, act) }
449
+
450
+ %w(index show edit update delete destroy).each { |act| @list.permit(@user2, act) }
451
+ end
452
+
453
+ it ":to should limit rule scope to specified actions" do
454
+ @user << :manager
455
+ @user2 << :trusted
456
+
457
+ @list = acl do
458
+ allow all, :to => [:index, :show]
459
+
460
+ allow 'manager', :to => :edit
461
+ allow 'manager', :to => 'update'
462
+ allow 'trusted', :to => %w(edit update delete destroy)
463
+ end
464
+ end
465
+
466
+ it ":except should limit rule scope to all actions except specified" do
467
+ @user << :manager
468
+ @user2 << :trusted
469
+
470
+ @list = acl do
471
+ allow all, :except => %w(edit update delete destroy)
472
+
473
+ allow 'manager', :except => %w(delete destroy)
474
+ allow 'trusted'
475
+ end
476
+ end
477
+ end
478
+ end
479
+
480
+ describe "several roles as arguments" do
481
+ it "#allow should be able to receive a role list (global roles)" do
482
+ @user << :bzz
483
+ @user2 << :whoa
484
+
485
+ acl do
486
+ allow :bzz, :whoa
487
+ end.permit(@user).permit(@user2).forbid(nil).forbid(@user3)
488
+ end
489
+
490
+ it "#allow should be able to receive a role list (object roles)" do
491
+ @user << [:maker, @foo]
492
+ @user2 << [:faker, @foo2]
493
+
494
+ acl do
495
+ allow :maker, :faker, :of => :foo
496
+ end.
497
+ permit(@user, :foo => @foo).
498
+ forbid(@user, :foo => @foo2).
499
+ permit(@user2, :foo => @foo2).
500
+ forbid(@user2, :foo => @foo).
501
+ forbid(@user3, :foo => @foo).
502
+ forbid(@user3, :foo => @foo2).
503
+ forbid(nil)
504
+ end
505
+
506
+ it "#allow should be able to receive a role list (class roles)" do
507
+ @user << [:frooble, Foo]
508
+ @user2 << [:oombigle, Foo]
509
+ @user3 << :frooble
510
+
511
+ acl do
512
+ allow :frooble, :oombigle, :by => Foo
513
+ end.
514
+ permit(@user).
515
+ permit(@user2).
516
+ forbid(@user3).
517
+ forbid(nil)
518
+ end
519
+
520
+ it "#deny should be able to receive a role list (global roles)" do
521
+ @user << :bzz
522
+ @user2 << :whoa
523
+
524
+ acl do
525
+ default :allow
526
+ deny :bzz, :whoa
527
+ end.forbid(@user).forbid(@user2).permit(nil).permit(@user3)
528
+ end
529
+
530
+ it "#deny should be able to receive a role list (object roles)" do
531
+ @user << [:maker, @foo]
532
+ @user2 << [:faker, @foo2]
533
+ @user3 = FakeUser.new
534
+
535
+ acl do
536
+ default :allow
537
+ deny :maker, :faker, :of => :foo
538
+ end.
539
+ forbid(@user, :foo => @foo).
540
+ permit(@user, :foo => @foo2).
541
+ forbid(@user2, :foo => @foo2).
542
+ permit(@user2, :foo => @foo).
543
+ permit(@user3, :foo => @foo).
544
+ permit(@user3, :foo => @foo2).
545
+ permit(nil)
546
+ end
547
+
548
+ it "#deny should be able to receive a role list (class roles)" do
549
+ @user << [:frooble, Foo]
550
+ @user2 << [:oombigle, Foo]
551
+ @user3 << :frooble
552
+
553
+ acl do
554
+ default :allow
555
+ deny :frooble, :oombigle, :by => Foo
556
+ end.
557
+ forbid(@user).
558
+ forbid(@user2).
559
+ permit(@user3).
560
+ permit(nil)
561
+ end
562
+
563
+ it "should also respect :to and :except" do
564
+ class Moo; end
565
+
566
+ @user << :foo
567
+ @user2 << [:joo, @foo]
568
+ @user3 << [:qoo, Moo]
569
+
570
+ acl do
571
+ allow :foo, :boo, :to => [:index, :show]
572
+ allow :zoo, :joo, :by => :foo, :to => [:edit, :update]
573
+ allow :qoo, :woo, :of => Moo
574
+ deny :qoo, :woo, :of => Moo, :except => [:delete, :destroy]
575
+ end.
576
+ permit(@user, 'index').
577
+ permit(@user, 'show').
578
+ forbid(@user, 'edit').
579
+ permit(@user2, 'edit', :foo => @foo).
580
+ permit(@user2, 'update', :foo => @foo).
581
+ forbid(@user2, 'show', :foo => @foo).
582
+ forbid(@user2, 'show').
583
+ permit(@user3, 'delete').
584
+ permit(@user3, 'destroy').
585
+ forbid(@user3, 'edit').
586
+ forbid(@user3, 'show')
587
+ end
588
+ end
589
+
590
+ describe "actions block" do
591
+ it "should raise an ArgumentError when actions has no block" do
592
+ arg_err do
593
+ actions :foo, :bar
594
+ end
595
+ end
596
+
597
+ it "should raise an ArgumentError when actions has no arguments" do
598
+ arg_err do
599
+ actions do end
600
+ end
601
+ end
602
+
603
+ it "should raise an ArgumentError when actions is called inside actions block" do
604
+ arg_err do
605
+ actions :foo, :bar do
606
+ actions :foo, :bar do
607
+ end
608
+ end
609
+ end
610
+ end
611
+
612
+ it "should raise an ArgumentError when default is called inside actions block" do
613
+ arg_err do
614
+ actions :foo, :bar do
615
+ default :allow
616
+ end
617
+ end
618
+ end
619
+
620
+ [:to, :except].each do |opt|
621
+ it "should raise an ArgumentError when allow is called with #{opt} option" do
622
+ arg_err do
623
+ actions :foo do
624
+ allow all, opt => :bar
625
+ end
626
+ end
627
+ end
628
+
629
+ it "should raise an ArgumentError when deny is called with #{opt} option" do
630
+ arg_err do
631
+ actions :foo do
632
+ deny all, opt => :bar
633
+ end
634
+ end
635
+ end
636
+ end
637
+
638
+ it "empty actions block should do nothing" do
639
+ acl do
640
+ actions :foo do
641
+ end
642
+
643
+ allow all
644
+ end.permit(nil).permit(nil, :foo)
645
+ end
646
+
647
+ it "#allow should limit its scope to specified actions" do
648
+ @user << :bee
649
+
650
+ acl do
651
+ actions :edit do
652
+ allow :bee
653
+ end
654
+ end.
655
+ permit(@user, :edit).
656
+ forbid(@user, :update)
657
+ end
658
+
659
+ it "#deny should limit its scope to specified actions" do
660
+ @user << :bee
661
+
662
+ acl do
663
+ default :allow
664
+ actions :edit do
665
+ deny :bee
666
+ end
667
+ end.
668
+ forbid(@user, :edit).
669
+ permit(@user, :update)
670
+ end
671
+
672
+ it "#allow and #deny should work together inside actions block" do
673
+ @foo = Foo.new
674
+ @user << [:owner, @foo]
675
+ @user2 << :hacker
676
+ @user2 << :the_destroyer
677
+ @user3 << [:owner, @foo]
678
+ @user3 << :hacker
679
+
680
+ list = acl do
681
+ actions :show, :index do
682
+ allow all
683
+ end
684
+
685
+ actions :edit, :update do
686
+ allow :owner, :of => :object
687
+ deny :hacker
688
+ end
689
+
690
+ actions :delete, :destroy do
691
+ allow :owner, :of => :object
692
+ allow :the_destroyer
693
+ end
694
+ end
695
+
696
+ @all_actions = %w(show index edit update delete destroy)
697
+
698
+ permit_some(list, @user, @all_actions, :object => @foo)
699
+ permit_some(list, @user2, %w(show index delete destroy))
700
+ permit_some(list, @user3, %w(show index delete destroy), :object => @foo)
701
+ end
702
+ end
703
+ end