credentials 2.3.1 → 2.4.0

Sign up to get free protection for your applications and to get access to all the features.
data/HISTORY CHANGED
@@ -1,4 +1,14 @@
1
- === 2.2.3 / 2009-11-27
1
+ === 2.4.0 / 2010-01-25
2
+
3
+ * Implemented Foo.metaclass.credentials { |foo| ... } to allow
4
+ declaration of credentials per instance. This is nice for
5
+ implementing RBA.
6
+
7
+ === 2.3.1 / 2009-12-17
8
+
9
+ * Minor bug fix (Class !== Class)
10
+
11
+ === 2.3.0 / 2009-12-16
2
12
 
3
13
  * Add support for prepositions.
4
14
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 2.3.1
1
+ 2.4.0
data/credentials.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{credentials}
8
- s.version = "2.3.1"
8
+ s.version = "2.4.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Matt Powell"]
12
- s.date = %q{2009-12-17}
12
+ s.date = %q{2010-01-25}
13
13
  s.description = %q{A generic actor/resource permission framework based on rules, not objects.}
14
14
  s.email = %q{fauxparse@gmail.com.com}
15
15
  s.extra_rdoc_files = [
@@ -52,9 +52,15 @@ module Credentials
52
52
 
53
53
  # Returns true if the receiver has access to the specified resource or action.
54
54
  def can?(*args)
55
- self.class.credentials.allow? self, *args
55
+ metaclass.credentials.allow?(self, *args)
56
56
  end
57
57
  alias_method :able_to?, :can?
58
+
59
+ def metaclass
60
+ class << self
61
+ self
62
+ end
63
+ end
58
64
 
59
65
  def self.included(receiver) #:nodoc:
60
66
  receiver.extend ClassMethods
@@ -81,7 +81,7 @@ module Credentials
81
81
  return false unless receiver.respond_to? condition
82
82
  !!receiver.send(condition, *args[0, receiver.method(condition).arity])
83
83
  when Proc
84
- raise ArgumentError, "wrong number of arguments to condition (#{args.size} to #{condition.arity})" unless args.size + 1 == condition.arity
84
+ raise ArgumentError, "wrong number of arguments to condition (#{args.size + 1} to #{condition.arity})" unless args.size + 1 == condition.arity
85
85
  !!condition.call(receiver, *args)
86
86
  else
87
87
  raise ArgumentError, "invalid :if or :unless option (expected Symbol or Proc, or array thereof; got #{condition.class})"
@@ -11,6 +11,7 @@ module Credentials
11
11
  attr_accessor :klass
12
12
  attr_accessor :options
13
13
  attr_accessor :rules
14
+ attr_reader :superklass_rulebook
14
15
 
15
16
  DEFAULT_OPTIONS = {
16
17
  :default => :deny
@@ -18,23 +19,28 @@ module Credentials
18
19
 
19
20
  def initialize(klass)
20
21
  self.klass = klass
21
- @rules = if klass.superclass.respond_to?(:credentials) && !klass.superclass.credentials.empty?
22
- klass.superclass.credentials.rules.dup
22
+ superklass = if klass.to_s =~ /^#<Class:#<([\w_]+)/ # there must be a better way
23
+ $1.constantize
23
24
  else
24
- []
25
+ klass.superclass
26
+ end
27
+
28
+ @rules = []
29
+ if superklass == Object
30
+ @superklass_rulebook = nil
31
+ @options = {}
32
+ else
33
+ @superklass_rulebook = superklass.credentials
34
+ @options = superklass_rulebook.options.dup
25
35
  end
26
- @options = {}
27
36
  end
28
37
 
29
38
  # Creates a Rulebook for the given class.
30
39
  # Should not be called directly: instead,
31
40
  # use +class.credentials+ (q.v.).
32
41
  def self.for(klass)
33
- rulebook = new(klass)
34
- if superclass && superclass.respond_to?(:credentials)
35
- rulebook.rules = superclass.credentials.rules.dup
36
- end
37
- rulebook
42
+ @rulebooks ||= {}
43
+ @rulebooks[klass] ||= new(klass)
38
44
  end
39
45
 
40
46
  # Returns +true+ if there are no rules defined in this Rulebook.
@@ -199,11 +205,13 @@ module Credentials
199
205
 
200
206
  # Subset of rules that grant permission by exposing an +allow?+ method.
201
207
  def allow_rules
208
+ @allow_rules ||= (superklass_rulebook ? superklass_rulebook.allow_rules : []) +
202
209
  rules.select { |rule| rule.respond_to? :allow? }
203
210
  end
204
211
 
205
212
  # Subset of rules that deny permission by exposing an +deny?+ method.
206
213
  def deny_rules
214
+ @deny_rules ||= (superklass_rulebook ? superklass_rulebook.deny_rules : []) +
207
215
  rules.select { |rule| rule.respond_to? :deny? }
208
216
  end
209
217
  end
@@ -9,4 +9,19 @@ describe Credentials::Rulebook do
9
9
  Animal.credentials.should_not == Carnivore.credentials
10
10
  Animal.credentials.rules.should_not == Carnivore.credentials.rules
11
11
  end
12
+
13
+ describe "created for an instance" do
14
+ before :all do
15
+ @penguin = Bird.new("Penguin")
16
+ @penguin.metaclass.credentials do |penguin|
17
+ penguin.can :swim
18
+ end
19
+ @emu = Bird.new("Emu")
20
+ end
21
+
22
+ it "should grant permissions only for that instance" do
23
+ @penguin.should be_able_to(:swim)
24
+ @emu.should_not be_able_to(:swim)
25
+ end
26
+ end
12
27
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: credentials
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.3.1
4
+ version: 2.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Matt Powell
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-12-17 00:00:00 +13:00
12
+ date: 2010-01-25 00:00:00 +13:00
13
13
  default_executable:
14
14
  dependencies: []
15
15