From cdc92d94e0c676bf86877a5794d72bd4dcf88c24 Mon Sep 17 00:00:00 2001 From: Phil Hughes Date: Fri, 25 May 2018 15:09:20 +0100 Subject: [PATCH] fixed pipeline actions spec --- .../ide/stores/modules/pipelines/actions.js | 1 + .../ide/stores/actions/project_spec.js | 111 +-------- .../stores/modules/pipelines/actions_spec.js | 215 ++++++------------ .../ide/stores/mutations/branch_spec.js | 36 --- 4 files changed, 70 insertions(+), 293 deletions(-) diff --git a/app/assets/javascripts/ide/stores/modules/pipelines/actions.js b/app/assets/javascripts/ide/stores/modules/pipelines/actions.js index 35b7be4d866..3c46e9d7a38 100644 --- a/app/assets/javascripts/ide/stores/modules/pipelines/actions.js +++ b/app/assets/javascripts/ide/stores/modules/pipelines/actions.js @@ -8,6 +8,7 @@ import * as types from './mutation_types'; let eTagPoll; +export const clearEtagPoll = () => (eTagPoll = null); export const stopPipelinePolling = () => eTagPoll.stop(); export const restartPipelinePolling = () => eTagPoll.restart(); diff --git a/spec/javascripts/ide/stores/actions/project_spec.js b/spec/javascripts/ide/stores/actions/project_spec.js index 8e078ae7138..d71fc0e035e 100644 --- a/spec/javascripts/ide/stores/actions/project_spec.js +++ b/spec/javascripts/ide/stores/actions/project_spec.js @@ -1,31 +1,10 @@ -import Visibility from 'visibilityjs'; -import MockAdapter from 'axios-mock-adapter'; -import { refreshLastCommitData, pollSuccessCallBack } from '~/ide/stores/actions'; +import { refreshLastCommitData } from '~/ide/stores/actions'; import store from '~/ide/stores'; import service from '~/ide/services'; -import axios from '~/lib/utils/axios_utils'; -import { fullPipelinesResponse } from '../../mock_data'; import { resetStore } from '../../helpers'; import testAction from '../../../helpers/vuex_action_helper'; describe('IDE store project actions', () => { - const setProjectState = () => { - store.state.currentProjectId = 'abc/def'; - store.state.currentBranchId = 'master'; - store.state.projects['abc/def'] = { - id: 4, - path_with_namespace: 'abc/def', - branches: { - master: { - commit: { - id: 'abc123def456ghi789jkl', - title: 'example', - }, - }, - }, - }; - }; - beforeEach(() => { store.state.projects['abc/def'] = {}; }); @@ -101,92 +80,4 @@ describe('IDE store project actions', () => { ); }); }); - - describe('pipelinePoll', () => { - let mock; - - beforeEach(() => { - setProjectState(); - jasmine.clock().install(); - mock = new MockAdapter(axios); - mock - .onGet('/abc/def/commit/abc123def456ghi789jkl/pipelines') - .reply(200, { data: { foo: 'bar' } }, { 'poll-interval': '10000' }); - }); - - afterEach(() => { - jasmine.clock().uninstall(); - mock.restore(); - store.dispatch('stopPipelinePolling'); - }); - - it('calls service periodically', done => { - spyOn(axios, 'get').and.callThrough(); - spyOn(Visibility, 'hidden').and.returnValue(false); - - store - .dispatch('pipelinePoll') - .then(() => { - jasmine.clock().tick(1000); - - expect(axios.get).toHaveBeenCalled(); - expect(axios.get.calls.count()).toBe(1); - }) - .then(() => new Promise(resolve => requestAnimationFrame(resolve))) - .then(() => { - jasmine.clock().tick(10000); - expect(axios.get.calls.count()).toBe(2); - }) - .then(() => new Promise(resolve => requestAnimationFrame(resolve))) - .then(() => { - jasmine.clock().tick(10000); - expect(axios.get.calls.count()).toBe(3); - }) - .then(() => new Promise(resolve => requestAnimationFrame(resolve))) - .then(() => { - jasmine.clock().tick(10000); - expect(axios.get.calls.count()).toBe(4); - }) - - .then(done) - .catch(done.fail); - }); - }); - - describe('pollSuccessCallBack', () => { - beforeEach(() => { - setProjectState(); - }); - - it('commits correct pipeline', done => { - testAction( - pollSuccessCallBack, - fullPipelinesResponse, - store.state, - [ - { - type: 'SET_LAST_COMMIT_PIPELINE', - payload: { - projectId: 'abc/def', - branchId: 'master', - pipeline: { - id: '50', - commit: { - id: 'abc123def456ghi789jkl', - }, - details: { - status: { - icon: 'status_passed', - text: 'passed', - }, - }, - }, - }, - }, - ], // mutations - [], // action - done, - ); - }); - }); }); diff --git a/spec/javascripts/ide/stores/modules/pipelines/actions_spec.js b/spec/javascripts/ide/stores/modules/pipelines/actions_spec.js index bcf9d9e1513..273e09f5d12 100644 --- a/spec/javascripts/ide/stores/modules/pipelines/actions_spec.js +++ b/spec/javascripts/ide/stores/modules/pipelines/actions_spec.js @@ -1,3 +1,4 @@ +import Visibility from 'visibilityjs'; import MockAdapter from 'axios-mock-adapter'; import axios from '~/lib/utils/axios_utils'; import actions, { @@ -5,15 +6,13 @@ import actions, { receiveLatestPipelineError, receiveLatestPipelineSuccess, fetchLatestPipeline, - requestStages, - receiveStagesError, - receiveStagesSuccess, - fetchStages, + stopPipelinePolling, + clearEtagPoll, } from '~/ide/stores/modules/pipelines/actions'; import state from '~/ide/stores/modules/pipelines/state'; import * as types from '~/ide/stores/modules/pipelines/mutation_types'; import testAction from '../../../../helpers/vuex_action_helper'; -import { pipelines, stages } from '../../../mock_data'; +import { pipelines } from '../../../mock_data'; describe('IDE pipelines actions', () => { let mockedState; @@ -51,7 +50,7 @@ describe('IDE pipelines actions', () => { null, mockedState, [{ type: types.RECEIVE_LASTEST_PIPELINE_ERROR }], - [], + [{ type: 'stopPipelinePolling' }], done, ); }); @@ -59,7 +58,7 @@ describe('IDE pipelines actions', () => { it('creates flash message', () => { const flashSpy = spyOnDependency(actions, 'flash'); - receiveLatestPipelineError({ commit() {} }); + receiveLatestPipelineError({ commit() {}, dispatch() {} }); expect(flashSpy).toHaveBeenCalled(); }); @@ -79,166 +78,88 @@ describe('IDE pipelines actions', () => { }); describe('fetchLatestPipeline', () => { - describe('success', () => { - beforeEach(() => { - mock.onGet(/\/api\/v4\/projects\/(.*)\/pipelines(.*)/).replyOnce(200, pipelines); - }); - - it('dispatches request', done => { - testAction( - fetchLatestPipeline, - '123', - mockedState, - [], - [{ type: 'requestLatestPipeline' }, { type: 'receiveLatestPipelineSuccess' }], - done, - ); - }); - - it('dispatches success with latest pipeline', done => { - testAction( - fetchLatestPipeline, - '123', - mockedState, - [], - [ - { type: 'requestLatestPipeline' }, - { type: 'receiveLatestPipelineSuccess', payload: pipelines[0] }, - ], - done, - ); - }); - - it('calls axios with correct params', () => { - const apiSpy = spyOn(axios, 'get').and.callThrough(); - - fetchLatestPipeline({ dispatch() {}, rootState: state }, '123'); - - expect(apiSpy).toHaveBeenCalledWith(jasmine.anything(), { - params: { - sha: '123', - per_page: '1', - }, - }); - }); - }); - - describe('error', () => { - beforeEach(() => { - mock.onGet(/\/api\/v4\/projects\/(.*)\/pipelines(.*)/).replyOnce(500); - }); - - it('dispatches error', done => { - testAction( - fetchLatestPipeline, - '123', - mockedState, - [], - [{ type: 'requestLatestPipeline' }, { type: 'receiveLatestPipelineError' }], - done, - ); - }); - }); - }); - - describe('requestStages', () => { - it('commits request', done => { - testAction(requestStages, null, mockedState, [{ type: types.REQUEST_STAGES }], [], done); - }); - }); - - describe('receiveJobsError', () => { - it('commits error', done => { - testAction( - receiveStagesError, - null, - mockedState, - [{ type: types.RECEIVE_STAGES_ERROR }], - [], - done, - ); - }); - - it('creates flash message', () => { - const flashSpy = spyOnDependency(actions, 'flash'); - - receiveStagesError({ commit() {} }); - - expect(flashSpy).toHaveBeenCalled(); - }); - }); - - describe('receiveStagesSuccess', () => { - it('commits jobs', done => { - testAction( - receiveStagesSuccess, - stages, - mockedState, - [{ type: types.RECEIVE_STAGES_SUCCESS, payload: stages }], - [], - done, - ); - }); - }); - - describe('fetchStages', () => { beforeEach(() => { - mockedState.latestPipeline = pipelines[0]; + jasmine.clock().install(); + }); + + afterEach(() => { + jasmine.clock().uninstall(); + stopPipelinePolling(); + clearEtagPoll(); }); describe('success', () => { beforeEach(() => { - mock.onGet(/\/(.*)\/pipelines\/(.*)\/builds.json/).replyOnce(200, stages); + mock + .onGet('/abc/def/commit/abc123def456ghi789jkl/pipelines') + .reply(200, { data: { foo: 'bar' } }, { 'poll-interval': '10000' }); }); it('dispatches request', done => { - testAction( - fetchStages, - null, - mockedState, - [], - [{ type: 'requestStages' }, { type: 'receiveStagesSuccess' }], - done, - ); - }); + spyOn(axios, 'get').and.callThrough(); + spyOn(Visibility, 'hidden').and.returnValue(false); - it('dispatches success with latest pipeline', done => { - testAction( - fetchStages, - null, - mockedState, - [], - [{ type: 'requestStages' }, { type: 'receiveStagesSuccess', payload: stages }], - done, - ); - }); + const dispatch = jasmine.createSpy('dispatch'); + const rootGetters = { + lastCommit: { id: 'abc123def456ghi789jkl' }, + currentProject: { path_with_namespace: 'abc/def' }, + }; - it('calls axios with correct URL', () => { - const apiSpy = spyOn(axios, 'get').and.callThrough(); + fetchLatestPipeline({ dispatch, rootGetters }); - fetchStages({ dispatch() {}, state: mockedState, rootState: mockedState }); + expect(dispatch.calls.argsFor(0)).toEqual(['requestLatestPipeline']); - expect(apiSpy).toHaveBeenCalledWith( - '/test/project/pipelines/1/builds.json', - jasmine.anything(), - ); + jasmine.clock().tick(1000); + + new Promise(resolve => requestAnimationFrame(resolve)) + .then(() => { + expect(axios.get).toHaveBeenCalled(); + expect(axios.get.calls.count()).toBe(1); + + expect(dispatch.calls.argsFor(1)).toEqual([ + 'receiveLatestPipelineSuccess', + jasmine.anything(), + ]); + + jasmine.clock().tick(10000); + }) + .then(() => new Promise(resolve => requestAnimationFrame(resolve))) + .then(() => { + expect(axios.get).toHaveBeenCalled(); + expect(axios.get.calls.count()).toBe(2); + + expect(dispatch.calls.argsFor(2)).toEqual([ + 'receiveLatestPipelineSuccess', + jasmine.anything(), + ]); + }) + .then(done) + .catch(done.fail); }); }); describe('error', () => { beforeEach(() => { - mock.onGet(/\/(.*)\/pipelines\/(.*)\/builds.json/).replyOnce(500); + mock.onGet('/abc/def/commit/abc123def456ghi789jkl/pipelines').reply(500); }); it('dispatches error', done => { - testAction( - fetchStages, - null, - mockedState, - [], - [{ type: 'requestStages' }, { type: 'receiveStagesError' }], - done, - ); + const dispatch = jasmine.createSpy('dispatch'); + const rootGetters = { + lastCommit: { id: 'abc123def456ghi789jkl' }, + currentProject: { path_with_namespace: 'abc/def' }, + }; + + fetchLatestPipeline({ dispatch, rootGetters }); + + jasmine.clock().tick(1500); + + new Promise(resolve => requestAnimationFrame(resolve)) + .then(() => { + expect(dispatch.calls.argsFor(1)).toEqual(['receiveLatestPipelineError']); + }) + .then(done) + .catch(done.fail); }); }); }); diff --git a/spec/javascripts/ide/stores/mutations/branch_spec.js b/spec/javascripts/ide/stores/mutations/branch_spec.js index f2f1f2a9a2e..29eb859ddaf 100644 --- a/spec/javascripts/ide/stores/mutations/branch_spec.js +++ b/spec/javascripts/ide/stores/mutations/branch_spec.js @@ -37,40 +37,4 @@ describe('Multi-file store branch mutations', () => { expect(localState.projects.Example.branches.master.commit.title).toBe('Example commit'); }); }); - - describe('SET_LAST_COMMIT_PIPELINE', () => { - it('sets the pipeline for the last commit on current project', () => { - localState.projects = { - Example: { - branches: { - master: { - commit: {}, - }, - }, - }, - }; - - mutations.SET_LAST_COMMIT_PIPELINE(localState, { - projectId: 'Example', - branchId: 'master', - pipeline: { - id: '50', - details: { - status: { - icon: 'status_passed', - text: 'passed', - }, - }, - }, - }); - - expect(localState.projects.Example.branches.master.commit.pipeline.id).toBe('50'); - expect(localState.projects.Example.branches.master.commit.pipeline.details.status.text).toBe( - 'passed', - ); - expect(localState.projects.Example.branches.master.commit.pipeline.details.status.icon).toBe( - 'status_passed', - ); - }); - }); });