Commit c66f640e authored by Sean McGivern's avatar Sean McGivern

Pick reviewers based on branch name

Change reviewer roulette to always pick the same reviewers for the same
branch name. We do this by:

1. Making the branch name 'canonical' across CE and EE by stripping a
   leading 'ce-' or 'ee-' and a trailing '-ce' or '-ee'. If people are
   following our branch naming guidelines, this should give the same
   branch name in both repos.
2. Converting the branch name to a stable integer by taking the integer
   form of its MD5.
3. Passing that integer as a seed to Ruby's `Random` class, which 'may
   be used to ensure repeatable sequences of pseudo-random numbers
   between different runs of the program' (from the Ruby documentation).

The upshot is that the same branch name (in CE and EE) should always
pick the same reviewers, and those should be evenly distributed across
the set of possible reviewers due to the use of MD5.
parent a516a4f3
# frozen_string_literal: true # frozen_string_literal: true
require 'digest/md5'
MESSAGE = <<MARKDOWN MESSAGE = <<MARKDOWN
## Reviewer roulette ## Reviewer roulette
...@@ -29,7 +31,9 @@ Please consider creating a merge request to ...@@ -29,7 +31,9 @@ Please consider creating a merge request to
for them. for them.
MARKDOWN MARKDOWN
def spin(team, project, category) def spin(team, project, category, branch_name)
rng = Random.new(Digest::MD5.hexdigest(branch_name).to_i(16))
reviewers = team.select { |member| member.reviewer?(project, category) } reviewers = team.select { |member| member.reviewer?(project, category) }
traintainers = team.select { |member| member.traintainer?(project, category) } traintainers = team.select { |member| member.traintainer?(project, category) }
maintainers = team.select { |member| member.maintainer?(project, category) } maintainers = team.select { |member| member.maintainer?(project, category) }
...@@ -41,8 +45,8 @@ def spin(team, project, category) ...@@ -41,8 +45,8 @@ def spin(team, project, category)
# https://gitlab.com/gitlab-org/gitlab-ce/issues/57653 # https://gitlab.com/gitlab-org/gitlab-ce/issues/57653
# Make traintainers have triple the chance to be picked as a reviewer # Make traintainers have triple the chance to be picked as a reviewer
reviewer = (reviewers + traintainers + traintainers).sample reviewer = (reviewers + traintainers + traintainers).sample(random: rng)
maintainer = maintainers.sample maintainer = maintainers.sample(random: rng)
"| #{helper.label_for_category(category)} | #{reviewer&.markdown_name} | #{maintainer&.markdown_name} |" "| #{helper.label_for_category(category)} | #{reviewer&.markdown_name} | #{maintainer&.markdown_name} |"
end end
...@@ -68,6 +72,12 @@ categories = changes.keys - [:unknown] ...@@ -68,6 +72,12 @@ categories = changes.keys - [:unknown]
# CSS Clean up MRs are reviewed using a slightly different process, so we # CSS Clean up MRs are reviewed using a slightly different process, so we
# disable the review roulette for such MRs. # disable the review roulette for such MRs.
if changes.any? && !gitlab.mr_labels.include?('single codebase') && !gitlab.mr_labels.include?('CSS cleanup') if changes.any? && !gitlab.mr_labels.include?('single codebase') && !gitlab.mr_labels.include?('CSS cleanup')
# Strip leading and trailing CE/EE markers
canonical_branch_name = gitlab
.mr_json['source_branch']
.gsub(/^[ce]e-/, '')
.gsub(/-[ce]e$/, '')
team = team =
begin begin
helper.project_team helper.project_team
...@@ -82,7 +92,7 @@ if changes.any? && !gitlab.mr_labels.include?('single codebase') && !gitlab.mr_l ...@@ -82,7 +92,7 @@ if changes.any? && !gitlab.mr_labels.include?('single codebase') && !gitlab.mr_l
project = helper.project_name project = helper.project_name
unknown = changes.fetch(:unknown, []) unknown = changes.fetch(:unknown, [])
rows = categories.map { |category| spin(team, project, category) } rows = categories.map { |category| spin(team, project, category, canonical_branch_name) }
markdown(MESSAGE) markdown(MESSAGE)
markdown(CATEGORY_TABLE_HEADER + rows.join("\n")) unless rows.empty? markdown(CATEGORY_TABLE_HEADER + rows.join("\n")) unless rows.empty?
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment