Commit 42484f55 authored by Grzegorz Bizon's avatar Grzegorz Bizon

Merge branch 'mk/simplify-internal-post-receive-messages' into 'master'

Simplify internal post receive messages

Closes #59808

See merge request gitlab-org/gitlab-ce!31640
parents dc3adc3a 50342028
...@@ -1705,6 +1705,18 @@ module API ...@@ -1705,6 +1705,18 @@ module API
class ClusterGroup < Cluster class ClusterGroup < Cluster
expose :group, using: Entities::BasicGroupDetails expose :group, using: Entities::BasicGroupDetails
end end
module InternalPostReceive
class Message < Grape::Entity
expose :message
expose :type
end
class Response < Grape::Entity
expose :messages, using: Message
expose :reference_counter_decreased
end
end
end end
end end
......
...@@ -44,8 +44,6 @@ module API ...@@ -44,8 +44,6 @@ module API
end end
def process_mr_push_options(push_options, project, user, changes) def process_mr_push_options(push_options, project, user, changes)
output = {}
Gitlab::QueryLimiting.whitelist('https://gitlab.com/gitlab-org/gitlab-ce/issues/61359') Gitlab::QueryLimiting.whitelist('https://gitlab.com/gitlab-org/gitlab-ce/issues/61359')
service = ::MergeRequests::PushOptionsHandlerService.new( service = ::MergeRequests::PushOptionsHandlerService.new(
...@@ -56,15 +54,13 @@ module API ...@@ -56,15 +54,13 @@ module API
).execute ).execute
if service.errors.present? if service.errors.present?
output[:warnings] = push_options_warning(service.errors.join("\n\n")) push_options_warning(service.errors.join("\n\n"))
end end
output
end end
def push_options_warning(warning) def push_options_warning(warning)
options = Array.wrap(params[:push_options]).map { |p| "'#{p}'" }.join(' ') options = Array.wrap(params[:push_options]).map { |p| "'#{p}'" }.join(' ')
"Error encountered with push options #{options}: #{warning}" "WARNINGS:\nError encountered with push options #{options}: #{warning}"
end end
def redis_ping def redis_ping
......
...@@ -256,25 +256,26 @@ module API ...@@ -256,25 +256,26 @@ module API
post '/post_receive' do post '/post_receive' do
status 200 status 200
output = {} # Messages to gitlab-shell response = Gitlab::InternalPostReceive::Response.new
user = identify(params[:identifier]) user = identify(params[:identifier])
project = Gitlab::GlRepository.parse(params[:gl_repository]).first project = Gitlab::GlRepository.parse(params[:gl_repository]).first
push_options = Gitlab::PushOptions.new(params[:push_options]) push_options = Gitlab::PushOptions.new(params[:push_options])
response.reference_counter_decreased = Gitlab::ReferenceCounter.new(params[:gl_repository]).decrease
PostReceive.perform_async(params[:gl_repository], params[:identifier], PostReceive.perform_async(params[:gl_repository], params[:identifier],
params[:changes], push_options.as_json) params[:changes], push_options.as_json)
mr_options = push_options.get(:merge_request) mr_options = push_options.get(:merge_request)
output.merge!(process_mr_push_options(mr_options, project, user, params[:changes])) if mr_options.present? if mr_options.present?
message = process_mr_push_options(mr_options, project, user, params[:changes])
response.add_alert_message(message)
end
broadcast_message = BroadcastMessage.current&.last&.message broadcast_message = BroadcastMessage.current&.last&.message
reference_counter_decreased = Gitlab::ReferenceCounter.new(params[:gl_repository]).decrease response.add_alert_message(broadcast_message)
output.merge!( response.add_merge_request_urls(merge_request_urls)
broadcast_message: broadcast_message,
reference_counter_decreased: reference_counter_decreased,
merge_request_urls: merge_request_urls
)
# A user is not guaranteed to be returned; an orphaned write deploy # A user is not guaranteed to be returned; an orphaned write deploy
# key could be used # key could be used
...@@ -282,11 +283,11 @@ module API ...@@ -282,11 +283,11 @@ module API
redirect_message = Gitlab::Checks::ProjectMoved.fetch_message(user.id, project.id) redirect_message = Gitlab::Checks::ProjectMoved.fetch_message(user.id, project.id)
project_created_message = Gitlab::Checks::ProjectCreated.fetch_message(user.id, project.id) project_created_message = Gitlab::Checks::ProjectCreated.fetch_message(user.id, project.id)
output[:redirected_message] = redirect_message if redirect_message response.add_basic_message(redirect_message)
output[:project_created_message] = project_created_message if project_created_message response.add_basic_message(project_created_message)
end end
output present response, with: Entities::InternalPostReceive::Response
end end
end end
end end
......
# frozen_string_literal: true
module Gitlab
module InternalPostReceive
class Response
attr_accessor :reference_counter_decreased
attr_reader :messages
Message = Struct.new(:message, :type) do
def self.basic(text)
new(text, :basic)
end
def self.alert(text)
new(text, :alert)
end
end
def initialize
@messages = []
@reference_counter_decreased = false
end
def add_merge_request_urls(urls_data)
urls_data.each do |url_data|
add_merge_request_url(url_data)
end
end
def add_merge_request_url(url_data)
message = if url_data[:new_merge_request]
"To create a merge request for #{url_data[:branch_name]}, visit:"
else
"View merge request for #{url_data[:branch_name]}:"
end
message += "\n #{url_data[:url]}"
add_basic_message(message)
end
def add_basic_message(text)
@messages << Message.basic(text) if text.present?
end
def add_alert_message(text)
@messages.unshift(Message.alert(text)) if text.present?
end
end
end
end
# frozen_string_literal: true
require 'spec_helper'
describe Gitlab::InternalPostReceive::Response do
subject { described_class.new }
describe '#add_merge_request_urls' do
context 'when there are urls_data' do
it 'adds a message for each merge request URL' do
urls_data = [
{ new_merge_request: false, branch_name: 'foo', url: 'http://example.com/foo/bar/merge_requests/1' },
{ new_merge_request: true, branch_name: 'bar', url: 'http://example.com/foo/bar/merge_requests/new?merge_request%5Bsource_branch%5D=bar' }
]
subject.add_merge_request_urls(urls_data)
expected = [a_kind_of(described_class::Message), a_kind_of(described_class::Message)]
expect(subject.messages).to match(expected)
end
end
end
describe '#add_merge_request_url' do
context 'when :new_merge_request is false' do
it 'adds a basic message to view the existing merge request' do
url_data = { new_merge_request: false, branch_name: 'foo', url: 'http://example.com/foo/bar/merge_requests/1' }
subject.add_merge_request_url(url_data)
message = <<~MESSAGE.strip
View merge request for foo:
http://example.com/foo/bar/merge_requests/1
MESSAGE
expect(subject.messages.first.message).to eq(message)
expect(subject.messages.first.type).to eq(:basic)
end
end
context 'when :new_merge_request is true' do
it 'adds a basic message to create a new merge request' do
url_data = { new_merge_request: true, branch_name: 'bar', url: 'http://example.com/foo/bar/merge_requests/new?merge_request%5Bsource_branch%5D=bar' }
subject.add_merge_request_url(url_data)
message = <<~MESSAGE.strip
To create a merge request for bar, visit:
http://example.com/foo/bar/merge_requests/new?merge_request%5Bsource_branch%5D=bar
MESSAGE
expect(subject.messages.first.message).to eq(message)
expect(subject.messages.first.type).to eq(:basic)
end
end
end
describe '#add_basic_message' do
context 'when text is present' do
it 'adds a basic message' do
subject.add_basic_message('hello')
expect(subject.messages.first.message).to eq('hello')
expect(subject.messages.first.type).to eq(:basic)
end
end
context 'when text is blank' do
it 'does not add a message' do
subject.add_basic_message(' ')
expect(subject.messages).to be_blank
end
end
end
describe '#add_alert_message' do
context 'when text is present' do
it 'adds a alert message' do
subject.add_alert_message('hello')
expect(subject.messages.first.message).to eq('hello')
expect(subject.messages.first.type).to eq(:alert)
end
end
context 'when text is blank' do
it 'does not add a message' do
subject.add_alert_message(' ')
expect(subject.messages).to be_blank
end
end
end
describe '#reference_counter_decreased' do
context 'initially' do
it 'reference_counter_decreased is set to false' do
expect(subject.reference_counter_decreased).to eq(false)
end
end
end
describe '#reference_counter_decreased=' do
context 'when the argument is truthy' do
it 'reference_counter_decreased is truthy' do
subject.reference_counter_decreased = true
expect(subject.reference_counter_decreased).to be_truthy
end
end
context 'when the argument is falsey' do
it 'reference_counter_decreased is falsey' do
subject.reference_counter_decreased = false
expect(subject.reference_counter_decreased).to be_falsey
end
end
end
end
...@@ -925,19 +925,20 @@ describe API::Internal do ...@@ -925,19 +925,20 @@ describe API::Internal do
it 'returns link to create new merge request' do it 'returns link to create new merge request' do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(json_response['merge_request_urls']).to match [{ message = <<~MESSAGE.strip
"branch_name" => branch_name, To create a merge request for #{branch_name}, visit:
"url" => "http://#{Gitlab.config.gitlab.host}/#{project.full_path}/merge_requests/new?merge_request%5Bsource_branch%5D=#{branch_name}", http://#{Gitlab.config.gitlab.host}/#{project.full_path}/merge_requests/new?merge_request%5Bsource_branch%5D=#{branch_name}
"new_merge_request" => true MESSAGE
}]
expect(json_response['messages']).to include(build_basic_message(message))
end end
it 'returns empty array if printing_merge_request_link_enabled is false' do it 'returns no merge request messages if printing_merge_request_link_enabled is false' do
project.update!(printing_merge_request_link_enabled: false) project.update!(printing_merge_request_link_enabled: false)
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(json_response['merge_request_urls']).to eq([]) expect(json_response['messages']).to be_blank
end end
it 'does not invoke MergeRequests::PushOptionsHandlerService' do it 'does not invoke MergeRequests::PushOptionsHandlerService' do
...@@ -968,11 +969,12 @@ describe API::Internal do ...@@ -968,11 +969,12 @@ describe API::Internal do
it 'links to the newly created merge request' do it 'links to the newly created merge request' do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(json_response['merge_request_urls']).to match [{ message = <<~MESSAGE.strip
'branch_name' => branch_name, View merge request for #{branch_name}:
'url' => "http://#{Gitlab.config.gitlab.host}/#{project.full_path}/merge_requests/1", http://#{Gitlab.config.gitlab.host}/#{project.full_path}/merge_requests/1
'new_merge_request' => false MESSAGE
}]
expect(json_response['messages']).to include(build_basic_message(message))
end end
it 'adds errors on the service instance to warnings' do it 'adds errors on the service instance to warnings' do
...@@ -982,7 +984,8 @@ describe API::Internal do ...@@ -982,7 +984,8 @@ describe API::Internal do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(json_response['warnings']).to eq('Error encountered with push options \'merge_request.create\': my error') message = "WARNINGS:\nError encountered with push options 'merge_request.create': my error"
expect(json_response['messages']).to include(build_alert_message(message))
end end
it 'adds ActiveRecord errors on invalid MergeRequest records to warnings' do it 'adds ActiveRecord errors on invalid MergeRequest records to warnings' do
...@@ -995,38 +998,39 @@ describe API::Internal do ...@@ -995,38 +998,39 @@ describe API::Internal do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(json_response['warnings']).to eq('Error encountered with push options \'merge_request.create\': my error') message = "WARNINGS:\nError encountered with push options 'merge_request.create': my error"
expect(json_response['messages']).to include(build_alert_message(message))
end end
end end
context 'broadcast message exists' do context 'broadcast message exists' do
let!(:broadcast_message) { create(:broadcast_message, starts_at: 1.day.ago, ends_at: 1.day.from_now ) } let!(:broadcast_message) { create(:broadcast_message, starts_at: 1.day.ago, ends_at: 1.day.from_now ) }
it 'returns one broadcast message' do it 'outputs a broadcast message' do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(response).to have_gitlab_http_status(200) expect(response).to have_gitlab_http_status(200)
expect(json_response['broadcast_message']).to eq(broadcast_message.message) expect(json_response['messages']).to include(build_alert_message(broadcast_message.message))
end end
end end
context 'broadcast message does not exist' do context 'broadcast message does not exist' do
it 'returns empty string' do it 'does not output a broadcast message' do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(response).to have_gitlab_http_status(200) expect(response).to have_gitlab_http_status(200)
expect(json_response['broadcast_message']).to eq(nil) expect(has_alert_messages?(json_response['messages'])).to be_falsey
end end
end end
context 'nil broadcast message' do context 'nil broadcast message' do
it 'returns empty string' do it 'does not output a broadcast message' do
allow(BroadcastMessage).to receive(:current).and_return(nil) allow(BroadcastMessage).to receive(:current).and_return(nil)
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(response).to have_gitlab_http_status(200) expect(response).to have_gitlab_http_status(200)
expect(json_response['broadcast_message']).to eq(nil) expect(has_alert_messages?(json_response['messages'])).to be_falsey
end end
end end
...@@ -1038,8 +1042,7 @@ describe API::Internal do ...@@ -1038,8 +1042,7 @@ describe API::Internal do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(response).to have_gitlab_http_status(200) expect(response).to have_gitlab_http_status(200)
expect(json_response["redirected_message"]).to be_present expect(json_response['messages']).to include(build_basic_message(project_moved.message))
expect(json_response["redirected_message"]).to eq(project_moved.message)
end end
end end
...@@ -1051,8 +1054,7 @@ describe API::Internal do ...@@ -1051,8 +1054,7 @@ describe API::Internal do
post api('/internal/post_receive'), params: valid_params post api('/internal/post_receive'), params: valid_params
expect(response).to have_gitlab_http_status(200) expect(response).to have_gitlab_http_status(200)
expect(json_response["project_created_message"]).to be_present expect(json_response['messages']).to include(build_basic_message(project_created.message))
expect(json_response["project_created_message"]).to eq(project_created.message)
end end
end end
...@@ -1172,4 +1174,18 @@ describe API::Internal do ...@@ -1172,4 +1174,18 @@ describe API::Internal do
} }
) )
end end
def build_alert_message(message)
{ 'type' => 'alert', 'message' => message }
end
def build_basic_message(message)
{ 'type' => 'basic', 'message' => message }
end
def has_alert_messages?(messages)
messages.any? do |message|
message['type'] == 'alert'
end
end
end end
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