simple_authorize 1.1.0 → 1.1.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +8 -0
- data/CLAUDE.md +1 -0
- data/lib/simple_authorize/policy_modules/approvable.rb +117 -0
- data/lib/simple_authorize/policy_modules/ownable.rb +65 -0
- data/lib/simple_authorize/policy_modules/publishable.rb +81 -0
- data/lib/simple_authorize/policy_modules/soft_deletable.rb +88 -0
- data/lib/simple_authorize/policy_modules/timestamped.rb +104 -0
- data/lib/simple_authorize/policy_modules.rb +27 -0
- data/lib/simple_authorize/version.rb +1 -1
- data/spec/examples.txt +24 -24
- metadata +8 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: b16462d63472a968792e6272f876b82beba2fadb48a675a5cb2d8d03dedec42f
|
|
4
|
+
data.tar.gz: 42553420c691366876062a93597613386542b26f997b42424d4fb8233aa09802
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 4013198e95c910dd1377835fab2701494666217ee87081621e6121e3a9750cf41cbad210583c6ff52ef95d5d7be7c9350e5966ccb350cc877da64b1f482ac2f8
|
|
7
|
+
data.tar.gz: 5fdc05879861c05aa16763b5fa7d3331e7fed2cf6d4e8443f7109fac0570f979dd584073774a557333157544f8ec223386fe6705ea64abc80f5283abb586cbd4
|
data/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,14 @@ All notable changes to this project will be documented in this file.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [1.1.1] - 2025-11-05
|
|
9
|
+
|
|
10
|
+
### Fixed
|
|
11
|
+
- RuboCop compliance for all new policy modules
|
|
12
|
+
- Method naming convention (`standard_permissions` instead of `standard_permissions?`)
|
|
13
|
+
- Simplified conditional logic in Approvable module
|
|
14
|
+
- Code style improvements across test files
|
|
15
|
+
|
|
8
16
|
## [1.1.0] - 2025-11-05
|
|
9
17
|
|
|
10
18
|
### Added
|
data/CLAUDE.md
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
- do not automatically commit or push to the repo, please
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module SimpleAuthorize
|
|
4
|
+
module PolicyModules
|
|
5
|
+
# Provides approval workflow authorization methods
|
|
6
|
+
#
|
|
7
|
+
# Include this module for content that requires approval:
|
|
8
|
+
#
|
|
9
|
+
# class DocumentPolicy < SimpleAuthorize::Policy
|
|
10
|
+
# include SimpleAuthorize::PolicyModules::Approvable
|
|
11
|
+
#
|
|
12
|
+
# def update?
|
|
13
|
+
# not_approved? && (owner? || admin?)
|
|
14
|
+
# end
|
|
15
|
+
# end
|
|
16
|
+
#
|
|
17
|
+
# Assumes records have approval-related fields like approved, approved_at,
|
|
18
|
+
# approval_status, pending_approval, etc.
|
|
19
|
+
module Approvable
|
|
20
|
+
protected
|
|
21
|
+
|
|
22
|
+
# Check if the record is approved
|
|
23
|
+
def approved?
|
|
24
|
+
return false unless record
|
|
25
|
+
|
|
26
|
+
if record.respond_to?(:approved?)
|
|
27
|
+
record.approved?
|
|
28
|
+
elsif record.respond_to?(:approved)
|
|
29
|
+
record.approved == true
|
|
30
|
+
elsif record.respond_to?(:approval_status)
|
|
31
|
+
record.approval_status == "approved"
|
|
32
|
+
elsif record.respond_to?(:approved_at)
|
|
33
|
+
record.approved_at.present?
|
|
34
|
+
else
|
|
35
|
+
false
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Check if the record is pending approval
|
|
40
|
+
def pending_approval?
|
|
41
|
+
return false unless record
|
|
42
|
+
|
|
43
|
+
if record.respond_to?(:pending_approval?)
|
|
44
|
+
record.pending_approval?
|
|
45
|
+
elsif record.respond_to?(:pending_approval)
|
|
46
|
+
record.pending_approval == true
|
|
47
|
+
elsif record.respond_to?(:approval_status)
|
|
48
|
+
record.approval_status == "pending"
|
|
49
|
+
elsif record.respond_to?(:submitted_for_approval_at)
|
|
50
|
+
record.submitted_for_approval_at.present? && !approved? && !rejected?
|
|
51
|
+
else
|
|
52
|
+
false
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
# Check if the record is rejected
|
|
57
|
+
def rejected?
|
|
58
|
+
return false unless record
|
|
59
|
+
|
|
60
|
+
if record.respond_to?(:rejected?)
|
|
61
|
+
record.rejected?
|
|
62
|
+
elsif record.respond_to?(:rejected)
|
|
63
|
+
record.rejected == true
|
|
64
|
+
elsif record.respond_to?(:approval_status)
|
|
65
|
+
record.approval_status == "rejected"
|
|
66
|
+
elsif record.respond_to?(:rejected_at)
|
|
67
|
+
record.rejected_at.present?
|
|
68
|
+
else
|
|
69
|
+
false
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
# Check if the record is not approved
|
|
74
|
+
def not_approved?
|
|
75
|
+
!approved?
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
# Check if user can approve (cannot approve own content)
|
|
79
|
+
def can_approve?
|
|
80
|
+
return false unless logged_in?
|
|
81
|
+
|
|
82
|
+
if admin?
|
|
83
|
+
true
|
|
84
|
+
elsif contributor?
|
|
85
|
+
# Contributors can approve others' content but not their own
|
|
86
|
+
!owner?
|
|
87
|
+
else
|
|
88
|
+
false
|
|
89
|
+
end
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
# Check if user can reject
|
|
93
|
+
def can_reject?
|
|
94
|
+
can_approve?
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
# Check if user can submit for approval
|
|
98
|
+
def can_submit_for_approval?
|
|
99
|
+
owner? && not_approved? && !pending_approval?
|
|
100
|
+
end
|
|
101
|
+
|
|
102
|
+
# Check if user can withdraw from approval
|
|
103
|
+
def can_withdraw_approval?
|
|
104
|
+
owner? && pending_approval?
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
# Check if content can be edited (typically not after approval)
|
|
108
|
+
def can_edit_with_approval?
|
|
109
|
+
if approved?
|
|
110
|
+
admin? # Only admins can edit approved content
|
|
111
|
+
else
|
|
112
|
+
owner? || admin? # Owner can edit rejected or unapproved content
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
end
|
|
116
|
+
end
|
|
117
|
+
end
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module SimpleAuthorize
|
|
4
|
+
module PolicyModules
|
|
5
|
+
# Provides ownership-based authorization methods
|
|
6
|
+
#
|
|
7
|
+
# Include this module in your policy to add owner-based permissions:
|
|
8
|
+
#
|
|
9
|
+
# class PostPolicy < SimpleAuthorize::Policy
|
|
10
|
+
# include SimpleAuthorize::PolicyModules::Ownable
|
|
11
|
+
#
|
|
12
|
+
# def show?
|
|
13
|
+
# published? || owner_or_admin?
|
|
14
|
+
# end
|
|
15
|
+
# end
|
|
16
|
+
#
|
|
17
|
+
# This module assumes your record has a `user_id` field that matches
|
|
18
|
+
# the user's ID. Override the `owner?` method if you need different logic.
|
|
19
|
+
module Ownable
|
|
20
|
+
protected
|
|
21
|
+
|
|
22
|
+
# Check if the current user owns the record
|
|
23
|
+
def owner?
|
|
24
|
+
return false unless user && record
|
|
25
|
+
|
|
26
|
+
if record.respond_to?(:user_id)
|
|
27
|
+
record.user_id == user.id
|
|
28
|
+
elsif record.respond_to?(:user)
|
|
29
|
+
record.user == user
|
|
30
|
+
elsif record.respond_to?(:owner_id)
|
|
31
|
+
record.owner_id == user.id
|
|
32
|
+
elsif record.respond_to?(:owner)
|
|
33
|
+
record.owner == user
|
|
34
|
+
else
|
|
35
|
+
false
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Check if the user is the owner or an admin
|
|
40
|
+
def owner_or_admin?
|
|
41
|
+
owner? || admin?
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Check if the user is the owner or a contributor
|
|
45
|
+
def owner_or_contributor?
|
|
46
|
+
owner? || contributor?
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
# Common pattern: owners and admins can modify
|
|
50
|
+
def can_modify?
|
|
51
|
+
owner_or_admin?
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Common pattern: anyone can view, but only owners/admins can modify
|
|
55
|
+
def standard_permissions
|
|
56
|
+
{
|
|
57
|
+
show: true,
|
|
58
|
+
create: logged_in?,
|
|
59
|
+
update: owner_or_admin?,
|
|
60
|
+
destroy: owner_or_admin?
|
|
61
|
+
}
|
|
62
|
+
end
|
|
63
|
+
end
|
|
64
|
+
end
|
|
65
|
+
end
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module SimpleAuthorize
|
|
4
|
+
module PolicyModules
|
|
5
|
+
# Provides publishing workflow authorization methods
|
|
6
|
+
#
|
|
7
|
+
# Include this module for content that has draft/published states:
|
|
8
|
+
#
|
|
9
|
+
# class ArticlePolicy < SimpleAuthorize::Policy
|
|
10
|
+
# include SimpleAuthorize::PolicyModules::Publishable
|
|
11
|
+
#
|
|
12
|
+
# def show?
|
|
13
|
+
# published? || can_preview?
|
|
14
|
+
# end
|
|
15
|
+
# end
|
|
16
|
+
#
|
|
17
|
+
# This module assumes your record responds to `published?` or has a
|
|
18
|
+
# `published` boolean field, and optionally `published_at` timestamp.
|
|
19
|
+
module Publishable
|
|
20
|
+
protected
|
|
21
|
+
|
|
22
|
+
# Check if the record is published
|
|
23
|
+
def published?
|
|
24
|
+
return false unless record
|
|
25
|
+
|
|
26
|
+
if record.respond_to?(:published?)
|
|
27
|
+
record.published?
|
|
28
|
+
elsif record.respond_to?(:published)
|
|
29
|
+
record.published == true
|
|
30
|
+
elsif record.respond_to?(:status)
|
|
31
|
+
record.status == "published"
|
|
32
|
+
elsif record.respond_to?(:published_at)
|
|
33
|
+
record.published_at && record.published_at <= Time.current
|
|
34
|
+
else
|
|
35
|
+
false
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Check if the record is a draft
|
|
40
|
+
def draft?
|
|
41
|
+
!published?
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Check if user can publish content
|
|
45
|
+
def can_publish?
|
|
46
|
+
admin? || (contributor? && owner?)
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
# Check if user can unpublish content
|
|
50
|
+
def can_unpublish?
|
|
51
|
+
admin? || (owner? && contributor?)
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Check if user can preview unpublished content
|
|
55
|
+
def can_preview?
|
|
56
|
+
owner? || admin? || contributor?
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
# Check if user can schedule publication
|
|
60
|
+
def can_schedule?
|
|
61
|
+
return false unless record.respond_to?(:scheduled_at) || record.respond_to?(:publish_at)
|
|
62
|
+
|
|
63
|
+
can_publish?
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
# Filter attributes based on published state
|
|
67
|
+
def publishable_visible_attributes(base_attributes = [])
|
|
68
|
+
if published? || can_preview?
|
|
69
|
+
base_attributes
|
|
70
|
+
else
|
|
71
|
+
base_attributes - sensitive_draft_attributes
|
|
72
|
+
end
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# Attributes that should be hidden in draft state
|
|
76
|
+
def sensitive_draft_attributes
|
|
77
|
+
%i[internal_notes draft_notes review_comments]
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module SimpleAuthorize
|
|
4
|
+
module PolicyModules
|
|
5
|
+
# Provides soft deletion authorization methods
|
|
6
|
+
#
|
|
7
|
+
# Include this module for records that support soft deletion:
|
|
8
|
+
#
|
|
9
|
+
# class CommentPolicy < SimpleAuthorize::Policy
|
|
10
|
+
# include SimpleAuthorize::PolicyModules::SoftDeletable
|
|
11
|
+
#
|
|
12
|
+
# def destroy?
|
|
13
|
+
# soft_deletable? && (owner? || admin?)
|
|
14
|
+
# end
|
|
15
|
+
# end
|
|
16
|
+
#
|
|
17
|
+
# Assumes records have a deleted_at timestamp or similar field.
|
|
18
|
+
module SoftDeletable
|
|
19
|
+
protected
|
|
20
|
+
|
|
21
|
+
# Check if the record is soft deleted
|
|
22
|
+
def soft_deleted?
|
|
23
|
+
return false unless record
|
|
24
|
+
|
|
25
|
+
if record.respond_to?(:deleted?)
|
|
26
|
+
record.deleted?
|
|
27
|
+
elsif record.respond_to?(:deleted_at)
|
|
28
|
+
record.deleted_at.present?
|
|
29
|
+
elsif record.respond_to?(:trashed?)
|
|
30
|
+
record.trashed?
|
|
31
|
+
elsif record.respond_to?(:archived?)
|
|
32
|
+
record.archived?
|
|
33
|
+
else
|
|
34
|
+
false
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
# Check if the record is not soft deleted
|
|
39
|
+
def not_deleted?
|
|
40
|
+
!soft_deleted?
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
# Check if the record supports soft deletion
|
|
44
|
+
def soft_deletable?
|
|
45
|
+
record && (
|
|
46
|
+
record.respond_to?(:deleted_at) ||
|
|
47
|
+
record.respond_to?(:deleted?) ||
|
|
48
|
+
record.respond_to?(:trash!) ||
|
|
49
|
+
record.respond_to?(:archive!)
|
|
50
|
+
)
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
# Check if user can restore soft deleted records
|
|
54
|
+
def can_restore?
|
|
55
|
+
soft_deleted? && (admin? || (owner? && within_restore_window?))
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
# Check if user can permanently delete
|
|
59
|
+
def can_permanently_destroy?
|
|
60
|
+
admin?
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
# Check if we're within the restore window (default 30 days)
|
|
64
|
+
def within_restore_window?(days = 30)
|
|
65
|
+
return true unless soft_deleted?
|
|
66
|
+
return true unless record.respond_to?(:deleted_at)
|
|
67
|
+
|
|
68
|
+
record.deleted_at > days.days.ago
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# Check if user can view soft deleted records
|
|
72
|
+
def can_view_deleted?
|
|
73
|
+
admin? || (owner? && within_restore_window?)
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
# Standard destroy that respects soft delete
|
|
77
|
+
def safe_destroy?
|
|
78
|
+
if soft_deletable?
|
|
79
|
+
# Soft delete if supported
|
|
80
|
+
owner_or_admin?
|
|
81
|
+
else
|
|
82
|
+
# Hard delete requires admin
|
|
83
|
+
admin?
|
|
84
|
+
end
|
|
85
|
+
end
|
|
86
|
+
end
|
|
87
|
+
end
|
|
88
|
+
end
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module SimpleAuthorize
|
|
4
|
+
module PolicyModules
|
|
5
|
+
# Provides time-based authorization methods
|
|
6
|
+
#
|
|
7
|
+
# Include this module for time-sensitive permissions:
|
|
8
|
+
#
|
|
9
|
+
# class EventPolicy < SimpleAuthorize::Policy
|
|
10
|
+
# include SimpleAuthorize::PolicyModules::Timestamped
|
|
11
|
+
#
|
|
12
|
+
# def update?
|
|
13
|
+
# not_expired? && (owner? || admin?)
|
|
14
|
+
# end
|
|
15
|
+
# end
|
|
16
|
+
#
|
|
17
|
+
# Works with records that have timestamp fields like expired_at,
|
|
18
|
+
# starts_at, ends_at, valid_until, etc.
|
|
19
|
+
module Timestamped
|
|
20
|
+
protected
|
|
21
|
+
|
|
22
|
+
# Check if the record has expired
|
|
23
|
+
def expired?
|
|
24
|
+
return false unless record
|
|
25
|
+
|
|
26
|
+
if record.respond_to?(:expired_at)
|
|
27
|
+
record.expired_at && record.expired_at < Time.current
|
|
28
|
+
elsif record.respond_to?(:expires_at)
|
|
29
|
+
record.expires_at && record.expires_at < Time.current
|
|
30
|
+
elsif record.respond_to?(:valid_until)
|
|
31
|
+
record.valid_until && record.valid_until < Time.current
|
|
32
|
+
elsif record.respond_to?(:ends_at)
|
|
33
|
+
record.ends_at && record.ends_at < Time.current
|
|
34
|
+
else
|
|
35
|
+
false
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Check if the record is not expired
|
|
40
|
+
def not_expired?
|
|
41
|
+
!expired?
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Check if the record is active (started but not ended)
|
|
45
|
+
def active?
|
|
46
|
+
started? && !ended?
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
# Check if the record has started
|
|
50
|
+
def started?
|
|
51
|
+
return true unless record
|
|
52
|
+
|
|
53
|
+
if record.respond_to?(:starts_at)
|
|
54
|
+
record.starts_at.nil? || record.starts_at <= Time.current
|
|
55
|
+
elsif record.respond_to?(:available_from)
|
|
56
|
+
record.available_from.nil? || record.available_from <= Time.current
|
|
57
|
+
elsif record.respond_to?(:valid_from)
|
|
58
|
+
record.valid_from.nil? || record.valid_from <= Time.current
|
|
59
|
+
else
|
|
60
|
+
true
|
|
61
|
+
end
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
# Check if the record has ended
|
|
65
|
+
def ended?
|
|
66
|
+
expired?
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# Check if record is within a time window
|
|
70
|
+
def within_time_window?
|
|
71
|
+
started? && not_expired?
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
# Check if the record is locked (cannot be modified)
|
|
75
|
+
def locked?
|
|
76
|
+
return false unless record
|
|
77
|
+
|
|
78
|
+
if record.respond_to?(:locked_at)
|
|
79
|
+
record.locked_at && record.locked_at < Time.current
|
|
80
|
+
elsif record.respond_to?(:locked?)
|
|
81
|
+
record.locked?
|
|
82
|
+
elsif record.respond_to?(:frozen_at)
|
|
83
|
+
record.frozen_at && record.frozen_at < Time.current
|
|
84
|
+
else
|
|
85
|
+
false
|
|
86
|
+
end
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# Check if record can be modified (not locked or expired)
|
|
90
|
+
def can_modify_time_based?
|
|
91
|
+
!locked? && not_expired?
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
# Business hours check (useful with context)
|
|
95
|
+
def within_business_hours?(time = Time.current)
|
|
96
|
+
hour = time.hour
|
|
97
|
+
weekday = time.wday
|
|
98
|
+
|
|
99
|
+
# Monday-Friday, 9 AM - 5 PM
|
|
100
|
+
weekday.between?(1, 5) && hour >= 9 && hour < 17
|
|
101
|
+
end
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
end
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
# Require all policy modules
|
|
4
|
+
require_relative "policy_modules/ownable"
|
|
5
|
+
require_relative "policy_modules/publishable"
|
|
6
|
+
require_relative "policy_modules/timestamped"
|
|
7
|
+
require_relative "policy_modules/approvable"
|
|
8
|
+
require_relative "policy_modules/soft_deletable"
|
|
9
|
+
|
|
10
|
+
module SimpleAuthorize
|
|
11
|
+
# Collection of reusable policy modules for common authorization patterns
|
|
12
|
+
#
|
|
13
|
+
# These modules can be mixed into your policy classes to add common
|
|
14
|
+
# authorization functionality without duplicating code.
|
|
15
|
+
#
|
|
16
|
+
# Example:
|
|
17
|
+
# class ArticlePolicy < SimpleAuthorize::Policy
|
|
18
|
+
# include SimpleAuthorize::PolicyModules::Ownable
|
|
19
|
+
# include SimpleAuthorize::PolicyModules::Publishable
|
|
20
|
+
#
|
|
21
|
+
# def show?
|
|
22
|
+
# published? || owner_or_admin?
|
|
23
|
+
# end
|
|
24
|
+
# end
|
|
25
|
+
module PolicyModules
|
|
26
|
+
end
|
|
27
|
+
end
|
data/spec/examples.txt
CHANGED
|
@@ -3,49 +3,49 @@ example_id | status | run_time |
|
|
|
3
3
|
./spec/rspec_matchers_spec.rb[1:1:1:1] | passed | 0.00003 seconds |
|
|
4
4
|
./spec/rspec_matchers_spec.rb[1:1:1:2] | passed | 0.00003 seconds |
|
|
5
5
|
./spec/rspec_matchers_spec.rb[1:1:1:3] | passed | 0.00004 seconds |
|
|
6
|
-
./spec/rspec_matchers_spec.rb[1:1:2:1] | passed | 0.
|
|
6
|
+
./spec/rspec_matchers_spec.rb[1:1:2:1] | passed | 0.00003 seconds |
|
|
7
7
|
./spec/rspec_matchers_spec.rb[1:1:2:2] | passed | 0.00004 seconds |
|
|
8
8
|
./spec/rspec_matchers_spec.rb[1:1:3:1] | passed | 0.00004 seconds |
|
|
9
9
|
./spec/rspec_matchers_spec.rb[1:1:3:2] | passed | 0.00004 seconds |
|
|
10
10
|
./spec/rspec_matchers_spec.rb[1:1:4:1] | passed | 0.00003 seconds |
|
|
11
|
-
./spec/rspec_matchers_spec.rb[1:1:4:2] | passed | 0.
|
|
12
|
-
./spec/rspec_matchers_spec.rb[1:2:1:1] | passed | 0.
|
|
11
|
+
./spec/rspec_matchers_spec.rb[1:1:4:2] | passed | 0.00004 seconds |
|
|
12
|
+
./spec/rspec_matchers_spec.rb[1:2:1:1] | passed | 0.00004 seconds |
|
|
13
13
|
./spec/rspec_matchers_spec.rb[1:2:1:2] | passed | 0.00004 seconds |
|
|
14
|
-
./spec/rspec_matchers_spec.rb[1:2:2:1] | passed | 0.
|
|
15
|
-
./spec/rspec_matchers_spec.rb[1:2:2:2] | passed | 0.
|
|
14
|
+
./spec/rspec_matchers_spec.rb[1:2:2:1] | passed | 0.00005 seconds |
|
|
15
|
+
./spec/rspec_matchers_spec.rb[1:2:2:2] | passed | 0.00014 seconds |
|
|
16
16
|
./spec/rspec_matchers_spec.rb[1:2:3:1] | passed | 0.00004 seconds |
|
|
17
|
-
./spec/rspec_matchers_spec.rb[1:2:3:2] | passed | 0.
|
|
18
|
-
./spec/rspec_matchers_spec.rb[1:2:4:1] | passed | 0.
|
|
19
|
-
./spec/rspec_matchers_spec.rb[1:2:4:2] | passed | 0.
|
|
20
|
-
./spec/rspec_matchers_spec.rb[1:3:1:1] | passed | 0.
|
|
21
|
-
./spec/rspec_matchers_spec.rb[1:3:1:2] | passed | 0.
|
|
17
|
+
./spec/rspec_matchers_spec.rb[1:2:3:2] | passed | 0.00006 seconds |
|
|
18
|
+
./spec/rspec_matchers_spec.rb[1:2:4:1] | passed | 0.00004 seconds |
|
|
19
|
+
./spec/rspec_matchers_spec.rb[1:2:4:2] | passed | 0.00004 seconds |
|
|
20
|
+
./spec/rspec_matchers_spec.rb[1:3:1:1] | passed | 0.00028 seconds |
|
|
21
|
+
./spec/rspec_matchers_spec.rb[1:3:1:2] | passed | 0.00028 seconds |
|
|
22
22
|
./spec/rspec_matchers_spec.rb[1:3:1:3] | passed | 0.00005 seconds |
|
|
23
|
-
./spec/rspec_matchers_spec.rb[1:3:2:1] | passed | 0.
|
|
23
|
+
./spec/rspec_matchers_spec.rb[1:3:2:1] | passed | 0.00034 seconds |
|
|
24
24
|
./spec/rspec_matchers_spec.rb[1:3:3:1] | passed | 0.00004 seconds |
|
|
25
|
-
./spec/rspec_matchers_spec.rb[1:3:3:2] | passed | 0.
|
|
26
|
-
./spec/rspec_matchers_spec.rb[1:3:4:1] | passed | 0.
|
|
25
|
+
./spec/rspec_matchers_spec.rb[1:3:3:2] | passed | 0.00027 seconds |
|
|
26
|
+
./spec/rspec_matchers_spec.rb[1:3:4:1] | passed | 0.0004 seconds |
|
|
27
27
|
./spec/rspec_matchers_spec.rb[1:3:4:2] | passed | 0.00003 seconds |
|
|
28
|
-
./spec/rspec_matchers_spec.rb[1:4:1:1] | passed | 0.
|
|
28
|
+
./spec/rspec_matchers_spec.rb[1:4:1:1] | passed | 0.00004 seconds |
|
|
29
29
|
./spec/rspec_matchers_spec.rb[1:4:2:1] | passed | 0.00003 seconds |
|
|
30
30
|
./spec/rspec_matchers_spec.rb[1:4:2:2] | passed | 0.00004 seconds |
|
|
31
31
|
./spec/rspec_matchers_spec.rb[1:4:3:1] | passed | 0.00004 seconds |
|
|
32
32
|
./spec/rspec_matchers_spec.rb[1:4:4:1] | passed | 0.00003 seconds |
|
|
33
33
|
./spec/rspec_matchers_spec.rb[1:4:4:2] | passed | 0.00003 seconds |
|
|
34
|
-
./spec/rspec_matchers_spec.rb[1:5:1:1] | passed | 0.
|
|
34
|
+
./spec/rspec_matchers_spec.rb[1:5:1:1] | passed | 0.00004 seconds |
|
|
35
35
|
./spec/rspec_matchers_spec.rb[1:5:1:2] | passed | 0.00003 seconds |
|
|
36
36
|
./spec/rspec_matchers_spec.rb[1:5:2:1] | passed | 0.00004 seconds |
|
|
37
|
-
./spec/rspec_matchers_spec.rb[1:5:3:1] | passed | 0.
|
|
38
|
-
./spec/rspec_matchers_spec.rb[1:5:3:2] | passed | 0.
|
|
37
|
+
./spec/rspec_matchers_spec.rb[1:5:3:1] | passed | 0.00006 seconds |
|
|
38
|
+
./spec/rspec_matchers_spec.rb[1:5:3:2] | passed | 0.00004 seconds |
|
|
39
39
|
./spec/rspec_matchers_spec.rb[1:5:4:1] | passed | 0.00003 seconds |
|
|
40
|
-
./spec/rspec_matchers_spec.rb[1:5:4:2] | passed | 0.
|
|
41
|
-
./spec/rspec_matchers_spec.rb[1:6:1:1] | passed | 0.
|
|
42
|
-
./spec/rspec_matchers_spec.rb[1:6:2:1] | passed | 0.
|
|
40
|
+
./spec/rspec_matchers_spec.rb[1:5:4:2] | passed | 0.00004 seconds |
|
|
41
|
+
./spec/rspec_matchers_spec.rb[1:6:1:1] | passed | 0.0004 seconds |
|
|
42
|
+
./spec/rspec_matchers_spec.rb[1:6:2:1] | passed | 0.00037 seconds |
|
|
43
43
|
./spec/rspec_matchers_spec.rb[1:6:2:2] | passed | 0.00004 seconds |
|
|
44
44
|
./spec/rspec_matchers_spec.rb[1:6:3:1] | passed | 0.00004 seconds |
|
|
45
45
|
./spec/rspec_matchers_spec.rb[1:6:3:2] | passed | 0.00004 seconds |
|
|
46
46
|
./spec/rspec_matchers_spec.rb[1:6:4:1] | passed | 0.00003 seconds |
|
|
47
|
-
./spec/rspec_matchers_spec.rb[1:6:4:2] | passed | 0.
|
|
47
|
+
./spec/rspec_matchers_spec.rb[1:6:4:2] | passed | 0.00035 seconds |
|
|
48
48
|
./spec/rspec_matchers_spec.rb[1:7:1:1] | passed | 0.00004 seconds |
|
|
49
|
-
./spec/rspec_matchers_spec.rb[1:7:1:2] | passed | 0.
|
|
50
|
-
./spec/rspec_matchers_spec.rb[1:7:1:3] | passed | 0.
|
|
51
|
-
./spec/rspec_matchers_spec.rb[1:7:2:1] | passed | 0.
|
|
49
|
+
./spec/rspec_matchers_spec.rb[1:7:1:2] | passed | 0.00003 seconds |
|
|
50
|
+
./spec/rspec_matchers_spec.rb[1:7:1:3] | passed | 0.00035 seconds |
|
|
51
|
+
./spec/rspec_matchers_spec.rb[1:7:2:1] | passed | 0.00128 seconds |
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: simple_authorize
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.1.
|
|
4
|
+
version: 1.1.1
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Scott
|
|
@@ -92,6 +92,7 @@ files:
|
|
|
92
92
|
- ".overcommit.yml"
|
|
93
93
|
- ".simplecov"
|
|
94
94
|
- CHANGELOG.md
|
|
95
|
+
- CLAUDE.md
|
|
95
96
|
- CODE_OF_CONDUCT.md
|
|
96
97
|
- CONTRIBUTING.md
|
|
97
98
|
- LICENSE.txt
|
|
@@ -110,6 +111,12 @@ files:
|
|
|
110
111
|
- lib/simple_authorize/configuration.rb
|
|
111
112
|
- lib/simple_authorize/controller.rb
|
|
112
113
|
- lib/simple_authorize/policy.rb
|
|
114
|
+
- lib/simple_authorize/policy_modules.rb
|
|
115
|
+
- lib/simple_authorize/policy_modules/approvable.rb
|
|
116
|
+
- lib/simple_authorize/policy_modules/ownable.rb
|
|
117
|
+
- lib/simple_authorize/policy_modules/publishable.rb
|
|
118
|
+
- lib/simple_authorize/policy_modules/soft_deletable.rb
|
|
119
|
+
- lib/simple_authorize/policy_modules/timestamped.rb
|
|
113
120
|
- lib/simple_authorize/railtie.rb
|
|
114
121
|
- lib/simple_authorize/rspec.rb
|
|
115
122
|
- lib/simple_authorize/test_helpers.rb
|