diff options
author | Shinya Maeda <shinya@gitlab.com> | 2017-11-07 19:46:53 +0300 |
---|---|---|
committer | Shinya Maeda <shinya@gitlab.com> | 2017-11-07 19:46:53 +0300 |
commit | 4fac95a64d0c04599af9c762edb94414d85bf42f (patch) | |
tree | b87775aff426603984bc547208860ad147fcff69 /spec | |
parent | 02878cd958557128cd9c22b27bd2fb97a843266b (diff) | |
parent | 396f45ade1dddec36df9861f8a1bb80aabd2ff15 (diff) |
Merge branch 'master' into 38464-k8s-apps
Diffstat (limited to 'spec')
19 files changed, 303 insertions, 211 deletions
diff --git a/spec/controllers/concerns/issuable_collections_spec.rb b/spec/controllers/concerns/issuable_collections_spec.rb index c9687af4dd2..cd3bf785d34 100644 --- a/spec/controllers/concerns/issuable_collections_spec.rb +++ b/spec/controllers/concerns/issuable_collections_spec.rb @@ -17,60 +17,6 @@ describe IssuableCollections do controller end - describe '#redirect_out_of_range' do - before do - allow(controller).to receive(:url_for) - end - - it 'returns true and redirects if the offset is out of range' do - relation = double(:relation, current_page: 10) - - expect(controller).to receive(:redirect_to) - expect(controller.send(:redirect_out_of_range, relation, 2)).to eq(true) - end - - it 'returns false if the offset is not out of range' do - relation = double(:relation, current_page: 1) - - expect(controller).not_to receive(:redirect_to) - expect(controller.send(:redirect_out_of_range, relation, 2)).to eq(false) - end - end - - describe '#issues_page_count' do - it 'returns the number of issue pages' do - project = create(:project, :public) - - create(:issue, project: project) - - finder = IssuesFinder.new(user) - issues = finder.execute - - allow(controller).to receive(:issues_finder) - .and_return(finder) - - expect(controller.send(:issues_page_count, issues)).to eq(1) - end - end - - describe '#merge_requests_page_count' do - it 'returns the number of merge request pages' do - project = create(:project, :public) - - create(:merge_request, source_project: project, target_project: project) - - finder = MergeRequestsFinder.new(user) - merge_requests = finder.execute - - allow(controller).to receive(:merge_requests_finder) - .and_return(finder) - - pages = controller.send(:merge_requests_page_count, merge_requests) - - expect(pages).to eq(1) - end - end - describe '#page_count_for_relation' do it 'returns the number of pages' do relation = double(:relation, limit_value: 20) diff --git a/spec/controllers/projects/refs_controller_spec.rb b/spec/controllers/projects/refs_controller_spec.rb index 3a3e7467ef2..748ae040928 100644 --- a/spec/controllers/projects/refs_controller_spec.rb +++ b/spec/controllers/projects/refs_controller_spec.rb @@ -23,12 +23,15 @@ describe Projects::RefsController do xhr :get, :logs_tree, namespace_id: project.namespace.to_param, - project_id: project, id: 'master', - path: 'foo/bar/baz.html', format: format + project_id: project, + id: 'master', + path: 'foo/bar/baz.html', + format: format end it 'never throws MissingTemplate' do expect { default_get }.not_to raise_error + expect { xhr_get(:json) }.not_to raise_error expect { xhr_get }.not_to raise_error end @@ -42,5 +45,12 @@ describe Projects::RefsController do xhr_get(:js) expect(response).to be_success end + + it 'renders JSON' do + xhr_get(:json) + + expect(response).to be_success + expect(json_response).to be_kind_of(Array) + end end end diff --git a/spec/factories/commit_statuses.rb b/spec/factories/commit_statuses.rb index 169590deb8e..abbe37df90e 100644 --- a/spec/factories/commit_statuses.rb +++ b/spec/factories/commit_statuses.rb @@ -1,6 +1,7 @@ FactoryGirl.define do factory :commit_status, class: CommitStatus do name 'default' + stage 'test' status 'success' description 'commit status' pipeline factory: :ci_pipeline_with_one_job diff --git a/spec/features/projects/commit/mini_pipeline_graph_spec.rb b/spec/features/projects/commit/mini_pipeline_graph_spec.rb index 807a2189cc4..91282063a8d 100644 --- a/spec/features/projects/commit/mini_pipeline_graph_spec.rb +++ b/spec/features/projects/commit/mini_pipeline_graph_spec.rb @@ -12,6 +12,13 @@ feature 'Mini Pipeline Graph in Commit View', :js do end let(:build) { create(:ci_build, pipeline: pipeline) } + it 'display icon with status' do + build.run + visit project_commit_path(project, project.commit.id) + + expect(page).to have_selector('.ci-status-icon-running') + end + it 'displays a mini pipeline graph' do build.run visit project_commit_path(project, project.commit.id) diff --git a/spec/features/projects/import_export/test_project_export.tar.gz b/spec/features/projects/import_export/test_project_export.tar.gz Binary files differindex 9614c72cdc3..fb6a3b8e733 100644 --- a/spec/features/projects/import_export/test_project_export.tar.gz +++ b/spec/features/projects/import_export/test_project_export.tar.gz diff --git a/spec/features/projects/tree/create_directory_spec.rb b/spec/features/projects/tree/create_directory_spec.rb index 8ee7b9cf015..1686e7fa342 100644 --- a/spec/features/projects/tree/create_directory_spec.rb +++ b/spec/features/projects/tree/create_directory_spec.rb @@ -31,10 +31,5 @@ feature 'Multi-file editor new directory', :js do click_button('Commit 1 file') expect(page).to have_selector('td', text: 'commit message') - - click_link('foldername') - - expect(page).to have_selector('td', text: 'commit message', count: 2) - expect(page).to have_selector('td', text: '.gitkeep') end end diff --git a/spec/javascripts/repo/components/repo_file_spec.js b/spec/javascripts/repo/components/repo_file_spec.js index c45f8a18d1f..bf9181fb09c 100644 --- a/spec/javascripts/repo/components/repo_file_spec.js +++ b/spec/javascripts/repo/components/repo_file_spec.js @@ -20,7 +20,7 @@ describe('RepoFile', () => { resetStore(vm.$store); }); - it('renders link, icon, name and last commit details', () => { + it('renders link, icon and name', () => { const RepoFile = Vue.extend(repoFile); vm = new RepoFile({ store, @@ -37,10 +37,9 @@ describe('RepoFile', () => { expect(vm.$el.querySelector(`.${vm.file.icon}`).style.marginLeft).toEqual('0px'); expect(name.href).toMatch(`/${vm.file.url}`); expect(name.textContent.trim()).toEqual(vm.file.name); - expect(vm.$el.querySelector('.commit-message').textContent.trim()).toBe(vm.file.lastCommit.message); - expect(vm.$el.querySelector('.commit-update').textContent.trim()).toBe(updated); expect(fileIcon.classList.contains(vm.file.icon)).toBeTruthy(); expect(fileIcon.style.marginLeft).toEqual(`${vm.file.level * 10}px`); + expect(vm.$el.querySelectorAll('.animation-container').length).toBe(2); }); it('does render if hasFiles is true and is loading tree', () => { diff --git a/spec/javascripts/smart_interval_spec.js b/spec/javascripts/smart_interval_spec.js index 7833bf3fb04..1c87fcec245 100644 --- a/spec/javascripts/smart_interval_spec.js +++ b/spec/javascripts/smart_interval_spec.js @@ -1,6 +1,6 @@ -import '~/smart_interval'; +import SmartInterval from '~/smart_interval'; -(() => { +describe('SmartInterval', function () { const DEFAULT_MAX_INTERVAL = 100; const DEFAULT_STARTING_INTERVAL = 5; const DEFAULT_SHORT_TIMEOUT = 75; @@ -9,7 +9,7 @@ import '~/smart_interval'; function createDefaultSmartInterval(config) { const defaultParams = { - callback: () => {}, + callback: () => Promise.resolve(), startingInterval: DEFAULT_STARTING_INTERVAL, maxInterval: DEFAULT_MAX_INTERVAL, incrementByFactorOf: DEFAULT_INCREMENT_FACTOR, @@ -22,158 +22,171 @@ import '~/smart_interval'; _.extend(defaultParams, config); } - return new gl.SmartInterval(defaultParams); + return new SmartInterval(defaultParams); } - describe('SmartInterval', function () { - describe('Increment Interval', function () { - beforeEach(function () { - this.smartInterval = createDefaultSmartInterval(); - }); + describe('Increment Interval', function () { + beforeEach(function () { + this.smartInterval = createDefaultSmartInterval(); + }); - it('should increment the interval delay', function (done) { - const interval = this.smartInterval; - setTimeout(() => { - const intervalConfig = this.smartInterval.cfg; - const iterationCount = 4; - const maxIntervalAfterIterations = intervalConfig.startingInterval * - (intervalConfig.incrementByFactorOf ** (iterationCount - 1)); // 40 - const currentInterval = interval.getCurrentInterval(); - - // Provide some flexibility for performance of testing environment - expect(currentInterval).toBeGreaterThan(intervalConfig.startingInterval); - expect(currentInterval <= maxIntervalAfterIterations).toBeTruthy(); - - done(); - }, DEFAULT_SHORT_TIMEOUT); // 4 iterations, increment by 2x = (5 + 10 + 20 + 40) - }); + it('should increment the interval delay', function (done) { + const interval = this.smartInterval; + setTimeout(() => { + const intervalConfig = this.smartInterval.cfg; + const iterationCount = 4; + const maxIntervalAfterIterations = intervalConfig.startingInterval * + (intervalConfig.incrementByFactorOf ** (iterationCount - 1)); // 40 + const currentInterval = interval.getCurrentInterval(); + + // Provide some flexibility for performance of testing environment + expect(currentInterval).toBeGreaterThan(intervalConfig.startingInterval); + expect(currentInterval <= maxIntervalAfterIterations).toBeTruthy(); + + done(); + }, DEFAULT_SHORT_TIMEOUT); // 4 iterations, increment by 2x = (5 + 10 + 20 + 40) + }); - it('should not increment past maxInterval', function (done) { - const interval = this.smartInterval; + it('should not increment past maxInterval', function (done) { + const interval = this.smartInterval; - setTimeout(() => { - const currentInterval = interval.getCurrentInterval(); - expect(currentInterval).toBe(interval.cfg.maxInterval); + setTimeout(() => { + const currentInterval = interval.getCurrentInterval(); + expect(currentInterval).toBe(interval.cfg.maxInterval); - done(); - }, DEFAULT_LONG_TIMEOUT); - }); + done(); + }, DEFAULT_LONG_TIMEOUT); }); - describe('Public methods', function () { - beforeEach(function () { - this.smartInterval = createDefaultSmartInterval(); + it('does not increment while waiting for callback', function () { + jasmine.clock().install(); + + const smartInterval = createDefaultSmartInterval({ + callback: () => new Promise($.noop), }); - it('should cancel an interval', function (done) { - const interval = this.smartInterval; + jasmine.clock().tick(DEFAULT_SHORT_TIMEOUT); + + const oneInterval = smartInterval.cfg.startingInterval * DEFAULT_INCREMENT_FACTOR; + expect(smartInterval.getCurrentInterval()).toEqual(oneInterval); - setTimeout(() => { - interval.cancel(); + jasmine.clock().uninstall(); + }); + }); - const intervalId = interval.state.intervalId; - const currentInterval = interval.getCurrentInterval(); - const intervalLowerLimit = interval.cfg.startingInterval; + describe('Public methods', function () { + beforeEach(function () { + this.smartInterval = createDefaultSmartInterval(); + }); - expect(intervalId).toBeUndefined(); - expect(currentInterval).toBe(intervalLowerLimit); + it('should cancel an interval', function (done) { + const interval = this.smartInterval; - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + setTimeout(() => { + interval.cancel(); - it('should resume an interval', function (done) { - const interval = this.smartInterval; + const intervalId = interval.state.intervalId; + const currentInterval = interval.getCurrentInterval(); + const intervalLowerLimit = interval.cfg.startingInterval; - setTimeout(() => { - interval.cancel(); + expect(intervalId).toBeUndefined(); + expect(currentInterval).toBe(intervalLowerLimit); - interval.resume(); + done(); + }, DEFAULT_SHORT_TIMEOUT); + }); - const intervalId = interval.state.intervalId; + it('should resume an interval', function (done) { + const interval = this.smartInterval; - expect(intervalId).toBeTruthy(); + setTimeout(() => { + interval.cancel(); - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + interval.resume(); + + const intervalId = interval.state.intervalId; + + expect(intervalId).toBeTruthy(); + + done(); + }, DEFAULT_SHORT_TIMEOUT); }); + }); - describe('DOM Events', function () { - beforeEach(function () { - // This ensures DOM and DOM events are initialized for these specs. - setFixtures('<div></div>'); + describe('DOM Events', function () { + beforeEach(function () { + // This ensures DOM and DOM events are initialized for these specs. + setFixtures('<div></div>'); - this.smartInterval = createDefaultSmartInterval(); - }); + this.smartInterval = createDefaultSmartInterval(); + }); - it('should pause when page is not visible', function (done) { - const interval = this.smartInterval; + it('should pause when page is not visible', function (done) { + const interval = this.smartInterval; - setTimeout(() => { - expect(interval.state.intervalId).toBeTruthy(); + setTimeout(() => { + expect(interval.state.intervalId).toBeTruthy(); - // simulates triggering of visibilitychange event - interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); + // simulates triggering of visibilitychange event + interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); - expect(interval.state.intervalId).toBeUndefined(); - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + expect(interval.state.intervalId).toBeUndefined(); + done(); + }, DEFAULT_SHORT_TIMEOUT); + }); - it('should change to the hidden interval when page is not visible', function (done) { - const HIDDEN_INTERVAL = 1500; - const interval = createDefaultSmartInterval({ hiddenInterval: HIDDEN_INTERVAL }); + it('should change to the hidden interval when page is not visible', function (done) { + const HIDDEN_INTERVAL = 1500; + const interval = createDefaultSmartInterval({ hiddenInterval: HIDDEN_INTERVAL }); - setTimeout(() => { - expect(interval.state.intervalId).toBeTruthy(); - expect(interval.getCurrentInterval() >= DEFAULT_STARTING_INTERVAL && - interval.getCurrentInterval() <= DEFAULT_MAX_INTERVAL).toBeTruthy(); + setTimeout(() => { + expect(interval.state.intervalId).toBeTruthy(); + expect(interval.getCurrentInterval() >= DEFAULT_STARTING_INTERVAL && + interval.getCurrentInterval() <= DEFAULT_MAX_INTERVAL).toBeTruthy(); - // simulates triggering of visibilitychange event - interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); + // simulates triggering of visibilitychange event + interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); - expect(interval.state.intervalId).toBeTruthy(); - expect(interval.getCurrentInterval()).toBe(HIDDEN_INTERVAL); - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + expect(interval.state.intervalId).toBeTruthy(); + expect(interval.getCurrentInterval()).toBe(HIDDEN_INTERVAL); + done(); + }, DEFAULT_SHORT_TIMEOUT); + }); - it('should resume when page is becomes visible at the previous interval', function (done) { - const interval = this.smartInterval; + it('should resume when page is becomes visible at the previous interval', function (done) { + const interval = this.smartInterval; - setTimeout(() => { - expect(interval.state.intervalId).toBeTruthy(); + setTimeout(() => { + expect(interval.state.intervalId).toBeTruthy(); - // simulates triggering of visibilitychange event - interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); + // simulates triggering of visibilitychange event + interval.handleVisibilityChange({ target: { visibilityState: 'hidden' } }); - expect(interval.state.intervalId).toBeUndefined(); + expect(interval.state.intervalId).toBeUndefined(); - // simulates triggering of visibilitychange event - interval.handleVisibilityChange({ target: { visibilityState: 'visible' } }); + // simulates triggering of visibilitychange event + interval.handleVisibilityChange({ target: { visibilityState: 'visible' } }); - expect(interval.state.intervalId).toBeTruthy(); + expect(interval.state.intervalId).toBeTruthy(); - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + done(); + }, DEFAULT_SHORT_TIMEOUT); + }); - it('should cancel on page unload', function (done) { - const interval = this.smartInterval; + it('should cancel on page unload', function (done) { + const interval = this.smartInterval; - setTimeout(() => { - $(document).triggerHandler('beforeunload'); - expect(interval.state.intervalId).toBeUndefined(); - expect(interval.getCurrentInterval()).toBe(interval.cfg.startingInterval); - done(); - }, DEFAULT_SHORT_TIMEOUT); - }); + setTimeout(() => { + $(document).triggerHandler('beforeunload'); + expect(interval.state.intervalId).toBeUndefined(); + expect(interval.getCurrentInterval()).toBe(interval.cfg.startingInterval); + done(); + }, DEFAULT_SHORT_TIMEOUT); + }); - it('should execute callback before first interval', function () { - const interval = createDefaultSmartInterval({ immediateExecution: true }); - expect(interval.cfg.immediateExecution).toBeFalsy(); - }); + it('should execute callback before first interval', function () { + const interval = createDefaultSmartInterval({ immediateExecution: true }); + expect(interval.cfg.immediateExecution).toBeFalsy(); }); }); -})(window.gl || (window.gl = {})); +}); diff --git a/spec/javascripts/vue_mr_widget/mr_widget_options_spec.js b/spec/javascripts/vue_mr_widget/mr_widget_options_spec.js index e4324e91502..ba3721e7c84 100644 --- a/spec/javascripts/vue_mr_widget/mr_widget_options_spec.js +++ b/spec/javascripts/vue_mr_widget/mr_widget_options_spec.js @@ -121,24 +121,28 @@ describe('mrWidgetOptions', () => { describe('initPolling', () => { it('should call SmartInterval', () => { - spyOn(gl, 'SmartInterval').and.returnValue({ - resume() {}, - stopTimer() {}, - }); + spyOn(vm, 'checkStatus').and.returnValue(Promise.resolve()); + jasmine.clock().install(); vm.initPolling(); + expect(vm.checkStatus).not.toHaveBeenCalled(); + + jasmine.clock().tick(10000); + expect(vm.pollingInterval).toBeDefined(); - expect(gl.SmartInterval).toHaveBeenCalled(); + expect(vm.checkStatus).toHaveBeenCalled(); + + jasmine.clock().uninstall(); }); }); describe('initDeploymentsPolling', () => { it('should call SmartInterval', () => { - spyOn(gl, 'SmartInterval'); + spyOn(vm, 'fetchDeployments').and.returnValue(Promise.resolve()); vm.initDeploymentsPolling(); expect(vm.deploymentsInterval).toBeDefined(); - expect(gl.SmartInterval).toHaveBeenCalled(); + expect(vm.fetchDeployments).toHaveBeenCalled(); }); }); diff --git a/spec/javascripts/vue_shared/components/skeleton_loading_container_spec.js b/spec/javascripts/vue_shared/components/skeleton_loading_container_spec.js new file mode 100644 index 00000000000..a5db0b2c59e --- /dev/null +++ b/spec/javascripts/vue_shared/components/skeleton_loading_container_spec.js @@ -0,0 +1,49 @@ +import Vue from 'vue'; +import skeletonLoadingContainer from '~/vue_shared/components/skeleton_loading_container.vue'; +import mountComponent from '../../helpers/vue_mount_component_helper'; + +describe('Skeleton loading container', () => { + let vm; + + beforeEach(() => { + const component = Vue.extend(skeletonLoadingContainer); + vm = mountComponent(component); + }); + + afterEach(() => { + vm.$destroy(); + }); + + it('renders 6 skeleton lines by default', () => { + expect(vm.$el.querySelector('.skeleton-line-6')).not.toBeNull(); + }); + + it('renders in full mode by default', () => { + expect(vm.$el.classList.contains('animation-container-small')).toBeFalsy(); + }); + + describe('small', () => { + beforeEach((done) => { + vm.small = true; + + Vue.nextTick(done); + }); + + it('renders in small mode', () => { + expect(vm.$el.classList.contains('animation-container-small')).toBeTruthy(); + }); + }); + + describe('lines', () => { + beforeEach((done) => { + vm.lines = 5; + + Vue.nextTick(done); + }); + + it('renders 5 lines', () => { + expect(vm.$el.querySelector('.skeleton-line-5')).not.toBeNull(); + expect(vm.$el.querySelector('.skeleton-line-6')).toBeNull(); + }); + }); +}); diff --git a/spec/lib/gitlab/ci/status/build/factory_spec.rb b/spec/lib/gitlab/ci/status/build/factory_spec.rb index 2b32e47e9ba..d196bc6a4c2 100644 --- a/spec/lib/gitlab/ci/status/build/factory_spec.rb +++ b/spec/lib/gitlab/ci/status/build/factory_spec.rb @@ -84,7 +84,7 @@ describe Gitlab::Ci::Status::Build::Factory do it 'fabricates status with correct details' do expect(status.text).to eq 'failed' - expect(status.icon).to eq 'warning' + expect(status.icon).to eq 'status_warning' expect(status.favicon).to eq 'favicon_status_failed' expect(status.label).to eq 'failed (allowed to fail)' expect(status).to have_details diff --git a/spec/lib/gitlab/ci/status/build/failed_allowed_spec.rb b/spec/lib/gitlab/ci/status/build/failed_allowed_spec.rb index 79a65fc67e8..99a5a7e4aca 100644 --- a/spec/lib/gitlab/ci/status/build/failed_allowed_spec.rb +++ b/spec/lib/gitlab/ci/status/build/failed_allowed_spec.rb @@ -18,7 +18,7 @@ describe Gitlab::Ci::Status::Build::FailedAllowed do describe '#icon' do it 'returns a warning icon' do - expect(subject.icon).to eq 'warning' + expect(subject.icon).to eq 'status_warning' end end diff --git a/spec/lib/gitlab/database/grant_spec.rb b/spec/lib/gitlab/database/grant_spec.rb index 651da3e8476..5ebf3f399b6 100644 --- a/spec/lib/gitlab/database/grant_spec.rb +++ b/spec/lib/gitlab/database/grant_spec.rb @@ -1,16 +1,6 @@ require 'spec_helper' describe Gitlab::Database::Grant do - describe '.scope_to_current_user' do - it 'scopes the relation to the current user' do - user = Gitlab::Database.username - column = Gitlab::Database.postgresql? ? :grantee : :User - names = described_class.scope_to_current_user.pluck(column).uniq - - expect(names).to eq([user]) - end - end - describe '.create_and_execute_trigger' do it 'returns true when the user can create and execute a trigger' do # We assume the DB/user is set up correctly so that triggers can be @@ -18,13 +8,11 @@ describe Gitlab::Database::Grant do expect(described_class.create_and_execute_trigger?('users')).to eq(true) end - it 'returns false when the user can not create and/or execute a trigger' do - allow(described_class).to receive(:scope_to_current_user) - .and_return(described_class.none) - - result = described_class.create_and_execute_trigger?('kittens') - - expect(result).to eq(false) + it 'returns false when the user can not create and/or execute a trigger', :postgresql do + # In case of MySQL the user may have SUPER permissions, making it + # impossible to have `false` returned when running tests; hence we only + # run these tests on PostgreSQL. + expect(described_class.create_and_execute_trigger?('foo')).to eq(false) end end end diff --git a/spec/lib/gitlab/import_export/merge_request_parser_spec.rb b/spec/lib/gitlab/import_export/merge_request_parser_spec.rb index 473ba40fae7..b793636c4d6 100644 --- a/spec/lib/gitlab/import_export/merge_request_parser_spec.rb +++ b/spec/lib/gitlab/import_export/merge_request_parser_spec.rb @@ -13,7 +13,7 @@ describe Gitlab::ImportExport::MergeRequestParser do let(:parsed_merge_request) do described_class.new(project, - merge_request.diff_head_sha, + 'abcd', merge_request, merge_request.as_json).parse! end @@ -29,4 +29,14 @@ describe Gitlab::ImportExport::MergeRequestParser do it 'has a target branch' do expect(project.repository.branch_exists?(parsed_merge_request.target_branch)).to be true end + + it 'parses a MR that has no source branch' do + allow_any_instance_of(described_class).to receive(:branch_exists?).and_call_original + allow_any_instance_of(described_class).to receive(:branch_exists?).with(merge_request.source_branch).and_return(false) + allow_any_instance_of(described_class).to receive(:fork_merge_request?).and_return(true) + allow(Gitlab::GitalyClient).to receive(:migrate).and_call_original + allow(Gitlab::GitalyClient).to receive(:migrate).with(:fetch_ref).and_return([nil, 0]) + + expect(parsed_merge_request).to eq(merge_request) + end end diff --git a/spec/lib/google_api/cloud_platform/client_spec.rb b/spec/lib/google_api/cloud_platform/client_spec.rb index acc5bd1da35..fac23dce44d 100644 --- a/spec/lib/google_api/cloud_platform/client_spec.rb +++ b/spec/lib/google_api/cloud_platform/client_spec.rb @@ -69,7 +69,7 @@ describe GoogleApi::CloudPlatform::Client do let(:cluster_name) { 'test-cluster' } let(:cluster_size) { 1 } - let(:machine_type) { 'n1-standard-4' } + let(:machine_type) { 'n1-standard-2' } let(:operation) { double } before do diff --git a/spec/models/clusters/providers/gcp_spec.rb b/spec/models/clusters/providers/gcp_spec.rb index ecd0a08c953..b38b5e6bcad 100644 --- a/spec/models/clusters/providers/gcp_spec.rb +++ b/spec/models/clusters/providers/gcp_spec.rb @@ -10,7 +10,7 @@ describe Clusters::Providers::Gcp do it "has default value" do expect(gcp.zone).to eq('us-central1-a') expect(gcp.num_nodes).to eq(3) - expect(gcp.machine_type).to eq('n1-standard-4') + expect(gcp.machine_type).to eq('n1-standard-2') end end diff --git a/spec/models/commit_status_spec.rb b/spec/models/commit_status_spec.rb index 858ec831200..c536dab2681 100644 --- a/spec/models/commit_status_spec.rb +++ b/spec/models/commit_status_spec.rb @@ -1,9 +1,9 @@ require 'spec_helper' describe CommitStatus do - let(:project) { create(:project, :repository) } + set(:project) { create(:project, :repository) } - let(:pipeline) do + set(:pipeline) do create(:ci_pipeline, project: project, sha: project.commit.id) end @@ -464,4 +464,73 @@ describe CommitStatus do it { is_expected.to be_script_failure } end end + + describe 'ensure stage assignment' do + context 'when commit status has a stage_id assigned' do + let!(:stage) do + create(:ci_stage_entity, project: project, pipeline: pipeline) + end + + let(:commit_status) do + create(:commit_status, stage_id: stage.id, name: 'rspec', stage: 'test') + end + + it 'does not create a new stage' do + expect { commit_status }.not_to change { Ci::Stage.count } + expect(commit_status.stage_id).to eq stage.id + end + end + + context 'when commit status does not have a stage_id assigned' do + let(:commit_status) do + create(:commit_status, name: 'rspec', stage: 'test', status: :success) + end + + let(:stage) { Ci::Stage.first } + + it 'creates a new stage' do + expect { commit_status }.to change { Ci::Stage.count }.by(1) + + expect(stage.name).to eq 'test' + expect(stage.project).to eq commit_status.project + expect(stage.pipeline).to eq commit_status.pipeline + expect(stage.status).to eq commit_status.status + expect(commit_status.stage_id).to eq stage.id + end + end + + context 'when commit status does not have stage but it exists' do + let!(:stage) do + create(:ci_stage_entity, project: project, + pipeline: pipeline, + name: 'test') + end + + let(:commit_status) do + create(:commit_status, project: project, + pipeline: pipeline, + name: 'rspec', + stage: 'test', + status: :success) + end + + it 'uses existing stage' do + expect { commit_status }.not_to change { Ci::Stage.count } + + expect(commit_status.stage_id).to eq stage.id + expect(stage.reload.status).to eq commit_status.status + end + end + + context 'when commit status is being imported' do + let(:commit_status) do + create(:commit_status, name: 'rspec', stage: 'test', importing: true) + end + + it 'does not create a new stage' do + expect { commit_status }.not_to change { Ci::Stage.count } + expect(commit_status.stage_id).not_to be_present + end + end + end end diff --git a/spec/serializers/pipeline_details_entity_spec.rb b/spec/serializers/pipeline_details_entity_spec.rb index f60d1843581..45e18086894 100644 --- a/spec/serializers/pipeline_details_entity_spec.rb +++ b/spec/serializers/pipeline_details_entity_spec.rb @@ -107,7 +107,7 @@ describe PipelineDetailsEntity do it 'contains stages' do expect(subject).to include(:details) expect(subject[:details]).to include(:stages) - expect(subject[:details][:stages].first).to include(name: 'external') + expect(subject[:details][:stages].first).to include(name: 'test') end end diff --git a/spec/support/cycle_analytics_helpers.rb b/spec/support/cycle_analytics_helpers.rb index 934b4557ba2..26fd271ce31 100644 --- a/spec/support/cycle_analytics_helpers.rb +++ b/spec/support/cycle_analytics_helpers.rb @@ -94,6 +94,7 @@ module CycleAnalyticsHelpers ref: 'master', tag: false, name: 'dummy', + stage: 'dummy', pipeline: dummy_pipeline, protected: false) end |