gitlab-dangerfiles 0.8.0 → 1.1.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/gitlab-dangerfiles.gemspec +1 -1
- data/lib/danger/{helper.rb → plugins/helper.rb} +88 -21
- data/lib/danger/{roulette.rb → plugins/roulette.rb} +10 -22
- data/lib/gitlab/dangerfiles.rb +1 -1
- data/lib/gitlab/dangerfiles/base_linter.rb +2 -1
- data/lib/gitlab/dangerfiles/spec_helper.rb +51 -5
- data/lib/gitlab/dangerfiles/teammate.rb +7 -0
- data/lib/gitlab/dangerfiles/version.rb +1 -1
- metadata +5 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f5e1069be5416d6980879af3330451834b57881c46101119bfc5917e2057edd7
|
4
|
+
data.tar.gz: e911c514f8d32d65e4aecef6ad111c80c808dd273b12775d57438532ba8a05b3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b3814724620240a6485ffce4191fb8a2461c267dda5dad2466b6dc5173fbe848b66cae92aaea69ef82a49dd4726db3a7e77c106fdbd73ea58738eaf4613c4cba
|
7
|
+
data.tar.gz: 0fcabbe03f856d29951ae2f35e9f6f9784fa22af8d8d6bfa13a41452b4a1c35a454135751443882e6a2762325ef05dd6b8bd1b3dde58c5c7661db65ffef4c5d7
|
data/gitlab-dangerfiles.gemspec
CHANGED
@@ -27,7 +27,7 @@ Gem::Specification.new do |spec|
|
|
27
27
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
28
28
|
spec.require_paths = ["lib"]
|
29
29
|
|
30
|
-
spec.add_dependency "danger"
|
30
|
+
spec.add_dependency "danger-gitlab"
|
31
31
|
|
32
32
|
spec.add_development_dependency "rspec", "~> 3.0"
|
33
33
|
spec.add_development_dependency "rspec-parameterized"
|
@@ -2,10 +2,10 @@
|
|
2
2
|
|
3
3
|
require "net/http"
|
4
4
|
require "json"
|
5
|
-
|
6
|
-
require_relative "
|
7
|
-
require_relative "
|
8
|
-
require_relative "
|
5
|
+
|
6
|
+
require_relative "../../gitlab/dangerfiles/changes"
|
7
|
+
require_relative "../../gitlab/dangerfiles/teammate"
|
8
|
+
require_relative "../../gitlab/dangerfiles/title_linting"
|
9
9
|
|
10
10
|
module Danger
|
11
11
|
# Common helper functions for our danger scripts.
|
@@ -19,6 +19,7 @@ module Danger
|
|
19
19
|
test: "~test ~Quality for `spec/features/*`",
|
20
20
|
engineering_productivity: '~"Engineering Productivity" for CI, Danger',
|
21
21
|
ci_template: '~"ci::templates"',
|
22
|
+
product_intelligence: '~"product intelligence"',
|
22
23
|
}.freeze
|
23
24
|
|
24
25
|
HTTPError = Class.new(StandardError)
|
@@ -51,8 +52,62 @@ module Danger
|
|
51
52
|
JSON.parse(rsp.body)
|
52
53
|
end
|
53
54
|
|
55
|
+
def added_files
|
56
|
+
@added_files ||= if changes_from_api
|
57
|
+
changes_from_api.select { |file| file["new_file"] }.map { |file| file["new_path"] }
|
58
|
+
else
|
59
|
+
git.added_files.to_a
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def modified_files
|
64
|
+
@modified_files ||= if changes_from_api
|
65
|
+
changes_from_api.select { |file| !file["new_file"] && !file["deleted_file"] && !file["renamed_file"] }.map { |file| file["new_path"] }
|
66
|
+
else
|
67
|
+
git.modified_files.to_a
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
def renamed_files
|
72
|
+
@renamed_files ||= if changes_from_api
|
73
|
+
changes_from_api.select { |file| file["renamed_file"] }.each_with_object([]) do |file, memo|
|
74
|
+
memo << { before: file["old_path"], after: file["new_path"] }
|
75
|
+
end
|
76
|
+
else
|
77
|
+
git.renamed_files.to_a
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
def deleted_files
|
82
|
+
@deleted_files ||= if changes_from_api
|
83
|
+
changes_from_api.select { |file| file["deleted_file"] }.map { |file| file["new_path"] }
|
84
|
+
else
|
85
|
+
git.deleted_files.to_a
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
def diff_for_file(filename)
|
90
|
+
if changes_from_api
|
91
|
+
changes_hash = changes_from_api.find { |file| file["new_path"] == filename }
|
92
|
+
changes_hash["diff"] if changes_hash
|
93
|
+
else
|
94
|
+
git.diff_for_file(filename)&.patch
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
def changes_from_api
|
99
|
+
return nil unless ci?
|
100
|
+
return nil if defined?(@force_changes_from_git)
|
101
|
+
|
102
|
+
@changes_from_api ||= gitlab_helper.mr_changes.to_h["changes"]
|
103
|
+
rescue
|
104
|
+
# Fallback to the Git strategy in any case
|
105
|
+
@force_changes_from_git = true
|
106
|
+
nil
|
107
|
+
end
|
108
|
+
|
54
109
|
# Returns a list of all files that have been added, modified or renamed.
|
55
|
-
# `
|
110
|
+
# `modified_files` might contain paths that already have been renamed,
|
56
111
|
# so we need to remove them from the list.
|
57
112
|
#
|
58
113
|
# Considering these changes:
|
@@ -70,10 +125,10 @@ module Danger
|
|
70
125
|
# @return [Array<String>]
|
71
126
|
def all_changed_files
|
72
127
|
Set.new
|
73
|
-
.merge(
|
74
|
-
.merge(
|
75
|
-
.merge(
|
76
|
-
.subtract(
|
128
|
+
.merge(added_files)
|
129
|
+
.merge(modified_files)
|
130
|
+
.merge(renamed_files.map { |x| x[:after] })
|
131
|
+
.subtract(renamed_files.map { |x| x[:before] })
|
77
132
|
.to_a
|
78
133
|
.sort
|
79
134
|
end
|
@@ -87,10 +142,10 @@ module Danger
|
|
87
142
|
# "+ # Test change",
|
88
143
|
# "- # Old change" ]
|
89
144
|
def changed_lines(changed_file)
|
90
|
-
diff =
|
145
|
+
diff = diff_for_file(changed_file)
|
91
146
|
return [] unless diff
|
92
147
|
|
93
|
-
diff.
|
148
|
+
diff.split("\n").select { |line| %r{^[+-]}.match?(line) }
|
94
149
|
end
|
95
150
|
|
96
151
|
def release_automation?
|
@@ -117,23 +172,23 @@ module Danger
|
|
117
172
|
# @return [Gitlab::Dangerfiles::Changes]
|
118
173
|
def changes(categories)
|
119
174
|
Gitlab::Dangerfiles::Changes.new([]).tap do |changes|
|
120
|
-
|
175
|
+
added_files.each do |file|
|
121
176
|
categories_for_file(file, categories).each { |category| changes << Gitlab::Dangerfiles::Change.new(file, :added, category) }
|
122
177
|
end
|
123
178
|
|
124
|
-
|
179
|
+
modified_files.each do |file|
|
125
180
|
categories_for_file(file, categories).each { |category| changes << Gitlab::Dangerfiles::Change.new(file, :modified, category) }
|
126
181
|
end
|
127
182
|
|
128
|
-
|
183
|
+
deleted_files.each do |file|
|
129
184
|
categories_for_file(file, categories).each { |category| changes << Gitlab::Dangerfiles::Change.new(file, :deleted, category) }
|
130
185
|
end
|
131
186
|
|
132
|
-
|
187
|
+
renamed_files.map { |x| x[:before] }.each do |file|
|
133
188
|
categories_for_file(file, categories).each { |category| changes << Gitlab::Dangerfiles::Change.new(file, :renamed_before, category) }
|
134
189
|
end
|
135
190
|
|
136
|
-
|
191
|
+
renamed_files.map { |x| x[:after] }.each do |file|
|
137
192
|
categories_for_file(file, categories).each { |category| changes << Gitlab::Dangerfiles::Change.new(file, :renamed_after, category) }
|
138
193
|
end
|
139
194
|
end
|
@@ -169,31 +224,43 @@ module Danger
|
|
169
224
|
end
|
170
225
|
|
171
226
|
def mr_iid
|
172
|
-
return "" unless
|
227
|
+
return "" unless ci?
|
173
228
|
|
174
229
|
gitlab_helper.mr_json["iid"]
|
175
230
|
end
|
176
231
|
|
232
|
+
def mr_author
|
233
|
+
return `whoami`.strip unless ci?
|
234
|
+
|
235
|
+
gitlab_helper.mr_author
|
236
|
+
end
|
237
|
+
|
177
238
|
def mr_title
|
178
|
-
return "" unless
|
239
|
+
return "" unless ci?
|
179
240
|
|
180
241
|
gitlab_helper.mr_json["title"]
|
181
242
|
end
|
182
243
|
|
183
244
|
def mr_web_url
|
184
|
-
return "" unless
|
245
|
+
return "" unless ci?
|
185
246
|
|
186
247
|
gitlab_helper.mr_json["web_url"]
|
187
248
|
end
|
188
249
|
|
189
250
|
def mr_labels
|
190
|
-
return [] unless
|
251
|
+
return [] unless ci?
|
191
252
|
|
192
253
|
gitlab_helper.mr_labels
|
193
254
|
end
|
194
255
|
|
256
|
+
def mr_source_branch
|
257
|
+
return `git rev-parse --abbrev-ref HEAD`.strip unless ci?
|
258
|
+
|
259
|
+
gitlab_helper.mr_json["source_branch"]
|
260
|
+
end
|
261
|
+
|
195
262
|
def mr_target_branch
|
196
|
-
return "" unless
|
263
|
+
return "" unless ci?
|
197
264
|
|
198
265
|
gitlab_helper.mr_json["target_branch"]
|
199
266
|
end
|
@@ -1,8 +1,8 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
require_relative "
|
4
|
-
require_relative "
|
5
|
-
require_relative "
|
3
|
+
require_relative "../../gitlab/dangerfiles/teammate"
|
4
|
+
require_relative "../../gitlab/dangerfiles/weightage/maintainers"
|
5
|
+
require_relative "../../gitlab/dangerfiles/weightage/reviewers"
|
6
6
|
|
7
7
|
module Danger
|
8
8
|
# Common helper functions for our danger scripts. See Danger::Helper
|
@@ -18,14 +18,14 @@ module Danger
|
|
18
18
|
Spin = Struct.new(:category, :reviewer, :maintainer, :optional_role, :timezone_experiment)
|
19
19
|
|
20
20
|
def team_mr_author
|
21
|
-
team.find { |person| person.username ==
|
21
|
+
team.find { |person| person.username == helper.mr_author }
|
22
22
|
end
|
23
23
|
|
24
24
|
# Assigns GitLab team members to be reviewer and maintainer
|
25
25
|
# for each change category that a Merge Request contains.
|
26
26
|
#
|
27
27
|
# @return [Array<Spin>]
|
28
|
-
def spin(project, categories, timezone_experiment: false)
|
28
|
+
def spin(project, categories = [nil], timezone_experiment: false)
|
29
29
|
spins = categories.sort.map do |category|
|
30
30
|
including_timezone = INCLUDE_TIMEZONE_FOR_CATEGORY.fetch(category, timezone_experiment)
|
31
31
|
|
@@ -59,6 +59,8 @@ module Danger
|
|
59
59
|
# Fetch an already picked backend maintainer, or pick one otherwise
|
60
60
|
spin.maintainer = backend_spin&.maintainer || spin_for_category(project, :backend, timezone_experiment: including_timezone).maintainer
|
61
61
|
end
|
62
|
+
when :product_intelligence
|
63
|
+
spin.optional_role = :maintainer
|
62
64
|
end
|
63
65
|
end
|
64
66
|
|
@@ -119,21 +121,7 @@ module Danger
|
|
119
121
|
# @param [Teammate] person
|
120
122
|
# @return [Boolean]
|
121
123
|
def mr_author?(person)
|
122
|
-
person.username ==
|
123
|
-
end
|
124
|
-
|
125
|
-
def mr_author_username
|
126
|
-
helper.gitlab_helper&.mr_author || `whoami`
|
127
|
-
end
|
128
|
-
|
129
|
-
def mr_source_branch
|
130
|
-
return `git rev-parse --abbrev-ref HEAD` unless helper.gitlab_helper&.mr_json
|
131
|
-
|
132
|
-
helper.gitlab_helper.mr_json["source_branch"]
|
133
|
-
end
|
134
|
-
|
135
|
-
def mr_labels
|
136
|
-
helper.gitlab_helper&.mr_labels || []
|
124
|
+
person.username == helper.mr_author
|
137
125
|
end
|
138
126
|
|
139
127
|
def new_random(seed)
|
@@ -142,7 +130,7 @@ module Danger
|
|
142
130
|
|
143
131
|
def spin_role_for_category(team, role, project, category)
|
144
132
|
team.select do |member|
|
145
|
-
member.public_send("#{role}?", project, category, mr_labels) # rubocop:disable GitlabSecurity/PublicSend
|
133
|
+
member.public_send("#{role}?", project, category, helper.mr_labels) # rubocop:disable GitlabSecurity/PublicSend
|
146
134
|
end
|
147
135
|
end
|
148
136
|
|
@@ -153,7 +141,7 @@ module Danger
|
|
153
141
|
spin_role_for_category(team, role, project, category)
|
154
142
|
end
|
155
143
|
|
156
|
-
random = new_random(mr_source_branch)
|
144
|
+
random = new_random(helper.mr_source_branch)
|
157
145
|
|
158
146
|
weighted_reviewers = Gitlab::Dangerfiles::Weightage::Reviewers.new(reviewers, traintainers).execute
|
159
147
|
weighted_maintainers = Gitlab::Dangerfiles::Weightage::Maintainers.new(maintainers).execute
|
data/lib/gitlab/dangerfiles.rb
CHANGED
@@ -3,7 +3,7 @@ require "gitlab/dangerfiles/version"
|
|
3
3
|
module Gitlab
|
4
4
|
module Dangerfiles
|
5
5
|
def self.import_plugins(danger)
|
6
|
-
danger.import_plugin(File.expand_path("../danger/*.rb", __dir__))
|
6
|
+
danger.import_plugin(File.expand_path("../danger/plugins/*.rb", __dir__))
|
7
7
|
end
|
8
8
|
end
|
9
9
|
end
|
@@ -59,7 +59,7 @@ module Gitlab
|
|
59
59
|
private
|
60
60
|
|
61
61
|
def subject
|
62
|
-
TitleLinting.remove_draft_flag(message_parts[0])
|
62
|
+
@subject ||= TitleLinting.remove_draft_flag(message_parts[0])
|
63
63
|
end
|
64
64
|
|
65
65
|
def subject_too_short?
|
@@ -75,6 +75,7 @@ module Gitlab
|
|
75
75
|
end
|
76
76
|
|
77
77
|
def subject_starts_with_lowercase?
|
78
|
+
return false if subject.empty?
|
78
79
|
return false if ("A".."Z").cover?(subject[0])
|
79
80
|
|
80
81
|
first_char = subject.sub(/\A(\[.+\]|\w+:)\s/, "")[0]
|
@@ -45,17 +45,63 @@ end
|
|
45
45
|
|
46
46
|
RSpec.shared_context "with dangerfile" do
|
47
47
|
let(:dangerfile) { DangerSpecHelper.testing_dangerfile }
|
48
|
-
let(:added_files) { %w[
|
49
|
-
let(:modified_files) { %w[
|
50
|
-
let(:deleted_files) { %w[
|
51
|
-
let(:renamed_before_file) { "renamed_before" }
|
52
|
-
let(:renamed_after_file) { "renamed_after" }
|
48
|
+
let(:added_files) { %w[added-from-git] }
|
49
|
+
let(:modified_files) { %w[modified-from-git] }
|
50
|
+
let(:deleted_files) { %w[deleted-from-git] }
|
51
|
+
let(:renamed_before_file) { "renamed_before-from-git" }
|
52
|
+
let(:renamed_after_file) { "renamed_after-from-git" }
|
53
53
|
let(:renamed_files) { [{ before: renamed_before_file, after: renamed_after_file }] }
|
54
54
|
let(:change_class) { Gitlab::Dangerfiles::Change }
|
55
55
|
let(:changes_class) { Gitlab::Dangerfiles::Changes }
|
56
56
|
let(:changes) { changes_class.new([]) }
|
57
57
|
let(:mr_title) { "Fake Title" }
|
58
58
|
let(:mr_labels) { [] }
|
59
|
+
let(:mr_changes_from_api) do
|
60
|
+
{
|
61
|
+
"changes" => [
|
62
|
+
{
|
63
|
+
"old_path" => "added-from-api",
|
64
|
+
"new_path" => "added-from-api",
|
65
|
+
"a_mode" => "100644",
|
66
|
+
"b_mode" => "100644",
|
67
|
+
"new_file" => true,
|
68
|
+
"renamed_file" => false,
|
69
|
+
"deleted_file" => false,
|
70
|
+
"diff" => "@@ -49,6 +49,14 @@\n- vendor/ruby/\n policy: pull\n \n+.danger-review-cache:\n",
|
71
|
+
},
|
72
|
+
{
|
73
|
+
"old_path" => "modified-from-api",
|
74
|
+
"new_path" => "modified-from-api",
|
75
|
+
"a_mode" => "100644",
|
76
|
+
"b_mode" => "100644",
|
77
|
+
"new_file" => false,
|
78
|
+
"renamed_file" => false,
|
79
|
+
"deleted_file" => false,
|
80
|
+
"diff" => "@@ -49,6 +49,14 @@\n- vendor/ruby/\n policy: pull\n \n+.danger-review-cache:\n",
|
81
|
+
},
|
82
|
+
{
|
83
|
+
"old_path" => "renamed_before-from-api",
|
84
|
+
"new_path" => "renamed_after-from-api",
|
85
|
+
"a_mode" => "100644",
|
86
|
+
"b_mode" => "100644",
|
87
|
+
"new_file" => false,
|
88
|
+
"renamed_file" => true,
|
89
|
+
"deleted_file" => false,
|
90
|
+
"diff" => "@@ -49,6 +49,14 @@\n- vendor/ruby/\n policy: pull\n \n+.danger-review-cache:\n",
|
91
|
+
},
|
92
|
+
{
|
93
|
+
"old_path" => "deleted-from-api",
|
94
|
+
"new_path" => "deleted-from-api",
|
95
|
+
"a_mode" => "100644",
|
96
|
+
"b_mode" => "100644",
|
97
|
+
"new_file" => false,
|
98
|
+
"renamed_file" => false,
|
99
|
+
"deleted_file" => true,
|
100
|
+
"diff" => "@@ -49,6 +49,14 @@\n- vendor/ruby/\n policy: pull\n \n+.danger-review-cache:\n",
|
101
|
+
},
|
102
|
+
],
|
103
|
+
}
|
104
|
+
end
|
59
105
|
|
60
106
|
let(:fake_git) { double("fake-git", added_files: added_files, modified_files: modified_files, deleted_files: deleted_files, renamed_files: renamed_files) }
|
61
107
|
let(:fake_helper) { double("fake-helper", changes: changes, mr_iid: 1234, mr_title: mr_title, mr_labels: mr_labels) }
|
@@ -101,6 +101,13 @@ module Gitlab
|
|
101
101
|
return true if capabilities(project).include?("#{kind} engineering_productivity")
|
102
102
|
|
103
103
|
capabilities(project).include?("#{kind} backend")
|
104
|
+
when :product_intelligence
|
105
|
+
return false unless role[/Engineer, Product Intelligence/]
|
106
|
+
|
107
|
+
# any reviewer of project from Product Intelligence team can review MR
|
108
|
+
kind == :reviewer && capabilities(project).any?
|
109
|
+
when nil
|
110
|
+
capabilities(project).include?("#{kind}")
|
104
111
|
else
|
105
112
|
capabilities(project).include?("#{kind} #{category}")
|
106
113
|
end
|
metadata
CHANGED
@@ -1,17 +1,17 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gitlab-dangerfiles
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 1.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Rémy Coutable
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-
|
11
|
+
date: 2021-04-01 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
|
-
name: danger
|
14
|
+
name: danger-gitlab
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
17
|
- - ">="
|
@@ -130,8 +130,8 @@ files:
|
|
130
130
|
- fixtures/emojis/aliases.json
|
131
131
|
- fixtures/emojis/digests.json
|
132
132
|
- gitlab-dangerfiles.gemspec
|
133
|
-
- lib/danger/helper.rb
|
134
|
-
- lib/danger/roulette.rb
|
133
|
+
- lib/danger/plugins/helper.rb
|
134
|
+
- lib/danger/plugins/roulette.rb
|
135
135
|
- lib/gitlab-dangerfiles.rb
|
136
136
|
- lib/gitlab/Dangerfile
|
137
137
|
- lib/gitlab/dangerfiles.rb
|