mongoid_ability 0.1.9 → 0.1.10
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.
- checksums.yaml +4 -4
- data/lib/mongoid_ability/lock.rb +1 -1
- data/lib/mongoid_ability/owner.rb +6 -0
- data/lib/mongoid_ability/subject.rb +31 -3
- data/lib/mongoid_ability/version.rb +1 -1
- data/test/mongoid_ability/lock_test.rb +13 -7
- data/test/mongoid_ability/owner_test.rb +20 -0
- data/test/mongoid_ability/subject_test.rb +42 -17
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5b22befcca304fbace4cd22f72704b7d5a109a0b
|
4
|
+
data.tar.gz: 56a19a326bdb60d7d462558c51cd0d7196146d8b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 740466111f499e95e981197abc5567740c7ecb829126a863bf6720cddadb5f4b9a75ad9fc851f93bfecb8e90e55ce73a40b20ee8d7741b893412270a7ac71c3b
|
7
|
+
data.tar.gz: 83f00db0cdb31b4f1ebd024c40f5b1390059a0b686119bcf7e27d97a081f4e5d7208286920cf929b55253e73450182201133c63c1dcf882bc10b4ca24e2ab35b
|
data/lib/mongoid_ability/lock.rb
CHANGED
@@ -45,7 +45,7 @@ module MongoidAbility
|
|
45
45
|
return calculated_outcome unless owner.present?
|
46
46
|
cloned_owner = owner.clone
|
47
47
|
cloned_owner.locks_relation = cloned_owner.locks_relation - [self]
|
48
|
-
MongoidAbility::Ability.new(cloned_owner).can? action, (
|
48
|
+
MongoidAbility::Ability.new(cloned_owner).can? action, (subject.present? ? subject : subject_class)
|
49
49
|
end
|
50
50
|
|
51
51
|
# ---------------------------------------------------------------------
|
@@ -38,6 +38,12 @@ module MongoidAbility
|
|
38
38
|
@ability ||= MongoidAbility::Ability.new(self)
|
39
39
|
end
|
40
40
|
|
41
|
+
# ---------------------------------------------------------------------
|
42
|
+
|
43
|
+
def has_lock? lock
|
44
|
+
locks_relation.where(action: lock.action, subject_type: lock.subject_type, subject_id: lock.subject_id.presence).exists?
|
45
|
+
end
|
46
|
+
|
41
47
|
private # =============================================================
|
42
48
|
|
43
49
|
def cleanup_locks
|
@@ -7,8 +7,6 @@ module MongoidAbility
|
|
7
7
|
end
|
8
8
|
end
|
9
9
|
|
10
|
-
# ---------------------------------------------------------------------
|
11
|
-
|
12
10
|
module ClassMethods
|
13
11
|
def default_locks
|
14
12
|
@default_locks ||= []
|
@@ -19,15 +17,25 @@ module MongoidAbility
|
|
19
17
|
end
|
20
18
|
|
21
19
|
def default_lock lock_cls, action, outcome, attrs={}
|
20
|
+
unless is_root_class?
|
21
|
+
unless root_class.has_default_lock_for_action?(action)
|
22
|
+
raise StandardError, "action is not defined on root class (#{root_class})"
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
22
26
|
lock = lock_cls.new( { subject_type: self.to_s, action: action, outcome: outcome }.merge(attrs))
|
23
27
|
|
24
|
-
|
28
|
+
# remove any existing locks
|
29
|
+
if existing_lock = default_locks.detect{ |l| l.action == lock.action }
|
25
30
|
default_locks.delete(existing_lock)
|
26
31
|
end
|
27
32
|
|
33
|
+
# add new lock
|
28
34
|
default_locks.push lock
|
29
35
|
end
|
30
36
|
|
37
|
+
# ---------------------------------------------------------------------
|
38
|
+
|
31
39
|
def self_and_ancestors_with_default_locks
|
32
40
|
ancestors.select { |a| a.is_a?(Class) && a.respond_to?(:default_locks) }
|
33
41
|
end
|
@@ -36,6 +44,26 @@ module MongoidAbility
|
|
36
44
|
self_and_ancestors_with_default_locks - [self]
|
37
45
|
end
|
38
46
|
|
47
|
+
def is_root_class?
|
48
|
+
root_class == self
|
49
|
+
end
|
50
|
+
|
51
|
+
def root_class
|
52
|
+
self_and_ancestors_with_default_locks.last
|
53
|
+
end
|
54
|
+
|
55
|
+
# ---------------------------------------------------------------------
|
56
|
+
|
57
|
+
def default_lock_for_action action
|
58
|
+
default_locks.detect{ |lock| lock.action == action.to_sym }
|
59
|
+
end
|
60
|
+
|
61
|
+
def has_default_lock_for_action? action
|
62
|
+
default_lock_for_action(action).present?
|
63
|
+
end
|
64
|
+
|
65
|
+
# ---------------------------------------------------------------------
|
66
|
+
|
39
67
|
def accessible_by ability, action=:read, options={}
|
40
68
|
AccessibleQueryBuilder.call(self, ability, action, options)
|
41
69
|
end
|
@@ -6,6 +6,11 @@ module MongoidAbility
|
|
6
6
|
subject { MyLock.new }
|
7
7
|
let(:my_subject) { MySubject.new }
|
8
8
|
let(:inherited_lock) { MyLock1.new }
|
9
|
+
# ---------------------------------------------------------------------
|
10
|
+
|
11
|
+
before do
|
12
|
+
MySubject.default_locks = [ MyLock.new(action: :read, outcome: true), MyLock.new(action: :update, outcome: false) ]
|
13
|
+
end
|
9
14
|
|
10
15
|
# ---------------------------------------------------------------------
|
11
16
|
|
@@ -54,12 +59,13 @@ module MongoidAbility
|
|
54
59
|
let(:subject_type_lock) { MyLock.new(subject_type: MySubject, action: :read, outcome: false) }
|
55
60
|
let(:subject_lock) { MyLock.new(subject: my_subject, action: :read, outcome: true) }
|
56
61
|
let(:owner) { MyOwner.new(my_locks: [subject_type_lock, subject_lock]) }
|
57
|
-
let(:ability) { Ability.new(owner) }
|
58
62
|
|
59
|
-
before
|
63
|
+
before do
|
64
|
+
@ability = Ability.new(owner) # initialize owner
|
65
|
+
end
|
60
66
|
|
61
67
|
it 'does not affect calculated_outcome' do
|
62
|
-
ability.can?(:read, my_subject).must_equal true
|
68
|
+
@ability.can?(:read, my_subject).must_equal true
|
63
69
|
end
|
64
70
|
|
65
71
|
it 'returns calculated_outcome without this lock' do
|
@@ -76,11 +82,11 @@ module MongoidAbility
|
|
76
82
|
# ---------------------------------------------------------------------
|
77
83
|
|
78
84
|
describe '#criteria' do
|
79
|
-
let(:open_subject_type_lock) {
|
80
|
-
let(:closed_subject_type_lock) {
|
85
|
+
let(:open_subject_type_lock) { MyLock.new(subject_type: MySubject, action: :read, outcome: true) }
|
86
|
+
let(:closed_subject_type_lock) { MyLock.new(subject_type: MySubject, action: :read, outcome: false) }
|
81
87
|
|
82
|
-
let(:open_subject_lock) {
|
83
|
-
let(:closed_subject_lock) {
|
88
|
+
let(:open_subject_lock) { MyLock.new(subject: my_subject, action: :read, outcome: true) }
|
89
|
+
let(:closed_subject_lock) { MyLock.new(subject: my_subject, action: :read, outcome: false) }
|
84
90
|
|
85
91
|
it 'returns conditions Hash' do
|
86
92
|
open_subject_type_lock.conditions.must_be_kind_of Hash
|
@@ -22,5 +22,25 @@ module MongoidAbility
|
|
22
22
|
it { subject.locks_relation.metadata[:name].must_equal :my_locks }
|
23
23
|
end
|
24
24
|
end
|
25
|
+
|
26
|
+
describe '#has_lock?' do
|
27
|
+
let(:subject_type_lock) { MyLock.new(action: :read, subject_type: MySubject) }
|
28
|
+
let(:subject_lock) { MyLock.new(action: :read, subject: MySubject.new) }
|
29
|
+
let(:other_lock) { MyLock.new(action: :update, subject: MySubject.new) }
|
30
|
+
let(:owner) { MyOwner.new(my_locks: [subject_type_lock, subject_lock]) }
|
31
|
+
|
32
|
+
it 'returns true when lock for same action & subject_type' do
|
33
|
+
owner.has_lock?(subject_type_lock).must_equal true
|
34
|
+
end
|
35
|
+
|
36
|
+
it 'returns true when lock for same action & subject' do
|
37
|
+
owner.has_lock?(subject_lock).must_equal true
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'returns false for non existing lock' do
|
41
|
+
owner.has_lock?(other_lock).must_equal false
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
25
45
|
end
|
26
46
|
end
|
@@ -2,41 +2,66 @@ require 'test_helper'
|
|
2
2
|
|
3
3
|
module MongoidAbility
|
4
4
|
describe Subject do
|
5
|
-
describe '.default_locks' do
|
6
5
|
|
6
|
+
describe '.default_lock' do
|
7
7
|
before do
|
8
8
|
MySubject.default_locks = []
|
9
9
|
MySubject1.default_locks = []
|
10
|
+
MySubject2.default_locks = []
|
10
11
|
|
11
12
|
MySubject.default_lock MyLock, :read, true
|
13
|
+
MySubject.default_lock MyLock, :update, true
|
12
14
|
MySubject1.default_lock MyLock1, :update, false
|
13
15
|
end
|
14
16
|
|
15
17
|
it 'stores them' do
|
16
|
-
MySubject.default_locks.map(&:action).map(&:to_s).sort.must_equal %w(read)
|
18
|
+
MySubject.default_locks.map(&:action).map(&:to_s).sort.must_equal %w(read update)
|
17
19
|
MySubject1.default_locks.map(&:action).map(&:to_s).sort.must_equal %w(update)
|
18
20
|
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe 'when lock not defined on superclass' do
|
24
|
+
before do
|
25
|
+
MySubject.default_locks = []
|
26
|
+
MySubject1.default_locks = []
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'must raise error' do
|
30
|
+
-> { MySubject1.default_lock MyLock, :test, true }.must_raise StandardError
|
31
|
+
end
|
32
|
+
end
|
19
33
|
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
34
|
+
describe 'prevents conflicts' do
|
35
|
+
before do
|
36
|
+
MySubject.default_locks = []
|
37
|
+
MySubject.default_lock MyLock, :read, false
|
38
|
+
MySubject.default_lock MyLock1, :read, false
|
39
|
+
end
|
26
40
|
|
27
|
-
|
28
|
-
|
29
|
-
|
41
|
+
it 'does not allow multiple locks for same action' do
|
42
|
+
MySubject.default_locks.select{ |l| l.action == :read }.count.must_equal 1
|
43
|
+
end
|
30
44
|
|
31
|
-
|
32
|
-
|
33
|
-
|
45
|
+
it 'replace existing locks with new attributes' do
|
46
|
+
MySubject.default_locks.detect{ |l| l.action == :read }.outcome.must_equal false
|
47
|
+
end
|
34
48
|
|
35
|
-
|
36
|
-
|
37
|
-
end
|
49
|
+
it 'replaces existing locks with new one' do
|
50
|
+
MySubject.default_locks.detect{ |l| l.action == :read }.class.must_equal MyLock1
|
38
51
|
end
|
52
|
+
end
|
53
|
+
|
54
|
+
describe '.is_root_class?' do
|
55
|
+
it { MySubject.is_root_class?.must_equal true }
|
56
|
+
it { MySubject1.is_root_class?.must_equal false }
|
57
|
+
it { MySubject2.is_root_class?.must_equal false }
|
58
|
+
end
|
39
59
|
|
60
|
+
describe ".root_class" do
|
61
|
+
it { MySubject.root_class.must_equal MySubject }
|
62
|
+
it { MySubject1.root_class.must_equal MySubject }
|
63
|
+
it { MySubject2.root_class.must_equal MySubject }
|
40
64
|
end
|
65
|
+
|
41
66
|
end
|
42
67
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mongoid_ability
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.10
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Tomas Celizna
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-09-
|
11
|
+
date: 2015-09-07 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: cancancan
|