Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2020-11-06 18:09:14 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2020-11-06 18:09:14 +0300
commita268b09416c8dc3da3af38933028fa26375b88e0 (patch)
tree8f10484408a40e386b79f8bb3c2f4095dded85f7 /spec/frontend/analytics
parent4ff56b118438f4fa6191b691fd968c75d8e94d5a (diff)
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'spec/frontend/analytics')
-rw-r--r--spec/frontend/analytics/instance_statistics/apollo_mock_data.js40
-rw-r--r--spec/frontend/analytics/instance_statistics/components/__snapshots__/instance_statistics_count_chart_spec.js.snap126
-rw-r--r--spec/frontend/analytics/instance_statistics/components/app_spec.js13
-rw-r--r--spec/frontend/analytics/instance_statistics/components/instance_statistics_count_chart_spec.js126
-rw-r--r--spec/frontend/analytics/instance_statistics/components/projects_and_groups_chart_spec.js16
-rw-r--r--spec/frontend/analytics/instance_statistics/components/users_chart_spec.js14
-rw-r--r--spec/frontend/analytics/instance_statistics/utils_spec.js67
7 files changed, 103 insertions, 299 deletions
diff --git a/spec/frontend/analytics/instance_statistics/apollo_mock_data.js b/spec/frontend/analytics/instance_statistics/apollo_mock_data.js
index 8697830672e..98eabd577ee 100644
--- a/spec/frontend/analytics/instance_statistics/apollo_mock_data.js
+++ b/spec/frontend/analytics/instance_statistics/apollo_mock_data.js
@@ -5,36 +5,7 @@ const defaultPageInfo = {
endCursor: null,
};
-export function getApolloResponse(options = {}) {
- const {
- pipelinesTotal = [],
- pipelinesSucceeded = [],
- pipelinesFailed = [],
- pipelinesCanceled = [],
- pipelinesSkipped = [],
- hasNextPage = false,
- } = options;
- return {
- data: {
- pipelinesTotal: { pageInfo: { ...defaultPageInfo, hasNextPage }, nodes: pipelinesTotal },
- pipelinesSucceeded: {
- pageInfo: { ...defaultPageInfo, hasNextPage },
- nodes: pipelinesSucceeded,
- },
- pipelinesFailed: { pageInfo: { ...defaultPageInfo, hasNextPage }, nodes: pipelinesFailed },
- pipelinesCanceled: {
- pageInfo: { ...defaultPageInfo, hasNextPage },
- nodes: pipelinesCanceled,
- },
- pipelinesSkipped: {
- pageInfo: { ...defaultPageInfo, hasNextPage },
- nodes: pipelinesSkipped,
- },
- },
- };
-}
-
-const mockApolloResponse = ({ hasNextPage = false, key, data }) => ({
+export const mockApolloResponse = ({ hasNextPage = false, key, data }) => ({
data: {
[key]: {
pageInfo: { ...defaultPageInfo, hasNextPage },
@@ -43,13 +14,8 @@ const mockApolloResponse = ({ hasNextPage = false, key, data }) => ({
},
});
-export const mockQueryResponse = ({
- key,
- data = [],
- loading = false,
- hasNextPage = false,
- additionalData = [],
-}) => {
+export const mockQueryResponse = ({ key, data = [], loading = false, additionalData = [] }) => {
+ const hasNextPage = Boolean(additionalData.length);
const response = mockApolloResponse({ hasNextPage, key, data });
if (loading) {
return jest.fn().mockReturnValue(new Promise(() => {}));
diff --git a/spec/frontend/analytics/instance_statistics/components/__snapshots__/instance_statistics_count_chart_spec.js.snap b/spec/frontend/analytics/instance_statistics/components/__snapshots__/instance_statistics_count_chart_spec.js.snap
index 2e76db65a0a..29bcd5f223b 100644
--- a/spec/frontend/analytics/instance_statistics/components/__snapshots__/instance_statistics_count_chart_spec.js.snap
+++ b/spec/frontend/analytics/instance_statistics/components/__snapshots__/instance_statistics_count_chart_spec.js.snap
@@ -5,87 +5,19 @@ Array [
Object {
"data": Array [
Array [
- "2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
- ],
- Array [
- "2020-08-01",
- 5,
- ],
- ],
- "name": "Total",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
- ],
- Array [
- "2020-08-01",
- 5,
- ],
- ],
- "name": "Succeeded",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 22,
- ],
- Array [
"2020-07-01",
41,
],
Array [
- "2020-08-01",
- 5,
- ],
- ],
- "name": "Failed",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
- ],
- Array [
- "2020-08-01",
- 5,
- ],
- ],
- "name": "Canceled",
- },
- Object {
- "data": Array [
- Array [
"2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
+ 22,
],
Array [
"2020-08-01",
5,
],
],
- "name": "Skipped",
+ "name": "Mock Query",
},
]
`;
@@ -95,67 +27,15 @@ Array [
Object {
"data": Array [
Array [
- "2020-06-01",
- 22,
- ],
- Array [
"2020-07-01",
41,
],
- ],
- "name": "Total",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
- ],
- ],
- "name": "Succeeded",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 21,
- ],
- Array [
- "2020-07-01",
- 10,
- ],
- ],
- "name": "Failed",
- },
- Object {
- "data": Array [
Array [
"2020-06-01",
22,
],
- Array [
- "2020-07-01",
- 41,
- ],
- ],
- "name": "Canceled",
- },
- Object {
- "data": Array [
- Array [
- "2020-06-01",
- 22,
- ],
- Array [
- "2020-07-01",
- 41,
- ],
],
- "name": "Skipped",
+ "name": "Mock Query",
},
]
`;
diff --git a/spec/frontend/analytics/instance_statistics/components/app_spec.js b/spec/frontend/analytics/instance_statistics/components/app_spec.js
index 159a7763d11..8ac663b3046 100644
--- a/spec/frontend/analytics/instance_statistics/components/app_spec.js
+++ b/spec/frontend/analytics/instance_statistics/components/app_spec.js
@@ -25,11 +25,14 @@ describe('InstanceStatisticsApp', () => {
expect(wrapper.find(InstanceCounts).exists()).toBe(true);
});
- it('displays the instance statistics count chart component', () => {
- const allCharts = wrapper.findAll(InstanceStatisticsCountChart);
- expect(allCharts).toHaveLength(2);
- expect(allCharts.at(0).exists()).toBe(true);
- expect(allCharts.at(1).exists()).toBe(true);
+ ['Pipelines', 'Issues & Merge Requests'].forEach(instance => {
+ it(`displays the ${instance} chart`, () => {
+ const chartTitles = wrapper
+ .findAll(InstanceStatisticsCountChart)
+ .wrappers.map(chartComponent => chartComponent.props('chartTitle'));
+
+ expect(chartTitles).toContain(instance);
+ });
});
it('displays the users chart component', () => {
diff --git a/spec/frontend/analytics/instance_statistics/components/instance_statistics_count_chart_spec.js b/spec/frontend/analytics/instance_statistics/components/instance_statistics_count_chart_spec.js
index 6efca20b67a..275a84988f8 100644
--- a/spec/frontend/analytics/instance_statistics/components/instance_statistics_count_chart_spec.js
+++ b/spec/frontend/analytics/instance_statistics/components/instance_statistics_count_chart_spec.js
@@ -4,46 +4,44 @@ import { GlAlert } from '@gitlab/ui';
import VueApollo from 'vue-apollo';
import createMockApollo from 'jest/helpers/mock_apollo_helper';
import InstanceStatisticsCountChart from '~/analytics/instance_statistics/components/instance_statistics_count_chart.vue';
-import pipelinesStatsQuery from '~/analytics/instance_statistics/graphql/queries/pipeline_stats.query.graphql';
+import statsQuery from '~/analytics/instance_statistics/graphql/queries/instance_count.query.graphql';
import ChartSkeletonLoader from '~/vue_shared/components/resizable_chart/skeleton_loader.vue';
-import { mockCountsData1, mockCountsData2 } from '../mock_data';
-import { getApolloResponse } from '../apollo_mock_data';
+import { mockCountsData1 } from '../mock_data';
+import { mockQueryResponse, mockApolloResponse } from '../apollo_mock_data';
const localVue = createLocalVue();
localVue.use(VueApollo);
-const PIPELINES_KEY_TO_NAME_MAP = {
- total: 'Total',
- succeeded: 'Succeeded',
- failed: 'Failed',
- canceled: 'Canceled',
- skipped: 'Skipped',
-};
const loadChartErrorMessage = 'My load error message';
const noDataMessage = 'My no data message';
+const queryResponseDataKey = 'instanceStatisticsMeasurements';
+const identifier = 'MOCK_QUERY';
+const mockQueryConfig = {
+ identifier,
+ title: 'Mock Query',
+ query: statsQuery,
+ loadError: 'Failed to load mock query data',
+};
+
+const mockChartConfig = {
+ loadChartErrorMessage,
+ noDataMessage,
+ chartTitle: 'Foo',
+ yAxisTitle: 'Bar',
+ xAxisTitle: 'Baz',
+ queries: [mockQueryConfig],
+};
+
describe('InstanceStatisticsCountChart', () => {
let wrapper;
let queryHandler;
- const createApolloProvider = pipelineStatsHandler => {
- return createMockApollo([[pipelinesStatsQuery, pipelineStatsHandler]]);
- };
-
- const createComponent = apolloProvider => {
+ const createComponent = ({ responseHandler }) => {
return shallowMount(InstanceStatisticsCountChart, {
localVue,
- apolloProvider,
- propsData: {
- keyToNameMap: PIPELINES_KEY_TO_NAME_MAP,
- prefix: 'pipelines',
- loadChartErrorMessage,
- noDataMessage,
- chartTitle: 'Foo',
- yAxisTitle: 'Bar',
- xAxisTitle: 'Baz',
- query: pipelinesStatsQuery,
- },
+ apolloProvider: createMockApollo([[statsQuery, responseHandler]]),
+ propsData: { ...mockChartConfig },
});
};
@@ -58,9 +56,8 @@ describe('InstanceStatisticsCountChart', () => {
describe('while loading', () => {
beforeEach(() => {
- queryHandler = jest.fn().mockReturnValue(new Promise(() => {}));
- const apolloProvider = createApolloProvider(queryHandler);
- wrapper = createComponent(apolloProvider);
+ queryHandler = mockQueryResponse({ key: queryResponseDataKey, loading: true });
+ wrapper = createComponent({ responseHandler: queryHandler });
});
it('requests data', () => {
@@ -82,10 +79,8 @@ describe('InstanceStatisticsCountChart', () => {
describe('without data', () => {
beforeEach(() => {
- const emptyResponse = getApolloResponse();
- queryHandler = jest.fn().mockResolvedValue(emptyResponse);
- const apolloProvider = createApolloProvider(queryHandler);
- wrapper = createComponent(apolloProvider);
+ queryHandler = mockQueryResponse({ key: queryResponseDataKey, data: [] });
+ wrapper = createComponent({ responseHandler: queryHandler });
});
it('renders an no data message', () => {
@@ -103,16 +98,8 @@ describe('InstanceStatisticsCountChart', () => {
describe('with data', () => {
beforeEach(() => {
- const response = getApolloResponse({
- pipelinesTotal: mockCountsData1,
- pipelinesSucceeded: mockCountsData2,
- pipelinesFailed: mockCountsData2,
- pipelinesCanceled: mockCountsData1,
- pipelinesSkipped: mockCountsData1,
- });
- queryHandler = jest.fn().mockResolvedValue(response);
- const apolloProvider = createApolloProvider(queryHandler);
- wrapper = createComponent(apolloProvider);
+ queryHandler = mockQueryResponse({ key: queryResponseDataKey, data: mockCountsData1 });
+ wrapper = createComponent({ responseHandler: queryHandler });
});
it('requests data', () => {
@@ -140,30 +127,14 @@ describe('InstanceStatisticsCountChart', () => {
const recordedAt = '2020-08-01';
describe('when the fetchMore query returns data', () => {
beforeEach(async () => {
- const newData = { recordedAt, count: 5 };
- const firstResponse = getApolloResponse({
- pipelinesTotal: mockCountsData2,
- pipelinesSucceeded: mockCountsData2,
- pipelinesFailed: mockCountsData1,
- pipelinesCanceled: mockCountsData2,
- pipelinesSkipped: mockCountsData2,
- hasNextPage: true,
- });
- const secondResponse = getApolloResponse({
- pipelinesTotal: [newData],
- pipelinesSucceeded: [newData],
- pipelinesFailed: [newData],
- pipelinesCanceled: [newData],
- pipelinesSkipped: [newData],
- hasNextPage: false,
+ const newData = [{ recordedAt, count: 5 }];
+ queryHandler = mockQueryResponse({
+ key: queryResponseDataKey,
+ data: mockCountsData1,
+ additionalData: newData,
});
- queryHandler = jest
- .fn()
- .mockResolvedValueOnce(firstResponse)
- .mockResolvedValueOnce(secondResponse);
- const apolloProvider = createApolloProvider(queryHandler);
- wrapper = createComponent(apolloProvider);
+ wrapper = createComponent({ responseHandler: queryHandler });
await wrapper.vm.$nextTick();
});
@@ -178,25 +149,24 @@ describe('InstanceStatisticsCountChart', () => {
describe('when the fetchMore query throws an error', () => {
beforeEach(async () => {
- const response = getApolloResponse({
- pipelinesTotal: mockCountsData2,
- pipelinesSucceeded: mockCountsData2,
- pipelinesFailed: mockCountsData1,
- pipelinesCanceled: mockCountsData2,
- pipelinesSkipped: mockCountsData2,
- hasNextPage: true,
- });
- queryHandler = jest.fn().mockResolvedValue(response);
- const apolloProvider = createApolloProvider(queryHandler);
- wrapper = createComponent(apolloProvider);
+ queryHandler = jest.fn().mockResolvedValueOnce(
+ mockApolloResponse({
+ key: queryResponseDataKey,
+ data: mockCountsData1,
+ hasNextPage: true,
+ }),
+ );
+
+ wrapper = createComponent({ responseHandler: queryHandler });
jest
- .spyOn(wrapper.vm.$apollo.queries.pipelineStats, 'fetchMore')
+ .spyOn(wrapper.vm.$apollo.queries[identifier], 'fetchMore')
.mockImplementation(jest.fn().mockRejectedValue());
+
await wrapper.vm.$nextTick();
});
it('calls fetchMore', () => {
- expect(wrapper.vm.$apollo.queries.pipelineStats.fetchMore).toHaveBeenCalledTimes(1);
+ expect(wrapper.vm.$apollo.queries[identifier].fetchMore).toHaveBeenCalledTimes(1);
});
it('show an error message', () => {
diff --git a/spec/frontend/analytics/instance_statistics/components/projects_and_groups_chart_spec.js b/spec/frontend/analytics/instance_statistics/components/projects_and_groups_chart_spec.js
index 265c867719b..d9f42430aa8 100644
--- a/spec/frontend/analytics/instance_statistics/components/projects_and_groups_chart_spec.js
+++ b/spec/frontend/analytics/instance_statistics/components/projects_and_groups_chart_spec.js
@@ -25,23 +25,21 @@ describe('ProjectsAndGroupChart', () => {
groups = [],
projectsLoading = false,
groupsLoading = false,
- projectsHasNextPage = false,
- groupsHasNextPage = false,
+ projectsAdditionalData = [],
+ groupsAdditionalData = [],
} = {}) => {
queryResponses = {
projects: mockQueryResponse({
key: 'projects',
data: projects,
loading: projectsLoading,
- hasNextPage: projectsHasNextPage,
- additionalData: mockAdditionalData,
+ additionalData: projectsAdditionalData,
}),
groups: mockQueryResponse({
key: 'groups',
data: groups,
loading: groupsLoading,
- hasNextPage: groupsHasNextPage,
- additionalData: mockAdditionalData,
+ additionalData: groupsAdditionalData,
}),
};
@@ -169,9 +167,9 @@ describe('ProjectsAndGroupChart', () => {
});
describe.each`
- metric | loadingState | newData
- ${'projects'} | ${{ projectsHasNextPage: true }} | ${{ projects: mockCountsData2 }}
- ${'groups'} | ${{ groupsHasNextPage: true }} | ${{ groups: mockCountsData2 }}
+ metric | loadingState | newData
+ ${'projects'} | ${{ projectsAdditionalData: mockAdditionalData }} | ${{ projects: mockCountsData2 }}
+ ${'groups'} | ${{ groupsAdditionalData: mockAdditionalData }} | ${{ groups: mockCountsData2 }}
`('$metric - fetchMore', ({ metric, loadingState, newData }) => {
describe('when the fetchMore query returns data', () => {
beforeEach(async () => {
diff --git a/spec/frontend/analytics/instance_statistics/components/users_chart_spec.js b/spec/frontend/analytics/instance_statistics/components/users_chart_spec.js
index 2942df95fdf..6ed9d203f3d 100644
--- a/spec/frontend/analytics/instance_statistics/components/users_chart_spec.js
+++ b/spec/frontend/analytics/instance_statistics/components/users_chart_spec.js
@@ -7,7 +7,11 @@ import { useFakeDate } from 'helpers/fake_date';
import UsersChart from '~/analytics/instance_statistics/components/users_chart.vue';
import ChartSkeletonLoader from '~/vue_shared/components/resizable_chart/skeleton_loader.vue';
import usersQuery from '~/analytics/instance_statistics/graphql/queries/users.query.graphql';
-import { mockCountsData2, roundedSortedCountsMonthlyChartData2 } from '../mock_data';
+import {
+ mockCountsData1,
+ mockCountsData2,
+ roundedSortedCountsMonthlyChartData2,
+} from '../mock_data';
import { mockQueryResponse } from '../apollo_mock_data';
const localVue = createLocalVue();
@@ -21,9 +25,9 @@ describe('UsersChart', () => {
loadingError = false,
loading = false,
users = [],
- hasNextPage = false,
+ additionalData = [],
} = {}) => {
- queryHandler = mockQueryResponse({ key: 'users', data: users, loading, hasNextPage });
+ queryHandler = mockQueryResponse({ key: 'users', data: users, loading, additionalData });
return shallowMount(UsersChart, {
props: {
@@ -128,7 +132,7 @@ describe('UsersChart', () => {
beforeEach(async () => {
wrapper = createComponent({
users: mockCountsData2,
- hasNextPage: true,
+ additionalData: mockCountsData1,
});
jest.spyOn(wrapper.vm.$apollo.queries.users, 'fetchMore');
@@ -148,7 +152,7 @@ describe('UsersChart', () => {
beforeEach(() => {
wrapper = createComponent({
users: mockCountsData2,
- hasNextPage: true,
+ additionalData: mockCountsData1,
});
jest
diff --git a/spec/frontend/analytics/instance_statistics/utils_spec.js b/spec/frontend/analytics/instance_statistics/utils_spec.js
index 1a0cf35ead1..3fd89c7f740 100644
--- a/spec/frontend/analytics/instance_statistics/utils_spec.js
+++ b/spec/frontend/analytics/instance_statistics/utils_spec.js
@@ -1,7 +1,7 @@
import {
getAverageByMonth,
- extractValues,
- sortByDate,
+ getEarliestDate,
+ generateDataKeys,
} from '~/analytics/instance_statistics/utils';
import {
mockCountsData1,
@@ -44,55 +44,38 @@ describe('getAverageByMonth', () => {
});
});
-describe('extractValues', () => {
- it('extracts only requested values', () => {
- const data = { fooBar: { baz: 'quis' }, ignored: 'ignored' };
- expect(extractValues(data, ['bar'], 'foo', 'baz')).toEqual({ bazBar: 'quis' });
+describe('getEarliestDate', () => {
+ it('returns the date of the final item in the array', () => {
+ expect(getEarliestDate(mockCountsData1)).toBe('2020-06-12');
});
- it('it renames with the `renameKey` if provided', () => {
- const data = { fooBar: { baz: 'quis' }, ignored: 'ignored' };
- expect(extractValues(data, ['bar'], 'foo', 'baz', { renameKey: 'renamed' })).toEqual({
- renamedBar: 'quis',
- });
+ it('returns null for an empty array', () => {
+ expect(getEarliestDate([])).toBeNull();
});
- it('is able to get nested data', () => {
- const data = { fooBar: { even: [{ further: 'nested' }] }, ignored: 'ignored' };
- expect(extractValues(data, ['bar'], 'foo', 'even[0].further')).toEqual({
- 'even[0].furtherBar': 'nested',
- });
- });
-
- it('is able to extract multiple values', () => {
- const data = {
- fooBar: { baz: 'quis' },
- fooBaz: { baz: 'quis' },
- fooQuis: { baz: 'quis' },
- };
- expect(extractValues(data, ['bar', 'baz', 'quis'], 'foo', 'baz')).toEqual({
- bazBar: 'quis',
- bazBaz: 'quis',
- bazQuis: 'quis',
- });
+ it("returns null if the array has data but `recordedAt` isn't defined", () => {
+ expect(
+ getEarliestDate(mockCountsData1.map(({ recordedAt: date, ...rest }) => ({ date, ...rest }))),
+ ).toBeNull();
});
+});
- it('returns empty data set when keys are not found', () => {
- const data = { foo: { baz: 'quis' }, ignored: 'ignored' };
- expect(extractValues(data, ['bar'], 'foo', 'baz')).toEqual({});
- });
+describe('generateDataKeys', () => {
+ const fakeQueries = [
+ { identifier: 'from' },
+ { identifier: 'first' },
+ { identifier: 'to' },
+ { identifier: 'last' },
+ ];
- it('returns empty data when params are missing', () => {
- expect(extractValues()).toEqual({});
- });
-});
+ const defaultValue = 'default value';
+ const res = generateDataKeys(fakeQueries, defaultValue);
-describe('sortByDate', () => {
- it('sorts the array by date', () => {
- expect(sortByDate(mockCountsData1)).toStrictEqual([...mockCountsData1].reverse());
+ it('extracts each query identifier and sets them as object keys', () => {
+ expect(Object.keys(res)).toEqual(['from', 'first', 'to', 'last']);
});
- it('does not modify the original array', () => {
- expect(sortByDate(countsMonthlyChartData1)).not.toBe(countsMonthlyChartData1);
+ it('sets every value to the `defaultValue` provided', () => {
+ expect(Object.values(res)).toEqual(Array(fakeQueries.length).fill(defaultValue));
});
});