righter 0.0.1

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.
Files changed (104) hide show
  1. checksums.yaml +7 -0
  2. data/MIT-LICENSE +20 -0
  3. data/Rakefile +28 -0
  4. data/app/models/righter_right.rb +75 -0
  5. data/app/models/righter_rights_righter_role.rb +4 -0
  6. data/app/models/righter_role.rb +82 -0
  7. data/app/models/righter_role_grant.rb +7 -0
  8. data/app/models/righter_roles_user.rb +2 -0
  9. data/db/migrate/20150910000000_create_righter_rights.rb +21 -0
  10. data/db/migrate/20150910000001_create_righter_roles.rb +20 -0
  11. data/db/migrate/20150910000002_righter_roles_righter_access_rights.rb +14 -0
  12. data/db/migrate/20150910000003_create_righter_roles_users.rb +14 -0
  13. data/lib/init.rb +1 -0
  14. data/lib/injections/righter_for_application_controller.rb +31 -0
  15. data/lib/injections/righter_for_resource.rb +110 -0
  16. data/lib/injections/righter_for_user.rb +186 -0
  17. data/lib/righter.rb +9 -0
  18. data/lib/righter/version.rb +3 -0
  19. data/lib/righter_error.rb +8 -0
  20. data/lib/tasks/righter_tasks.rake +4 -0
  21. data/test/dummy/README.rdoc +28 -0
  22. data/test/dummy/Rakefile +11 -0
  23. data/test/dummy/app/assets/javascripts/application.js +13 -0
  24. data/test/dummy/app/assets/stylesheets/application.css +15 -0
  25. data/test/dummy/app/controllers/application_controller.rb +6 -0
  26. data/test/dummy/app/controllers/doors_controller.rb +23 -0
  27. data/test/dummy/app/helpers/application_helper.rb +2 -0
  28. data/test/dummy/app/models/door.rb +10 -0
  29. data/test/dummy/app/models/house.rb +7 -0
  30. data/test/dummy/app/models/player.rb +7 -0
  31. data/test/dummy/app/models/righter_roles_player.rb +2 -0
  32. data/test/dummy/app/models/user.rb +4 -0
  33. data/test/dummy/app/views/doors/show.html.erb +1 -0
  34. data/test/dummy/app/views/layouts/application.html.erb +14 -0
  35. data/test/dummy/bin/bundle +3 -0
  36. data/test/dummy/bin/rails +4 -0
  37. data/test/dummy/bin/rake +4 -0
  38. data/test/dummy/bin/setup +29 -0
  39. data/test/dummy/config.ru +4 -0
  40. data/test/dummy/config/application.rb +25 -0
  41. data/test/dummy/config/boot.rb +5 -0
  42. data/test/dummy/config/database.yml +25 -0
  43. data/test/dummy/config/environment.rb +5 -0
  44. data/test/dummy/config/environments/development.rb +41 -0
  45. data/test/dummy/config/environments/production.rb +79 -0
  46. data/test/dummy/config/environments/test.rb +42 -0
  47. data/test/dummy/config/initializers/assets.rb +11 -0
  48. data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
  49. data/test/dummy/config/initializers/cookies_serializer.rb +3 -0
  50. data/test/dummy/config/initializers/filter_parameter_logging.rb +4 -0
  51. data/test/dummy/config/initializers/inflections.rb +16 -0
  52. data/test/dummy/config/initializers/mime_types.rb +4 -0
  53. data/test/dummy/config/initializers/session_store.rb +3 -0
  54. data/test/dummy/config/initializers/wrap_parameters.rb +14 -0
  55. data/test/dummy/config/locales/en.yml +23 -0
  56. data/test/dummy/config/routes.rb +8 -0
  57. data/test/dummy/config/secrets.yml +22 -0
  58. data/test/dummy/db/migrate/20150911000000_create_players.rb +18 -0
  59. data/test/dummy/db/migrate/20150911000002_create_users_table.rb +15 -0
  60. data/test/dummy/db/migrate/20150911000003_create_doors.rb +14 -0
  61. data/test/dummy/db/migrate/20150911000004_create_houses.rb +13 -0
  62. data/test/dummy/db/migrate/20150911000005_add_house_reference_to_doors.rb +9 -0
  63. data/test/dummy/db/schema.rb +90 -0
  64. data/test/dummy/db/test.sqlite3 +0 -0
  65. data/test/dummy/log/development.log +35 -0
  66. data/test/dummy/log/test.log +117973 -0
  67. data/test/dummy/public/404.html +67 -0
  68. data/test/dummy/public/422.html +67 -0
  69. data/test/dummy/public/500.html +66 -0
  70. data/test/dummy/public/favicon.ico +0 -0
  71. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/0-mgT1BVDUIUlj7bJxvh7Ud3uSbC1DJf0Ok7Ehgieds.cache +1 -0
  72. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/5Lly_CA8DZvPhQV2jDQx-Y6P_y3Ygra9t5jfSlGhHDA.cache +2 -0
  73. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/9jPCqzZvmeFf31Rz8y3OEo8OQXEHVcwmLgkx0tXs-o8.cache +1 -0
  74. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/OI6uxGcnsKavdWTtwDAasU3wPx8QXhzBgV0X2n1KjMQ.cache +3 -0
  75. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/VTeG_7OBrkPzWFSh3MrTa0NSl2wOuJfTJ-XP7JqBG2w.cache +0 -0
  76. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/a2CYO1s9hME5T1pntwZMB7J6dYjS0zCmDxw_7zX1T14.cache +0 -0
  77. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/d71F8V8hdfF1jAttqkXKdizYR9PcM_zuKn_Lj_73gfE.cache +1 -0
  78. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/hCBjLjjeqhUCs4tdwCYlGcFA4xohMwurjmZx6OY1a7g.cache +0 -0
  79. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/hZi1k6tpxxCGYxRe7zY74ItcOI8gZrREOpGuA8JSpGg.cache +3 -0
  80. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/ifgPguUzTOUeqB0zW0GV8DL6HEvPpakIWAzNPVuCGW0.cache +1 -0
  81. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/j8yaH5wiyIN5a2xePYA_lQm39RgOQh27UiF5A7i6b28.cache +0 -0
  82. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/o2kqwqoUQ3gkgncZO1IWdVRzFD0wCSQ-HyL62cINFOU.cache +1 -0
  83. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/pEhaat2KBd5SrT7szC_8R1_6hK17FTpvoRFkmCRSD3M.cache +2 -0
  84. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/pIwp2wi1sfaJlhiwzzvyyV0hKOihhYkP6709hRtpHxg.cache +0 -0
  85. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/pQIgTfLmEPykNamzxdqBww21SMT7YlZlZGy6hgQ6eVE.cache +1 -0
  86. data/test/dummy/tmp/cache/assets/test/sprockets/v3.0/td9wUl9SLRnSSgE2ZK_VqCzLxTkFiCW50KkOhE916Wo.cache +1 -0
  87. data/test/factories/doors.rb +10 -0
  88. data/test/factories/houses.rb +7 -0
  89. data/test/factories/players.rb +6 -0
  90. data/test/factories/righter_rights.rb +11 -0
  91. data/test/factories/righter_roles.rb +9 -0
  92. data/test/factories/users.rb +9 -0
  93. data/test/fixtures/players.yml +6 -0
  94. data/test/fixtures/righter_rights.yml +21 -0
  95. data/test/fixtures/righter_roles.yml +29 -0
  96. data/test/fixtures/users.yml +27 -0
  97. data/test/functional/doors_controller_test.rb +71 -0
  98. data/test/righter_test.rb +9 -0
  99. data/test/test_helper.rb +54 -0
  100. data/test/unit/righter_for_resource_test.rb +137 -0
  101. data/test/unit/righter_right_test.rb +74 -0
  102. data/test/unit/righter_role_test.rb +197 -0
  103. data/test/unit/righter_user_test.rb +271 -0
  104. metadata +271 -0
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 3ac85163e735cd9d03caa544ba91b6d88539d9b6
4
+ data.tar.gz: 65bc2c981b1e7f5c149e03137b4aeb687259a929
5
+ SHA512:
6
+ metadata.gz: e3e2cb186084e75d40995114023d84f625b6fbada0fa8aed906c255cefe294ea6d1c1b7691749e169fa4e64e9b9930e9b7ec87073eaa5f930061b4f00ca40f97
7
+ data.tar.gz: 0fb265cd1658460b5c2ddeab122008892326130527bda696b21b73d9eccf0fbc299e17b8b7c6d4581a9b2c9ffe2cc33c543f48be287cd1af37f1c88ef79b0dc6
@@ -0,0 +1,20 @@
1
+ Copyright 2015 adamliesko
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.
@@ -0,0 +1,28 @@
1
+ begin
2
+ require 'bundler/setup'
3
+ rescue LoadError
4
+ puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
5
+ end
6
+
7
+ require 'rdoc/task'
8
+
9
+ RDoc::Task.new(:rdoc) do |rdoc|
10
+ rdoc.rdoc_dir = 'rdoc'
11
+ rdoc.title = 'Righter'
12
+ rdoc.options << '--line-numbers'
13
+ rdoc.rdoc_files.include('README.rdoc')
14
+ rdoc.rdoc_files.include('lib/**/*.rb')
15
+ end
16
+
17
+ Bundler::GemHelper.install_tasks
18
+
19
+ require 'rake/testtask'
20
+
21
+ Rake::TestTask.new(:test) do |t|
22
+ t.libs << 'lib'
23
+ t.libs << 'test'
24
+ t.pattern = 'test/**/*_test.rb'
25
+ t.verbose = false
26
+ end
27
+
28
+ task default: :test
@@ -0,0 +1,75 @@
1
+ class RighterRight < ActiveRecord::Base
2
+ has_many :righter_rights_righter_roles, dependent: :destroy
3
+ has_many :righter_roles, -> { uniq }, through: :righter_rights_righter_roles
4
+ belongs_to :parent, class_name: 'RighterRight', foreign_key: :parent_id
5
+
6
+ scope :top_level_rights, lambda {
7
+ where parent_id: nil
8
+ }
9
+
10
+ scope :visible, lambda {
11
+ where hidden: [false, nil]
12
+ }
13
+
14
+ serialize :actions, Array
15
+ validates :name, uniqueness: true
16
+
17
+ after_save do
18
+ RighterRight.clear_cache
19
+ end
20
+
21
+ after_create do
22
+ RighterRight.clear_cache
23
+ end
24
+
25
+ after_destroy do
26
+ RighterRight.clear_cache
27
+ end
28
+
29
+ @@cache = nil
30
+
31
+ def self.load_cache
32
+ unless @@cache
33
+ @@cache = {}
34
+ RighterRight.find_each do |right|
35
+ @@cache[right.name.to_sym] = right
36
+ end
37
+ end
38
+ end
39
+
40
+ def self.cached_find_by_name(name)
41
+ load_cache
42
+ @@cache[name.to_sym]
43
+ end
44
+
45
+ def self.clear_cache
46
+ @@cache = nil
47
+ end
48
+
49
+ validate :validate_cycles
50
+
51
+ def validate_cycles(receiver = nil)
52
+ return unless parent_id
53
+ if receiver
54
+ if parent == receiver
55
+ receiver.errors.add :righter_right, "disallowed to create loops, collision with RighterRight #{name}"
56
+ else
57
+ parent.validate_cycles receiver
58
+ end
59
+ else
60
+ parent.validate_cycles self
61
+ end
62
+ end
63
+
64
+ def add_access_to(opts = {})
65
+ fail RighterError.new('controller cannot be nil') unless opts[:controller]
66
+ fail RighterError.new('actions should be in form of an array') unless opts[:actions].class == Array
67
+ self.controller = opts[:controller]
68
+ self.actions = opts[:actions]
69
+ save!
70
+ end
71
+
72
+ def children
73
+ self.class.where parent_id: id
74
+ end
75
+ end
@@ -0,0 +1,4 @@
1
+ class RighterRightsRighterRole < ActiveRecord::Base
2
+ belongs_to :righter_right
3
+ belongs_to :righter_role
4
+ end
@@ -0,0 +1,82 @@
1
+ class RighterRole < ActiveRecord::Base
2
+ has_many :righter_rights_righter_roles, dependent: :destroy
3
+ has_many :righter_rights, through: :righter_rights_righter_roles
4
+ has_many :righter_role_grants, dependent: :destroy
5
+ has_many :grantable_righter_roles, -> { uniq }, through: :righter_role_grants
6
+
7
+ validates :name, :human_name, uniqueness: true, presence: true
8
+
9
+ scope :visible, lambda {
10
+ where hidden: [false, nil]
11
+ }
12
+
13
+ after_destroy do
14
+ RighterRoleGrant.where(righter_role_id: id).destroy_all
15
+ RighterRoleGrant.where(grantable_righter_role_id: id).destroy_all
16
+ end
17
+
18
+ def add_right(right)
19
+ unless right.is_a?(RighterRight)
20
+ fail RighterError.new("RighterRole.add_right accepts only RighterRight instance as input (provided :#{right.class.inspect})")
21
+ end
22
+ righter_rights << right unless righter_rights.include?(right)
23
+ save!
24
+
25
+ if right.parent
26
+ add_right right.parent unless righter_rights.include?(right.parent)
27
+ end
28
+ end
29
+
30
+ def add_self_and_child_rights(right)
31
+ add_right right
32
+ right.children.each { |r| add_self_and_child_rights r }
33
+ end
34
+
35
+ def remove_right(right)
36
+ unless right.is_a?(RighterRight)
37
+ fail RighterError.new("RighterRole.remove_right accepts only RighterRight instance as input (provided :#{right.class.inspect})")
38
+ end
39
+
40
+ righter_rights.delete right
41
+
42
+ right.children.each do |child_r|
43
+ remove_right child_r
44
+ end
45
+ end
46
+
47
+ def allow_to_grant_role(role)
48
+ grantable_righter_roles << role unless grantable_righter_roles.include?(role)
49
+ end
50
+
51
+ def disallow_to_grant_role(role)
52
+ grantable_righter_roles.destroy(role)
53
+ end
54
+
55
+ def disallow_all_granted_roles
56
+ grantable_righter_roles.destroy_all
57
+ end
58
+
59
+ alias_method :grantable_roles, :grantable_righter_roles
60
+
61
+ def create_or_update_with_grants(name, human_name, granted_role_names)
62
+ passed_validation = false
63
+
64
+ self.name = name
65
+ self.human_name = human_name
66
+ self.class.transaction do
67
+ if save
68
+ passed_validation = true
69
+
70
+ disallow_all_granted_roles
71
+ if granted_role_names
72
+ granted_role_names.each do |role_name|
73
+ role_to_grant = self.class.find_by_name role_name # this is badly inneficient
74
+ allow_to_grant_role role_to_grant if role_to_grant
75
+ end
76
+ end
77
+ end
78
+ end
79
+
80
+ passed_validation
81
+ end
82
+ end
@@ -0,0 +1,7 @@
1
+ class RighterRoleGrant < ActiveRecord::Base
2
+ belongs_to :righter_role
3
+ belongs_to :grantable_righter_role, class_name: 'RighterRole'
4
+
5
+ validates :righter_role_id, presence: true
6
+ validates :grantable_righter_role_id, presence: true
7
+ end
@@ -0,0 +1,2 @@
1
+ class RighterRolesUser < ActiveRecord::Base
2
+ end
@@ -0,0 +1,21 @@
1
+ class CreateRighterRights < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :righter_rights do |t|
4
+ t.string :name
5
+ t.string :human_name
6
+ t.string :controller
7
+ t.integer :resource_id
8
+ t.string :resource_class
9
+ t.text :actions
10
+ t.integer :parent_id
11
+ t.boolean :hidden, default: false
12
+ t.timestamps null: false
13
+ end
14
+
15
+ add_index :righter_rights, :parent_id, name: 'index_rr_on_pid'
16
+ end
17
+
18
+ def self.down
19
+ drop_table :righter_rights
20
+ end
21
+ end
@@ -0,0 +1,20 @@
1
+ class CreateRighterRoles < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :righter_roles do |t|
4
+ t.string :name
5
+ t.string :human_name
6
+ t.boolean :hidden, default: false
7
+ t.timestamps null: false
8
+ end
9
+
10
+ create_table :righter_role_grants do |t|
11
+ t.integer :righter_role_id
12
+ t.integer :grantable_righter_role_id
13
+ end
14
+ end
15
+
16
+ def self.down
17
+ drop_table :righter_roles
18
+ drop_table :righter_role_grants
19
+ end
20
+ end
@@ -0,0 +1,14 @@
1
+ class RighterRolesRighterAccessRights < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :righter_rights_righter_roles do |t|
4
+ t.integer :righter_role_id
5
+ t.integer :righter_right_id
6
+ end
7
+
8
+ add_index :righter_rights_righter_roles, [:righter_role_id, :righter_right_id], name: 'index_ir_on_iroi_irii'
9
+ end
10
+
11
+ def self.down
12
+ drop_table :righter_rights_righter_roles
13
+ end
14
+ end
@@ -0,0 +1,14 @@
1
+ class CreateRighterRolesUsers < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :righter_roles_users do |t|
4
+ t.integer :righter_role_id
5
+ t.integer :user_id
6
+ end
7
+
8
+ add_index :righter_roles_users, [:user_id, :righter_role_id], name: 'index_rr_on_ui_rroi'
9
+ end
10
+
11
+ def self.down
12
+ drop_table :righter_roles_users
13
+ end
14
+ end
@@ -0,0 +1 @@
1
+ require "#{File.dirname(__FILE__)}/righter.rb"
@@ -0,0 +1,31 @@
1
+ module RighterForApplicationController
2
+ def self.included(controller_klass)
3
+ controller_klass.before_filter :enforce_righter
4
+ end
5
+
6
+ def enforce_righter
7
+ u = righter_user
8
+ fail RighterNoUserError.new unless u
9
+ c = params[:controller].to_sym
10
+ a = params[:action].to_sym
11
+ unless u.righter_accessible?(controller: c, action: a)
12
+ fail RighterError.new("user #{u.login} is trying to reach prohibited content: #{c}/#{a}")
13
+ end
14
+ end
15
+
16
+ def enforce_resource_security(right_name, resource, options = {}) # currently need to call this manually as soon as the instance of the resource is retrieved in the controller action
17
+ u = righter_user
18
+ fail RighterNoUserError.new unless u
19
+
20
+ options.merge!(resource: resource, right: right_name)
21
+ unless u.righter_accessible?(options)
22
+ fail RighterError.new("user #{u.login} is not authorized to '#{right_name}' resource #{resource.inspect}")
23
+ end
24
+ end
25
+
26
+ # Override this method in your application
27
+ # @return [User]
28
+ def righter_user
29
+ User.current_user
30
+ end
31
+ end
@@ -0,0 +1,110 @@
1
+ module RighterForResource
2
+ extend ActiveSupport::Concern
3
+
4
+ included do
5
+ extend ClassMethodsForActiveRecord if ancestors.include?(ActiveRecord::Base)
6
+ end
7
+
8
+ module ClassMethods
9
+ def create_righter_right(right_name_prefix, options = {})
10
+ options[:resource] = self unless options[:resource].present?
11
+ resource = options[:resource]
12
+ if options[:parent_right]
13
+ if options[:parent_right].is_a? Proc
14
+ parent_right = options[:parent_right].call(resource)
15
+ else
16
+ parent_right = options[:parent_right]
17
+ end
18
+
19
+ parent = RighterRight.cached_find_by_name(parent_right) if parent_right
20
+ end
21
+
22
+ right = RighterRight.create(name: right_name(right_name_prefix, options),
23
+ resource_class: resource.righter_right_resource_class,
24
+ resource_id: resource.righter_right_resource_id,
25
+ hidden: false,
26
+ parent: parent,
27
+ human_name: resource.righter_right_human_name(right_name_prefix))
28
+
29
+ if options[:auto_associate_roles]
30
+ options[:auto_associate_roles].each do |role_name|
31
+ role = RighterRole.find_by_name(role_name)
32
+ role.add_right(right)
33
+ end
34
+ end
35
+ right
36
+ end
37
+
38
+ def destroy_righter_right(right_name_prefix, options = {})
39
+ righter_right(right_name_prefix, options).destroy
40
+ end
41
+
42
+ def righter_right(right_name_prefix, options = {})
43
+ RighterRight.cached_find_by_name(right_name(right_name_prefix, options))
44
+ end
45
+
46
+ def righter_right_resource_class
47
+ name # name of the class
48
+ end
49
+
50
+ def righter_right_resource_id
51
+ nil # class resources have no explicit ID
52
+ end
53
+
54
+ def righter_right_human_name(right_name_prefix)
55
+ "#{right_name_prefix} #{righter_right_resource_class} #{righter_right_resource_id}"
56
+ end
57
+
58
+ private
59
+
60
+ def right_name(right_name_prefix, options = {})
61
+ unless right_name_prefix.present?
62
+ fail RighterArgumentError.new('No prefix for righter_right name provided...')
63
+ end
64
+ resource = options[:resource]
65
+ resource ||= self
66
+ resource_class = resource.righter_right_resource_class
67
+ resource_id = resource.righter_right_resource_id
68
+ resource_id.present? ? "#{right_name_prefix}_#{resource_class}_#{resource_id}" : "#{right_name_prefix}_#{resource_class}"
69
+ end
70
+ end
71
+
72
+ def create_righter_right(right_name_prefix, options = {})
73
+ options = options.merge(resource: self)
74
+ self.class.create_righter_right(right_name_prefix, options)
75
+ end
76
+
77
+ def destroy_righter_right(right_name_prefix, options = {})
78
+ options = options.merge(resource: self)
79
+ self.class.destroy_righter_right(right_name_prefix, options)
80
+ end
81
+
82
+ def righter_right(right_name_prefix, options = {})
83
+ options = options.merge(resource: self)
84
+ self.class.righter_right(right_name_prefix, options)
85
+ end
86
+
87
+ def righter_right_resource_class
88
+ self.class.name
89
+ end
90
+
91
+ def righter_right_resource_id
92
+ return id if respond_to?(:id)
93
+ fail RighterError.new("Don't know how to compute instance_id for resource role. Please implement righter_right_resource_id method for this resource.")
94
+ end
95
+
96
+ def righter_right_human_name(right_name_prefix)
97
+ "#{right_name_prefix} #{righter_right_resource_class} #{righter_right_resource_id}"
98
+ end
99
+
100
+ module ClassMethodsForActiveRecord
101
+ def auto_manage_righter_right(right_name_prefix, options = {})
102
+ unless right_name_prefix.present?
103
+ fail RighterArgumentError.new('No prefix for autocreated right name provided...')
104
+ end
105
+
106
+ after_create { create_righter_right(right_name_prefix, options) } # called on instance level
107
+ before_destroy { destroy_righter_right(right_name_prefix, options) } # called on instance level
108
+ end
109
+ end
110
+ end