Commit 2087e3e2 authored by Mireya Andres's avatar Mireya Andres Committed by Sarah Groff Hennigh-Palermo

Integrate new pipeline query for pipeline editor

This integrates the new backend query for fetching the pipeline status
using the commit sha instead of the pipeline iid.

This was previously implemented under a disabled feature flag
(`pipeline_status_for_pipeline_editor`) using a client resolver.
parent 60444b92
<script>
import { GlIcon, GlLink, GlLoadingIcon, GlSprintf } from '@gitlab/ui';
import { getIdFromGraphQLId } from '~/graphql_shared/utils';
import { truncateSha } from '~/lib/utils/text_utility';
import { s__ } from '~/locale';
import getCommitSha from '~/pipeline_editor/graphql/queries/client/commit_sha.graphql';
import getPipelineQuery from '~/pipeline_editor/graphql/queries/client/pipeline.graphql';
import { toggleQueryPollingByVisibility } from '~/pipelines/components/graph/utils';
import CiIcon from '~/vue_shared/components/ci_icon.vue';
const POLL_INTERVAL = 10000;
......@@ -38,13 +40,11 @@ export default {
};
},
update: (data) => {
const { id, commitPath = '', shortSha = '', detailedStatus = {} } =
data.project?.pipeline || {};
const { id, commitPath = '', detailedStatus = {} } = data.project?.pipeline || {};
return {
id,
commitPath,
shortSha,
detailedStatus,
};
},
......@@ -61,24 +61,34 @@ export default {
},
computed: {
hasPipelineData() {
return Boolean(this.$apollo.queries.pipeline?.id);
return Boolean(this.pipeline?.id);
},
isQueryLoading() {
return this.$apollo.queries.pipeline.loading && !this.hasPipelineData;
pipelineId() {
return getIdFromGraphQLId(this.pipeline.id);
},
showLoadingState() {
// the query is set to poll regularly, so if there is no pipeline data
// (e.g. pipeline is null during fetch when the pipeline hasn't been
// triggered yet), we can just show the loading state until the pipeline
// details are ready to be fetched
return this.$apollo.queries.pipeline.loading || (!this.hasPipelineData && !this.hasError);
},
shortSha() {
return truncateSha(this.commitSha);
},
status() {
return this.pipeline.detailedStatus;
},
pipelineId() {
return getIdFromGraphQLId(this.pipeline.id);
},
},
mounted() {
toggleQueryPollingByVisibility(this.$apollo.queries.pipeline, POLL_INTERVAL);
},
};
</script>
<template>
<div class="gl-white-space-nowrap gl-max-w-full">
<template v-if="isQueryLoading">
<template v-if="showLoadingState">
<gl-loading-icon class="gl-mr-auto gl-display-inline-block" size="sm" />
<span data-testid="pipeline-loading-msg">{{ $options.i18n.fetchLoading }}</span>
</template>
......@@ -110,7 +120,7 @@ export default {
target="_blank"
data-testid="pipeline-commit"
>
{{ pipeline.shortSha }}
{{ shortSha }}
</gl-link>
</template>
</gl-sprintf>
......
query getPipeline($fullPath: ID!, $sha: String!) {
project(fullPath: $fullPath) @client {
project(fullPath: $fullPath) {
pipeline(sha: $sha) {
commitPath
id
iid
shortSha
status
detailedStatus {
detailsPath
......
......@@ -11,29 +11,6 @@ export const resolvers = {
}),
};
},
/* eslint-disable @gitlab/require-i18n-strings */
project() {
return {
__typename: 'Project',
pipeline: {
__typename: 'Pipeline',
commitPath: `/-/commit/aabbccdd`,
id: 'gid://gitlab/Ci::Pipeline/118',
iid: '28',
shortSha: 'aabbccdd',
status: 'SUCCESS',
detailedStatus: {
__typename: 'DetailedStatus',
detailsPath: '/root/sample-ci-project/-/pipelines/118"',
group: 'success',
icon: 'status_success',
text: 'passed',
},
},
};
},
/* eslint-enable @gitlab/require-i18n-strings */
},
Mutation: {
lintCI: (_, { endpoint, content, dry_run }) => {
......
......@@ -4,6 +4,7 @@ import VueApollo from 'vue-apollo';
import createMockApollo from 'helpers/mock_apollo_helper';
import waitForPromises from 'helpers/wait_for_promises';
import PipelineStatus, { i18n } from '~/pipeline_editor/components/header/pipeline_status.vue';
import getPipelineQuery from '~/pipeline_editor/graphql/queries/client/pipeline.graphql';
import CiIcon from '~/vue_shared/components/ci_icon.vue';
import { mockCommitSha, mockProjectPipeline, mockProjectFullPath } from '../../mock_data';
......@@ -19,32 +20,9 @@ describe('Pipeline Status', () => {
let mockApollo;
let mockPipelineQuery;
const createComponent = ({ hasPipeline = true, isQueryLoading = false }) => {
const pipeline = hasPipeline
? { loading: isQueryLoading, ...mockProjectPipeline.pipeline }
: { loading: isQueryLoading };
wrapper = shallowMount(PipelineStatus, {
provide: mockProvide,
stubs: { GlLink, GlSprintf },
data: () => (hasPipeline ? { pipeline } : {}),
mocks: {
$apollo: {
queries: {
pipeline,
},
},
},
});
};
const createComponentWithApollo = () => {
const resolvers = {
Query: {
project: mockPipelineQuery,
},
};
mockApollo = createMockApollo([], resolvers);
const handlers = [[getPipelineQuery, mockPipelineQuery]];
mockApollo = createMockApollo(handlers);
wrapper = shallowMount(PipelineStatus, {
localVue,
......@@ -78,16 +56,17 @@ describe('Pipeline Status', () => {
wrapper = null;
});
describe('while querying', () => {
it('renders loading icon', () => {
createComponent({ isQueryLoading: true, hasPipeline: false });
describe('loading icon', () => {
it('renders while query is being fetched', () => {
createComponentWithApollo();
expect(findLoadingIcon().exists()).toBe(true);
expect(findPipelineLoadingMsg().text()).toBe(i18n.fetchLoading);
});
it('does not render loading icon if pipeline data is already set', () => {
createComponent({ isQueryLoading: true });
it('does not render if query is no longer loading', async () => {
createComponentWithApollo();
await waitForPromises();
expect(findLoadingIcon().exists()).toBe(false);
});
......@@ -96,7 +75,9 @@ describe('Pipeline Status', () => {
describe('when querying data', () => {
describe('when data is set', () => {
beforeEach(async () => {
mockPipelineQuery.mockResolvedValue(mockProjectPipeline);
mockPipelineQuery.mockResolvedValue({
data: { project: mockProjectPipeline },
});
createComponentWithApollo();
await waitForPromises();
......@@ -104,14 +85,10 @@ describe('Pipeline Status', () => {
it('query is called with correct variables', async () => {
expect(mockPipelineQuery).toHaveBeenCalledTimes(1);
expect(mockPipelineQuery).toHaveBeenCalledWith(
expect.anything(),
{
fullPath: mockProjectFullPath,
},
expect.anything(),
expect.anything(),
);
expect(mockPipelineQuery).toHaveBeenCalledWith({
fullPath: mockProjectFullPath,
sha: mockCommitSha,
});
});
it('does not render error', () => {
......
......@@ -46,24 +46,6 @@ describe('~/pipeline_editor/graphql/resolvers', () => {
await expect(result.rawData).resolves.toBe(mockCiYml);
});
});
describe('pipeline', () => {
it('resolves pipeline data with type names', async () => {
const result = await resolvers.Query.project(null);
// eslint-disable-next-line no-underscore-dangle
expect(result.__typename).toBe('Project');
});
it('resolves pipeline data with necessary data', async () => {
const result = await resolvers.Query.project(null);
const pipelineKeys = Object.keys(result.pipeline);
const statusKeys = Object.keys(result.pipeline.detailedStatus);
expect(pipelineKeys).toContain('id', 'commitPath', 'detailedStatus', 'shortSha');
expect(statusKeys).toContain('detailsPath', 'text');
});
});
});
describe('Mutation', () => {
......
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