summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKamil Trzcinski <ayufan@ayufan.eu>2016-09-19 15:03:51 +0200
committerGrzegorz Bizon <grzesiek.bizon@gmail.com>2016-10-03 12:34:05 +0200
commit4567e624a06358f0e3451be51d134f8dd22c199d (patch)
tree6a45033ce16277554e84586535d661c38a346c3a
parentd9f9ad9d7d672574a227dd6143cd3d08f2381be5 (diff)
downloadgitlab-ce-4567e624a06358f0e3451be51d134f8dd22c199d.tar.gz
Make pipeline processing asynchronous
Conflicts: app/models/ci/pipeline.rb app/models/commit_status.rb
-rw-r--r--app/models/ci/build.rb2
-rw-r--r--app/models/ci/pipeline.rb11
-rw-r--r--app/models/commit_status.rb14
-rw-r--r--app/services/merge_requests/add_todo_when_build_fails_service.rb8
-rw-r--r--app/services/merge_requests/base_service.rb15
-rw-r--r--app/services/merge_requests/merge_when_build_succeeds_service.rb7
-rw-r--r--app/workers/process_pipeline_worker.rb17
7 files changed, 51 insertions, 23 deletions
diff --git a/app/models/ci/build.rb b/app/models/ci/build.rb
index 5dbf66173de..7c9899334ad 100644
--- a/app/models/ci/build.rb
+++ b/app/models/ci/build.rb
@@ -67,7 +67,7 @@ module Ci
environment: build.environment,
status_event: 'enqueue'
)
- MergeRequests::AddTodoWhenBuildFailsService.new(build.project, nil).close(new_build)
+ MergeRequests::AddTodoWhenBuildFailsService.new(build.project, nil).close(new_build.pipeline)
build.pipeline.mark_as_processable_after_stage(build.stage_idx)
new_build
end
diff --git a/app/models/ci/pipeline.rb b/app/models/ci/pipeline.rb
index 663c5b1e231..da0b9d83e1d 100644
--- a/app/models/ci/pipeline.rb
+++ b/app/models/ci/pipeline.rb
@@ -73,6 +73,14 @@ module Ci
after_transition do |pipeline, transition|
pipeline.execute_hooks unless transition.loopback?
end
+
+ after_transition [:created, :pending, :running] => :success do |pipeline|
+ MergeRequests::MergeWhenBuildSucceedsService.new(pipeline.project, nil).trigger(pipeline)
+ end
+
+ after_transition any => :failed do |pipeline|
+ MergeRequests::AddTodoWhenBuildFailsService.new(pipeline.project, nil).execute(pipeline)
+ end
end
# ref can't be HEAD or SHA, can only be branch/tag name
@@ -251,9 +259,8 @@ module Ci
Ci::ProcessPipelineService.new(project, user).execute(self)
end
- def build_updated
+ def update_status
with_lock do
- reload
case latest_builds_status
when 'pending' then enqueue
when 'running' then run
diff --git a/app/models/commit_status.rb b/app/models/commit_status.rb
index 736db1ab0f6..3d5e449f403 100644
--- a/app/models/commit_status.rb
+++ b/app/models/commit_status.rb
@@ -74,10 +74,6 @@ class CommitStatus < ActiveRecord::Base
true
end
- after_transition do |commit_status, transition|
- commit_status.pipeline.try(:build_updated) unless transition.loopback?
- end
-
after_transition [:created, :pending, :running] => :success do |commit_status|
MergeRequests::MergeWhenBuildSucceedsService.new(commit_status.pipeline.project, nil).trigger(commit_status)
end
@@ -85,6 +81,16 @@ class CommitStatus < ActiveRecord::Base
after_transition any => :failed do |commit_status|
MergeRequests::AddTodoWhenBuildFailsService.new(commit_status.pipeline.project, nil).execute(commit_status)
end
+
+ after_transition do |commit_status, transition|
+ if commit_status.pipeline && !transition.loopback?
+ ProcessPipelineWorker.perform_async(
+ commit_status.pipeline.id,
+ process: HasStatus.COMPLETED_STATUSES.include?(commit_status.status))
+ end
+
+ true
+ end
end
delegate :sha, :short_sha, to: :pipeline
diff --git a/app/services/merge_requests/add_todo_when_build_fails_service.rb b/app/services/merge_requests/add_todo_when_build_fails_service.rb
index 566049525cb..45c73789886 100644
--- a/app/services/merge_requests/add_todo_when_build_fails_service.rb
+++ b/app/services/merge_requests/add_todo_when_build_fails_service.rb
@@ -1,15 +1,15 @@
module MergeRequests
class AddTodoWhenBuildFailsService < MergeRequests::BaseService
# Adds a todo to the parent merge_request when a CI build fails
- def execute(commit_status)
- each_merge_request(commit_status) do |merge_request|
+ def execute(pipeline)
+ each_merge_request(pipeline) do |merge_request|
todo_service.merge_request_build_failed(merge_request)
end
end
# Closes any pending build failed todos for the parent MRs when a build is retried
- def close(commit_status)
- each_merge_request(commit_status) do |merge_request|
+ def close(pipeline)
+ each_merge_request(pipeline) do |merge_request|
todo_service.merge_request_build_retried(merge_request)
end
end
diff --git a/app/services/merge_requests/base_service.rb b/app/services/merge_requests/base_service.rb
index d0d155b7ee1..95b4f0ff733 100644
--- a/app/services/merge_requests/base_service.rb
+++ b/app/services/merge_requests/base_service.rb
@@ -42,11 +42,11 @@ module MergeRequests
super(:merge_request)
end
- def merge_request_from(commit_status)
- branches = commit_status.ref
+ def merge_request_from(pipeline)
+ branches = pipeline.ref
# This is for ref-less builds
- branches ||= @project.repository.branch_names_contains(commit_status.sha)
+ branches ||= @project.repository.branch_names_contains(pipeline.sha)
return [] if branches.blank?
@@ -56,14 +56,11 @@ module MergeRequests
merge_requests.uniq.select(&:source_project)
end
- def each_merge_request(commit_status)
+ def each_merge_request(pipeline)
merge_request_from(commit_status).each do |merge_request|
- pipeline = merge_request.pipeline
+ next unless pipeline == merge_request.pipeline
- next unless pipeline
- next unless pipeline.sha == commit_status.sha
-
- yield merge_request, pipeline
+ yield merge_request
end
end
end
diff --git a/app/services/merge_requests/merge_when_build_succeeds_service.rb b/app/services/merge_requests/merge_when_build_succeeds_service.rb
index 4ad5fb08311..60d6085f9eb 100644
--- a/app/services/merge_requests/merge_when_build_succeeds_service.rb
+++ b/app/services/merge_requests/merge_when_build_succeeds_service.rb
@@ -19,11 +19,12 @@ module MergeRequests
end
# Triggers the automatic merge of merge_request once the build succeeds
- def trigger(commit_status)
- each_merge_request(commit_status) do |merge_request, pipeline|
+ def trigger(pipeline)
+ return unless pipeline.success?
+
+ each_merge_request(pipeline) do |merge_request|
next unless merge_request.merge_when_build_succeeds?
next unless merge_request.mergeable?
- next unless pipeline.success?
MergeWorker.perform_async(merge_request.id, merge_request.merge_user_id, merge_request.merge_params)
end
diff --git a/app/workers/process_pipeline_worker.rb b/app/workers/process_pipeline_worker.rb
new file mode 100644
index 00000000000..fb59a1efb7a
--- /dev/null
+++ b/app/workers/process_pipeline_worker.rb
@@ -0,0 +1,17 @@
+class ProcessPipelineWorker
+ include Sidekiq::Worker
+
+ sidekiq_options queue: :default
+
+ def perform(pipeline_id, params)
+ begin
+ pipeline = Ci::Pipeline.find(pipeline_id)
+ rescue ActiveRecord::RecordNotFound
+ return
+ end
+
+ pipeline.process! if params[:process]
+
+ pipeline.update_status
+ end
+end