authoritah 0.0.5 → 0.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.
data/lib/authoritah.rb
CHANGED
@@ -28,6 +28,9 @@ module Authoritah
|
|
28
28
|
options = args.extract_options!
|
29
29
|
args.each {|a| options[a] = nil}
|
30
30
|
actions = options.delete(action_identifier)
|
31
|
+
on_reject = options.delete(:on_reject) || :render_404
|
32
|
+
|
33
|
+
raise ":on_reject must be a symbol or a Proc" unless on_reject.is_a?(Symbol) || on_reject.is_a?(Proc)
|
31
34
|
|
32
35
|
check_role_selectors(options)
|
33
36
|
|
@@ -35,8 +38,13 @@ module Authoritah
|
|
35
38
|
role_predicate = options.to_a.first[1]
|
36
39
|
|
37
40
|
controller_permissions[controller_name.to_sym] ||= PermissionSet.new
|
38
|
-
controller_permissions[controller_name.to_sym] <<
|
39
|
-
|
41
|
+
controller_permissions[controller_name.to_sym] << {
|
42
|
+
:type => perm_type,
|
43
|
+
:role_method => role_method,
|
44
|
+
:role_predicate => role_predicate,
|
45
|
+
:actions => actions ? Array(actions) : nil,
|
46
|
+
:on_reject => on_reject
|
47
|
+
}
|
40
48
|
end
|
41
49
|
|
42
50
|
def this_controllers_permissions
|
@@ -61,16 +69,18 @@ module Authoritah
|
|
61
69
|
module InstanceMethods
|
62
70
|
|
63
71
|
def check_permissions
|
64
|
-
|
65
|
-
render(:file => File.join(RAILS_ROOT, 'public', '404.html'), :status => 404)
|
66
|
-
false
|
72
|
+
permitted?(action_name.to_sym)
|
67
73
|
end
|
68
74
|
|
69
75
|
protected
|
70
76
|
|
77
|
+
def render_404
|
78
|
+
render(:file => File.join(RAILS_ROOT, 'public', '404.html'), :status => 404)
|
79
|
+
end
|
80
|
+
|
71
81
|
def permitted?(action)
|
72
82
|
return true unless permissions = self.class.this_controllers_permissions
|
73
|
-
permissions.permits?(self, action)
|
83
|
+
permissions.permits?(self, action)
|
74
84
|
end
|
75
85
|
end
|
76
86
|
|
@@ -90,39 +100,52 @@ module Authoritah
|
|
90
100
|
end
|
91
101
|
|
92
102
|
def permits?(controller, action)
|
93
|
-
|
103
|
+
permitted, on_reject_action = apply_rule_chain(:permit, controller, action)
|
104
|
+
if permitted
|
105
|
+
return true
|
106
|
+
else
|
107
|
+
if on_reject_action.is_a?(Proc)
|
108
|
+
# debugger
|
109
|
+
# on_reject_action.call(controller)
|
110
|
+
controller.instance_eval(&on_reject_action)
|
111
|
+
else
|
112
|
+
controller.send(on_reject_action)
|
113
|
+
end
|
114
|
+
return false
|
115
|
+
end
|
94
116
|
end
|
95
117
|
|
96
|
-
def forbids?(controller, action)
|
97
|
-
apply_rules(:forbid, controller, action).include?(true)
|
98
|
-
end
|
99
|
-
|
100
118
|
def permissions
|
101
119
|
@permissions ||= []
|
102
120
|
end
|
103
121
|
|
104
122
|
protected
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
p[:actions].include?(action) || p[:actions].include?(:all)
|
111
|
-
}.map do |permission|
|
123
|
+
|
124
|
+
# Returns [true, nil] if the rule chain applied without a problem.
|
125
|
+
# Returns [false, :reject_to]
|
126
|
+
def apply_rule_chain(rule_type, controller, action)
|
127
|
+
select_permissions_for(action).each do |permission|
|
112
128
|
begin
|
113
|
-
if permission[:role_predicate].is_a? Symbol
|
129
|
+
response = if permission[:role_predicate].is_a? Symbol
|
114
130
|
controller.send(permission[:role_method]).send(permission[:role_predicate])
|
115
131
|
elsif permission[:role_predicate].is_a? Proc
|
116
132
|
permission[:role_predicate].call(controller.send(permission[:role_method]))
|
117
133
|
elsif permission[:role_predicate] == nil
|
118
134
|
controller.send(permission[:role_method])
|
119
|
-
else
|
120
|
-
false
|
121
135
|
end
|
136
|
+
response = !response if permission[:type] == :forbid
|
137
|
+
return [false, permission[:on_reject]] unless response
|
122
138
|
rescue
|
123
|
-
|
139
|
+
return [permission[:type] == :forbid, permission[:on_reject]]
|
124
140
|
end
|
125
141
|
end
|
142
|
+
[true, nil]
|
143
|
+
end
|
144
|
+
|
145
|
+
def select_permissions_for(action)
|
146
|
+
permissions.select{|p|
|
147
|
+
p[:actions].include?(action) || p[:actions].include?(:all)
|
148
|
+
}
|
126
149
|
end
|
127
150
|
end
|
128
151
|
|
data/spec/authoritah_spec.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
require File.dirname(__FILE__) + '/spec_helper'
|
2
|
-
|
2
|
+
require 'ruby-debug'
|
3
3
|
describe Authoritah::Controller do
|
4
4
|
|
5
5
|
before(:each) do
|
@@ -200,6 +200,9 @@ describe TestAuthorizerController, :type => :controller do
|
|
200
200
|
end
|
201
201
|
end
|
202
202
|
context "an unauthenticated user" do
|
203
|
+
before(:each) do
|
204
|
+
controller.stubs(:current_user => false)
|
205
|
+
end
|
203
206
|
it "should render index" do get :index; response.should render_template('index') end
|
204
207
|
end
|
205
208
|
end
|
@@ -245,15 +248,73 @@ describe TestAuthorizerController, :type => :controller do
|
|
245
248
|
end
|
246
249
|
end
|
247
250
|
|
248
|
-
describe "
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
251
|
+
describe "specifying a different action to run on failure" do
|
252
|
+
|
253
|
+
it "should check that :on_reject is a Proc or Symbol" do
|
254
|
+
lambda do
|
255
|
+
TestAuthorizerController.permits(:current_user => :logged_in?, :on_reject => :method)
|
256
|
+
end.should_not raise_error
|
257
|
+
lambda do
|
258
|
+
TestAuthorizerController.permits(:current_user => :logged_in?, :on_reject => Proc.new {})
|
259
|
+
end.should_not raise_error
|
260
|
+
lambda do
|
261
|
+
TestAuthorizerController.permits(:current_user => :logged_in?, :on_reject => 5)
|
262
|
+
end.should raise_error
|
263
|
+
end
|
264
|
+
|
265
|
+
context "when :on_reject => :set_flash_and_redirect" do
|
266
|
+
before(:each) do
|
267
|
+
TestAuthorizerController.permits(:current_user => :logged_in?, :on_reject => :set_flash_and_redirect)
|
268
|
+
TestAuthorizerController.send(:define_method, :set_flash_and_redirect) do
|
269
|
+
flash[:error] = "You need to be logged in to do that"
|
270
|
+
redirect_to root_url
|
271
|
+
end
|
272
|
+
end
|
273
|
+
context "an unauthenticated user" do
|
274
|
+
it "should redirect to /" do
|
275
|
+
get :index
|
276
|
+
response.should redirect_to(root_url)
|
277
|
+
end
|
278
|
+
it "should set the flash" do
|
279
|
+
get :index
|
280
|
+
flash[:error].should == "You need to be logged in to do that"
|
281
|
+
end
|
282
|
+
end
|
283
|
+
end
|
284
|
+
|
285
|
+
context "when :on_reject => Proc" do
|
286
|
+
before(:each) do
|
287
|
+
TestAuthorizerController.permits(:current_user => :logged_in?, :on_reject => Proc.new { redirect_to root_url })
|
288
|
+
end
|
289
|
+
context "an unauthenticated user" do
|
290
|
+
it "should redirect to /" do
|
291
|
+
get :index
|
292
|
+
response.should redirect_to(root_url)
|
293
|
+
end
|
255
294
|
end
|
256
295
|
end
|
257
|
-
|
296
|
+
|
297
|
+
context "with multiple rules" do
|
298
|
+
before(:each) do
|
299
|
+
TestAuthorizerController.permits(:current_user => :logged_in?)
|
300
|
+
TestAuthorizerController.forbids(:current_user => :blacklisted?, :on_reject => :set_blacklisted)
|
301
|
+
TestAuthorizerController.send(:define_method, :set_blacklisted) do
|
302
|
+
flash[:error] = "You can't be blacklisted to do that"
|
303
|
+
redirect_to '/blacklisted'
|
304
|
+
end
|
305
|
+
end
|
306
|
+
|
307
|
+
context "as a blacklisted user" do
|
308
|
+
before(:each) do
|
309
|
+
controller.stubs(:current_user => stub(:logged_in? => true, :blacklisted? => true))
|
310
|
+
end
|
311
|
+
it 'should redirect to /blacklisted' do
|
312
|
+
get :index
|
313
|
+
response.should redirect_to('/blacklisted')
|
314
|
+
end
|
315
|
+
end
|
316
|
+
|
317
|
+
end
|
258
318
|
end
|
319
|
+
|
259
320
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: authoritah
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Steven Mohapi-Banks
|
@@ -9,7 +9,7 @@ autorequire:
|
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
11
|
|
12
|
-
date: 2009-
|
12
|
+
date: 2009-11-04 00:00:00 +00:00
|
13
13
|
default_executable:
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
@@ -20,7 +20,7 @@ dependencies:
|
|
20
20
|
requirements:
|
21
21
|
- - ">="
|
22
22
|
- !ruby/object:Gem::Version
|
23
|
-
version: 1.2.
|
23
|
+
version: 1.2.9
|
24
24
|
version:
|
25
25
|
- !ruby/object:Gem::Dependency
|
26
26
|
name: rspec-rails
|
@@ -30,7 +30,7 @@ dependencies:
|
|
30
30
|
requirements:
|
31
31
|
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: 1.2.
|
33
|
+
version: 1.2.9
|
34
34
|
version:
|
35
35
|
- !ruby/object:Gem::Dependency
|
36
36
|
name: mocha
|
@@ -80,7 +80,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
80
80
|
requirements: []
|
81
81
|
|
82
82
|
rubyforge_project:
|
83
|
-
rubygems_version: 1.3.
|
83
|
+
rubygems_version: 1.3.5
|
84
84
|
signing_key:
|
85
85
|
specification_version: 3
|
86
86
|
summary: A really simple authorization plugin for Rails.
|
@@ -91,9 +91,7 @@ test_files:
|
|
91
91
|
- spec/railsenv/config/boot.rb
|
92
92
|
- spec/railsenv/config/database.yml
|
93
93
|
- spec/railsenv/config/environment.rb
|
94
|
-
- spec/railsenv/config/environments/cucumber.rb
|
95
94
|
- spec/railsenv/config/environments/development.rb
|
96
|
-
- spec/railsenv/config/environments/production.rb
|
97
95
|
- spec/railsenv/config/environments/test.rb
|
98
96
|
- spec/railsenv/config/initializers/backtrace_silencers.rb
|
99
97
|
- spec/railsenv/config/initializers/inflections.rb
|
@@ -1,23 +0,0 @@
|
|
1
|
-
config.cache_classes = true # This must be true for Cucumber to operate correctly!
|
2
|
-
|
3
|
-
# Log error messages when you accidentally call methods on nil.
|
4
|
-
config.whiny_nils = true
|
5
|
-
|
6
|
-
# Show full error reports and disable caching
|
7
|
-
config.action_controller.consider_all_requests_local = true
|
8
|
-
config.action_controller.perform_caching = false
|
9
|
-
|
10
|
-
# Disable request forgery protection in test environment
|
11
|
-
config.action_controller.allow_forgery_protection = false
|
12
|
-
|
13
|
-
# Tell Action Mailer not to deliver emails to the real world.
|
14
|
-
# The :test delivery method accumulates sent emails in the
|
15
|
-
# ActionMailer::Base.deliveries array.
|
16
|
-
config.action_mailer.delivery_method = :test
|
17
|
-
|
18
|
-
config.gem 'cucumber', :lib => false, :version => '>=0.3.100' unless File.directory?(File.join(Rails.root, 'vendor/plugins/cucumber'))
|
19
|
-
config.gem 'webrat', :lib => false, :version => '>=0.5.0' unless File.directory?(File.join(Rails.root, 'vendor/plugins/webrat'))
|
20
|
-
config.gem 'rspec', :lib => false, :version => '>=1.2.6' unless File.directory?(File.join(Rails.root, 'vendor/plugins/rspec'))
|
21
|
-
config.gem 'rspec-rails', :lib => 'spec/rails', :version => '>=1.2.6' unless File.directory?(File.join(Rails.root, 'vendor/plugins/rspec-rails'))
|
22
|
-
|
23
|
-
config.gem 'spork', :lib => false, :version => '>=0.5.9' unless File.directory?(File.join(Rails.root, 'vendor/plugins/spork'))
|
@@ -1,28 +0,0 @@
|
|
1
|
-
# Settings specified here will take precedence over those in config/environment.rb
|
2
|
-
|
3
|
-
# The production environment is meant for finished, "live" apps.
|
4
|
-
# Code is not reloaded between requests
|
5
|
-
config.cache_classes = true
|
6
|
-
|
7
|
-
# Full error reports are disabled and caching is turned on
|
8
|
-
config.action_controller.consider_all_requests_local = false
|
9
|
-
config.action_controller.perform_caching = true
|
10
|
-
config.action_view.cache_template_loading = true
|
11
|
-
|
12
|
-
# See everything in the log (default is :info)
|
13
|
-
# config.log_level = :debug
|
14
|
-
|
15
|
-
# Use a different logger for distributed setups
|
16
|
-
# config.logger = SyslogLogger.new
|
17
|
-
|
18
|
-
# Use a different cache store in production
|
19
|
-
# config.cache_store = :mem_cache_store
|
20
|
-
|
21
|
-
# Enable serving of images, stylesheets, and javascripts from an asset server
|
22
|
-
# config.action_controller.asset_host = "http://assets.example.com"
|
23
|
-
|
24
|
-
# Disable delivery errors, bad email addresses will be ignored
|
25
|
-
# config.action_mailer.raise_delivery_errors = false
|
26
|
-
|
27
|
-
# Enable threaded mode
|
28
|
-
# config.threadsafe!
|