diff options
Diffstat (limited to 'spec/models/ci')
-rw-r--r-- | spec/models/ci/build_spec.rb | 68 | ||||
-rw-r--r-- | spec/models/ci/job_artifact_spec.rb | 16 | ||||
-rw-r--r-- | spec/models/ci/pipeline_spec.rb | 10 | ||||
-rw-r--r-- | spec/models/ci/processable_spec.rb | 161 | ||||
-rw-r--r-- | spec/models/ci/runner_spec.rb | 30 |
5 files changed, 149 insertions, 136 deletions
diff --git a/spec/models/ci/build_spec.rb b/spec/models/ci/build_spec.rb index ff9f26faad3..5e9226989a5 100644 --- a/spec/models/ci/build_spec.rb +++ b/spec/models/ci/build_spec.rb @@ -2280,6 +2280,7 @@ describe Ci::Build do { key: 'CI_REGISTRY_USER', value: 'gitlab-ci-token', public: true, masked: false }, { key: 'CI_REGISTRY_PASSWORD', value: 'my-token', public: false, masked: true }, { key: 'CI_REPOSITORY_URL', value: build.repo_url, public: false, masked: false }, + { key: 'CI_JOB_JWT', value: 'ci.job.jwt', public: false, masked: true }, { key: 'CI_JOB_NAME', value: 'test', public: true, masked: false }, { key: 'CI_JOB_STAGE', value: 'test', public: true, masked: false }, { key: 'CI_NODE_TOTAL', value: '1', public: true, masked: false }, @@ -2332,23 +2333,36 @@ describe Ci::Build do end before do + allow(Gitlab::Ci::Jwt).to receive(:for_build).with(build).and_return('ci.job.jwt') build.set_token('my-token') build.yaml_variables = [] end it { is_expected.to eq(predefined_variables) } + context 'when ci_job_jwt feature flag is disabled' do + before do + stub_feature_flags(ci_job_jwt: false) + end + + it 'CI_JOB_JWT is not included' do + expect(subject.pluck(:key)).not_to include('CI_JOB_JWT') + end + end + describe 'variables ordering' do context 'when variables hierarchy is stubbed' do let(:build_pre_var) { { key: 'build', value: 'value', public: true, masked: false } } let(:project_pre_var) { { key: 'project', value: 'value', public: true, masked: false } } let(:pipeline_pre_var) { { key: 'pipeline', value: 'value', public: true, masked: false } } let(:build_yaml_var) { { key: 'yaml', value: 'value', public: true, masked: false } } + let(:job_jwt_var) { { key: 'CI_JOB_JWT', value: 'ci.job.jwt', public: false, masked: true } } before do allow(build).to receive(:predefined_variables) { [build_pre_var] } allow(build).to receive(:yaml_variables) { [build_yaml_var] } allow(build).to receive(:persisted_variables) { [] } + allow(build).to receive(:job_jwt_variables) { [job_jwt_var] } allow_any_instance_of(Project) .to receive(:predefined_variables) { [project_pre_var] } @@ -2361,7 +2375,8 @@ describe Ci::Build do it 'returns variables in order depending on resource hierarchy' do is_expected.to eq( - [build_pre_var, + [job_jwt_var, + build_pre_var, project_pre_var, pipeline_pre_var, build_yaml_var, @@ -3797,8 +3812,13 @@ describe Ci::Build do create(:ci_job_artifact, :junit_with_corrupted_data, job: build, project: build.project) end - it 'raises an error' do - expect { subject }.to raise_error(Gitlab::Ci::Parsers::Test::Junit::JunitParserError) + it 'returns no test data and includes a suite_error message' do + expect { subject }.not_to raise_error + + expect(test_reports.get_suite(build.name).total_count).to eq(0) + expect(test_reports.get_suite(build.name).success_count).to eq(0) + expect(test_reports.get_suite(build.name).failed_count).to eq(0) + expect(test_reports.get_suite(build.name).suite_error).to eq('JUnit XML parsing failed: 1:1: FATAL: Document is empty') end end end @@ -3851,6 +3871,48 @@ describe Ci::Build do end end + describe '#collect_terraform_reports!' do + let(:terraform_reports) { Gitlab::Ci::Reports::TerraformReports.new } + + it 'returns an empty hash' do + expect(build.collect_terraform_reports!(terraform_reports).plans).to eq({}) + end + + context 'when build has a terraform report' do + context 'when there is a valid tfplan.json' do + before do + create(:ci_job_artifact, :terraform, job: build, project: build.project) + end + + it 'parses blobs and add the results to the terraform report' do + expect { build.collect_terraform_reports!(terraform_reports) }.not_to raise_error + + expect(terraform_reports.plans).to match( + a_hash_including( + 'tfplan.json' => a_hash_including( + 'create' => 0, + 'update' => 1, + 'delete' => 0 + ) + ) + ) + end + end + + context 'when there is an invalid tfplan.json' do + before do + create(:ci_job_artifact, :terraform_with_corrupted_data, job: build, project: build.project) + end + + it 'raises an error' do + expect { build.collect_terraform_reports!(terraform_reports) }.to raise_error( + Gitlab::Ci::Parsers::Terraform::Tfplan::TfplanParserError + ) + end + end + end + end + describe '#report_artifacts' do subject { build.report_artifacts } diff --git a/spec/models/ci/job_artifact_spec.rb b/spec/models/ci/job_artifact_spec.rb index 6f6ff3704b4..f9e33657ca3 100644 --- a/spec/models/ci/job_artifact_spec.rb +++ b/spec/models/ci/job_artifact_spec.rb @@ -86,6 +86,22 @@ describe Ci::JobArtifact do end end + describe '.terraform_reports' do + context 'when there is a terraform report' do + it 'return the job artifact' do + artifact = create(:ci_job_artifact, :terraform) + + expect(described_class.terraform_reports).to eq([artifact]) + end + end + + context 'when there are no terraform reports' do + it 'return the an empty array' do + expect(described_class.terraform_reports).to eq([]) + end + end + end + describe '.erasable' do subject { described_class.erasable } diff --git a/spec/models/ci/pipeline_spec.rb b/spec/models/ci/pipeline_spec.rb index 90412136c1d..c9eddd76a24 100644 --- a/spec/models/ci/pipeline_spec.rb +++ b/spec/models/ci/pipeline_spec.rb @@ -364,6 +364,16 @@ describe Ci::Pipeline, :mailer do end end + context 'when pipeline has a terraform report' do + it 'selects the pipeline' do + pipeline_with_report = create(:ci_pipeline, :with_terraform_reports) + + expect(described_class.with_reports(Ci::JobArtifact.terraform_reports)).to eq( + [pipeline_with_report] + ) + end + end + context 'when pipeline does not have metrics reports' do subject { described_class.with_reports(Ci::JobArtifact.test_reports) } diff --git a/spec/models/ci/processable_spec.rb b/spec/models/ci/processable_spec.rb index 4490371bde5..d57b962c972 100644 --- a/spec/models/ci/processable_spec.rb +++ b/spec/models/ci/processable_spec.rb @@ -6,16 +6,12 @@ describe Ci::Processable do let_it_be(:project) { create(:project) } let_it_be(:pipeline) { create(:ci_pipeline, project: project) } - let_it_be(:detached_merge_request_pipeline) do - create(:ci_pipeline, :detached_merge_request_pipeline, :with_job, project: project) - end - - let_it_be(:legacy_detached_merge_request_pipeline) do - create(:ci_pipeline, :legacy_detached_merge_request_pipeline, :with_job, project: project) - end + describe 'delegations' do + subject { Ci::Processable.new } - let_it_be(:merged_result_pipeline) do - create(:ci_pipeline, :merged_result_pipeline, :with_job, project: project) + it { is_expected.to delegate_method(:merge_request?).to(:pipeline) } + it { is_expected.to delegate_method(:merge_request_ref?).to(:pipeline) } + it { is_expected.to delegate_method(:legacy_detached_merge_request_pipeline?).to(:pipeline) } end describe '#aggregated_needs_names' do @@ -52,69 +48,34 @@ describe Ci::Processable do end describe 'validate presence of scheduling_type' do - context 'on create' do - let(:processable) do - build( - :ci_build, :created, project: project, pipeline: pipeline, - importing: importing, scheduling_type: nil - ) - end - - context 'when importing' do - let(:importing) { true } - - context 'when validate_scheduling_type_of_processables is true' do - before do - stub_feature_flags(validate_scheduling_type_of_processables: true) - end + using RSpec::Parameterized::TableSyntax - it 'does not validate' do - expect(processable).to be_valid - end - end + subject { build(:ci_build, project: project, pipeline: pipeline, importing: importing) } - context 'when validate_scheduling_type_of_processables is false' do - before do - stub_feature_flags(validate_scheduling_type_of_processables: false) - end + where(:importing, :validate_scheduling_type_flag, :should_validate) do + false | true | true + false | false | false + true | true | false + true | false | false + end - it 'does not validate' do - expect(processable).to be_valid - end - end + with_them do + before do + stub_feature_flags(validate_scheduling_type_of_processables: validate_scheduling_type_flag) end - context 'when not importing' do - let(:importing) { false } - - context 'when validate_scheduling_type_of_processables is true' do - before do - stub_feature_flags(validate_scheduling_type_of_processables: true) - end - - it 'validates' do - expect(processable).not_to be_valid - end - end - - context 'when validate_scheduling_type_of_processables is false' do - before do - stub_feature_flags(validate_scheduling_type_of_processables: false) - end - - it 'does not validate' do - expect(processable).to be_valid + context 'on create' do + it 'validates presence' do + if should_validate + is_expected.to validate_presence_of(:scheduling_type).on(:create) + else + is_expected.not_to validate_presence_of(:scheduling_type).on(:create) end end end - end - context 'on update' do - let(:processable) { create(:ci_build, :created, project: project, pipeline: pipeline) } - - it 'does not validate' do - processable.scheduling_type = nil - expect(processable).to be_valid + context 'on update' do + it { is_expected.not_to validate_presence_of(:scheduling_type).on(:update) } end end end @@ -147,6 +108,8 @@ describe Ci::Processable do describe '#needs_attributes' do let(:build) { create(:ci_build, :created, project: project, pipeline: pipeline) } + subject { build.needs_attributes } + context 'with needs' do before do create(:ci_build_need, build: build, name: 'test1') @@ -154,7 +117,7 @@ describe Ci::Processable do end it 'returns all needs attributes' do - expect(build.needs_attributes).to contain_exactly( + is_expected.to contain_exactly( { 'artifacts' => true, 'name' => 'test1' }, { 'artifacts' => true, 'name' => 'test2' } ) @@ -162,75 +125,7 @@ describe Ci::Processable do end context 'without needs' do - it 'returns all needs attributes' do - expect(build.needs_attributes).to be_empty - end - end - end - - describe '#merge_request?' do - subject { pipeline.processables.first.merge_request? } - - context 'in a detached merge request pipeline' do - let(:pipeline) { detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.merge_request?) } - end - - context 'in a legacy detached merge_request_pipeline' do - let(:pipeline) { legacy_detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.merge_request?) } - end - - context 'in a pipeline for merged results' do - let(:pipeline) { merged_result_pipeline } - - it { is_expected.to eq(pipeline.merge_request?) } - end - end - - describe '#merge_request_ref?' do - subject { pipeline.processables.first.merge_request_ref? } - - context 'in a detached merge request pipeline' do - let(:pipeline) { detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.merge_request_ref?) } - end - - context 'in a legacy detached merge_request_pipeline' do - let(:pipeline) { legacy_detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.merge_request_ref?) } - end - - context 'in a pipeline for merged results' do - let(:pipeline) { merged_result_pipeline } - - it { is_expected.to eq(pipeline.merge_request_ref?) } - end - end - - describe '#legacy_detached_merge_request_pipeline?' do - subject { pipeline.processables.first.legacy_detached_merge_request_pipeline? } - - context 'in a detached merge request pipeline' do - let(:pipeline) { detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.legacy_detached_merge_request_pipeline?) } - end - - context 'in a legacy detached merge_request_pipeline' do - let(:pipeline) { legacy_detached_merge_request_pipeline } - - it { is_expected.to eq(pipeline.legacy_detached_merge_request_pipeline?) } - end - - context 'in a pipeline for merged results' do - let(:pipeline) { merged_result_pipeline } - - it { is_expected.to eq(pipeline.legacy_detached_merge_request_pipeline?) } + it { is_expected.to be_empty } end end end diff --git a/spec/models/ci/runner_spec.rb b/spec/models/ci/runner_spec.rb index b8034ba5bf2..2dedff7f15b 100644 --- a/spec/models/ci/runner_spec.rb +++ b/spec/models/ci/runner_spec.rb @@ -78,6 +78,36 @@ describe Ci::Runner do .to raise_error(ActiveRecord::RecordInvalid) end end + + context 'cost factors validations' do + it 'dissalows :private_projects_minutes_cost_factor being nil' do + runner = build(:ci_runner, private_projects_minutes_cost_factor: nil) + + expect(runner).to be_invalid + expect(runner.errors.full_messages).to include('Private projects minutes cost factor needs to be non-negative') + end + + it 'dissalows :public_projects_minutes_cost_factor being nil' do + runner = build(:ci_runner, public_projects_minutes_cost_factor: nil) + + expect(runner).to be_invalid + expect(runner.errors.full_messages).to include('Public projects minutes cost factor needs to be non-negative') + end + + it 'dissalows :private_projects_minutes_cost_factor being negative' do + runner = build(:ci_runner, private_projects_minutes_cost_factor: -1.1) + + expect(runner).to be_invalid + expect(runner.errors.full_messages).to include('Private projects minutes cost factor needs to be non-negative') + end + + it 'dissalows :public_projects_minutes_cost_factor being negative' do + runner = build(:ci_runner, public_projects_minutes_cost_factor: -2.2) + + expect(runner).to be_invalid + expect(runner.errors.full_messages).to include('Public projects minutes cost factor needs to be non-negative') + end + end end describe 'constraints' do |