Commit 30ca3ca7 authored by Balasankar "Balu" C's avatar Balasankar "Balu" C

Support CI variables to pased via git push options

Signed-off-by: default avatarBalasankar "Balu" C <balasankar@gitlab.com>
parent 9549fa1a
...@@ -85,12 +85,36 @@ module Git ...@@ -85,12 +85,36 @@ module Git
before: oldrev, before: oldrev,
after: newrev, after: newrev,
ref: ref, ref: ref,
variables_attributes: generate_vars_from_push_options || [],
push_options: params[:push_options] || {}, push_options: params[:push_options] || {},
checkout_sha: Gitlab::DataBuilder::Push.checkout_sha( checkout_sha: Gitlab::DataBuilder::Push.checkout_sha(
project.repository, newrev, ref) project.repository, newrev, ref)
} }
end end
def ci_variables_from_push_options
strong_memoize(:ci_variables_from_push_options) do
params[:push_options]&.deep_symbolize_keys&.dig(:ci, :variable)
end
end
def generate_vars_from_push_options
return [] unless ci_variables_from_push_options
ci_variables_from_push_options.map do |var_definition, _count|
key, value = var_definition.to_s.split("=", 2)
# Accept only valid format. We ignore the following formats
# 1. "=123". In this case, `key` will be an empty string
# 2. "FOO". In this case, `value` will be nil.
# However, the format "FOO=" will result in key beign `FOO` and value
# being an empty string. This is acceptable.
next if key.blank? || value.nil?
{ "key" => key, "variable_type" => "env_var", "secret_value" => value }
end.compact
end
def push_data_params(commits:, with_changed_files: true) def push_data_params(commits:, with_changed_files: true)
{ {
oldrev: oldrev, oldrev: oldrev,
......
---
title: Support passing CI variables via git push options
merge_request: 20255
author:
type: added
...@@ -16,11 +16,12 @@ module Gitlab ...@@ -16,11 +16,12 @@ module Gitlab
] ]
}, },
ci: { ci: {
keys: [:skip] keys: [:skip, :variable]
} }
}).freeze }).freeze
MULTI_VALUE_OPTIONS = [ MULTI_VALUE_OPTIONS = [
%w[ci variable],
%w[merge_request label], %w[merge_request label],
%w[merge_request unlabel] %w[merge_request unlabel]
].freeze ].freeze
......
...@@ -11,6 +11,7 @@ describe Git::BaseHooksService do ...@@ -11,6 +11,7 @@ describe Git::BaseHooksService do
let(:oldrev) { Gitlab::Git::BLANK_SHA } let(:oldrev) { Gitlab::Git::BLANK_SHA }
let(:newrev) { "8a2a6eb295bb170b34c24c76c49ed0e9b2eaf34b" } # gitlab-test: git rev-parse refs/tags/v1.1.0 let(:newrev) { "8a2a6eb295bb170b34c24c76c49ed0e9b2eaf34b" } # gitlab-test: git rev-parse refs/tags/v1.1.0
let(:ref) { 'refs/tags/v1.1.0' } let(:ref) { 'refs/tags/v1.1.0' }
let(:checkout_sha) { '5937ac0a7beb003549fc5fd26fc247adbce4a52e' }
let(:test_service) do let(:test_service) do
Class.new(described_class) do Class.new(described_class) do
...@@ -131,4 +132,104 @@ describe Git::BaseHooksService do ...@@ -131,4 +132,104 @@ describe Git::BaseHooksService do
end end
end end
end end
describe 'Generating CI variables from push options' do
let(:pipeline_params) do
{
after: newrev,
before: oldrev,
checkout_sha: checkout_sha,
push_options: push_options, # defined in each context
ref: ref,
variables_attributes: variables_attributes # defined in each context
}
end
shared_examples 'creates pipeline with params and expected variables' do
it 'calls the create pipeline service' do
expect(Ci::CreatePipelineService)
.to receive(:new)
.with(project, user, pipeline_params)
.and_return(double(execute!: true))
subject.execute
end
end
context 'with empty push options' do
let(:push_options) { {} }
let(:variables_attributes) { [] }
it_behaves_like 'creates pipeline with params and expected variables'
end
context 'with push options not specifying variables' do
let(:push_options) do
{
mr: {
create: true
}
}
end
let(:variables_attributes) { [] }
before do
params[:push_options] = push_options
end
it_behaves_like 'creates pipeline with params and expected variables'
end
context 'with push options specifying variables' do
let(:push_options) do
{
ci: {
variable: {
"FOO=123": 1,
"BAR=456": 1,
"MNO=890=ABC": 1
}
}
}
end
let(:variables_attributes) do
[
{ "key" => "FOO", "variable_type" => "env_var", "secret_value" => "123" },
{ "key" => "BAR", "variable_type" => "env_var", "secret_value" => "456" },
{ "key" => "MNO", "variable_type" => "env_var", "secret_value" => "890=ABC" }
]
end
before do
params[:push_options] = push_options
end
it_behaves_like 'creates pipeline with params and expected variables'
end
context 'with push options not specifying variables in correct format' do
let(:push_options) do
{
ci: {
variable: {
"FOO=123": 1,
"BAR": 1,
"=MNO": 1
}
}
}
end
let(:variables_attributes) do
[
{ "key" => "FOO", "variable_type" => "env_var", "secret_value" => "123" }
]
end
before do
params[:push_options] = push_options
end
it_behaves_like 'creates pipeline with params and expected variables'
end
end
end end
...@@ -86,6 +86,7 @@ describe Git::BranchPushService, services: true do ...@@ -86,6 +86,7 @@ describe Git::BranchPushService, services: true do
after: newrev, after: newrev,
ref: ref, ref: ref,
checkout_sha: SeedRepo::Commit::ID, checkout_sha: SeedRepo::Commit::ID,
variables_attributes: [],
push_options: {} push_options: {}
}).and_call_original }).and_call_original
......
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