Commit a3607aa4 authored by Sean McGivern's avatar Sean McGivern

Merge branch 'issue_27168_2' into 'master'

Preloads head pipeline for each merge request

Closes #27168

See merge request !10064
parents a325a50a 2ccee716
...@@ -47,7 +47,7 @@ module IssuableCollections ...@@ -47,7 +47,7 @@ module IssuableCollections
end end
def merge_requests_collection def merge_requests_collection
merge_requests_finder.execute.preload(:source_project, :target_project, :author, :assignee, :labels, :milestone, :merge_request_diff, target_project: :namespace) merge_requests_finder.execute.preload(:source_project, :target_project, :author, :assignee, :labels, :milestone, :merge_request_diff, :head_pipeline, target_project: :namespace)
end end
def issues_finder def issues_finder
......
...@@ -18,6 +18,10 @@ module Ci ...@@ -18,6 +18,10 @@ module Ci
has_many :builds, foreign_key: :commit_id has_many :builds, foreign_key: :commit_id
has_many :trigger_requests, dependent: :destroy, foreign_key: :commit_id has_many :trigger_requests, dependent: :destroy, foreign_key: :commit_id
# Merge requests for which the current pipeline is running against
# the merge request's latest commit.
has_many :merge_requests, foreign_key: "head_pipeline_id"
has_many :pending_builds, -> { pending }, foreign_key: :commit_id, class_name: 'Ci::Build' has_many :pending_builds, -> { pending }, foreign_key: :commit_id, class_name: 'Ci::Build'
has_many :retryable_builds, -> { latest.failed_or_canceled }, foreign_key: :commit_id, class_name: 'Ci::Build' has_many :retryable_builds, -> { latest.failed_or_canceled }, foreign_key: :commit_id, class_name: 'Ci::Build'
has_many :cancelable_statuses, -> { cancelable }, foreign_key: :commit_id, class_name: 'CommitStatus' has_many :cancelable_statuses, -> { cancelable }, foreign_key: :commit_id, class_name: 'CommitStatus'
...@@ -381,14 +385,6 @@ module Ci ...@@ -381,14 +385,6 @@ module Ci
project.execute_services(data, :pipeline_hooks) project.execute_services(data, :pipeline_hooks)
end end
# Merge requests for which the current pipeline is running against
# the merge request's latest commit.
def merge_requests
@merge_requests ||= project.merge_requests
.where(source_branch: self.ref)
.select { |merge_request| merge_request.head_pipeline.try(:id) == self.id }
end
# All the merge requests for which the current pipeline runs/ran against # All the merge requests for which the current pipeline runs/ran against
def all_merge_requests def all_merge_requests
@all_merge_requests ||= project.merge_requests.where(source_branch: ref) @all_merge_requests ||= project.merge_requests.where(source_branch: ref)
......
...@@ -13,6 +13,8 @@ class MergeRequest < ActiveRecord::Base ...@@ -13,6 +13,8 @@ class MergeRequest < ActiveRecord::Base
has_one :merge_request_diff, has_one :merge_request_diff,
-> { order('merge_request_diffs.id DESC') } -> { order('merge_request_diffs.id DESC') }
belongs_to :head_pipeline, foreign_key: "head_pipeline_id", class_name: "Ci::Pipeline"
has_many :events, as: :target, dependent: :destroy has_many :events, as: :target, dependent: :destroy
has_many :merge_requests_closing_issues, class_name: 'MergeRequestsClosingIssues', dependent: :delete_all has_many :merge_requests_closing_issues, class_name: 'MergeRequestsClosingIssues', dependent: :delete_all
...@@ -829,12 +831,6 @@ class MergeRequest < ActiveRecord::Base ...@@ -829,12 +831,6 @@ class MergeRequest < ActiveRecord::Base
diverged_commits_count > 0 diverged_commits_count > 0
end end
def head_pipeline
return unless diff_head_sha && source_project
@head_pipeline ||= source_project.pipeline_for(source_branch, diff_head_sha)
end
def all_pipelines def all_pipelines
return Ci::Pipeline.none unless source_project return Ci::Pipeline.none unless source_project
......
...@@ -47,7 +47,7 @@ module Ci ...@@ -47,7 +47,7 @@ module Ci
end end
Ci::Pipeline.transaction do Ci::Pipeline.transaction do
pipeline.save update_merge_requests_head_pipeline if pipeline.save
Ci::CreatePipelineBuildsService Ci::CreatePipelineBuildsService
.new(project, current_user) .new(project, current_user)
...@@ -118,6 +118,11 @@ module Ci ...@@ -118,6 +118,11 @@ module Ci
origin_sha && origin_sha != Gitlab::Git::BLANK_SHA origin_sha && origin_sha != Gitlab::Git::BLANK_SHA
end end
def update_merge_requests_head_pipeline
MergeRequest.where(source_branch: @pipeline.ref, source_project: @pipeline.project).
update_all(head_pipeline_id: @pipeline.id)
end
def error(message, save: false) def error(message, save: false)
pipeline.errors.add(:base, message) pipeline.errors.add(:base, message)
pipeline.drop if save pipeline.drop if save
......
---
title: Preloads head pipeline for merge request collection
merge_request:
author:
class AddHeadPipelineIdToMergeRequests < ActiveRecord::Migration
DOWNTIME = false
def change
add_column :merge_requests, :head_pipeline_id, :integer
end
end
class AddHeadPipelineForEachMergeRequest < ActiveRecord::Migration
include Gitlab::Database::MigrationHelpers
DOWNTIME = false
def up
disable_statement_timeout
pipelines = Arel::Table.new(:ci_pipelines)
merge_requests = Arel::Table.new(:merge_requests)
head_id = pipelines.
project(Arel::Nodes::NamedFunction.new('max', [pipelines[:id]])).
from(pipelines).
where(pipelines[:ref].eq(merge_requests[:source_branch])).
where(pipelines[:project_id].eq(merge_requests[:source_project_id]))
sub_query = Arel::Nodes::SqlLiteral.new(Arel::Nodes::Grouping.new(head_id).to_sql)
update_column_in_batches(:merge_requests, :head_pipeline_id, sub_query)
end
def down
end
end
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
# #
# It's strongly recommended that you check this file into your version control system. # It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema.define(version: 20170506185517) do ActiveRecord::Schema.define(version: 20170508170547) do
# These are extensions that must be enabled in order to support this database # These are extensions that must be enabled in order to support this database
enable_extension "plpgsql" enable_extension "plpgsql"
...@@ -690,6 +690,7 @@ ActiveRecord::Schema.define(version: 20170506185517) do ...@@ -690,6 +690,7 @@ ActiveRecord::Schema.define(version: 20170506185517) do
t.integer "cached_markdown_version" t.integer "cached_markdown_version"
t.datetime "last_edited_at" t.datetime "last_edited_at"
t.integer "last_edited_by_id" t.integer "last_edited_by_id"
t.integer "head_pipeline_id"
end end
add_index "merge_requests", ["assignee_id"], name: "index_merge_requests_on_assignee_id", using: :btree add_index "merge_requests", ["assignee_id"], name: "index_merge_requests_on_assignee_id", using: :btree
......
...@@ -557,6 +557,7 @@ class Spinach::Features::ProjectMergeRequests < Spinach::FeatureSteps ...@@ -557,6 +557,7 @@ class Spinach::Features::ProjectMergeRequests < Spinach::FeatureSteps
project = merge_request.source_project project = merge_request.source_project
project.enable_ci project.enable_ci
pipeline = create :ci_pipeline, project: project, sha: merge_request.diff_head_sha, ref: merge_request.source_branch pipeline = create :ci_pipeline, project: project, sha: merge_request.diff_head_sha, ref: merge_request.source_branch
merge_request.update(head_pipeline: pipeline)
create :ci_build, pipeline: pipeline create :ci_build, pipeline: pipeline
end end
......
...@@ -345,7 +345,8 @@ describe Projects::MergeRequestsController do ...@@ -345,7 +345,8 @@ describe Projects::MergeRequestsController do
end end
before do before do
create(:ci_empty_pipeline, project: project, sha: merge_request.diff_head_sha, ref: merge_request.source_branch) pipeline = create(:ci_empty_pipeline, project: project, sha: merge_request.diff_head_sha, ref: merge_request.source_branch)
merge_request.update(head_pipeline: pipeline)
end end
it 'returns :merge_when_pipeline_succeeds' do it 'returns :merge_when_pipeline_succeeds' do
...@@ -1159,7 +1160,10 @@ describe Projects::MergeRequestsController do ...@@ -1159,7 +1160,10 @@ describe Projects::MergeRequestsController do
let(:status) { pipeline.detailed_status(double('user')) } let(:status) { pipeline.detailed_status(double('user')) }
before { get_pipeline_status } before do
merge_request.update(head_pipeline: pipeline)
get_pipeline_status
end
it 'return a detailed head_pipeline status in json' do it 'return a detailed head_pipeline status in json' do
expect(response).to have_http_status(:ok) expect(response).to have_http_status(:ok)
......
...@@ -12,8 +12,10 @@ feature 'Cycle Analytics', feature: true, js: true do ...@@ -12,8 +12,10 @@ feature 'Cycle Analytics', feature: true, js: true do
context 'as an allowed user' do context 'as an allowed user' do
context 'when project is new' do context 'when project is new' do
before do before do
project.team << [user, :master] project.add_master(user)
login_as(user) login_as(user)
visit namespace_project_cycle_analytics_path(project.namespace, project) visit namespace_project_cycle_analytics_path(project.namespace, project)
wait_for_ajax wait_for_ajax
end end
...@@ -30,7 +32,9 @@ feature 'Cycle Analytics', feature: true, js: true do ...@@ -30,7 +32,9 @@ feature 'Cycle Analytics', feature: true, js: true do
context "when there's cycle analytics data" do context "when there's cycle analytics data" do
before do before do
project.team << [user, :master] allow_any_instance_of(Gitlab::ReferenceExtractor).to receive(:issues).and_return([issue])
mr.update(head_pipeline: pipeline)
project.add_master(user)
create_cycle create_cycle
deploy_master deploy_master
...@@ -84,7 +88,7 @@ feature 'Cycle Analytics', feature: true, js: true do ...@@ -84,7 +88,7 @@ feature 'Cycle Analytics', feature: true, js: true do
context "as a guest" do context "as a guest" do
before do before do
project.team << [guest, :guest] project.add_guest(guest)
allow_any_instance_of(Gitlab::ReferenceExtractor).to receive(:issues).and_return([issue]) allow_any_instance_of(Gitlab::ReferenceExtractor).to receive(:issues).and_return([issue])
create_cycle create_cycle
......
...@@ -52,6 +52,9 @@ describe 'issuable list', feature: true do ...@@ -52,6 +52,9 @@ describe 'issuable list', feature: true do
create(:issue, project: project, author: user) create(:issue, project: project, author: user)
else else
create(:merge_request, source_project: project, source_branch: generate(:branch)) create(:merge_request, source_project: project, source_branch: generate(:branch))
source_branch = FFaker::Name.name
pipeline = create(:ci_empty_pipeline, project: project, ref: source_branch, status: %w(running failed success).sample, sha: 'any')
create(:merge_request, title: FFaker::Lorem.sentence, source_project: project, source_branch: source_branch, head_pipeline: pipeline)
end end
2.times do 2.times do
......
...@@ -4,16 +4,18 @@ feature 'Merge immediately', :feature, :js do ...@@ -4,16 +4,18 @@ feature 'Merge immediately', :feature, :js do
let(:user) { create(:user) } let(:user) { create(:user) }
let(:project) { create(:project, :public) } let(:project) { create(:project, :public) }
let(:merge_request) do let!(:merge_request) do
create(:merge_request_with_diffs, source_project: project, create(:merge_request_with_diffs, source_project: project,
author: user, author: user,
title: 'Bug NS-04') title: 'Bug NS-04',
head_pipeline: pipeline,
source_branch: pipeline.ref)
end end
let(:pipeline) do let(:pipeline) do
create(:ci_pipeline, project: project, create(:ci_pipeline, project: project,
sha: merge_request.diff_head_sha, ref: 'master',
ref: merge_request.source_branch) sha: project.repository.commit('master').id)
end end
before { project.team << [user, :master] } before { project.team << [user, :master] }
......
...@@ -16,7 +16,10 @@ feature 'Merge When Pipeline Succeeds', :feature, :js do ...@@ -16,7 +16,10 @@ feature 'Merge When Pipeline Succeeds', :feature, :js do
ref: merge_request.source_branch) ref: merge_request.source_branch)
end end
before { project.team << [user, :master] } before do
project.add_master(user)
merge_request.update(head_pipeline_id: pipeline.id)
end
context 'when there is active pipeline for merge request' do context 'when there is active pipeline for merge request' do
background do background do
......
...@@ -3,7 +3,7 @@ require 'rails_helper' ...@@ -3,7 +3,7 @@ require 'rails_helper'
feature 'Mini Pipeline Graph', :js, :feature do feature 'Mini Pipeline Graph', :js, :feature do
let(:user) { create(:user) } let(:user) { create(:user) }
let(:project) { create(:project, :public) } let(:project) { create(:project, :public) }
let(:merge_request) { create(:merge_request, source_project: project) } let(:merge_request) { create(:merge_request, source_project: project, head_pipeline: pipeline) }
let(:pipeline) { create(:ci_empty_pipeline, project: project, ref: 'master', status: 'running', sha: project.commit.id) } let(:pipeline) { create(:ci_empty_pipeline, project: project, ref: 'master', status: 'running', sha: project.commit.id) }
let(:build) { create(:ci_build, pipeline: pipeline, stage: 'test', commands: 'test') } let(:build) { create(:ci_build, pipeline: pipeline, stage: 'test', commands: 'test') }
......
...@@ -31,6 +31,8 @@ feature 'Only allow merge requests to be merged if the pipeline succeeds', featu ...@@ -31,6 +31,8 @@ feature 'Only allow merge requests to be merged if the pipeline succeeds', featu
status: status) status: status)
end end
before { merge_request.update(head_pipeline: pipeline) }
context 'when merge requests can only be merged if the pipeline succeeds' do context 'when merge requests can only be merged if the pipeline succeeds' do
before do before do
project.update_attribute(:only_allow_merge_if_pipeline_succeeds, true) project.update_attribute(:only_allow_merge_if_pipeline_succeeds, true)
......
...@@ -91,6 +91,8 @@ describe 'Merge request', :feature, :js do ...@@ -91,6 +91,8 @@ describe 'Merge request', :feature, :js do
statuses: [commit_status]) statuses: [commit_status])
create(:ci_build, :pending, pipeline: pipeline) create(:ci_build, :pending, pipeline: pipeline)
merge_request.update(head_pipeline: pipeline)
visit namespace_project_merge_request_path(project.namespace, project, merge_request) visit namespace_project_merge_request_path(project.namespace, project, merge_request)
end end
...@@ -103,10 +105,15 @@ describe 'Merge request', :feature, :js do ...@@ -103,10 +105,15 @@ describe 'Merge request', :feature, :js do
context 'when merge request is in the blocked pipeline state' do context 'when merge request is in the blocked pipeline state' do
before do before do
create(:ci_pipeline, project: project, pipeline = create(
sha: merge_request.diff_head_sha, :ci_pipeline,
ref: merge_request.source_branch, project: project,
status: :manual) sha: merge_request.diff_head_sha,
ref: merge_request.source_branch,
status: :manual
)
merge_request.update(head_pipeline: pipeline)
visit namespace_project_merge_request_path(project.namespace, visit namespace_project_merge_request_path(project.namespace,
project, project,
...@@ -131,6 +138,8 @@ describe 'Merge request', :feature, :js do ...@@ -131,6 +138,8 @@ describe 'Merge request', :feature, :js do
statuses: [commit_status]) statuses: [commit_status])
create(:ci_build, :pending, pipeline: pipeline) create(:ci_build, :pending, pipeline: pipeline)
merge_request.update(head_pipeline: pipeline)
visit namespace_project_merge_request_path(project.namespace, project, merge_request) visit namespace_project_merge_request_path(project.namespace, project, merge_request)
end end
......
...@@ -130,6 +130,8 @@ describe 'cycle analytics events' do ...@@ -130,6 +130,8 @@ describe 'cycle analytics events' do
end end
before do before do
merge_request.update(head_pipeline: pipeline)
create(:ci_build, pipeline: pipeline, status: :success, author: user) create(:ci_build, pipeline: pipeline, status: :success, author: user)
create(:ci_build, pipeline: pipeline, status: :success, author: user) create(:ci_build, pipeline: pipeline, status: :success, author: user)
...@@ -226,6 +228,8 @@ describe 'cycle analytics events' do ...@@ -226,6 +228,8 @@ describe 'cycle analytics events' do
end end
before do before do
merge_request.update(head_pipeline: pipeline)
create(:ci_build, pipeline: pipeline, status: :success, author: user) create(:ci_build, pipeline: pipeline, status: :success, author: user)
create(:ci_build, pipeline: pipeline, status: :success, author: user) create(:ci_build, pipeline: pipeline, status: :success, author: user)
......
...@@ -85,6 +85,7 @@ merge_requests: ...@@ -85,6 +85,7 @@ merge_requests:
- merge_requests_closing_issues - merge_requests_closing_issues
- metrics - metrics
- timelogs - timelogs
- head_pipeline
merge_request_diff: merge_request_diff:
- merge_request - merge_request
pipelines: pipelines:
...@@ -102,6 +103,7 @@ pipelines: ...@@ -102,6 +103,7 @@ pipelines:
- manual_actions - manual_actions
- artifacts - artifacts
- pipeline_schedule - pipeline_schedule
- merge_requests
statuses: statuses:
- project - project
- pipeline - pipeline
......
...@@ -158,6 +158,7 @@ MergeRequest: ...@@ -158,6 +158,7 @@ MergeRequest:
- time_estimate - time_estimate
- last_edited_at - last_edited_at
- last_edited_by_id - last_edited_by_id
- head_pipeline_id
MergeRequestDiff: MergeRequestDiff:
- id - id
- state - state
......
require 'spec_helper'
require Rails.root.join('db', 'post_migrate', '20170508170547_add_head_pipeline_for_each_merge_request.rb')
describe AddHeadPipelineForEachMergeRequest do
let(:migration) { described_class.new }
let!(:project) { create(:empty_project) }
let!(:forked_project_link) { create(:forked_project_link, forked_from_project: project) }
let!(:other_project) { forked_project_link.forked_to_project }
let!(:pipeline_1) { create(:ci_pipeline, project: project, ref: "branch_1") }
let!(:pipeline_2) { create(:ci_pipeline, project: other_project, ref: "branch_1") }
let!(:pipeline_3) { create(:ci_pipeline, project: other_project, ref: "branch_1") }
let!(:pipeline_4) { create(:ci_pipeline, project: project, ref: "branch_2") }
let!(:mr_1) { create(:merge_request, source_project: project, target_project: project, source_branch: "branch_1", target_branch: "target_1") }
let!(:mr_2) { create(:merge_request, source_project: other_project, target_project: project, source_branch: "branch_1", target_branch: "target_2") }
let!(:mr_3) { create(:merge_request, source_project: project, target_project: project, source_branch: "branch_2", target_branch: "master") }
let!(:mr_4) { create(:merge_request, source_project: project, target_project: project, source_branch: "branch_3", target_branch: "master") }
context "#up" do
context "when source_project and source_branch of pipeline are the same of merge request" do
it "sets head_pipeline_id of given merge requests" do
migration.up
expect(mr_1.reload.head_pipeline_id).to eq(pipeline_1.id)
expect(mr_2.reload.head_pipeline_id).to eq(pipeline_3.id)
expect(mr_3.reload.head_pipeline_id).to eq(pipeline_4.id)
expect(mr_4.reload.head_pipeline_id).to be_nil
end
end
end
end
...@@ -1044,8 +1044,8 @@ describe Ci::Pipeline, models: true do ...@@ -1044,8 +1044,8 @@ describe Ci::Pipeline, models: true do
let(:pipeline) { create(:ci_empty_pipeline, status: 'created', project: project, ref: 'master', sha: 'a288a022a53a5a944fae87bcec6efc87b7061808') } let(:pipeline) { create(:ci_empty_pipeline, status: 'created', project: project, ref: 'master', sha: 'a288a022a53a5a944fae87bcec6efc87b7061808') }
it "returns merge requests whose `diff_head_sha` matches the pipeline's SHA" do it "returns merge requests whose `diff_head_sha` matches the pipeline's SHA" do
merge_request = create(:merge_request, source_project: project, source_branch: pipeline.ref)
allow_any_instance_of(MergeRequest).to receive(:diff_head_sha) { 'a288a022a53a5a944fae87bcec6efc87b7061808' } allow_any_instance_of(MergeRequest).to receive(:diff_head_sha) { 'a288a022a53a5a944fae87bcec6efc87b7061808' }
merge_request = create(:merge_request, source_project: project, head_pipeline: pipeline, source_branch: pipeline.ref)
expect(pipeline.merge_requests).to eq([merge_request]) expect(pipeline.merge_requests).to eq([merge_request])
end end
......
...@@ -14,6 +14,7 @@ describe 'CycleAnalytics#test', feature: true do ...@@ -14,6 +14,7 @@ describe 'CycleAnalytics#test', feature: true do
issue = context.create(:issue, project: context.project) issue = context.create(:issue, project: context.project)
merge_request = context.create_merge_request_closing_issue(issue) merge_request = context.create_merge_request_closing_issue(issue)
pipeline = context.create(:ci_pipeline, ref: merge_request.source_branch, sha: merge_request.diff_head_sha, project: context.project) pipeline = context.create(:ci_pipeline, ref: merge_request.source_branch, sha: merge_request.diff_head_sha, project: context.project)
merge_request.update(head_pipeline: pipeline)
{ pipeline: pipeline, issue: issue } { pipeline: pipeline, issue: issue }
end, end,
start_time_conditions: [["pipeline is started", -> (context, data) { data[:pipeline].run! }]], start_time_conditions: [["pipeline is started", -> (context, data) { data[:pipeline].run! }]],
......
...@@ -760,13 +760,8 @@ describe MergeRequest, models: true do ...@@ -760,13 +760,8 @@ describe MergeRequest, models: true do
describe '#head_pipeline' do describe '#head_pipeline' do
describe 'when the source project exists' do describe 'when the source project exists' do
it 'returns the latest pipeline' do it 'returns the latest pipeline' do
pipeline = double(:ci_pipeline, ref: 'master') pipeline = create(:ci_empty_pipeline, project: subject.source_project, ref: 'master', status: 'running', sha: "123abc")
subject.update(head_pipeline: pipeline)
allow(subject).to receive(:diff_head_sha).and_return('123abc')
expect(subject.source_project).to receive(:pipeline_for).
with('master', '123abc').
and_return(pipeline)
expect(subject.head_pipeline).to eq(pipeline) expect(subject.head_pipeline).to eq(pipeline)
end end
...@@ -1504,11 +1499,15 @@ describe MergeRequest, models: true do ...@@ -1504,11 +1499,15 @@ describe MergeRequest, models: true do
describe '#mergeable_with_slash_command?' do describe '#mergeable_with_slash_command?' do
def create_pipeline(status) def create_pipeline(status)
create(:ci_pipeline_with_one_job, pipeline = create(:ci_pipeline_with_one_job,
project: project, project: project,
ref: merge_request.source_branch, ref: merge_request.source_branch,
sha: merge_request.diff_head_sha, sha: merge_request.diff_head_sha,
status: status) status: status)
merge_request.update(head_pipeline: pipeline)
pipeline
end end
let(:project) { create(:project, :public, :repository, only_allow_merge_if_pipeline_succeeds: true) } let(:project) { create(:project, :public, :repository, only_allow_merge_if_pipeline_succeeds: true) }
......
...@@ -122,6 +122,7 @@ describe 'cycle analytics events', api: true do ...@@ -122,6 +122,7 @@ describe 'cycle analytics events', api: true do
mr = create_merge_request_closing_issue(issue, commit_message: "References #{issue.to_reference}") mr = create_merge_request_closing_issue(issue, commit_message: "References #{issue.to_reference}")
pipeline = create(:ci_empty_pipeline, status: 'created', project: project, ref: mr.source_branch, sha: mr.source_branch_sha) pipeline = create(:ci_empty_pipeline, status: 'created', project: project, ref: mr.source_branch, sha: mr.source_branch_sha)
mr.update(head_pipeline_id: pipeline.id)
pipeline.run pipeline.run
create(:ci_build, pipeline: pipeline, status: :success, author: user) create(:ci_build, pipeline: pipeline, status: :success, author: user)
......
...@@ -34,6 +34,42 @@ describe Ci::CreatePipelineService, services: true do ...@@ -34,6 +34,42 @@ describe Ci::CreatePipelineService, services: true do
it { expect(pipeline).to have_attributes(status: 'pending') } it { expect(pipeline).to have_attributes(status: 'pending') }
it { expect(pipeline.builds.first).to be_kind_of(Ci::Build) } it { expect(pipeline.builds.first).to be_kind_of(Ci::Build) }
context '#update_merge_requests_head_pipeline' do
it 'updates head pipeline of each merge request' do
merge_request_1 = create(:merge_request, source_branch: 'master', target_branch: "branch_1", source_project: project)
merge_request_2 = create(:merge_request, source_branch: 'master', target_branch: "branch_2", source_project: project)
head_pipeline = pipeline
expect(merge_request_1.reload.head_pipeline).to eq(head_pipeline)
expect(merge_request_2.reload.head_pipeline).to eq(head_pipeline)
end
context 'when there is no pipeline for source branch' do
it "does not update merge request head pipeline" do
merge_request = create(:merge_request, source_branch: 'other_branch', target_branch: "branch_1", source_project: project)
head_pipeline = pipeline
expect(merge_request.reload.head_pipeline).not_to eq(head_pipeline)
end
end
context 'when merge request target project is different from source project' do
let!(:target_project) { create(:empty_project) }
let!(:forked_project_link) { create(:forked_project_link, forked_to_project: project, forked_from_project: target_project) }
it 'updates head pipeline for merge request' do
merge_request =
create(:merge_request, source_branch: 'master', target_branch: "branch_1", source_project: project, target_project: target_project)
head_pipeline = pipeline
expect(merge_request.reload.head_pipeline).to eq(head_pipeline)
end
end
end
context 'auto-cancel enabled' do context 'auto-cancel enabled' do
before do before do
project.update(auto_cancel_pending_pipelines: 'enabled') project.update(auto_cancel_pending_pipelines: 'enabled')
......
...@@ -82,6 +82,10 @@ describe MergeRequests::MergeWhenPipelineSucceedsService do ...@@ -82,6 +82,10 @@ describe MergeRequests::MergeWhenPipelineSucceedsService do
sha: merge_request_head, status: 'success') sha: merge_request_head, status: 'success')
end end
before do
mr_merge_if_green_enabled.update(head_pipeline: triggering_pipeline)
end
it "merges all merge requests with merge when the pipeline succeeds enabled" do it "merges all merge requests with merge when the pipeline succeeds enabled" do
expect(MergeWorker).to receive(:perform_async) expect(MergeWorker).to receive(:perform_async)
service.trigger(triggering_pipeline) service.trigger(triggering_pipeline)
...@@ -124,6 +128,8 @@ describe MergeRequests::MergeWhenPipelineSucceedsService do ...@@ -124,6 +128,8 @@ describe MergeRequests::MergeWhenPipelineSucceedsService do
sha: mr_conflict.diff_head_sha, status: 'success') sha: mr_conflict.diff_head_sha, status: 'success')
end end
before { mr_conflict.update(head_pipeline: conflict_pipeline) }
it 'does not merge the merge request' do it 'does not merge the merge request' do
expect(MergeWorker).not_to receive(:perform_async) expect(MergeWorker).not_to receive(:perform_async)
......
...@@ -174,11 +174,13 @@ describe MergeRequests::UpdateService, services: true do ...@@ -174,11 +174,13 @@ describe MergeRequests::UpdateService, services: true do
context 'with active pipeline' do context 'with active pipeline' do
before do before do
service_mock = double service_mock = double
create(:ci_pipeline_with_one_job, pipeline = create(:ci_pipeline_with_one_job,
project: project, project: project,
ref: merge_request.source_branch, ref: merge_request.source_branch,
sha: merge_request.diff_head_sha) sha: merge_request.diff_head_sha)
merge_request.update(head_pipeline: pipeline)
expect(MergeRequests::MergeWhenPipelineSucceedsService).to receive(:new).with(project, user). expect(MergeRequests::MergeWhenPipelineSucceedsService).to receive(:new).with(project, user).
and_return(service_mock) and_return(service_mock)
expect(service_mock).to receive(:execute).with(merge_request) expect(service_mock).to receive(:execute).with(merge_request)
......
...@@ -2,7 +2,7 @@ require 'spec_helper' ...@@ -2,7 +2,7 @@ require 'spec_helper'
describe PipelineMetricsWorker do describe PipelineMetricsWorker do
let(:project) { create(:project, :repository) } let(:project) { create(:project, :repository) }
let!(:merge_request) { create(:merge_request, source_project: project, source_branch: pipeline.ref) } let!(:merge_request) { create(:merge_request, source_project: project, source_branch: pipeline.ref, head_pipeline: pipeline) }
let(:pipeline) do let(:pipeline) do
create(:ci_empty_pipeline, create(:ci_empty_pipeline,
......
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