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
path: root/spec
diff options
context:
space:
mode:
Diffstat (limited to 'spec')
-rw-r--r--spec/features/issues/bulk_assignment_labels_spec.rb4
-rw-r--r--spec/features/issues/issue_sidebar_spec.rb2
-rw-r--r--spec/features/issues/note_polling_spec.rb2
-rw-r--r--spec/features/issues/user_creates_branch_and_merge_request_spec.rb2
-rw-r--r--spec/features/issues/user_creates_confidential_merge_request_spec.rb2
-rw-r--r--spec/features/issues/user_edits_issue_spec.rb4
-rw-r--r--spec/features/issues/user_filters_issues_spec.rb2
-rw-r--r--spec/features/issues/user_sees_live_update_spec.rb2
-rw-r--r--spec/features/issues/user_sorts_issues_spec.rb46
-rw-r--r--spec/frontend/__helpers__/vue_test_utils_helper.js73
-rw-r--r--spec/frontend/__helpers__/vue_test_utils_helper_spec.js208
-rw-r--r--spec/frontend/members/components/action_buttons/access_request_action_buttons_spec.js1
-rw-r--r--spec/frontend/members/components/action_buttons/invite_action_buttons_spec.js1
-rw-r--r--spec/frontend/members/components/action_buttons/remove_member_button_spec.js2
-rw-r--r--spec/frontend/members/components/action_buttons/user_action_buttons_spec.js1
-rw-r--r--spec/frontend/vue_shared/components/remove_member_modal_spec.js11
-rw-r--r--spec/graphql/resolvers/ci/jobs_resolver_spec.rb17
-rw-r--r--spec/graphql/types/ci/job_type_spec.rb1
-rw-r--r--spec/models/concerns/batch_destroy_dependent_associations_spec.rb1
-rw-r--r--spec/models/concerns/featurable_spec.rb1
-rw-r--r--spec/requests/api/commit_statuses_spec.rb8
-rw-r--r--spec/requests/api/deployments_spec.rb4
-rw-r--r--spec/requests/api/environments_spec.rb2
-rw-r--r--spec/requests/api/go_proxy_spec.rb4
-rw-r--r--spec/requests/api/graphql/mutations/merge_requests/set_labels_spec.rb2
-rw-r--r--spec/requests/api/group_import_spec.rb2
-rw-r--r--spec/requests/api/group_milestones_spec.rb6
-rw-r--r--spec/requests/api/internal/base_spec.rb2
-rw-r--r--spec/requests/api/issues/get_group_issues_spec.rb2
-rw-r--r--spec/requests/api/issues/post_projects_issues_spec.rb2
-rw-r--r--spec/requests/api/jobs_spec.rb12
-rw-r--r--spec/requests/api/labels_spec.rb6
-rw-r--r--spec/requests/api/project_import_spec.rb4
33 files changed, 371 insertions, 68 deletions
diff --git a/spec/features/issues/bulk_assignment_labels_spec.rb b/spec/features/issues/bulk_assignment_labels_spec.rb
index aa61aff3b05..80bf964e2ee 100644
--- a/spec/features/issues/bulk_assignment_labels_spec.rb
+++ b/spec/features/issues/bulk_assignment_labels_spec.rb
@@ -295,8 +295,8 @@ RSpec.describe 'Issues > Labels bulk assignment' do
before do
issue1.milestone = milestone
issue2.milestone = milestone
- issue1.save
- issue2.save
+ issue1.save!
+ issue2.save!
issue1.labels << bug
issue2.labels << feature
diff --git a/spec/features/issues/issue_sidebar_spec.rb b/spec/features/issues/issue_sidebar_spec.rb
index ca44978d223..bbf2a889880 100644
--- a/spec/features/issues/issue_sidebar_spec.rb
+++ b/spec/features/issues/issue_sidebar_spec.rb
@@ -171,7 +171,7 @@ RSpec.describe 'Issue Sidebar' do
context 'editing issue labels', :js do
before do
- issue.update(labels: [label])
+ issue.update!(labels: [label])
page.within('.block.labels') do
click_on 'Edit'
end
diff --git a/spec/features/issues/note_polling_spec.rb b/spec/features/issues/note_polling_spec.rb
index bc4c67fdd79..5e02d5ad038 100644
--- a/spec/features/issues/note_polling_spec.rb
+++ b/spec/features/issues/note_polling_spec.rb
@@ -103,7 +103,7 @@ RSpec.describe 'Issue notes polling', :js do
end
def update_note(note, new_text)
- note.update(note: new_text)
+ note.update!(note: new_text)
wait_for_requests
end
diff --git a/spec/features/issues/user_creates_branch_and_merge_request_spec.rb b/spec/features/issues/user_creates_branch_and_merge_request_spec.rb
index e225a45481d..6e8b3e4fb7c 100644
--- a/spec/features/issues/user_creates_branch_and_merge_request_spec.rb
+++ b/spec/features/issues/user_creates_branch_and_merge_request_spec.rb
@@ -150,7 +150,7 @@ RSpec.describe 'User creates branch and merge request on issue page', :js do
context 'when merge requests are disabled' do
before do
- project.project_feature.update(merge_requests_access_level: 0)
+ project.project_feature.update!(merge_requests_access_level: 0)
visit project_issue_path(project, issue)
end
diff --git a/spec/features/issues/user_creates_confidential_merge_request_spec.rb b/spec/features/issues/user_creates_confidential_merge_request_spec.rb
index ea96165d7b7..6b4526cd624 100644
--- a/spec/features/issues/user_creates_confidential_merge_request_spec.rb
+++ b/spec/features/issues/user_creates_confidential_merge_request_spec.rb
@@ -38,7 +38,7 @@ RSpec.describe 'User creates confidential merge request on issue page', :js do
let(:forked_project) { fork_project(project, user, repository: true) }
before do
- forked_project.update(visibility: Gitlab::VisibilityLevel::PRIVATE)
+ forked_project.update!(visibility: Gitlab::VisibilityLevel::PRIVATE)
visit_confidential_issue
end
diff --git a/spec/features/issues/user_edits_issue_spec.rb b/spec/features/issues/user_edits_issue_spec.rb
index b8e35c9afa3..4b0886ee85e 100644
--- a/spec/features/issues/user_edits_issue_spec.rb
+++ b/spec/features/issues/user_edits_issue_spec.rb
@@ -78,7 +78,7 @@ RSpec.describe "Issues > User edits issue", :js do
end
it 'warns about version conflict' do
- issue.update(title: "New title")
+ issue.update!(title: "New title")
fill_in 'issue_title', with: 'bug 345'
fill_in 'issue_description', with: 'bug description'
@@ -307,7 +307,7 @@ RSpec.describe "Issues > User edits issue", :js do
before do
project.add_guest(guest)
issue.milestone = milestone
- issue.save
+ issue.save!
end
it 'shows milestone text' do
diff --git a/spec/features/issues/user_filters_issues_spec.rb b/spec/features/issues/user_filters_issues_spec.rb
index 1b246181523..5d05df6aaf0 100644
--- a/spec/features/issues/user_filters_issues_spec.rb
+++ b/spec/features/issues/user_filters_issues_spec.rb
@@ -18,7 +18,7 @@ RSpec.describe 'User filters issues', :js do
@issue = Issue.find_by(title: 'foobar')
@issue.milestone = create(:milestone, project: project)
@issue.assignees = []
- @issue.save
+ @issue.save!
end
let(:issue) { @issue }
diff --git a/spec/features/issues/user_sees_live_update_spec.rb b/spec/features/issues/user_sees_live_update_spec.rb
index 79c6978cbc0..7e4880f209e 100644
--- a/spec/features/issues/user_sees_live_update_spec.rb
+++ b/spec/features/issues/user_sees_live_update_spec.rb
@@ -18,7 +18,7 @@ RSpec.describe 'Issues > User sees live update', :js do
expect(page).to have_text("new title")
- issue.update(title: "updated title")
+ issue.update!(title: "updated title")
wait_for_requests
expect(page).to have_text("updated title")
diff --git a/spec/features/issues/user_sorts_issues_spec.rb b/spec/features/issues/user_sorts_issues_spec.rb
index f0bb055c6f2..c161e1deb83 100644
--- a/spec/features/issues/user_sorts_issues_spec.rb
+++ b/spec/features/issues/user_sorts_issues_spec.rb
@@ -77,7 +77,7 @@ RSpec.describe "User sorts issues" do
it 'sorts by most recently updated', :js do
issue3.updated_at = Time.now + 100
- issue3.save
+ issue3.save!
visit project_issues_path(project, sort: sort_value_recently_updated)
expect(first_issue).to include('baz')
@@ -85,8 +85,8 @@ RSpec.describe "User sorts issues" do
describe 'sorting by due date', :js do
before do
- issue1.update(due_date: 1.day.from_now)
- issue2.update(due_date: 6.days.from_now)
+ issue1.update!(due_date: 1.day.from_now)
+ issue2.update!(due_date: 6.days.from_now)
end
it 'sorts by due date' do
@@ -96,7 +96,7 @@ RSpec.describe "User sorts issues" do
end
it 'sorts by due date by excluding nil due dates' do
- issue2.update(due_date: nil)
+ issue2.update!(due_date: nil)
visit project_issues_path(project, sort: sort_value_due_date)
@@ -111,7 +111,7 @@ RSpec.describe "User sorts issues" do
end
it 'sorts by least recently due date by excluding nil due dates' do
- issue2.update(due_date: nil)
+ issue2.update!(due_date: nil)
visit project_issues_path(project, label_names: [label.name], sort: sort_value_due_date_later)
@@ -122,8 +122,8 @@ RSpec.describe "User sorts issues" do
describe 'filtering by due date', :js do
before do
- issue1.update(due_date: 1.day.from_now)
- issue2.update(due_date: 6.days.from_now)
+ issue1.update!(due_date: 1.day.from_now)
+ issue2.update!(due_date: 6.days.from_now)
end
it 'filters by none' do
@@ -147,9 +147,9 @@ RSpec.describe "User sorts issues" do
end
it 'filters by due this week' do
- issue1.update(due_date: Date.today.beginning_of_week + 2.days)
- issue2.update(due_date: Date.today.end_of_week)
- issue3.update(due_date: Date.today - 8.days)
+ issue1.update!(due_date: Date.today.beginning_of_week + 2.days)
+ issue2.update!(due_date: Date.today.end_of_week)
+ issue3.update!(due_date: Date.today - 8.days)
visit project_issues_path(project, due_date: Issue::DueThisWeek.name)
@@ -161,9 +161,9 @@ RSpec.describe "User sorts issues" do
end
it 'filters by due this month' do
- issue1.update(due_date: Date.today.beginning_of_month + 2.days)
- issue2.update(due_date: Date.today.end_of_month)
- issue3.update(due_date: Date.today - 50.days)
+ issue1.update!(due_date: Date.today.beginning_of_month + 2.days)
+ issue2.update!(due_date: Date.today.end_of_month)
+ issue3.update!(due_date: Date.today - 50.days)
visit project_issues_path(project, due_date: Issue::DueThisMonth.name)
@@ -175,9 +175,9 @@ RSpec.describe "User sorts issues" do
end
it 'filters by overdue' do
- issue1.update(due_date: Date.today + 2.days)
- issue2.update(due_date: Date.today + 20.days)
- issue3.update(due_date: Date.yesterday)
+ issue1.update!(due_date: Date.today + 2.days)
+ issue2.update!(due_date: Date.today + 20.days)
+ issue3.update!(due_date: Date.yesterday)
visit project_issues_path(project, due_date: Issue::Overdue.name)
@@ -189,9 +189,9 @@ RSpec.describe "User sorts issues" do
end
it 'filters by due next month and previous two weeks' do
- issue1.update(due_date: Date.today - 4.weeks)
- issue2.update(due_date: (Date.today + 2.months).beginning_of_month)
- issue3.update(due_date: Date.yesterday)
+ issue1.update!(due_date: Date.today - 4.weeks)
+ issue2.update!(due_date: (Date.today + 2.months).beginning_of_month)
+ issue3.update!(due_date: Date.yesterday)
visit project_issues_path(project, due_date: Issue::DueNextMonthAndPreviousTwoWeeks.name)
@@ -206,9 +206,9 @@ RSpec.describe "User sorts issues" do
describe 'sorting by milestone', :js do
before do
issue1.milestone = newer_due_milestone
- issue1.save
+ issue1.save!
issue2.milestone = later_due_milestone
- issue2.save
+ issue2.save!
end
it 'sorts by milestone' do
@@ -224,9 +224,9 @@ RSpec.describe "User sorts issues" do
before do
issue1.assignees << user2
- issue1.save
+ issue1.save!
issue2.assignees << user2
- issue2.save
+ issue2.save!
end
it 'sorts with a filter applied' do
diff --git a/spec/frontend/__helpers__/vue_test_utils_helper.js b/spec/frontend/__helpers__/vue_test_utils_helper.js
index d6132ef84ac..a94cee84f74 100644
--- a/spec/frontend/__helpers__/vue_test_utils_helper.js
+++ b/spec/frontend/__helpers__/vue_test_utils_helper.js
@@ -1,4 +1,6 @@
-import { isArray } from 'lodash';
+import * as testingLibrary from '@testing-library/dom';
+import { createWrapper, WrapperArray, mount, shallowMount } from '@vue/test-utils';
+import { isArray, upperFirst } from 'lodash';
const vNodeContainsText = (vnode, text) =>
(vnode.text && vnode.text.includes(text)) ||
@@ -37,6 +39,17 @@ export const waitForMutation = (store, expectedMutationType) =>
});
export const extendedWrapper = (wrapper) => {
+ // https://testing-library.com/docs/queries/about
+ const AVAILABLE_QUERIES = [
+ 'byRole',
+ 'byLabelText',
+ 'byPlaceholderText',
+ 'byText',
+ 'byDisplayValue',
+ 'byAltText',
+ 'byTitle',
+ ];
+
if (isArray(wrapper) || !wrapper?.find) {
// eslint-disable-next-line no-console
console.warn(
@@ -56,5 +69,63 @@ export const extendedWrapper = (wrapper) => {
return this.findAll(`[data-testid="${id}"]`);
},
},
+ // `findBy`
+ ...AVAILABLE_QUERIES.reduce((accumulator, query) => {
+ return {
+ ...accumulator,
+ [`find${upperFirst(query)}`]: {
+ value(text, options = {}) {
+ const elements = testingLibrary[`queryAll${upperFirst(query)}`](
+ wrapper.element,
+ text,
+ options,
+ );
+
+ // Return VTU `ErrorWrapper` if element is not found
+ // https://github.com/vuejs/vue-test-utils/blob/dev/packages/test-utils/src/error-wrapper.js
+ // VTU does not expose `ErrorWrapper` so, as of now, this is the best way to
+ // create an `ErrorWrapper`
+ if (!elements.length) {
+ const emptyElement = document.createElement('div');
+
+ return createWrapper(emptyElement).find('testing-library-element-not-found');
+ }
+
+ return createWrapper(elements[0], this.options || {});
+ },
+ },
+ };
+ }, {}),
+ // `findAllBy`
+ ...AVAILABLE_QUERIES.reduce((accumulator, query) => {
+ return {
+ ...accumulator,
+ [`findAll${upperFirst(query)}`]: {
+ value(text, options = {}) {
+ const elements = testingLibrary[`queryAll${upperFirst(query)}`](
+ wrapper.element,
+ text,
+ options,
+ );
+
+ const wrappers = elements.map((element) => {
+ const elementWrapper = createWrapper(element, this.options || {});
+ elementWrapper.selector = text;
+
+ return elementWrapper;
+ });
+
+ const wrapperArray = new WrapperArray(wrappers);
+ wrapperArray.selector = text;
+
+ return wrapperArray;
+ },
+ },
+ };
+ }, {}),
});
};
+
+export const shallowMountExtended = (...args) => extendedWrapper(shallowMount(...args));
+
+export const mountExtended = (...args) => extendedWrapper(mount(...args));
diff --git a/spec/frontend/__helpers__/vue_test_utils_helper_spec.js b/spec/frontend/__helpers__/vue_test_utils_helper_spec.js
index d4f8e36c169..dfe5a483223 100644
--- a/spec/frontend/__helpers__/vue_test_utils_helper_spec.js
+++ b/spec/frontend/__helpers__/vue_test_utils_helper_spec.js
@@ -1,7 +1,27 @@
-import { shallowMount } from '@vue/test-utils';
-import { extendedWrapper, shallowWrapperContainsSlotText } from './vue_test_utils_helper';
+import * as testingLibrary from '@testing-library/dom';
+import * as vtu from '@vue/test-utils';
+import {
+ shallowMount,
+ Wrapper as VTUWrapper,
+ WrapperArray as VTUWrapperArray,
+} from '@vue/test-utils';
+import {
+ extendedWrapper,
+ shallowMountExtended,
+ mountExtended,
+ shallowWrapperContainsSlotText,
+} from './vue_test_utils_helper';
+
+jest.mock('@testing-library/dom', () => ({
+ __esModule: true,
+ ...jest.requireActual('@testing-library/dom'),
+}));
describe('Vue test utils helpers', () => {
+ afterAll(() => {
+ jest.unmock('@testing-library/dom');
+ });
+
describe('shallowWrapperContainsSlotText', () => {
const mockText = 'text';
const mockSlot = `<div>${mockText}</div>`;
@@ -84,7 +104,7 @@ describe('Vue test utils helpers', () => {
);
});
- it('should find the component by test id', () => {
+ it('should find the element by test id', () => {
expect(mockComponent.findByTestId(testId).exists()).toBe(true);
});
});
@@ -105,5 +125,187 @@ describe('Vue test utils helpers', () => {
expect(mockComponent.findAllByTestId(testId)).toHaveLength(2);
});
});
+
+ describe.each`
+ findMethod | expectedQuery
+ ${'findByRole'} | ${'queryAllByRole'}
+ ${'findByLabelText'} | ${'queryAllByLabelText'}
+ ${'findByPlaceholderText'} | ${'queryAllByPlaceholderText'}
+ ${'findByText'} | ${'queryAllByText'}
+ ${'findByDisplayValue'} | ${'queryAllByDisplayValue'}
+ ${'findByAltText'} | ${'queryAllByAltText'}
+ `('$findMethod', ({ findMethod, expectedQuery }) => {
+ const text = 'foo bar';
+ const options = { selector: 'div' };
+ const mockDiv = document.createElement('div');
+
+ let wrapper;
+ beforeEach(() => {
+ wrapper = extendedWrapper(
+ shallowMount({
+ template: `<div>foo bar</div>`,
+ }),
+ );
+ });
+
+ it(`calls Testing Library \`${expectedQuery}\` function with correct parameters`, () => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => [mockDiv]);
+
+ wrapper[findMethod](text, options);
+
+ expect(testingLibrary[expectedQuery]).toHaveBeenLastCalledWith(
+ wrapper.element,
+ text,
+ options,
+ );
+ });
+
+ describe('when element is found', () => {
+ beforeEach(() => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => [mockDiv]);
+ jest.spyOn(vtu, 'createWrapper');
+ });
+
+ it('returns a VTU wrapper', () => {
+ const result = wrapper[findMethod](text, options);
+
+ expect(vtu.createWrapper).toHaveBeenCalledWith(mockDiv, wrapper.options);
+ expect(result).toBeInstanceOf(VTUWrapper);
+ });
+ });
+
+ describe('when multiple elements are found', () => {
+ beforeEach(() => {
+ const mockSpan = document.createElement('span');
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => [mockDiv, mockSpan]);
+ jest.spyOn(vtu, 'createWrapper');
+ });
+
+ it('returns the first element as a VTU wrapper', () => {
+ const result = wrapper[findMethod](text, options);
+
+ expect(vtu.createWrapper).toHaveBeenCalledWith(mockDiv, wrapper.options);
+ expect(result).toBeInstanceOf(VTUWrapper);
+ });
+ });
+
+ describe('when element is not found', () => {
+ beforeEach(() => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => []);
+ });
+
+ it('returns a VTU error wrapper', () => {
+ expect(wrapper[findMethod](text, options).exists()).toBe(false);
+ });
+ });
+ });
+
+ describe.each`
+ findMethod | expectedQuery
+ ${'findAllByRole'} | ${'queryAllByRole'}
+ ${'findAllByLabelText'} | ${'queryAllByLabelText'}
+ ${'findAllByPlaceholderText'} | ${'queryAllByPlaceholderText'}
+ ${'findAllByText'} | ${'queryAllByText'}
+ ${'findAllByDisplayValue'} | ${'queryAllByDisplayValue'}
+ ${'findAllByAltText'} | ${'queryAllByAltText'}
+ `('$findMethod', ({ findMethod, expectedQuery }) => {
+ const text = 'foo bar';
+ const options = { selector: 'div' };
+ const mockElements = [
+ document.createElement('li'),
+ document.createElement('li'),
+ document.createElement('li'),
+ ];
+
+ let wrapper;
+ beforeEach(() => {
+ wrapper = extendedWrapper(
+ shallowMount({
+ template: `
+ <ul>
+ <li>foo</li>
+ <li>bar</li>
+ <li>baz</li>
+ </ul>
+ `,
+ }),
+ );
+ });
+
+ it(`calls Testing Library \`${expectedQuery}\` function with correct parameters`, () => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => mockElements);
+
+ wrapper[findMethod](text, options);
+
+ expect(testingLibrary[expectedQuery]).toHaveBeenLastCalledWith(
+ wrapper.element,
+ text,
+ options,
+ );
+ });
+
+ describe('when elements are found', () => {
+ beforeEach(() => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => mockElements);
+ });
+
+ it('returns a VTU wrapper array', () => {
+ const result = wrapper[findMethod](text, options);
+
+ expect(result).toBeInstanceOf(VTUWrapperArray);
+ expect(
+ result.wrappers.every(
+ (resultWrapper) =>
+ resultWrapper instanceof VTUWrapper && resultWrapper.options === wrapper.options,
+ ),
+ ).toBe(true);
+ expect(result.length).toBe(3);
+ });
+ });
+
+ describe('when elements are not found', () => {
+ beforeEach(() => {
+ jest.spyOn(testingLibrary, expectedQuery).mockImplementation(() => []);
+ });
+
+ it('returns an empty VTU wrapper array', () => {
+ const result = wrapper[findMethod](text, options);
+
+ expect(result).toBeInstanceOf(VTUWrapperArray);
+ expect(result.length).toBe(0);
+ });
+ });
+ });
+ });
+
+ describe.each`
+ mountExtendedFunction | expectedMountFunction
+ ${shallowMountExtended} | ${'shallowMount'}
+ ${mountExtended} | ${'mount'}
+ `('$mountExtendedFunction', ({ mountExtendedFunction, expectedMountFunction }) => {
+ const FakeComponent = jest.fn();
+ const options = {
+ propsData: {
+ foo: 'bar',
+ },
+ };
+
+ beforeEach(() => {
+ const mockWrapper = { find: jest.fn() };
+ jest.spyOn(vtu, expectedMountFunction).mockImplementation(() => mockWrapper);
+ });
+
+ it(`calls \`${expectedMountFunction}\` with passed arguments`, () => {
+ mountExtendedFunction(FakeComponent, options);
+
+ expect(vtu[expectedMountFunction]).toHaveBeenCalledWith(FakeComponent, options);
+ });
+
+ it('returns extended wrapper', () => {
+ const result = mountExtendedFunction(FakeComponent, options);
+
+ expect(result).toHaveProperty('find');
+ expect(result).toHaveProperty('findByTestId');
+ });
});
});
diff --git a/spec/frontend/members/components/action_buttons/access_request_action_buttons_spec.js b/spec/frontend/members/components/action_buttons/access_request_action_buttons_spec.js
index f86237dc160..f1471f625f8 100644
--- a/spec/frontend/members/components/action_buttons/access_request_action_buttons_spec.js
+++ b/spec/frontend/members/components/action_buttons/access_request_action_buttons_spec.js
@@ -42,6 +42,7 @@ describe('AccessRequestActionButtons', () => {
memberId: member.id,
title: 'Deny access',
isAccessRequest: true,
+ isInvite: false,
icon: 'close',
});
});
diff --git a/spec/frontend/members/components/action_buttons/invite_action_buttons_spec.js b/spec/frontend/members/components/action_buttons/invite_action_buttons_spec.js
index 55866f90baa..e7a99a96da6 100644
--- a/spec/frontend/members/components/action_buttons/invite_action_buttons_spec.js
+++ b/spec/frontend/members/components/action_buttons/invite_action_buttons_spec.js
@@ -43,6 +43,7 @@ describe('InviteActionButtons', () => {
message: `Are you sure you want to revoke the invitation for ${member.invite.email} to join "${member.source.fullName}"`,
title: 'Revoke invite',
isAccessRequest: false,
+ isInvite: true,
icon: 'remove',
});
});
diff --git a/spec/frontend/members/components/action_buttons/remove_member_button_spec.js b/spec/frontend/members/components/action_buttons/remove_member_button_spec.js
index 0d66f343fda..952ce679a2f 100644
--- a/spec/frontend/members/components/action_buttons/remove_member_button_spec.js
+++ b/spec/frontend/members/components/action_buttons/remove_member_button_spec.js
@@ -28,6 +28,7 @@ describe('RemoveMemberButton', () => {
message: 'Are you sure you want to remove John Smith?',
title: 'Remove member',
isAccessRequest: true,
+ isInvite: true,
...propsData,
},
directives: {
@@ -48,6 +49,7 @@ describe('RemoveMemberButton', () => {
'data-member-type': 'GroupMember',
'data-message': 'Are you sure you want to remove John Smith?',
'data-is-access-request': 'true',
+ 'data-is-invite': 'true',
'aria-label': 'Remove member',
title: 'Remove member',
icon: 'remove',
diff --git a/spec/frontend/members/components/action_buttons/user_action_buttons_spec.js b/spec/frontend/members/components/action_buttons/user_action_buttons_spec.js
index f43779b8970..2f13c436fd9 100644
--- a/spec/frontend/members/components/action_buttons/user_action_buttons_spec.js
+++ b/spec/frontend/members/components/action_buttons/user_action_buttons_spec.js
@@ -43,6 +43,7 @@ describe('UserActionButtons', () => {
message: `Are you sure you want to remove ${member.user.name} from "${member.source.fullName}"`,
title: 'Remove member',
isAccessRequest: false,
+ isInvite: false,
icon: 'remove',
});
});
diff --git a/spec/frontend/vue_shared/components/remove_member_modal_spec.js b/spec/frontend/vue_shared/components/remove_member_modal_spec.js
index 1ef3cc348bd..7a04de13615 100644
--- a/spec/frontend/vue_shared/components/remove_member_modal_spec.js
+++ b/spec/frontend/vue_shared/components/remove_member_modal_spec.js
@@ -15,16 +15,18 @@ describe('RemoveMemberModal', () => {
});
describe.each`
- state | memberType | isAccessRequest | actionText | removeSubMembershipsCheckboxExpected | unassignIssuablesCheckboxExpected | message
- ${'removing a group member'} | ${'GroupMember'} | ${'false'} | ${'Remove member'} | ${true} | ${true} | ${'Are you sure you want to remove Jane Doe from the Gitlab Org / Gitlab Test project?'}
- ${'removing a project member'} | ${'ProjectMember'} | ${'false'} | ${'Remove member'} | ${false} | ${true} | ${'Are you sure you want to remove Jane Doe from the Gitlab Org / Gitlab Test project?'}
- ${'denying an access request'} | ${'ProjectMember'} | ${'true'} | ${'Deny access request'} | ${false} | ${false} | ${"Are you sure you want to deny Jane Doe's request to join the Gitlab Org / Gitlab Test project?"}
+ state | memberType | isAccessRequest | isInvite | actionText | removeSubMembershipsCheckboxExpected | unassignIssuablesCheckboxExpected | message
+ ${'removing a group member'} | ${'GroupMember'} | ${'false'} | ${'false'} | ${'Remove member'} | ${true} | ${true} | ${'Are you sure you want to remove Jane Doe from the Gitlab Org / Gitlab Test project?'}
+ ${'removing a project member'} | ${'ProjectMember'} | ${'false'} | ${'false'} | ${'Remove member'} | ${false} | ${true} | ${'Are you sure you want to remove Jane Doe from the Gitlab Org / Gitlab Test project?'}
+ ${'denying an access request'} | ${'ProjectMember'} | ${'true'} | ${'false'} | ${'Deny access request'} | ${false} | ${false} | ${"Are you sure you want to deny Jane Doe's request to join the Gitlab Org / Gitlab Test project?"}
+ ${'revoking invite'} | ${'ProjectMember'} | ${'false'} | ${'true'} | ${'Revoke invite'} | ${false} | ${false} | ${'Are you sure you want to revoke the invitation for foo@bar.com to join the Gitlab Org / Gitlab Test project?'}
`(
'when $state',
({
actionText,
memberType,
isAccessRequest,
+ isInvite,
message,
removeSubMembershipsCheckboxExpected,
unassignIssuablesCheckboxExpected,
@@ -35,6 +37,7 @@ describe('RemoveMemberModal', () => {
return {
modalData: {
isAccessRequest,
+ isInvite,
message,
memberPath,
memberType,
diff --git a/spec/graphql/resolvers/ci/jobs_resolver_spec.rb b/spec/graphql/resolvers/ci/jobs_resolver_spec.rb
index c44f6b623d7..1b69bf7f63a 100644
--- a/spec/graphql/resolvers/ci/jobs_resolver_spec.rb
+++ b/spec/graphql/resolvers/ci/jobs_resolver_spec.rb
@@ -13,6 +13,7 @@ RSpec.describe Resolvers::Ci::JobsResolver do
create(:ci_build, :sast, name: 'DAST job', pipeline: pipeline)
create(:ci_build, :dast, name: 'SAST job', pipeline: pipeline)
create(:ci_build, :container_scanning, name: 'Container scanning job', pipeline: pipeline)
+ create(:ci_build, name: 'Job with tags', pipeline: pipeline, tag_list: ['review'])
end
describe '#resolve' do
@@ -24,7 +25,8 @@ RSpec.describe Resolvers::Ci::JobsResolver do
have_attributes(name: 'Normal job'),
have_attributes(name: 'DAST job'),
have_attributes(name: 'SAST job'),
- have_attributes(name: 'Container scanning job')
+ have_attributes(name: 'Container scanning job'),
+ have_attributes(name: 'Job with tags')
)
end
end
@@ -43,5 +45,18 @@ RSpec.describe Resolvers::Ci::JobsResolver do
)
end
end
+
+ context 'when a job has tags' do
+ it "returns jobs with tags when applicable" do
+ jobs = resolve(described_class, obj: pipeline)
+ expect(jobs).to contain_exactly(
+ have_attributes(tag_list: []),
+ have_attributes(tag_list: []),
+ have_attributes(tag_list: []),
+ have_attributes(tag_list: []),
+ have_attributes(tag_list: ['review'])
+ )
+ end
+ end
end
end
diff --git a/spec/graphql/types/ci/job_type_spec.rb b/spec/graphql/types/ci/job_type_spec.rb
index 75a178bc8f6..787e2174070 100644
--- a/spec/graphql/types/ci/job_type_spec.rb
+++ b/spec/graphql/types/ci/job_type_spec.rb
@@ -33,6 +33,7 @@ RSpec.describe Types::Ci::JobType do
stage
started_at
status
+ tags
]
expect(described_class).to have_graphql_fields(*expected_fields)
diff --git a/spec/models/concerns/batch_destroy_dependent_associations_spec.rb b/spec/models/concerns/batch_destroy_dependent_associations_spec.rb
index a8fcb714c64..993afd47a57 100644
--- a/spec/models/concerns/batch_destroy_dependent_associations_spec.rb
+++ b/spec/models/concerns/batch_destroy_dependent_associations_spec.rb
@@ -26,6 +26,7 @@ RSpec.describe BatchDestroyDependentAssociations do
let_it_be(:project) { create(:project) }
let_it_be(:build) { create(:ci_build, project: project) }
let_it_be(:notification_setting) { create(:notification_setting, project: project) }
+
let!(:todos) { create(:todo, project: project) }
it 'destroys multiple builds' do
diff --git a/spec/models/concerns/featurable_spec.rb b/spec/models/concerns/featurable_spec.rb
index b550d22f686..bcff5ce383e 100644
--- a/spec/models/concerns/featurable_spec.rb
+++ b/spec/models/concerns/featurable_spec.rb
@@ -4,6 +4,7 @@ require 'spec_helper'
RSpec.describe Featurable do
let_it_be(:user) { create(:user) }
+
let(:project) { create(:project) }
let(:feature_class) { subject.class }
let(:features) { feature_class::FEATURES }
diff --git a/spec/requests/api/commit_statuses_spec.rb b/spec/requests/api/commit_statuses_spec.rb
index 10fa15d468f..ac125e81acd 100644
--- a/spec/requests/api/commit_statuses_spec.rb
+++ b/spec/requests/api/commit_statuses_spec.rb
@@ -14,8 +14,8 @@ RSpec.describe API::CommitStatuses do
let(:get_url) { "/projects/#{project.id}/repository/commits/#{sha}/statuses" }
context 'ci commit exists' do
- let!(:master) { project.ci_pipelines.create(source: :push, sha: commit.id, ref: 'master', protected: false) }
- let!(:develop) { project.ci_pipelines.create(source: :push, sha: commit.id, ref: 'develop', protected: false) }
+ let!(:master) { project.ci_pipelines.create!(source: :push, sha: commit.id, ref: 'master', protected: false) }
+ let!(:develop) { project.ci_pipelines.create!(source: :push, sha: commit.id, ref: 'develop', protected: false) }
context "reporter user" do
let(:statuses_id) { json_response.map { |status| status['id'] } }
@@ -270,8 +270,8 @@ RSpec.describe API::CommitStatuses do
end
context 'when a pipeline id is specified' do
- let!(:first_pipeline) { project.ci_pipelines.create(source: :push, sha: commit.id, ref: 'master', status: 'created') }
- let!(:other_pipeline) { project.ci_pipelines.create(source: :push, sha: commit.id, ref: 'master', status: 'created') }
+ let!(:first_pipeline) { project.ci_pipelines.create!(source: :push, sha: commit.id, ref: 'master', status: 'created') }
+ let!(:other_pipeline) { project.ci_pipelines.create!(source: :push, sha: commit.id, ref: 'master', status: 'created') }
subject do
post api(post_url, developer), params: {
diff --git a/spec/requests/api/deployments_spec.rb b/spec/requests/api/deployments_spec.rb
index d6a0423e83c..c89c59a2151 100644
--- a/spec/requests/api/deployments_spec.rb
+++ b/spec/requests/api/deployments_spec.rb
@@ -345,7 +345,7 @@ RSpec.describe API::Deployments do
context 'as a maintainer' do
it 'returns a 403 when updating a deployment with a build' do
- deploy.update(deployable: build)
+ deploy.update!(deployable: build)
put(
api("/projects/#{project.id}/deployments/#{deploy.id}", user),
@@ -394,7 +394,7 @@ RSpec.describe API::Deployments do
end
it 'returns a 403 when updating a deployment with a build' do
- deploy.update(deployable: build)
+ deploy.update!(deployable: build)
put(
api("/projects/#{project.id}/deployments/#{deploy.id}", developer),
diff --git a/spec/requests/api/environments_spec.rb b/spec/requests/api/environments_spec.rb
index 303e510883d..aa1a4643593 100644
--- a/spec/requests/api/environments_spec.rb
+++ b/spec/requests/api/environments_spec.rb
@@ -214,7 +214,7 @@ RSpec.describe API::Environments do
context 'as a maintainer' do
context 'with a stoppable environment' do
before do
- environment.update(state: :available)
+ environment.update!(state: :available)
post api("/projects/#{project.id}/environments/#{environment.id}/stop", user)
end
diff --git a/spec/requests/api/go_proxy_spec.rb b/spec/requests/api/go_proxy_spec.rb
index d45e24241b2..e678b6cf1c8 100644
--- a/spec/requests/api/go_proxy_spec.rb
+++ b/spec/requests/api/go_proxy_spec.rb
@@ -363,7 +363,7 @@ RSpec.describe API::GoProxy do
let(:module_name) { base }
before do
- project.update(visibility_level: Gitlab::VisibilityLevel::PRIVATE)
+ project.update!(visibility_level: Gitlab::VisibilityLevel::PRIVATE)
end
describe 'GET /projects/:id/packages/go/*module_name/@v/list' do
@@ -412,7 +412,7 @@ RSpec.describe API::GoProxy do
let(:module_name) { base }
before do
- project.update(visibility_level: Gitlab::VisibilityLevel::PUBLIC)
+ project.update!(visibility_level: Gitlab::VisibilityLevel::PUBLIC)
end
describe 'GET /projects/:id/packages/go/*module_name/@v/list' do
diff --git a/spec/requests/api/graphql/mutations/merge_requests/set_labels_spec.rb b/spec/requests/api/graphql/mutations/merge_requests/set_labels_spec.rb
index 34d347c76fd..0d0cc66c52a 100644
--- a/spec/requests/api/graphql/mutations/merge_requests/set_labels_spec.rb
+++ b/spec/requests/api/graphql/mutations/merge_requests/set_labels_spec.rb
@@ -52,7 +52,7 @@ RSpec.describe 'Setting labels of a merge request' do
end
it 'sets the merge request labels, removing existing ones' do
- merge_request.update(labels: [label2])
+ merge_request.update!(labels: [label2])
post_graphql_mutation(mutation, current_user: current_user)
diff --git a/spec/requests/api/group_import_spec.rb b/spec/requests/api/group_import_spec.rb
index bb7436502ed..f632e49bf3a 100644
--- a/spec/requests/api/group_import_spec.rb
+++ b/spec/requests/api/group_import_spec.rb
@@ -218,12 +218,14 @@ RSpec.describe API::GroupImport do
stub_uploads_object_storage(ImportExportUploader, direct_upload: true)
end
+ # rubocop:disable Rails/SaveBang
let(:tmp_object) do
fog_connection.directories.new(key: 'uploads').files.create(
key: "tmp/uploads/#{file_name}",
body: file_upload
)
end
+ # rubocop:enable Rails/SaveBang
let(:fog_file) { fog_to_uploaded_file(tmp_object) }
let(:params) do
diff --git a/spec/requests/api/group_milestones_spec.rb b/spec/requests/api/group_milestones_spec.rb
index 7d387079b3a..e3e0164e5a7 100644
--- a/spec/requests/api/group_milestones_spec.rb
+++ b/spec/requests/api/group_milestones_spec.rb
@@ -20,7 +20,7 @@ RSpec.describe API::GroupMilestones do
let_it_be(:params) { { include_parent_milestones: true } }
before_all do
- group.update(parent: ancestor_group)
+ group.update!(parent: ancestor_group)
end
shared_examples 'listing all milestones' do
@@ -83,9 +83,9 @@ RSpec.describe API::GroupMilestones do
end
def setup_for_group
- context_group.update(visibility_level: Gitlab::VisibilityLevel::PUBLIC)
+ context_group.update!(visibility_level: Gitlab::VisibilityLevel::PUBLIC)
context_group.add_developer(user)
- public_project.update(namespace: context_group)
+ public_project.update!(namespace: context_group)
context_group.reload
end
end
diff --git a/spec/requests/api/internal/base_spec.rb b/spec/requests/api/internal/base_spec.rb
index 8b060fa2217..6bedd43e5c4 100644
--- a/spec/requests/api/internal/base_spec.rb
+++ b/spec/requests/api/internal/base_spec.rb
@@ -887,7 +887,7 @@ RSpec.describe API::Internal::Base do
context 'project does not exist' do
context 'git pull' do
it 'returns a 200 response with status: false' do
- project.destroy
+ project.destroy!
pull(key, project)
diff --git a/spec/requests/api/issues/get_group_issues_spec.rb b/spec/requests/api/issues/get_group_issues_spec.rb
index 3870c78deee..cebde747210 100644
--- a/spec/requests/api/issues/get_group_issues_spec.rb
+++ b/spec/requests/api/issues/get_group_issues_spec.rb
@@ -754,7 +754,7 @@ RSpec.describe API::Issues do
let(:parent_group) { create(:group) }
before do
- group.update(parent_id: parent_group.id)
+ group.update!(parent_id: parent_group.id)
group_closed_issue.reload
end
diff --git a/spec/requests/api/issues/post_projects_issues_spec.rb b/spec/requests/api/issues/post_projects_issues_spec.rb
index 5b3e2363669..7f1db620d4f 100644
--- a/spec/requests/api/issues/post_projects_issues_spec.rb
+++ b/spec/requests/api/issues/post_projects_issues_spec.rb
@@ -111,7 +111,7 @@ RSpec.describe API::Issues do
let(:not_member) { create(:user) }
before do
- project.project_feature.update(issues_access_level: ProjectFeature::PRIVATE)
+ project.project_feature.update!(issues_access_level: ProjectFeature::PRIVATE)
end
it 'renders 403' do
diff --git a/spec/requests/api/jobs_spec.rb b/spec/requests/api/jobs_spec.rb
index fe00b654d3b..4f73917763f 100644
--- a/spec/requests/api/jobs_spec.rb
+++ b/spec/requests/api/jobs_spec.rb
@@ -215,7 +215,7 @@ RSpec.describe API::Jobs do
first_build = create(:ci_build, :trace_artifact, :artifacts, :test_reports, pipeline: pipeline)
first_build.runner = create(:ci_runner)
first_build.user = create(:user)
- first_build.save
+ first_build.save!
control_count = ActiveRecord::QueryRecorder.new { go }.count
@@ -223,7 +223,7 @@ RSpec.describe API::Jobs do
second_build = create(:ci_build, :trace_artifact, :artifacts, :test_reports, pipeline: second_pipeline)
second_build.runner = create(:ci_runner)
second_build.user = create(:user)
- second_build.save
+ second_build.save!
expect { go }.not_to exceed_query_limit(control_count)
end
@@ -684,7 +684,7 @@ RSpec.describe API::Jobs do
context 'with regular branch' do
before do
pipeline.reload
- pipeline.update(ref: 'master',
+ pipeline.update!(ref: 'master',
sha: project.commit('master').sha)
get_for_ref('master')
@@ -696,7 +696,7 @@ RSpec.describe API::Jobs do
context 'with branch name containing slash' do
before do
pipeline.reload
- pipeline.update(ref: 'improve/awesome',
+ pipeline.update!(ref: 'improve/awesome',
sha: project.commit('improve/awesome').sha)
end
@@ -732,7 +732,7 @@ RSpec.describe API::Jobs do
stub_artifacts_object_storage
job.success
- project.update(visibility_level: visibility_level,
+ project.update!(visibility_level: visibility_level,
public_builds: public_builds)
get_artifact_file(artifact)
@@ -826,7 +826,7 @@ RSpec.describe API::Jobs do
context 'with branch name containing slash' do
before do
pipeline.reload
- pipeline.update(ref: 'improve/awesome',
+ pipeline.update!(ref: 'improve/awesome',
sha: project.commit('improve/awesome').sha)
end
diff --git a/spec/requests/api/labels_spec.rb b/spec/requests/api/labels_spec.rb
index e3fffd3e3fd..26377c40b73 100644
--- a/spec/requests/api/labels_spec.rb
+++ b/spec/requests/api/labels_spec.rb
@@ -119,7 +119,7 @@ RSpec.describe API::Labels do
expect(label).not_to be_nil
- label.priorities.create(project: label.project, priority: 1)
+ label.priorities.create!(project: label.project, priority: 1)
label.save!
request_params = {
@@ -139,7 +139,7 @@ RSpec.describe API::Labels do
expect(label).not_to be_nil
label_id = spec_params[:name] || spec_params[:label_id]
- label.priorities.create(project: label.project, priority: 1)
+ label.priorities.create!(project: label.project, priority: 1)
label.save!
request_params = {
@@ -383,7 +383,7 @@ RSpec.describe API::Labels do
it 'returns 409 if label already exists in group' do
group = create(:group)
group_label = create(:group_label, group: group)
- project.update(group: group)
+ project.update!(group: group)
post api("/projects/#{project.id}/labels", user),
params: {
diff --git a/spec/requests/api/project_import_spec.rb b/spec/requests/api/project_import_spec.rb
index a049d7d7515..f6cdf370e5c 100644
--- a/spec/requests/api/project_import_spec.rb
+++ b/spec/requests/api/project_import_spec.rb
@@ -235,12 +235,14 @@ RSpec.describe API::ProjectImport do
stub_uploads_object_storage(ImportExportUploader, direct_upload: true)
end
+ # rubocop:disable Rails/SaveBang
let(:tmp_object) do
fog_connection.directories.new(key: 'uploads').files.create(
key: "tmp/uploads/#{file_name}",
body: fixture_file_upload(file)
)
end
+ # rubocop:enable Rails/SaveBang
let(:file_upload) { fog_to_uploaded_file(tmp_object) }
@@ -285,7 +287,7 @@ RSpec.describe API::ProjectImport do
it 'returns the import status and the error if failed' do
project = create(:project, :import_failed)
project.add_maintainer(user)
- project.import_state.update(last_error: 'error')
+ project.import_state.update!(last_error: 'error')
get api("/projects/#{project.id}/import", user)