roles_mongo_mapper 0.1.4 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (38) hide show
  1. data/README.markdown +11 -2
  2. data/Rakefile +7 -6
  3. data/VERSION +1 -1
  4. data/lib/roles_mongo_mapper/base.rb +21 -4
  5. data/lib/roles_mongo_mapper/embedded_role.rb +35 -0
  6. data/lib/roles_mongo_mapper/role.rb +7 -5
  7. data/lib/roles_mongo_mapper/strategy/multi.rb +59 -0
  8. data/lib/roles_mongo_mapper/strategy/multi/embed_many_roles.rb +71 -0
  9. data/lib/roles_mongo_mapper/strategy/multi/many_roles.rb +69 -23
  10. data/lib/roles_mongo_mapper/strategy/multi/role_strings.rb +44 -24
  11. data/lib/roles_mongo_mapper/strategy/multi/roles_mask.rb +67 -19
  12. data/lib/roles_mongo_mapper/strategy/shared.rb +29 -0
  13. data/lib/roles_mongo_mapper/strategy/single.rb +34 -0
  14. data/lib/roles_mongo_mapper/strategy/single/admin_flag.rb +50 -15
  15. data/lib/roles_mongo_mapper/strategy/single/embed_one_role.rb +79 -0
  16. data/lib/roles_mongo_mapper/strategy/single/one_role.rb +38 -30
  17. data/lib/roles_mongo_mapper/strategy/single/role_string.rb +20 -18
  18. data/roles_mongo_mapper.gemspec +51 -32
  19. data/sandbox/test.rb +13 -3
  20. data/spec/roles_mongo_mapper/strategy/api_examples.rb +199 -0
  21. data/spec/roles_mongo_mapper/strategy/hooks.rb +7 -0
  22. data/spec/roles_mongo_mapper/strategy/multi/embed_many_roles_spec.rb +19 -0
  23. data/spec/roles_mongo_mapper/strategy/multi/many_roles_spec.rb +19 -0
  24. data/spec/roles_mongo_mapper/strategy/multi/role_strings_spec.rb +19 -0
  25. data/spec/roles_mongo_mapper/strategy/multi/roles_mask_spec.rb +18 -0
  26. data/spec/roles_mongo_mapper/strategy/single/admin_flag_spec.rb +18 -0
  27. data/spec/roles_mongo_mapper/strategy/single/embed_one_role_spec.rb +19 -0
  28. data/spec/roles_mongo_mapper/strategy/single/one_role_spec.rb +20 -0
  29. data/spec/roles_mongo_mapper/strategy/single/role_string_spec.rb +19 -0
  30. data/spec/roles_mongo_mapper/strategy/user_setup.rb +13 -0
  31. data/spec/spec_helper.rb +11 -6
  32. metadata +60 -32
  33. data/spec/roles_mongo_mapper/strategy/admin_flag_spec.rb +0 -76
  34. data/spec/roles_mongo_mapper/strategy/many_roles_spec.rb +0 -69
  35. data/spec/roles_mongo_mapper/strategy/one_role_spec.rb +0 -66
  36. data/spec/roles_mongo_mapper/strategy/role_string_spec.rb +0 -68
  37. data/spec/roles_mongo_mapper/strategy/role_strings_spec.rb +0 -69
  38. data/spec/roles_mongo_mapper/strategy/roles_mask_spec.rb +0 -69
data/README.markdown CHANGED
@@ -5,7 +5,8 @@ A *Mongo Mapper* implementation of [roles generic](http://github.com/kristianman
5
5
  ## Intro
6
6
 
7
7
  Implements the [roles generic](http://github.com/kristianmandrup/roles_generic) Roles API
8
- It also implements the following Role strategies:
8
+
9
+ Generic Role strategies implemented:
9
10
 
10
11
  * admin_flag
11
12
  * many_roles
@@ -14,13 +15,21 @@ It also implements the following Role strategies:
14
15
  * role_string
15
16
  * role_strings
16
17
 
18
+ *Update Nov 24, 2010*
19
+ Version 0.3.1 and up is a major refactoring to support Roles Generic 0.3 and above with a new and improved architecture and testing framework.
20
+ Since 0.3.2 development of some basic infrastructure to support embedded role strategies in the future has been initiated.
21
+
22
+ * embed_one_role
23
+ * embed_many_roles
24
+
25
+ Please join in the effort to implement and add these strategies to the mix.
26
+
17
27
  ## Install
18
28
 
19
29
  <code>gem install roles_mongo_mapper</code>
20
30
 
21
31
  ## Rails generator
22
32
 
23
-
24
33
  The library comes with a Rails 3 generator that lets you populate a user model with a role strategy of your choice.
25
34
 
26
35
  The following role strategies are included by default. Add your own by adding extra files inside the strategy folder, one file for each role strategy is recommended.
data/Rakefile CHANGED
@@ -8,15 +8,16 @@ begin
8
8
  gem.homepage = "http://github.com/kristianmandrup/roles_mongo_mapper"
9
9
  gem.authors = ["Kristian Mandrup"]
10
10
 
11
- gem.add_development_dependency "rspec", ">= 2.0.0.rc"
11
+ gem.add_development_dependency "rspec", ">= 2.1"
12
12
  gem.add_development_dependency 'generator-spec', "~> 0.6.5"
13
13
 
14
- gem.add_dependency "mongo_mapper", '~> 0.8.4'
15
- gem.add_dependency "activesupport", '~> 3.0.0'
14
+ gem.add_dependency "mongo_mapper", '>= 0.8.4'
15
+ gem.add_dependency "activesupport", '~> 3.0'
16
16
  gem.add_dependency "require_all", '~> 1.2.0'
17
- gem.add_dependency "sugar-high", '~> 0.2.11'
18
- gem.add_dependency "roles_generic", '~> 0.2.7'
19
- gem.add_dependency 'logging_assist', '~> 0.1.3'
17
+ gem.add_dependency "sugar-high", '~> 0.3.0'
18
+ gem.add_dependency "roles_generic", '~> 0.3.3'
19
+ gem.add_dependency 'rails3_artifactor', '~> 0.3.0'
20
+ gem.add_dependency 'logging_assist', '>= 0.1.5'
20
21
 
21
22
  end
22
23
  Jeweler::GemcutterTasks.new
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.4
1
+ 0.2.0
@@ -17,18 +17,35 @@ module Roles::MongoMapper
17
17
  :admin_flag => "key :admin_flag, Boolean",
18
18
  # :many_roles => "references_many :many_roles, :stored_as => :array, :class_name => 'Role', :default => []",
19
19
  # :one_role => "references_one :one_role, :class_name => 'Role'",
20
- :roles_mask => "key :roles_mask, Integer, :default => 1",
20
+
21
+ # :embed_many_roles => "many :many_roles, :class_name => 'Role'",
22
+ # :embed_one_role => "one :one_role, :class_name => 'Role'",
23
+
24
+ :roles_mask => "key :roles_mask, Integer, :default => 0",
21
25
  :role_string => "key :role_string, String",
22
26
  :role_strings => "key :role_strings, Array",
23
27
  :roles_string => "key :roles_string, String"
24
28
  }
25
29
 
26
- def strategy name, options = nil
27
- if options == :default && MAP[name]
30
+ def strategy name, options = {}
31
+ if (options == :default || options[:config] == :default) && MAP[name]
28
32
  instance_eval MAP[name]
29
33
  end
30
34
 
31
- role_strategy name, options
35
+ if !options.kind_of? Symbol
36
+ role_class = options[:role_class] ? options[:role_class].to_s.camelize.constantize : (Role if defined? Role)
37
+ end
38
+
39
+ # case name
40
+ # when :embed_one_role
41
+ # raise ArgumentError, "#strategy class method must take :role_class option when using an embedded role strategy" if !role_class
42
+ # role_class.embedded_in :user, :inverse_of => :one_role
43
+ # when :embed_many_roles
44
+ # raise ArgumentError, "#strategy class method must take :role_class option when using an embedded role strategy" if !role_class
45
+ # role_class.embedded_in :user, :inverse_of => :many_roles
46
+ # end
47
+
48
+ set_role_strategy name, options
32
49
  end
33
50
  end
34
51
  end
@@ -0,0 +1,35 @@
1
+ module Roles::Base
2
+ def valid_roles_are(*role_list)
3
+ strategy_class.valid_roles = role_list.to_symbols
4
+ if role_class_name
5
+ role_list.each do |name|
6
+ role_class_name.create(:name => name.to_s)
7
+ end
8
+ end
9
+ end
10
+ end
11
+
12
+ class Role
13
+ include MongoMapper::EmbeddedDocument
14
+ key :name, String
15
+
16
+ key :user_id, ObjectId
17
+ belongs_to :user
18
+
19
+ # scope :by_name, lambda { |name| where(:name => name.to_s) }
20
+ # scope :by_names, lambda { |*names| where(:name => names.to_strings) }
21
+
22
+ class << self
23
+ def find_roles(*role_names)
24
+ role_names.flatten!
25
+ by_names(role_names).all
26
+ end
27
+
28
+ def find_role role_name
29
+ raise ArgumentError, "#find_role takes a single role name as argument, not: #{role_name.inspect}" if !role_name.kind_of_label?
30
+ by_name(role_name).first
31
+ end
32
+ end
33
+ end
34
+
35
+
@@ -3,7 +3,7 @@ module Roles::Base
3
3
  strategy_class.valid_roles = role_list.to_symbols
4
4
  if role_class_name
5
5
  role_list.each do |name|
6
- role_class_name.create(:name => name.to_s).save
6
+ role_class_name.create(:name => name.to_s)
7
7
  end
8
8
  end
9
9
  end
@@ -16,11 +16,11 @@ class Role
16
16
  scope :by_name, lambda { |name| where(:name => name.to_s) }
17
17
  scope :by_names, lambda { |*names| where(:name => names.to_strings) }
18
18
 
19
-
20
19
  class << self
21
- def find_roles(*role_names)
22
- # return all(:name => role_names.to_strings)
23
- by_names(*role_names).all
20
+ def find_roles(*role_names)
21
+ role_names.flatten!
22
+ by_names(role_names).all
23
+ # where(:name => role_names.to_strings).all
24
24
  end
25
25
 
26
26
  def find_role role_name
@@ -29,3 +29,5 @@ class Role
29
29
  end
30
30
  end
31
31
  end
32
+
33
+
@@ -0,0 +1,59 @@
1
+ require 'roles_mongo_mapper/strategy/shared'
2
+
3
+ module Roles::MongoMapper
4
+ module Strategy
5
+ module Multi
6
+ # assign multiple roles
7
+ def roles=(*role_names)
8
+ extracted_roles = extract_roles(role_names)
9
+ return nil if extracted_roles.empty?
10
+ set_roles(select_valid_roles extracted_roles)
11
+ end
12
+
13
+ def add_roles *roles
14
+ new_roles = select_valid_roles(roles)
15
+ if !new_roles.empty?
16
+ self.roles = self.roles + new_roles
17
+ end
18
+ end
19
+
20
+ # should remove the current single role (set = nil)
21
+ # only if it is contained in the list of roles to be removed
22
+ def remove_roles *role_names
23
+ role_names = role_names.flat_uniq
24
+ set_empty_roles and return if roles_diff(role_names).empty?
25
+ roles_to_remove = select_valid_roles(role_names)
26
+ diff = roles_diff(role_names)
27
+ diff = role_class.find_roles(diff).to_a if self.class.role_strategy.type == :complex
28
+ set_roles(diff)
29
+ true
30
+ end
31
+
32
+ # query assigned roles
33
+ def roles
34
+ get_roles.to_a.map do |role|
35
+ role.respond_to?(:sym) ? role.to_sym : role
36
+ end
37
+ end
38
+
39
+ def roles_list
40
+ my_roles = [roles].flat_uniq
41
+ return [] if my_roles.empty?
42
+ has_role_class? ? my_roles.map{|r| r.name.to_sym } : my_roles
43
+ end
44
+
45
+ protected
46
+
47
+ def set_roles *roles
48
+ roles = roles.flat_uniq
49
+ roles = roles.first if self.class.role_strategy.multiplicity == :single
50
+ # self.send("#{role_attribute}").send(:<<, roles)
51
+ self.send("#{role_attribute}=", roles)
52
+ end
53
+
54
+ def get_roles
55
+ self.send(role_attribute)
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,71 @@
1
+ module RoleStrategy::MongoMapper
2
+ module ManyRoles
3
+ def self.default_role_attribute
4
+ :many_roles
5
+ end
6
+
7
+ def self.included base
8
+ base.extend Roles::Generic::Role::ClassMethods
9
+ base.extend ClassMethods
10
+ base.key :many_roles_ids, Array, :typecast => 'ObjectId'
11
+ base.many :many_roles, class_name: 'Role', :in => :many_roles_ids
12
+ base.ensure_index :many_role_ids
13
+ end
14
+
15
+ module ClassMethods
16
+ def role_attribute
17
+ strategy_class.roles_attribute_name
18
+ end
19
+
20
+ def role_id_attribute
21
+ "#{role_attribute}_ids".to_sym
22
+ end
23
+
24
+ def in_role(role_name)
25
+ role = Role.find_role(role_name)
26
+ res = all(role_id_attribute => role.id)
27
+ end
28
+
29
+ def in_roles(*role_names)
30
+ role_ids = Role.find_roles(role_names).map{|role| role.id}
31
+ all(role_id_attribute.in => role_ids)
32
+ end
33
+ end
34
+
35
+ module Implementation
36
+ def role_id_attribute
37
+ "#{role_attribute}_ids".to_sym
38
+ end
39
+
40
+ # assign roles
41
+ def roles=(*_roles)
42
+ _roles = get_roles(_roles)
43
+ return nil if _roles.none?
44
+
45
+ role_relations = role_class.find_roles(_roles)
46
+ self.send("#{role_attribute}=", role_relations)
47
+ save
48
+ end
49
+
50
+ def add_roles(*role_names)
51
+ raise "Role class #{role_class} does not have a #find_role(role) method" if !role_class.respond_to? :find_role
52
+ role_relations = role_class.find_roles(*role_names)
53
+ self.send(role_attribute) << role_relations
54
+ save
55
+ end
56
+
57
+ # query assigned roles
58
+ def roles
59
+ self.send(role_attribute)
60
+ end
61
+
62
+ def roles_list
63
+ [roles].flatten.map{|r| r.name }.compact.to_symbols
64
+ end
65
+ end
66
+
67
+ extend Roles::Generic::User::Configuration
68
+ configure :type => :role_class
69
+ end
70
+ end
71
+
@@ -1,3 +1,5 @@
1
+ require 'roles_mongo_mapper/strategy/multi'
2
+
1
3
  module RoleStrategy::MongoMapper
2
4
  module ManyRoles
3
5
  def self.default_role_attribute
@@ -8,7 +10,7 @@ module RoleStrategy::MongoMapper
8
10
  base.extend Roles::Generic::Role::ClassMethods
9
11
  base.extend ClassMethods
10
12
  base.key :many_roles_ids, Array, :typecast => 'ObjectId'
11
- base.many :many_roles, class_name: 'Role', :in => :many_roles_ids
13
+ base.many :many_roles, :class_name => 'Role', :in => :many_roles_ids
12
14
  base.ensure_index :many_role_ids
13
15
  end
14
16
 
@@ -26,42 +28,86 @@ module RoleStrategy::MongoMapper
26
28
  res = all(role_id_attribute => role.id)
27
29
  end
28
30
 
29
- def in_roles(*role_names)
31
+ def in_any_role(*role_names)
30
32
  role_ids = Role.find_roles(role_names).map{|role| role.id}
31
33
  all(role_id_attribute.in => role_ids)
32
34
  end
33
35
  end
34
36
 
35
- module Implementation
36
- def role_id_attribute
37
- "#{role_attribute}_ids".to_sym
37
+ module Implementation
38
+ include Roles::MongoMapper::Strategy::Multi
39
+
40
+ def has_roles?(*roles_names)
41
+ compare_roles = extract_roles(roles_names.flat_uniq)
42
+ (roles_list & compare_roles).not.empty?
38
43
  end
39
-
40
- # assign roles
41
- def roles=(*_roles)
42
- _roles = get_roles(_roles)
43
- return nil if _roles.none?
44
44
 
45
- role_relations = role_class.find_roles(_roles)
46
- self.send("#{role_attribute}=", role_relations)
47
- save
45
+ def get_roles
46
+ self.send(role_attribute)
47
+ end
48
+
49
+ def roles
50
+ get_roles.to_a.map do |role|
51
+ role.respond_to?(:sym) ? role.to_sym : role
52
+ end
48
53
  end
49
54
 
50
- def add_roles(*role_names)
51
- raise "Role class #{role_class} does not have a #find_role(role) method" if !role_class.respond_to? :find_role
52
- role_relations = role_class.find_roles(*role_names)
53
- self.send(role_attribute) << role_relations
54
- save
55
+ def roles_list
56
+ my_roles = [roles].flat_uniq
57
+ return [] if my_roles.empty?
58
+ has_role_class? ? my_roles.map{|r| r.name.to_sym } : my_roles
59
+ end
60
+
61
+ # assign multiple roles
62
+ def roles=(*role_names)
63
+ role_names = role_names.flat_uniq
64
+ role_names = extract_roles(role_names)
65
+ return nil if role_names.empty?
66
+ valids = role_class.find_roles(role_names).to_a
67
+ vrs = select_valid_roles role_names
68
+ set_roles(vrs)
55
69
  end
56
70
 
57
- # query assigned roles
58
- def roles
59
- self.send(role_attribute)
71
+ def new_roles *role_names
72
+ role_class.find_roles(extract_roles role_names)
60
73
  end
61
74
 
62
- def roles_list
63
- [roles].flatten.map{|r| r.name }.compact.to_symbols
75
+ def present_roles roles_names
76
+ roles_names.to_a.map{|role| role.name.to_s.to_sym}
64
77
  end
78
+
79
+ def set_empty_roles
80
+ self.send("#{role_attribute}=", [])
81
+ end
82
+ # def role_id_attribute
83
+ # "#{role_attribute}_ids".to_sym
84
+ # end
85
+ #
86
+ # # assign roles
87
+ # def roles=(*_roles)
88
+ # _roles = get_roles(_roles)
89
+ # return nil if _roles.none?
90
+ #
91
+ # role_relations = role_class.find_roles(_roles)
92
+ # self.send("#{role_attribute}=", role_relations)
93
+ # save
94
+ # end
95
+ #
96
+ # def add_roles(*role_names)
97
+ # raise "Role class #{role_class} does not have a #find_role(role) method" if !role_class.respond_to? :find_role
98
+ # role_relations = role_class.find_roles(*role_names)
99
+ # self.send(role_attribute) << role_relations
100
+ # save
101
+ # end
102
+ #
103
+ # # query assigned roles
104
+ # def roles
105
+ # self.send(role_attribute)
106
+ # end
107
+ #
108
+ # def roles_list
109
+ # [roles].flatten.map{|r| r.name }.compact.to_symbols
110
+ # end
65
111
  end
66
112
 
67
113
  extend Roles::Generic::User::Configuration
@@ -1,3 +1,5 @@
1
+ require 'roles_mongo_mapper/strategy/multi'
2
+
1
3
  module RoleStrategy::MongoMapper
2
4
  module RoleStrings
3
5
  def self.default_role_attribute
@@ -14,10 +16,10 @@ module RoleStrategy::MongoMapper
14
16
  end
15
17
 
16
18
  def in_role(role_name)
17
- in_roles(role_name)
19
+ in_any_role(role_name)
18
20
  end
19
21
 
20
- def in_roles(*role_names)
22
+ def in_any_role(*role_names)
21
23
  begin
22
24
  where(role_attribute.in => role_names.to_strings)
23
25
  rescue
@@ -26,31 +28,49 @@ module RoleStrategy::MongoMapper
26
28
  end
27
29
  end
28
30
 
29
- module Implementation
30
- # assign roles
31
- def roles=(*new_roles)
32
- new_roles = new_roles.flatten.map{|r| r.to_s if valid_role?(r)}.compact
33
- if new_roles && new_roles.not.empty?
34
- self.send("#{role_attribute}=", new_roles.compact.uniq)
35
- end
36
- end
37
- alias_method :role=, :roles=
31
+ module Implementation
32
+ include Roles::MongoMapper::Strategy::Multi
33
+
34
+ def new_roles *roles
35
+ ::Set.new select_valid_roles(roles)
36
+ end
38
37
 
39
- def add_roles(*roles_to_add)
40
- roles_to_add = roles_to_add.flatten.map{|r| r.to_s if valid_role?(r)}.compact
41
- if new_roles && new_roles.not.empty?
42
- self.send(role_attribute) << new_roles.compact.uniq
43
- end
44
- end
38
+ def select_valid_roles *roles
39
+ roles.flat_uniq.select{|role| valid_role? role }.map(&:to_sym)
40
+ end
41
+
42
+ def set_empty_roles
43
+ self.send("#{role_attribute}=", [])
44
+ end
45
45
 
46
- # query assigned roles
47
- def roles
48
- self.send(role_attribute).map{|r| r.to_sym}
46
+ def present_roles roles_names
47
+ roles_names.to_a
49
48
  end
50
-
51
- def roles_list
52
- [roles].flatten
53
- end
49
+
50
+ # # assign roles
51
+ # def roles=(*new_roles)
52
+ # new_roles = new_roles.flatten.map{|r| r.to_s if valid_role?(r)}.compact
53
+ # if new_roles && new_roles.not.empty?
54
+ # self.send("#{role_attribute}=", new_roles.compact.uniq)
55
+ # end
56
+ # end
57
+ # alias_method :role=, :roles=
58
+ #
59
+ # def add_roles(*roles_to_add)
60
+ # roles_to_add = roles_to_add.flatten.map{|r| r.to_s if valid_role?(r)}.compact
61
+ # if new_roles && new_roles.not.empty?
62
+ # self.send(role_attribute) << new_roles.compact.uniq
63
+ # end
64
+ # end
65
+ #
66
+ # # query assigned roles
67
+ # def roles
68
+ # self.send(role_attribute).map{|r| r.to_sym}
69
+ # end
70
+ #
71
+ # def roles_list
72
+ # [roles].flatten
73
+ # end
54
74
  end
55
75
 
56
76
  extend Roles::Generic::User::Configuration