roles_mongoid 0.2.4

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/.bundle/config ADDED
@@ -0,0 +1,2 @@
1
+ ---
2
+ BUNDLE_DISABLE_SHARED_GEMS: "1"
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ README.rdoc
2
+ lib/**/*.rb
3
+ bin/*
4
+ features/**/*.feature
5
+ LICENSE
data/.gitignore ADDED
@@ -0,0 +1,21 @@
1
+ ## MAC OS
2
+ .DS_Store
3
+
4
+ ## TEXTMATE
5
+ *.tmproj
6
+ tmtags
7
+
8
+ ## EMACS
9
+ *~
10
+ \#*
11
+ .\#*
12
+
13
+ ## VIM
14
+ *.swp
15
+
16
+ ## PROJECT::GENERAL
17
+ coverage
18
+ rdoc
19
+ pkg
20
+
21
+ ## PROJECT::SPECIFIC
data/.rspec ADDED
@@ -0,0 +1 @@
1
+ --format nested --color
data/Gemfile ADDED
@@ -0,0 +1,15 @@
1
+ source :rubygems
2
+ source 'http://gems.github.com/'
3
+
4
+ group :default do
5
+ gem "mongoid", '~> 2.0.0.beta.18'
6
+ gem 'bson', '~> 1.0.7'
7
+ gem "activesupport", '~> 3.0.0'
8
+ gem "require_all", '~> 1.2.0'
9
+ gem "sugar-high", '~> 0.2.10'
10
+ gem "roles_generic", '~> 0.2.6'
11
+ end
12
+
13
+ group :test do
14
+ gem "rspec", '~> 2.0.0.beta.22'
15
+ end
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 Kristian Mandrup
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.markdown ADDED
@@ -0,0 +1,59 @@
1
+ # Roles for Mongoid
2
+
3
+ A Mongoid implementation of [roles generic](http://github.com/kristianmandrup/roles_generic)
4
+
5
+ ## Intro
6
+
7
+ Implements the [roles generic](http://github.com/kristianmandrup/roles_generic) Roles API
8
+ It also implements the following Role strategies:
9
+
10
+ * admin_flag
11
+ * many_roles
12
+ * one_role
13
+ * roles_mask
14
+ * role_string
15
+ * role_strings
16
+
17
+ # Install
18
+
19
+ <code>gem install roles_mongoid</code>
20
+
21
+ ## Rails generator
22
+
23
+ The library comes with a Rails 3 generator that lets you populate a user model with a role strategy of your choice.
24
+
25
+ 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.
26
+
27
+ * admin_flag
28
+ * many_roles
29
+ * one_role
30
+ * roles_mask
31
+ * role_string
32
+ * role_strings
33
+
34
+ *Roles generator*
35
+
36
+ Apply :admin_flag Role strategy to User model using default roles :admin and :guest (default)
37
+
38
+ <code>$ rails g mongoid:roles User --strategy admin_flag</code>
39
+
40
+ Apply :admin_flag Role strategy to User model using default roles and extra role :author
41
+
42
+ <code>$ rails g mongoid:roles_migration User --strategy admin_flag --roles author</code>
43
+
44
+ Apply :one_role Role strategy to User model without default roles, only with roles :user, :special and :editor
45
+
46
+ <code>$ rails g mongoid:roles_migration User --strategy one_role --roles user special editor --no-default-roles</code>
47
+ ## Note on Patches/Pull Requests
48
+
49
+ * Fork the project.
50
+ * Make your feature addition or bug fix.
51
+ * Add tests for it. This is important so I don't break it in a
52
+ future version unintentionally.
53
+ * Commit, do not mess with rakefile, version, or history.
54
+ (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
55
+ * Send me a pull request. Bonus points for topic branches.
56
+
57
+ ## Copyright
58
+
59
+ Copyright (c) 2010 Kristian Mandrup. See LICENSE for details.
data/Rakefile ADDED
@@ -0,0 +1,24 @@
1
+ begin
2
+ require 'jeweler'
3
+ Jeweler::Tasks.new do |gem|
4
+ gem.name = "roles_mongoid"
5
+ gem.summary = %Q{Implementation of Roles generic API for Mongoid}
6
+ gem.description = %Q{Makes it easy to set a role strategy on your User model in Mongoid}
7
+ gem.email = "kmandrup@gmail.com"
8
+ gem.homepage = "http://github.com/kristianmandrup/roles_mongoid"
9
+ gem.authors = ["Kristian Mandrup"]
10
+ gem.add_development_dependency "rspec", '~> 2.0.0.beta.22'
11
+
12
+ gem.add_dependency "mongoid", '~> 2.0.0.beta.18'
13
+ gem.add_dependency 'bson', '~> 1.0.7'
14
+ gem.add_dependency "activesupport", '~> 3.0.0'
15
+ gem.add_dependency "require_all", '~> 1.2.0'
16
+ gem.add_dependency "sugar-high", '~> 0.2.11'
17
+ gem.add_dependency "roles_generic", '~> 0.2.7'
18
+
19
+ end
20
+ Jeweler::GemcutterTasks.new
21
+ rescue LoadError
22
+ puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
23
+ end
24
+
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.2.4
@@ -0,0 +1,68 @@
1
+ require 'rails3_artifactor'
2
+ require 'logging_assist'
3
+
4
+ module Mongoid
5
+ module Generators
6
+ class RolesGenerator < Rails::Generators::NamedBase
7
+ desc "Add role strategy to a model"
8
+
9
+ class_option :strategy, :type => :string, :aliases => "-s", :default => 'role_string',
10
+ :desc => "Role strategy to use (admin_flag, role_string, roles_string, role_strings, one_role, many_roles, roles_mask)"
11
+
12
+
13
+ class_option :roles, :type => :array, :aliases => "-r", :default => [], :desc => "Valid roles"
14
+
15
+ def apply_role_strategy
16
+ log.add_logfile
17
+ log.debug "apply_role_strategy for : #{strategy} in model #{name}"
18
+ insert_into_model name do
19
+ insertion_text
20
+ end
21
+ end
22
+
23
+ protected
24
+
25
+ extend Rails3::Assist::UseMacro
26
+ use_orm :mongoid
27
+ include Rails::Assist::BasicLogging
28
+
29
+ def orm
30
+ :mongoid
31
+ end
32
+
33
+ def default_roles
34
+ [:admin, :guest]
35
+ end
36
+
37
+ def roles_to_add
38
+ @roles_to_add ||= default_roles.concat(options[:roles]).to_symbols.uniq
39
+ end
40
+
41
+ def roles
42
+ roles_to_add.map{|r| ":#{r}" }
43
+ end
44
+
45
+ def role_strategy_statement
46
+ "strategy :#{strategy}, :default\n#{role_class_stmt}"
47
+ end
48
+
49
+ def role_class_stmt
50
+ " role_class :role" if [:one_role, :many_roles].include? (strategy.to_sym)
51
+ end
52
+
53
+ def roles_statement
54
+ roles ? "valid_roles_are #{roles.join(', ')}" : ''
55
+ end
56
+
57
+ def insertion_text
58
+ %Q{include Roles::#{orm.to_s.camelize}
59
+ #{role_strategy_statement}
60
+ #{roles_statement}}
61
+ end
62
+
63
+ def strategy
64
+ options[:strategy]
65
+ end
66
+ end
67
+ end
68
+ 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
+ end
5
+ end
6
+
7
+ module Roles
8
+ module Mongoid
9
+ def self.included(base)
10
+ base.extend Roles::Base
11
+ base.extend ClassMethods
12
+ base.orm_name = :mongoid
13
+ end
14
+
15
+ module ClassMethods
16
+
17
+ MAP = {
18
+ :admin_flag => "field :admin_flag, :type => Boolean",
19
+ :many_roles => "references_many :many_roles, :stored_as => :array, :class_name => 'Role', :default => []",
20
+ :one_role => "references_one :one_role, :class_name => 'Role'",
21
+ :roles_mask => "field :roles_mask, :type => Integer, :default => 1",
22
+ :role_string => "field :role_string, :type => String",
23
+ :role_strings => "field :role_strings, :type => Array",
24
+ :roles_string => "field :roles_string, :type => String"
25
+ }
26
+
27
+ def strategy name, options=nil
28
+ if options == :default && MAP[name]
29
+ instance_eval MAP[name]
30
+ end
31
+ role_strategy name, options
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,12 @@
1
+ require 'sugar-high/module'
2
+
3
+ module Roles
4
+ modules :mongoid do
5
+ nested_modules :user, :role
6
+ end
7
+ modules :base, :strategy
8
+ end
9
+
10
+ module RoleStrategy
11
+ modules :mongoid
12
+ end
@@ -0,0 +1,28 @@
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 Mongoid::Document
14
+ field :name, :type => String
15
+ referenced_in :user
16
+
17
+ class << self
18
+ def find_roles(*role_names)
19
+ where(:name.in => role_names.flatten).to_a
20
+ end
21
+
22
+ def find_role role_name
23
+ raise ArgumentError, "#find_role takes a single role name as argument, not: #{role_name.inspect}" if !role_name.kind_of_label?
24
+ res = find_roles(role_name)
25
+ res ? res.first : res
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,67 @@
1
+ module RoleStrategy::Mongoid
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
+ end
11
+
12
+ module ClassMethods
13
+ def role_attribute
14
+ "#{strategy_class.roles_attribute_name.to_s.singularize}_ids".to_sym
15
+ end
16
+
17
+ def in_role(role_name)
18
+ in_roles(role_name)
19
+ end
20
+
21
+ def in_roles(*role_names)
22
+ begin
23
+ role_ids = Role.where(:name.in => role_names.to_strings).to_a.map(&:_id)
24
+ criteria.in(role_attribute => role_ids).to_a
25
+ rescue
26
+ return []
27
+ end
28
+ end
29
+ end
30
+
31
+ module Implementation
32
+ def role_attribute
33
+ strategy_class.roles_attribute_name
34
+ end
35
+
36
+ # assign roles
37
+ def roles=(*_roles)
38
+ _roles = get_roles(_roles)
39
+ return nil if roles.none?
40
+
41
+ role_relations = role_class.find_roles(_roles)
42
+ self.send("#{role_attribute}=", role_relations)
43
+ save
44
+ end
45
+
46
+ def add_roles(*roles)
47
+ raise "Role class #{role_class} does not have a #find_role(role) method" if !role_class.respond_to? :find_role
48
+ role_relations = role_class.find_roles(*roles)
49
+ self.send(role_attribute) << role_relations
50
+ save
51
+ end
52
+
53
+ # query assigned roles
54
+ def roles
55
+ self.send(role_attribute)
56
+ end
57
+
58
+ def roles_list
59
+ [roles].flatten.map{|r| r.name }.compact.to_symbols
60
+ end
61
+ end
62
+
63
+ extend Roles::Generic::User::Configuration
64
+ configure :type => :role_class
65
+ end
66
+ end
67
+
@@ -0,0 +1,59 @@
1
+ module RoleStrategy::Mongoid
2
+ module RoleStrings
3
+ def self.default_role_attribute
4
+ :role_strings
5
+ end
6
+
7
+ def self.included base
8
+ base.extend ClassMethods
9
+ end
10
+
11
+ module ClassMethods
12
+ def role_attribute
13
+ strategy_class.roles_attribute_name.to_sym
14
+ end
15
+
16
+ def in_role(role_name)
17
+ in_roles(role_name)
18
+ end
19
+
20
+ def in_roles(*role_names)
21
+ begin
22
+ where(role_attribute.in => role_names).to_a
23
+ rescue
24
+ return []
25
+ end
26
+ end
27
+ end
28
+
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=
38
+
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
45
+
46
+ # query assigned roles
47
+ def roles
48
+ self.send(role_attribute).map{|r| r.to_sym}
49
+ end
50
+
51
+ def roles_list
52
+ [roles].flatten
53
+ end
54
+ end
55
+
56
+ extend Roles::Generic::User::Configuration
57
+ configure
58
+ end
59
+ end
@@ -0,0 +1,81 @@
1
+ module RoleStrategy::Mongoid
2
+ module RolesMask
3
+ def self.default_role_attribute
4
+ :roles_mask
5
+ end
6
+
7
+ def self.included base
8
+ base.extend ClassMethods
9
+ end
10
+
11
+ module ClassMethods
12
+ def role_attribute
13
+ strategy_class.roles_attribute_name.to_sym
14
+ end
15
+
16
+ def in_role(role)
17
+ mask = calc_index(role.to_s)
18
+ all.select do |user|
19
+ (user.send(role_attribute) & mask) > 0
20
+ end
21
+ end
22
+
23
+ def in_roles(*roles)
24
+ all.select do |user|
25
+ roles.flatten.any? do |role|
26
+ mask = calc_index(role.to_s)
27
+ (user.send(role_attribute) & mask) > 0
28
+ end
29
+ end
30
+ end
31
+
32
+ def calc_index(r)
33
+ 2**strategy_class.valid_roles.index(r.to_sym)
34
+ end
35
+ end
36
+
37
+ module Implementation
38
+ class Roles < ::Set # :nodoc:
39
+ attr_reader :model_instance
40
+
41
+ def initialize(sender, *roles)
42
+ super(*roles)
43
+ @model_instance = sender
44
+ end
45
+
46
+ def <<(role)
47
+ model_instance.roles = super.to_a
48
+ self
49
+ end
50
+ end
51
+
52
+ def role_attribute
53
+ strategy_class.roles_attribute_name
54
+ end
55
+
56
+ # assign roles
57
+ def roles=(*roles)
58
+ self.send("#{role_attribute}=", (roles.flatten.map { |r| r.to_sym } & strategy_class.valid_roles).map { |r| calc_index(r) }.inject { |sum, bitvalue| sum + bitvalue })
59
+ end
60
+ alias_method :role=, :roles=
61
+
62
+ # query assigned roles
63
+ def roles
64
+ strategy_class::Roles.new(self, strategy_class.valid_roles.reject { |r| ((self.send(role_attribute) || 0) & calc_index(r)).zero? })
65
+ end
66
+
67
+ def roles_list
68
+ roles.to_a
69
+ end
70
+
71
+ protected
72
+
73
+ def calc_index(r)
74
+ 2**strategy_class.valid_roles.index(r)
75
+ end
76
+ end
77
+
78
+ extend Roles::Generic::User::Configuration
79
+ configure
80
+ end
81
+ end
@@ -0,0 +1,53 @@
1
+ module RoleStrategy::Mongoid
2
+ module AdminFlag
3
+ def self.default_role_attribute
4
+ :admin_flag
5
+ end
6
+
7
+ def self.included base
8
+ base.extend ClassMethods
9
+ end
10
+
11
+ module ClassMethods
12
+ def role_attribute
13
+ strategy_class.roles_attribute_name.to_sym
14
+ end
15
+
16
+ def in_role(role_name)
17
+ case role_name.downcase.to_sym
18
+ when :admin
19
+ where(role_attribute => true)
20
+ else
21
+ where(role_attribute => false)
22
+ end
23
+ end
24
+ end
25
+
26
+ module Implementation
27
+ def role_attribute
28
+ strategy_class.roles_attribute_name
29
+ end
30
+
31
+ # assign roles
32
+ def roles=(*new_roles)
33
+ first_role = new_roles.flatten.first
34
+ if valid_role?(first_role)
35
+ self.send("#{role_attribute}=", new_roles.flatten.first.admin?)
36
+ else
37
+ raise ArgumentError, "The role #{first_role} is not a valid role"
38
+ end
39
+ end
40
+
41
+ # query assigned roles
42
+ def roles
43
+ role = self.send(role_attribute) ? strategy_class.admin_role_key : strategy_class.default_role_key
44
+ [role]
45
+ end
46
+ alias_method :roles_list, :roles
47
+
48
+ end # Implementation
49
+
50
+ extend Roles::Generic::User::Configuration
51
+ configure :num => :single
52
+ end
53
+ end
@@ -0,0 +1,57 @@
1
+ module RoleStrategy::Mongoid
2
+ module OneRole
3
+ def self.default_role_attribute
4
+ :one_role
5
+ end
6
+
7
+ def self.included base
8
+ base.extend Roles::Generic::Role::ClassMethods
9
+ base.extend ClassMethods
10
+ end
11
+
12
+ module ClassMethods
13
+ def role_attribute
14
+ strategy_class.roles_attribute_name.to_sym
15
+ end
16
+
17
+ def in_role(role_name)
18
+ in_roles(role_name)
19
+ end
20
+
21
+ def in_roles(*role_names)
22
+ begin
23
+ role_ids = Role.where(:name.in => role_names.to_strings).to_a.map(&:user_id)
24
+ where(:_id.in => role_ids)
25
+ rescue
26
+ return []
27
+ end
28
+ end
29
+ end
30
+
31
+ module Implementation
32
+ # assign roles
33
+ def roles=(*_roles)
34
+ _roles = get_roles(_roles)
35
+ return nil if _roles.none?
36
+
37
+ role_relation = role_class.find_role(_roles.first)
38
+ self.send("#{role_attribute}=", role_relation)
39
+ one_role.save
40
+ end
41
+ alias_method :role=, :roles=
42
+
43
+ # query assigned roles
44
+ def roles
45
+ role = self.send(role_attribute)
46
+ role ? [role.name.to_sym] : []
47
+ end
48
+
49
+ def roles_list
50
+ self.roles.to_a
51
+ end
52
+ end
53
+
54
+ extend Roles::Generic::User::Configuration
55
+ configure :num => :single, :type => :role_class
56
+ end
57
+ end
@@ -0,0 +1,51 @@
1
+ module RoleStrategy::Mongoid
2
+ module RoleString
3
+ def self.default_role_attribute
4
+ :role_string
5
+ end
6
+
7
+ def self.included base
8
+ base.extend ClassMethods
9
+ end
10
+
11
+ module ClassMethods
12
+ def role_attribute
13
+ strategy_class.roles_attribute_name.to_sym
14
+ end
15
+
16
+ def in_role(role_name)
17
+ where(role_attribute => role_name)
18
+ end
19
+ end
20
+
21
+
22
+ module Implementation
23
+ def role_attribute
24
+ strategy_class.roles_attribute_name
25
+ end
26
+
27
+ # assign roles
28
+ def roles=(*roles)
29
+ self.role = roles.select_labels.first.to_s
30
+ end
31
+
32
+ def role= role_name
33
+ if role_name.kind_of_label? && valid_role?(role_name)
34
+ self.send("#{role_attribute}=", role_name.to_s)
35
+ end
36
+ end
37
+
38
+ # query assigned roles
39
+ def roles
40
+ role = self.send(role_attribute)
41
+ [role.to_sym]
42
+ end
43
+ alias_method :roles_list, :roles
44
+ end
45
+
46
+ extend Roles::Generic::User::Configuration
47
+ configure :num => :single
48
+ end
49
+ end
50
+
51
+
@@ -0,0 +1,15 @@
1
+ require 'sugar-high/file'
2
+ require 'sugar-high/array'
3
+
4
+ module Roles::Strategy
5
+ class << self
6
+ def role_dir
7
+ File.dirname(__FILE__)
8
+ end
9
+
10
+ def gem_name
11
+ :roles_mongoid
12
+ end
13
+ end
14
+ end
15
+