declarative_policy 1.0.0 → 2.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +20 -0
- data/CONTRIBUTING.md +41 -0
- data/LICENSE.txt +4 -1
- data/README.md +81 -12
- data/{declarative_policy.gemspec → declarative-policy.gemspec} +23 -8
- data/doc/caching.md +299 -1
- data/doc/defining-policies.md +76 -12
- data/doc/optimization.md +277 -0
- data/lib/declarative_policy/base.rb +61 -29
- data/lib/declarative_policy/cache.rb +1 -1
- data/lib/declarative_policy/condition.rb +26 -7
- data/lib/declarative_policy/configuration.rb +7 -1
- data/lib/declarative_policy/delegate_dsl.rb +1 -1
- data/lib/declarative_policy/policy_dsl.rb +2 -2
- data/lib/declarative_policy/preferred_scope.rb +1 -1
- data/lib/declarative_policy/rule.rb +5 -5
- data/lib/declarative_policy/rule_dsl.rb +1 -1
- data/lib/declarative_policy/runner.rb +58 -26
- data/lib/declarative_policy/version.rb +1 -1
- data/lib/declarative_policy.rb +30 -40
- metadata +117 -26
- data/.gitignore +0 -10
- data/.gitlab-ci.yml +0 -48
- data/.rspec +0 -4
- data/.rubocop.yml +0 -10
- data/Dangerfile +0 -16
- data/Gemfile +0 -24
- data/Gemfile.lock +0 -197
- data/Rakefile +0 -8
- data/danger/plugins/project_helper.rb +0 -58
- data/danger/roulette/Dangerfile +0 -97
@@ -7,6 +7,7 @@ module DeclarativePolicy
|
|
7
7
|
def initialize
|
8
8
|
@named_policies = {}
|
9
9
|
@name_transformation = ->(name) { "#{name}Policy" }
|
10
|
+
@class_for = ->(name) { Object.const_get(name) }
|
10
11
|
end
|
11
12
|
|
12
13
|
def named_policy(name, policy = nil)
|
@@ -26,10 +27,15 @@ module DeclarativePolicy
|
|
26
27
|
nil
|
27
28
|
end
|
28
29
|
|
30
|
+
def class_for(&block)
|
31
|
+
@class_for = block
|
32
|
+
nil
|
33
|
+
end
|
34
|
+
|
29
35
|
def policy_class(domain_class_name)
|
30
36
|
return unless domain_class_name
|
31
37
|
|
32
|
-
@name_transformation.call(domain_class_name)
|
38
|
+
@class_for.call(@name_transformation.call(domain_class_name))
|
33
39
|
rescue NameError
|
34
40
|
nil
|
35
41
|
end
|
@@ -33,10 +33,10 @@ module DeclarativePolicy
|
|
33
33
|
@context_class.prevent_all_when(@rule)
|
34
34
|
end
|
35
35
|
|
36
|
-
def method_missing(msg,
|
36
|
+
def method_missing(msg, ...)
|
37
37
|
return super unless @context_class.respond_to?(msg)
|
38
38
|
|
39
|
-
@context_class.__send__(msg,
|
39
|
+
@context_class.__send__(msg, ...) # rubocop: disable GitlabSecurity/PublicSend
|
40
40
|
end
|
41
41
|
|
42
42
|
def respond_to_missing?(msg)
|
@@ -210,7 +210,7 @@ module DeclarativePolicy
|
|
210
210
|
cached = cached_pass?(context)
|
211
211
|
return cached unless cached.nil?
|
212
212
|
|
213
|
-
@rules.all? { |r| r.pass?(context) }
|
213
|
+
@rules.sort_by { |r| r.score(context) }.all? { |r| r.pass?(context) }
|
214
214
|
end
|
215
215
|
|
216
216
|
def cached_pass?(context)
|
@@ -240,7 +240,7 @@ module DeclarativePolicy
|
|
240
240
|
cached = cached_pass?(context)
|
241
241
|
return cached unless cached.nil?
|
242
242
|
|
243
|
-
@rules.any? { |r| r.pass?(context) }
|
243
|
+
@rules.sort_by { |r| r.score(context) }.any? { |r| r.pass?(context) }
|
244
244
|
end
|
245
245
|
|
246
246
|
def simplify
|
@@ -285,9 +285,9 @@ module DeclarativePolicy
|
|
285
285
|
|
286
286
|
def simplify
|
287
287
|
case @rule
|
288
|
-
when And then Or.new(@rule.rules.map(&:negate)).simplify
|
289
|
-
when Or then And.new(@rule.rules.map(&:negate)).simplify
|
290
|
-
when Not then @rule.rule.simplify
|
288
|
+
when And then Or.new(@rule.rules.map(&:negate)).simplify # DeMorgan's laws
|
289
|
+
when Or then And.new(@rule.rules.map(&:negate)).simplify # DeMorgan's laws
|
290
|
+
when Not then @rule.rule.simplify # double negation
|
291
291
|
else Not.new(@rule.simplify)
|
292
292
|
end
|
293
293
|
end
|
@@ -1,11 +1,16 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
+
require 'set'
|
4
|
+
|
3
5
|
module DeclarativePolicy
|
4
6
|
class Runner
|
5
7
|
class State
|
8
|
+
attr_reader :called_conditions
|
9
|
+
|
6
10
|
def initialize
|
7
11
|
@enabled = false
|
8
12
|
@prevented = false
|
13
|
+
@called_conditions = Set.new
|
9
14
|
end
|
10
15
|
|
11
16
|
def enable!
|
@@ -27,6 +32,10 @@ module DeclarativePolicy
|
|
27
32
|
def pass?
|
28
33
|
!prevented? && enabled?
|
29
34
|
end
|
35
|
+
|
36
|
+
def register(manifest_condition)
|
37
|
+
@called_conditions << manifest_condition.cache_key
|
38
|
+
end
|
30
39
|
end
|
31
40
|
|
32
41
|
# a Runner contains a list of Steps to be run.
|
@@ -44,6 +53,11 @@ module DeclarativePolicy
|
|
44
53
|
!!@state
|
45
54
|
end
|
46
55
|
|
56
|
+
# Delete the cached state - allowing this runner to be re-used if the facts have changed.
|
57
|
+
def uncache!
|
58
|
+
@state = nil
|
59
|
+
end
|
60
|
+
|
47
61
|
# used by Rule::Ability. See #steps_by_score
|
48
62
|
def score
|
49
63
|
return 0 if cached?
|
@@ -55,11 +69,20 @@ module DeclarativePolicy
|
|
55
69
|
Runner.new(@steps + other.steps)
|
56
70
|
end
|
57
71
|
|
72
|
+
def dependencies
|
73
|
+
return Set.new unless @state
|
74
|
+
|
75
|
+
@state.called_conditions
|
76
|
+
end
|
77
|
+
|
58
78
|
# The main entry point, called for making an ability decision.
|
59
79
|
# See #run and DeclarativePolicy::Base#can?
|
60
80
|
def pass?
|
61
81
|
run unless cached?
|
62
82
|
|
83
|
+
parent_state = Thread.current[:declarative_policy_current_runner_state]
|
84
|
+
parent_state&.called_conditions&.merge(@state.called_conditions)
|
85
|
+
|
63
86
|
@state.pass?
|
64
87
|
end
|
65
88
|
|
@@ -70,6 +93,16 @@ module DeclarativePolicy
|
|
70
93
|
|
71
94
|
private
|
72
95
|
|
96
|
+
def with_state
|
97
|
+
@state = State.new
|
98
|
+
old_runner_state = Thread.current[:declarative_policy_current_runner_state]
|
99
|
+
Thread.current[:declarative_policy_current_runner_state] = @state
|
100
|
+
|
101
|
+
yield
|
102
|
+
ensure
|
103
|
+
Thread.current[:declarative_policy_current_runner_state] = old_runner_state
|
104
|
+
end
|
105
|
+
|
73
106
|
def flatten_steps!
|
74
107
|
@steps = @steps.flat_map { |s| s.flattened(@steps) }
|
75
108
|
end
|
@@ -78,33 +111,31 @@ module DeclarativePolicy
|
|
78
111
|
# It relies on #steps_by_score for the main loop, and updates @state
|
79
112
|
# with the result of the step.
|
80
113
|
def run(debug = nil)
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
@state.prevent! if passed
|
114
|
+
with_state do
|
115
|
+
steps_by_score(!!debug) do |step, score|
|
116
|
+
break if !debug && @state.prevented?
|
117
|
+
|
118
|
+
passed = nil
|
119
|
+
case step.action
|
120
|
+
when :enable
|
121
|
+
# we only check :enable actions if they have a chance of
|
122
|
+
# changing the outcome - if no other rule has enabled or
|
123
|
+
# prevented.
|
124
|
+
unless @state.enabled? || @state.prevented?
|
125
|
+
passed = step.pass?
|
126
|
+
@state.enable! if passed
|
127
|
+
end
|
128
|
+
when :prevent
|
129
|
+
# we only check :prevent actions if the state hasn't already
|
130
|
+
# been prevented.
|
131
|
+
unless @state.prevented?
|
132
|
+
passed = step.pass?
|
133
|
+
@state.prevent! if passed
|
134
|
+
end
|
135
|
+
else raise "invalid action #{step.action.inspect}"
|
104
136
|
end
|
105
137
|
|
106
138
|
debug << inspect_step(step, score, passed) if debug
|
107
|
-
else raise "invalid action #{step.action.inspect}"
|
108
139
|
end
|
109
140
|
end
|
110
141
|
|
@@ -131,7 +162,7 @@ module DeclarativePolicy
|
|
131
162
|
#
|
132
163
|
# For each step, we yield the step object along with the computed score
|
133
164
|
# for debugging purposes.
|
134
|
-
def steps_by_score
|
165
|
+
def steps_by_score(debugging)
|
135
166
|
flatten_steps!
|
136
167
|
|
137
168
|
if @steps.size > 50
|
@@ -156,6 +187,7 @@ module DeclarativePolicy
|
|
156
187
|
# if the permission hasn't yet been enabled and we only have
|
157
188
|
# prevent steps left, we short-circuit the state here
|
158
189
|
@state.prevent!
|
190
|
+
return unless debugging
|
159
191
|
end
|
160
192
|
|
161
193
|
return if remaining_steps.empty?
|
@@ -185,7 +217,7 @@ module DeclarativePolicy
|
|
185
217
|
break if lowest_score.zero?
|
186
218
|
end
|
187
219
|
|
188
|
-
[next_step,
|
220
|
+
[next_step, lowest_score]
|
189
221
|
end
|
190
222
|
|
191
223
|
# Formatter for debugging output.
|
data/lib/declarative_policy.rb
CHANGED
@@ -1,8 +1,6 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require '
|
4
|
-
require 'active_support/core_ext'
|
5
|
-
|
3
|
+
require 'set'
|
6
4
|
require_relative 'declarative_policy/cache'
|
7
5
|
require_relative 'declarative_policy/condition'
|
8
6
|
require_relative 'declarative_policy/delegate_dsl'
|
@@ -20,21 +18,32 @@ require_relative 'declarative_policy/configuration'
|
|
20
18
|
module DeclarativePolicy
|
21
19
|
extend PreferredScope
|
22
20
|
|
23
|
-
CLASS_CACHE_MUTEX = Mutex.new
|
24
|
-
CLASS_CACHE_IVAR = :@__DeclarativePolicy_CLASS_CACHE
|
25
|
-
|
26
21
|
class << self
|
27
22
|
def policy_for(user, subject, opts = {})
|
28
23
|
cache = opts[:cache] || {}
|
29
24
|
key = Cache.policy_key(user, subject)
|
30
25
|
|
31
|
-
cache[key] ||=
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
26
|
+
cache[key] ||= class_for(subject).new(user, subject, opts)
|
27
|
+
end
|
28
|
+
|
29
|
+
# Find the list of runners with now invalidated keys, and invalidate the runners
|
30
|
+
def invalidate(cache, invalidated_keys)
|
31
|
+
return unless cache&.any?
|
32
|
+
return unless invalidated_keys&.any?
|
33
|
+
|
34
|
+
keys = invalidated_keys.to_set
|
35
|
+
|
36
|
+
policies = cache.select { |k, _| k.is_a?(String) && k.start_with?('/dp/policy/') }
|
37
|
+
|
38
|
+
policies.each_value do |policy|
|
39
|
+
policy.runners.each do |runner|
|
40
|
+
runner.uncache! if keys.intersect?(runner.dependencies)
|
37
41
|
end
|
42
|
+
end
|
43
|
+
|
44
|
+
invalidated_keys.each { |k| cache.delete(k) }
|
45
|
+
|
46
|
+
nil
|
38
47
|
end
|
39
48
|
|
40
49
|
def class_for(subject)
|
@@ -72,38 +81,19 @@ module DeclarativePolicy
|
|
72
81
|
@configuration ||= DeclarativePolicy::Configuration.new
|
73
82
|
end
|
74
83
|
|
75
|
-
# This method is heavily cached because there are a lot of anonymous
|
76
|
-
# modules in play in a typical rails app, and #name performs quite
|
77
|
-
# slowly for anonymous classes and modules.
|
78
|
-
#
|
79
|
-
# See https://bugs.ruby-lang.org/issues/11119
|
80
|
-
#
|
81
|
-
# if the above bug is resolved, this caching could likely be removed.
|
82
84
|
def class_for_class(subject_class)
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
85
|
+
if subject_class.respond_to?(:declarative_policy_class)
|
86
|
+
Object.const_get(subject_class.declarative_policy_class)
|
87
|
+
else
|
88
|
+
subject_class.ancestors.each do |klass|
|
89
|
+
name = klass.name
|
90
|
+
klass = policy_class(name)
|
91
|
+
|
92
|
+
return klass if klass
|
90
93
|
end
|
91
|
-
end
|
92
|
-
|
93
|
-
subject_class.instance_variable_get(CLASS_CACHE_IVAR)
|
94
|
-
end
|
95
94
|
|
96
|
-
|
97
|
-
return subject_class.declarative_policy_class.constantize if subject_class.respond_to?(:declarative_policy_class)
|
98
|
-
|
99
|
-
subject_class.ancestors.each do |klass|
|
100
|
-
name = klass.name
|
101
|
-
klass = policy_class(name)
|
102
|
-
|
103
|
-
return klass if klass
|
95
|
+
nil
|
104
96
|
end
|
105
|
-
|
106
|
-
nil
|
107
97
|
end
|
108
98
|
|
109
99
|
def policy_class(name)
|
metadata
CHANGED
@@ -1,16 +1,113 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: declarative_policy
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 2.0.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
|
-
-
|
8
|
-
|
9
|
-
autorequire:
|
7
|
+
- group::authorization
|
8
|
+
autorequire:
|
10
9
|
bindir: exe
|
11
10
|
cert_chain: []
|
12
|
-
date:
|
13
|
-
dependencies:
|
11
|
+
date: 2025-08-23 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: benchmark-ips
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '2.12'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '2.12'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: gitlab-dangerfiles
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '3.8'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '3.8'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: gitlab-styles
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '12.0'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '12.0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: pry-byebug
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - ">="
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - ">="
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: rake
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - "~>"
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '12.0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - "~>"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '12.0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: rspec
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - "~>"
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '3.10'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - "~>"
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '3.10'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: rspec-parameterized
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - "~>"
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '1.0'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - "~>"
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '1.0'
|
14
111
|
description: |
|
15
112
|
This library provides an authorization framework with a declarative DSL
|
16
113
|
|
@@ -19,28 +116,21 @@ description: |
|
|
19
116
|
|
20
117
|
This library is in production use at GitLab.com
|
21
118
|
email:
|
22
|
-
-
|
119
|
+
- engineering@gitlab.com
|
23
120
|
executables: []
|
24
121
|
extensions: []
|
25
122
|
extra_rdoc_files: []
|
26
123
|
files:
|
27
|
-
-
|
28
|
-
- ".gitlab-ci.yml"
|
29
|
-
- ".rspec"
|
30
|
-
- ".rubocop.yml"
|
124
|
+
- CHANGELOG.md
|
31
125
|
- CODE_OF_CONDUCT.md
|
32
|
-
-
|
33
|
-
- Gemfile
|
34
|
-
- Gemfile.lock
|
126
|
+
- CONTRIBUTING.md
|
35
127
|
- LICENSE.txt
|
36
128
|
- README.md
|
37
|
-
-
|
38
|
-
- danger/plugins/project_helper.rb
|
39
|
-
- danger/roulette/Dangerfile
|
40
|
-
- declarative_policy.gemspec
|
129
|
+
- declarative-policy.gemspec
|
41
130
|
- doc/caching.md
|
42
131
|
- doc/configuration.md
|
43
132
|
- doc/defining-policies.md
|
133
|
+
- doc/optimization.md
|
44
134
|
- lib/declarative_policy.rb
|
45
135
|
- lib/declarative_policy/base.rb
|
46
136
|
- lib/declarative_policy/cache.rb
|
@@ -55,14 +145,15 @@ files:
|
|
55
145
|
- lib/declarative_policy/runner.rb
|
56
146
|
- lib/declarative_policy/step.rb
|
57
147
|
- lib/declarative_policy/version.rb
|
58
|
-
homepage: https://gitlab.com/gitlab-org/declarative-policy
|
148
|
+
homepage: https://gitlab.com/gitlab-org/ruby/gems/declarative-policy
|
59
149
|
licenses:
|
60
150
|
- MIT
|
61
151
|
metadata:
|
62
|
-
homepage_uri: https://gitlab.com/gitlab-org/declarative-policy
|
63
|
-
source_code_uri: https://gitlab.com/gitlab-org/declarative-policy
|
64
|
-
changelog_uri: https://gitlab.com/gitlab-org/declarative-policy/-/
|
65
|
-
|
152
|
+
homepage_uri: https://gitlab.com/gitlab-org/ruby/gems/declarative-policy
|
153
|
+
source_code_uri: https://gitlab.com/gitlab-org/ruby/gems/declarative-policy
|
154
|
+
changelog_uri: https://gitlab.com/gitlab-org/ruby/gems/declarative-policy/-/blob/main/CHANGELOG.md
|
155
|
+
rubygems_mfa_required: 'false'
|
156
|
+
post_install_message:
|
66
157
|
rdoc_options: []
|
67
158
|
require_paths:
|
68
159
|
- lib
|
@@ -70,15 +161,15 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
70
161
|
requirements:
|
71
162
|
- - ">="
|
72
163
|
- !ruby/object:Gem::Version
|
73
|
-
version:
|
164
|
+
version: 3.0.0
|
74
165
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
75
166
|
requirements:
|
76
167
|
- - ">="
|
77
168
|
- !ruby/object:Gem::Version
|
78
169
|
version: '0'
|
79
170
|
requirements: []
|
80
|
-
rubygems_version: 3.
|
81
|
-
signing_key:
|
171
|
+
rubygems_version: 3.5.22
|
172
|
+
signing_key:
|
82
173
|
specification_version: 4
|
83
174
|
summary: An authorization library with a focus on declarative policy definitions.
|
84
175
|
test_files: []
|
data/.gitignore
DELETED
data/.gitlab-ci.yml
DELETED
@@ -1,48 +0,0 @@
|
|
1
|
-
image: "ruby:2.7"
|
2
|
-
|
3
|
-
.tests:
|
4
|
-
stage: test
|
5
|
-
only:
|
6
|
-
refs:
|
7
|
-
- master
|
8
|
-
- tags
|
9
|
-
- merge_requests
|
10
|
-
|
11
|
-
# Cache gems in between builds
|
12
|
-
cache:
|
13
|
-
paths:
|
14
|
-
- vendor/ruby
|
15
|
-
|
16
|
-
before_script:
|
17
|
-
- ruby -v # Print out ruby version for debugging
|
18
|
-
- bundle install -j $(nproc) --path vendor # Install dependencies into ./vendor/ruby
|
19
|
-
|
20
|
-
rubocop:
|
21
|
-
extends: .tests
|
22
|
-
script:
|
23
|
-
- bundle exec rubocop
|
24
|
-
|
25
|
-
rspec:
|
26
|
-
extends: .tests
|
27
|
-
image: "ruby:$RUBY_VERSION"
|
28
|
-
script:
|
29
|
-
- bundle exec rspec
|
30
|
-
parallel:
|
31
|
-
matrix:
|
32
|
-
- RUBY_VERSION:
|
33
|
-
- "2.7"
|
34
|
-
- "3.0"
|
35
|
-
|
36
|
-
danger-review:
|
37
|
-
extends: .tests
|
38
|
-
needs: []
|
39
|
-
script:
|
40
|
-
- >
|
41
|
-
if [ -z "$DANGER_GITLAB_API_TOKEN" ]; then
|
42
|
-
# Force danger to skip CI source GitLab and fallback to "local only git repo".
|
43
|
-
unset GITLAB_CI
|
44
|
-
# We need to base SHA to help danger determine the base commit for this shallow clone.
|
45
|
-
bundle exec danger dry_run --fail-on-errors=true --verbose --base="$CI_MERGE_REQUEST_DIFF_BASE_SHA"
|
46
|
-
else
|
47
|
-
bundle exec danger --fail-on-errors=true --verbose
|
48
|
-
fi
|
data/.rspec
DELETED
data/.rubocop.yml
DELETED
data/Dangerfile
DELETED
@@ -1,16 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
require 'gitlab-dangerfiles'
|
4
|
-
|
5
|
-
Gitlab::Dangerfiles.import_plugins(danger)
|
6
|
-
danger.import_plugin('danger/plugins/*.rb')
|
7
|
-
|
8
|
-
return if helper.release_automation?
|
9
|
-
|
10
|
-
danger.import_dangerfile(path: File.join('danger', 'roulette'))
|
11
|
-
|
12
|
-
anything_to_post = status_report.values.any?(&:any?)
|
13
|
-
|
14
|
-
if helper.ci? && anything_to_post
|
15
|
-
markdown("**If needed, you can retry the [`danger-review` job](#{ENV['CI_JOB_URL']}) that generated this comment.**")
|
16
|
-
end
|
data/Gemfile
DELETED
@@ -1,24 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
source 'https://rubygems.org'
|
4
|
-
|
5
|
-
# Specify your gem's dependencies in declarative-policy.gemspec
|
6
|
-
gemspec
|
7
|
-
|
8
|
-
gem 'activesupport', '>= 6.0'
|
9
|
-
gem 'rake', '~> 12.0'
|
10
|
-
gem 'rubocop', require: false
|
11
|
-
|
12
|
-
group :test do
|
13
|
-
gem 'rspec', '~> 3.0'
|
14
|
-
gem 'rspec-parameterized', require: false
|
15
|
-
gem 'pry-byebug'
|
16
|
-
end
|
17
|
-
|
18
|
-
group :development, :test do
|
19
|
-
gem 'gitlab-styles', '~> 6.1.0', require: false
|
20
|
-
end
|
21
|
-
|
22
|
-
group :development, :test, :danger do
|
23
|
-
gem 'gitlab-dangerfiles', '~> 1.1.0', require: false
|
24
|
-
end
|