diff options
Diffstat (limited to 'spec/services/ci/update_instance_variables_service_spec.rb')
-rw-r--r-- | spec/services/ci/update_instance_variables_service_spec.rb | 230 |
1 files changed, 230 insertions, 0 deletions
diff --git a/spec/services/ci/update_instance_variables_service_spec.rb b/spec/services/ci/update_instance_variables_service_spec.rb new file mode 100644 index 00000000000..93f6e5d3ea8 --- /dev/null +++ b/spec/services/ci/update_instance_variables_service_spec.rb @@ -0,0 +1,230 @@ +# frozen_string_literal: true + +require 'spec_helper' + +describe Ci::UpdateInstanceVariablesService do + let(:params) { { variables_attributes: variables_attributes } } + + subject { described_class.new(params) } + + describe '#execute' do + context 'without variables' do + let(:variables_attributes) { [] } + + it { expect(subject.execute).to be_truthy } + end + + context 'with insert only variables' do + let(:variables_attributes) do + [ + { key: 'var_a', secret_value: 'dummy_value_for_a', protected: true }, + { key: 'var_b', secret_value: 'dummy_value_for_b', protected: false } + ] + end + + it { expect(subject.execute).to be_truthy } + + it 'persists all the records' do + expect { subject.execute } + .to change { Ci::InstanceVariable.count } + .by variables_attributes.size + end + + it 'persists attributes' do + subject.execute + + expect(Ci::InstanceVariable.all).to contain_exactly( + have_attributes(key: 'var_a', secret_value: 'dummy_value_for_a', protected: true), + have_attributes(key: 'var_b', secret_value: 'dummy_value_for_b', protected: false) + ) + end + end + + context 'with update only variables' do + let!(:var_a) { create(:ci_instance_variable) } + let!(:var_b) { create(:ci_instance_variable, protected: false) } + + let(:variables_attributes) do + [ + { + id: var_a.id, + key: var_a.key, + secret_value: 'new_dummy_value_for_a', + protected: var_a.protected?.to_s + }, + { + id: var_b.id, + key: 'var_b_key', + secret_value: 'new_dummy_value_for_b', + protected: 'true' + } + ] + end + + it { expect(subject.execute).to be_truthy } + + it 'does not change the count' do + expect { subject.execute } + .not_to change { Ci::InstanceVariable.count } + end + + it 'updates the records in place', :aggregate_failures do + subject.execute + + expect(var_a.reload).to have_attributes(secret_value: 'new_dummy_value_for_a') + + expect(var_b.reload).to have_attributes( + key: 'var_b_key', secret_value: 'new_dummy_value_for_b', protected: true) + end + end + + context 'with insert and update variables' do + let!(:var_a) { create(:ci_instance_variable) } + + let(:variables_attributes) do + [ + { + id: var_a.id, + key: var_a.key, + secret_value: 'new_dummy_value_for_a', + protected: var_a.protected?.to_s + }, + { + key: 'var_b', + secret_value: 'dummy_value_for_b', + protected: true + } + ] + end + + it { expect(subject.execute).to be_truthy } + + it 'inserts only one record' do + expect { subject.execute } + .to change { Ci::InstanceVariable.count }.by 1 + end + + it 'persists all the records', :aggregate_failures do + subject.execute + var_b = Ci::InstanceVariable.find_by(key: 'var_b') + + expect(var_a.reload.secret_value).to eq('new_dummy_value_for_a') + expect(var_b.secret_value).to eq('dummy_value_for_b') + end + end + + context 'with insert, update, and destroy variables' do + let!(:var_a) { create(:ci_instance_variable) } + let!(:var_b) { create(:ci_instance_variable) } + + let(:variables_attributes) do + [ + { + id: var_a.id, + key: var_a.key, + secret_value: 'new_dummy_value_for_a', + protected: var_a.protected?.to_s + }, + { + id: var_b.id, + key: var_b.key, + secret_value: 'dummy_value_for_b', + protected: var_b.protected?.to_s, + '_destroy' => 'true' + }, + { + key: 'var_c', + secret_value: 'dummy_value_for_c', + protected: true + } + ] + end + + it { expect(subject.execute).to be_truthy } + + it 'persists all the records', :aggregate_failures do + subject.execute + var_c = Ci::InstanceVariable.find_by(key: 'var_c') + + expect(var_a.reload.secret_value).to eq('new_dummy_value_for_a') + expect { var_b.reload }.to raise_error(ActiveRecord::RecordNotFound) + expect(var_c.secret_value).to eq('dummy_value_for_c') + end + end + + context 'with invalid variables' do + let!(:var_a) { create(:ci_instance_variable, secret_value: 'dummy_value_for_a') } + + let(:variables_attributes) do + [ + { + key: '...?', + secret_value: 'nice_value' + }, + { + id: var_a.id, + key: var_a.key, + secret_value: 'new_dummy_value_for_a', + protected: var_a.protected?.to_s + }, + { + key: var_a.key, + secret_value: 'other_value' + } + ] + end + + it { expect(subject.execute).to be_falsey } + + it 'does not insert any records' do + expect { subject.execute } + .not_to change { Ci::InstanceVariable.count } + end + + it 'does not update existing records' do + subject.execute + + expect(var_a.reload.secret_value).to eq('dummy_value_for_a') + end + + it 'returns errors' do + subject.execute + + expect(subject.errors).to match_array( + [ + "Key (#{var_a.key}) has already been taken", + "Key can contain only letters, digits and '_'." + ]) + end + end + + context 'when deleting non existing variables' do + let(:variables_attributes) do + [ + { + id: 'some-id', + key: 'some_key', + secret_value: 'other_value', + '_destroy' => 'true' + } + ] + end + + it { expect { subject.execute }.to raise_error(ActiveRecord::RecordNotFound) } + end + + context 'when updating non existing variables' do + let(:variables_attributes) do + [ + { + id: 'some-id', + key: 'some_key', + secret_value: 'other_value' + } + ] + end + + it { expect { subject.execute }.to raise_error(ActiveRecord::RecordNotFound) } + end + end +end |