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:
authorGitLab Bot <gitlab-bot@gitlab.com>2022-11-08 18:09:34 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2022-11-08 18:09:34 +0300
commitb5bdf6e5219b3b57107aee49ba7c103affb65dd9 (patch)
tree54c1ea8b3140d60af9a6c64867edc0a484ef7735 /spec
parent81f062b841f6062601662061850934a51e77ceea (diff)
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'spec')
-rw-r--r--spec/controllers/groups/settings/repository_controller_spec.rb117
-rw-r--r--spec/controllers/projects/artifacts_controller_spec.rb34
-rw-r--r--spec/controllers/projects/settings/repository_controller_spec.rb102
-rw-r--r--spec/features/groups/settings/repository_spec.rb23
-rw-r--r--spec/features/projects/settings/repository_settings_spec.rb1
-rw-r--r--spec/features/projects/settings/user_sees_revoke_deploy_token_modal_spec.rb1
-rw-r--r--spec/frontend/boards/board_card_inner_spec.js11
-rw-r--r--spec/frontend/boards/board_list_spec.js6
-rw-r--r--spec/frontend/boards/components/board_card_move_to_position_spec.js1
-rw-r--r--spec/frontend/search/mock_data.js84
-rw-r--r--spec/frontend/search/sidebar/components/app_spec.js109
-rw-r--r--spec/frontend/search/sidebar/components/filters_spec.js132
-rw-r--r--spec/frontend/search/sidebar/components/scope_navigation_spec.js80
-rw-r--r--spec/frontend/search/store/actions_spec.js35
-rw-r--r--spec/frontend/search/store/mutations_spec.js22
-rw-r--r--spec/helpers/search_helper_spec.rb26
-rw-r--r--spec/models/ci/bridge_spec.rb14
-rw-r--r--spec/models/ci/processable_spec.rb6
-rw-r--r--spec/services/ci/retry_job_service_spec.rb44
-rw-r--r--spec/views/shared/deploy_tokens/_form.html.haml_spec.rb62
20 files changed, 501 insertions, 409 deletions
diff --git a/spec/controllers/groups/settings/repository_controller_spec.rb b/spec/controllers/groups/settings/repository_controller_spec.rb
index cbf55218b94..73a205069f5 100644
--- a/spec/controllers/groups/settings/repository_controller_spec.rb
+++ b/spec/controllers/groups/settings/repository_controller_spec.rb
@@ -13,88 +13,73 @@ RSpec.describe Groups::Settings::RepositoryController do
end
describe 'POST create_deploy_token' do
- context 'when ajax_new_deploy_token feature flag is disabled for the project' do
- before do
- stub_feature_flags(ajax_new_deploy_token: false)
- entity.add_owner(user)
- end
+ let(:good_deploy_token_params) do
+ {
+ name: 'name',
+ expires_at: 1.day.from_now.to_s,
+ username: 'deployer',
+ read_repository: '1',
+ deploy_token_type: DeployToken.deploy_token_types[:group_type]
+ }
+ end
- it_behaves_like 'a created deploy token' do
- let(:entity) { group }
- let(:create_entity_params) { { group_id: group } }
- let(:deploy_token_type) { DeployToken.deploy_token_types[:group_type] }
- end
+ let(:request_params) do
+ {
+ group_id: group.to_param,
+ deploy_token: deploy_token_params
+ }
end
- context 'when ajax_new_deploy_token feature flag is enabled for the project' do
- let(:good_deploy_token_params) do
- {
- name: 'name',
- expires_at: 1.day.from_now.to_s,
- username: 'deployer',
- read_repository: '1',
- deploy_token_type: DeployToken.deploy_token_types[:group_type]
- }
- end
+ before do
+ group.add_owner(user)
+ end
+
+ subject { post :create_deploy_token, params: request_params, format: :json }
- let(:request_params) do
+ context('a good request') do
+ let(:deploy_token_params) { good_deploy_token_params }
+ let(:expected_response) do
{
- group_id: group.to_param,
- deploy_token: deploy_token_params
+ 'id' => be_a(Integer),
+ 'name' => deploy_token_params[:name],
+ 'username' => deploy_token_params[:username],
+ 'expires_at' => Time.zone.parse(deploy_token_params[:expires_at]),
+ 'token' => be_a(String),
+ 'expired' => false,
+ 'revoked' => false,
+ 'scopes' => deploy_token_params.inject([]) do |scopes, kv|
+ key, value = kv
+ key.to_s.start_with?('read_') && value.to_i != 0 ? scopes << key.to_s : scopes
+ end
}
end
- before do
- group.add_owner(user)
- end
+ it 'creates the deploy token' do
+ subject
- subject { post :create_deploy_token, params: request_params, format: :json }
-
- context('a good request') do
- let(:deploy_token_params) { good_deploy_token_params }
- let(:expected_response) do
- {
- 'id' => be_a(Integer),
- 'name' => deploy_token_params[:name],
- 'username' => deploy_token_params[:username],
- 'expires_at' => Time.zone.parse(deploy_token_params[:expires_at]),
- 'token' => be_a(String),
- 'expired' => false,
- 'revoked' => false,
- 'scopes' => deploy_token_params.inject([]) do |scopes, kv|
- key, value = kv
- key.to_s.start_with?('read_') && value.to_i != 0 ? scopes << key.to_s : scopes
- end
- }
- end
-
- it 'creates the deploy token' do
- subject
-
- expect(response).to have_gitlab_http_status(:created)
- expect(response).to match_response_schema('public_api/v4/deploy_token')
- expect(json_response).to match(expected_response)
- end
+ expect(response).to have_gitlab_http_status(:created)
+ expect(response).to match_response_schema('public_api/v4/deploy_token')
+ expect(json_response).to match(expected_response)
end
+ end
- context('a bad request') do
- let(:deploy_token_params) { good_deploy_token_params.except(:read_repository) }
- let(:expected_response) { { 'message' => "Scopes can't be blank" } }
+ context('a bad request') do
+ let(:deploy_token_params) { good_deploy_token_params.except(:read_repository) }
+ let(:expected_response) { { 'message' => "Scopes can't be blank" } }
- it 'does not create the deploy token' do
- subject
+ it 'does not create the deploy token' do
+ subject
- expect(response).to have_gitlab_http_status(:bad_request)
- expect(json_response).to match(expected_response)
- end
+ expect(response).to have_gitlab_http_status(:bad_request)
+ expect(json_response).to match(expected_response)
end
+ end
- context('an invalid request') do
- let(:deploy_token_params) { good_deploy_token_params.except(:name) }
+ context('an invalid request') do
+ let(:deploy_token_params) { good_deploy_token_params.except(:name) }
- it 'raises a validation error' do
- expect { subject }.to raise_error(ActiveRecord::StatementInvalid)
- end
+ it 'raises a validation error' do
+ expect { subject }.to raise_error(ActiveRecord::StatementInvalid)
end
end
end
diff --git a/spec/controllers/projects/artifacts_controller_spec.rb b/spec/controllers/projects/artifacts_controller_spec.rb
index 2d145b6ff1d..81c1d4acd36 100644
--- a/spec/controllers/projects/artifacts_controller_spec.rb
+++ b/spec/controllers/projects/artifacts_controller_spec.rb
@@ -30,28 +30,10 @@ RSpec.describe Projects::ArtifactsController do
stub_feature_flags(artifacts_management_page: true)
end
- it 'sets the artifacts variable' do
+ it 'renders the page' do
subject
- expect(assigns(:artifacts)).to contain_exactly(*project.job_artifacts)
- end
-
- it 'sets the total size variable' do
- subject
-
- expect(assigns(:total_size)).to eq(project.job_artifacts.total_size)
- end
-
- describe 'pagination' do
- before do
- stub_const("#{described_class}::MAX_PER_PAGE", 1)
- end
-
- it 'paginates artifacts' do
- subject
-
- expect(assigns(:artifacts)).to contain_exactly(project.reload.job_artifacts.last)
- end
+ expect(response).to have_gitlab_http_status(:ok)
end
end
@@ -65,18 +47,6 @@ RSpec.describe Projects::ArtifactsController do
expect(response).to have_gitlab_http_status(:no_content)
end
-
- it 'does not set the artifacts variable' do
- subject
-
- expect(assigns(:artifacts)).to eq(nil)
- end
-
- it 'does not set the total size variable' do
- subject
-
- expect(assigns(:total_size)).to eq(nil)
- end
end
end
diff --git a/spec/controllers/projects/settings/repository_controller_spec.rb b/spec/controllers/projects/settings/repository_controller_spec.rb
index 6e04e3991ab..ea50ff6caa0 100644
--- a/spec/controllers/projects/settings/repository_controller_spec.rb
+++ b/spec/controllers/projects/settings/repository_controller_spec.rb
@@ -51,78 +51,64 @@ RSpec.describe Projects::Settings::RepositoryController do
end
describe 'POST create_deploy_token' do
- context 'when ajax_new_deploy_token feature flag is disabled for the project' do
- before do
- stub_feature_flags(ajax_new_deploy_token: false)
- end
-
- it_behaves_like 'a created deploy token' do
- let(:entity) { project }
- let(:create_entity_params) { base_params }
- let(:deploy_token_type) { DeployToken.deploy_token_types[:project_type] }
- end
+ let(:good_deploy_token_params) do
+ {
+ name: 'name',
+ expires_at: 1.day.from_now.to_s,
+ username: 'deployer',
+ read_repository: '1',
+ deploy_token_type: DeployToken.deploy_token_types[:project_type]
+ }
end
- context 'when ajax_new_deploy_token feature flag is enabled for the project' do
- let(:good_deploy_token_params) do
+ let(:request_params) { base_params.merge({ deploy_token: deploy_token_params }) }
+
+ subject { post :create_deploy_token, params: request_params, format: :json }
+
+ context('a good request') do
+ let(:deploy_token_params) { good_deploy_token_params }
+ let(:expected_response) do
{
- name: 'name',
- expires_at: 1.day.from_now.to_s,
- username: 'deployer',
- read_repository: '1',
- deploy_token_type: DeployToken.deploy_token_types[:project_type]
+ 'id' => be_a(Integer),
+ 'name' => deploy_token_params[:name],
+ 'username' => deploy_token_params[:username],
+ 'expires_at' => Time.zone.parse(deploy_token_params[:expires_at]),
+ 'token' => be_a(String),
+ 'expired' => false,
+ 'revoked' => false,
+ 'scopes' => deploy_token_params.inject([]) do |scopes, kv|
+ key, value = kv
+ key.to_s.start_with?('read_') && value.to_i != 0 ? scopes << key.to_s : scopes
+ end
}
end
- let(:request_params) { base_params.merge({ deploy_token: deploy_token_params }) }
-
- subject { post :create_deploy_token, params: request_params, format: :json }
-
- context('a good request') do
- let(:deploy_token_params) { good_deploy_token_params }
- let(:expected_response) do
- {
- 'id' => be_a(Integer),
- 'name' => deploy_token_params[:name],
- 'username' => deploy_token_params[:username],
- 'expires_at' => Time.zone.parse(deploy_token_params[:expires_at]),
- 'token' => be_a(String),
- 'expired' => false,
- 'revoked' => false,
- 'scopes' => deploy_token_params.inject([]) do |scopes, kv|
- key, value = kv
- key.to_s.start_with?('read_') && value.to_i != 0 ? scopes << key.to_s : scopes
- end
- }
- end
+ it 'creates the deploy token' do
+ subject
- it 'creates the deploy token' do
- subject
-
- expect(response).to have_gitlab_http_status(:created)
- expect(response).to match_response_schema('public_api/v4/deploy_token')
- expect(json_response).to match(expected_response)
- end
+ expect(response).to have_gitlab_http_status(:created)
+ expect(response).to match_response_schema('public_api/v4/deploy_token')
+ expect(json_response).to match(expected_response)
end
+ end
- context('a bad request') do
- let(:deploy_token_params) { good_deploy_token_params.except(:read_repository) }
- let(:expected_response) { { 'message' => "Scopes can't be blank" } }
+ context('a bad request') do
+ let(:deploy_token_params) { good_deploy_token_params.except(:read_repository) }
+ let(:expected_response) { { 'message' => "Scopes can't be blank" } }
- it 'does not create the deploy token' do
- subject
+ it 'does not create the deploy token' do
+ subject
- expect(response).to have_gitlab_http_status(:bad_request)
- expect(json_response).to match(expected_response)
- end
+ expect(response).to have_gitlab_http_status(:bad_request)
+ expect(json_response).to match(expected_response)
end
+ end
- context('an invalid request') do
- let(:deploy_token_params) { good_deploy_token_params.except(:name) }
+ context('an invalid request') do
+ let(:deploy_token_params) { good_deploy_token_params.except(:name) }
- it 'raises a validation error' do
- expect { subject }.to raise_error(ActiveRecord::StatementInvalid)
- end
+ it 'raises a validation error' do
+ expect { subject }.to raise_error(ActiveRecord::StatementInvalid)
end
end
end
diff --git a/spec/features/groups/settings/repository_spec.rb b/spec/features/groups/settings/repository_spec.rb
index f6b8bbdd35f..cd7dcbdb28d 100644
--- a/spec/features/groups/settings/repository_spec.rb
+++ b/spec/features/groups/settings/repository_spec.rb
@@ -23,26 +23,9 @@ RSpec.describe 'Group Repository settings', :js do
stub_container_registry_config(enabled: true)
end
- context 'when ajax deploy tokens is enabled' do
- before do
- stub_feature_flags(ajax_new_deploy_token: true)
- end
-
- it_behaves_like 'a deploy token in settings' do
- let(:entity_type) { 'group' }
- let(:page_path) { group_settings_repository_path(group) }
- end
- end
-
- context 'when ajax deploy tokens is disabled' do
- before do
- stub_feature_flags(ajax_new_deploy_token: false)
- end
-
- it_behaves_like 'a deploy token in settings' do
- let(:entity_type) { 'group' }
- let(:page_path) { group_settings_repository_path(group) }
- end
+ it_behaves_like 'a deploy token in settings' do
+ let(:entity_type) { 'group' }
+ let(:page_path) { group_settings_repository_path(group) }
end
end
diff --git a/spec/features/projects/settings/repository_settings_spec.rb b/spec/features/projects/settings/repository_settings_spec.rb
index d9bdbf7aa1a..b25ae80b3c3 100644
--- a/spec/features/projects/settings/repository_settings_spec.rb
+++ b/spec/features/projects/settings/repository_settings_spec.rb
@@ -30,7 +30,6 @@ RSpec.describe 'Projects > Settings > Repository settings' do
before do
stub_container_registry_config(enabled: true)
- stub_feature_flags(ajax_new_deploy_token: project)
end
it_behaves_like 'a deploy token in settings' do
diff --git a/spec/features/projects/settings/user_sees_revoke_deploy_token_modal_spec.rb b/spec/features/projects/settings/user_sees_revoke_deploy_token_modal_spec.rb
index eed3494ef5b..47383be1ba1 100644
--- a/spec/features/projects/settings/user_sees_revoke_deploy_token_modal_spec.rb
+++ b/spec/features/projects/settings/user_sees_revoke_deploy_token_modal_spec.rb
@@ -11,7 +11,6 @@ RSpec.describe 'Repository Settings > User sees revoke deploy token modal', :js
before do
project.add_role(user, role)
sign_in(user)
- stub_feature_flags(ajax_new_deploy_token: project)
visit(project_settings_repository_path(project))
click_button('Revoke')
end
diff --git a/spec/frontend/boards/board_card_inner_spec.js b/spec/frontend/boards/board_card_inner_spec.js
index 3ebc51c4bcb..3b77c999a9e 100644
--- a/spec/frontend/boards/board_card_inner_spec.js
+++ b/spec/frontend/boards/board_card_inner_spec.js
@@ -7,7 +7,6 @@ import { createMockDirective, getBinding } from 'helpers/vue_mock_directive';
import { mountExtended } from 'helpers/vue_test_utils_helper';
import IssuableBlockedIcon from '~/vue_shared/components/issuable_blocked_icon/issuable_blocked_icon.vue';
import BoardCardInner from '~/boards/components/board_card_inner.vue';
-import BoardCardMoveToPosition from '~/boards/components/board_card_move_to_position.vue';
import WorkItemTypeIcon from '~/work_items/components/work_item_type_icon.vue';
import { issuableTypes } from '~/boards/constants';
import eventHub from '~/boards/eventhub';
@@ -49,7 +48,6 @@ describe('Board card component', () => {
const findEpicCountablesTotalWeight = () => wrapper.findByTestId('epic-countables-total-weight');
const findEpicProgressTooltip = () => wrapper.findByTestId('epic-progress-tooltip-content');
const findHiddenIssueIcon = () => wrapper.findByTestId('hidden-icon');
- const findMoveToPositionComponent = () => wrapper.findComponent(BoardCardMoveToPosition);
const findWorkItemIcon = () => wrapper.findComponent(WorkItemTypeIcon);
const performSearchMock = jest.fn();
@@ -143,10 +141,6 @@ describe('Board card component', () => {
expect(findHiddenIssueIcon().exists()).toBe(false);
});
- it('renders the move to position icon', () => {
- expect(findMoveToPositionComponent().exists()).toBe(true);
- });
-
it('does not render the work type icon by default', () => {
expect(findWorkItemIcon().exists()).toBe(false);
});
@@ -595,10 +589,5 @@ describe('Board card component', () => {
expect(findEpicCountablesTotalWeight().text()).toBe('15');
expect(findEpicProgressTooltip().text()).toBe('10 of 15 weight completed');
});
-
- it('does not render the move to position icon', () => {
- createWrapper();
- expect(findMoveToPositionComponent().exists()).toBe(false);
- });
});
});
diff --git a/spec/frontend/boards/board_list_spec.js b/spec/frontend/boards/board_list_spec.js
index 9b0c0b93ffb..3a2beb714e9 100644
--- a/spec/frontend/boards/board_list_spec.js
+++ b/spec/frontend/boards/board_list_spec.js
@@ -6,6 +6,7 @@ import waitForPromises from 'helpers/wait_for_promises';
import createComponent from 'jest/boards/board_list_helper';
import BoardCard from '~/boards/components/board_card.vue';
import eventHub from '~/boards/eventhub';
+import BoardCardMoveToPosition from '~/boards/components/board_card_move_to_position.vue';
import { mockIssues } from './mock_data';
@@ -15,6 +16,7 @@ describe('Board list component', () => {
const findByTestId = (testId) => wrapper.find(`[data-testid="${testId}"]`);
const findIssueCountLoadingIcon = () => wrapper.find('[data-testid="count-loading-icon"]');
const findDraggable = () => wrapper.findComponent(Draggable);
+ const findMoveToPositionComponent = () => wrapper.findComponent(BoardCardMoveToPosition);
const startDrag = (
params = {
@@ -99,6 +101,10 @@ describe('Board list component', () => {
await nextTick();
expect(wrapper.find('.board-list-count').attributes('data-issue-id')).toBe('-1');
});
+
+ it('renders the move to position icon', () => {
+ expect(findMoveToPositionComponent().exists()).toBe(true);
+ });
});
describe('load more issues', () => {
diff --git a/spec/frontend/boards/components/board_card_move_to_position_spec.js b/spec/frontend/boards/components/board_card_move_to_position_spec.js
index 7254b9486ef..8dee3c77787 100644
--- a/spec/frontend/boards/components/board_card_move_to_position_spec.js
+++ b/spec/frontend/boards/components/board_card_move_to_position_spec.js
@@ -48,6 +48,7 @@ describe('Board Card Move to position', () => {
propsData: {
item: mockIssue2,
list: mockList,
+ listItemsLength: 3,
index: 0,
...propsData,
},
diff --git a/spec/frontend/search/mock_data.js b/spec/frontend/search/mock_data.js
index 0542e96c77c..fa5ccfeb478 100644
--- a/spec/frontend/search/mock_data.js
+++ b/spec/frontend/search/mock_data.js
@@ -107,3 +107,87 @@ export const PROMISE_ALL_EXPECTED_MUTATIONS = {
payload: { key: PROJECTS_LOCAL_STORAGE_KEY, data: [MOCK_FRESH_DATA_RES, MOCK_FRESH_DATA_RES] },
},
};
+
+export const MOCK_NAVIGATION = {
+ projects: {
+ label: 'Projects',
+ scope: 'projects',
+ link: '/search?scope=projects&search=et',
+ count_link: '/search/count?scope=projects&search=et',
+ },
+ blobs: {
+ label: 'Code',
+ scope: 'blobs',
+ link: '/search?scope=blobs&search=et',
+ count_link: '/search/count?scope=blobs&search=et',
+ },
+ issues: {
+ label: 'Issues',
+ scope: 'issues',
+ link: '/search?scope=issues&search=et',
+ active: true,
+ count: '2,430',
+ },
+ merge_requests: {
+ label: 'Merge requests',
+ scope: 'merge_requests',
+ link: '/search?scope=merge_requests&search=et',
+ count_link: '/search/count?scope=merge_requests&search=et',
+ },
+ wiki_blobs: {
+ label: 'Wiki',
+ scope: 'wiki_blobs',
+ link: '/search?scope=wiki_blobs&search=et',
+ count_link: '/search/count?scope=wiki_blobs&search=et',
+ },
+ commits: {
+ label: 'Commits',
+ scope: 'commits',
+ link: '/search?scope=commits&search=et',
+ count_link: '/search/count?scope=commits&search=et',
+ },
+ notes: {
+ label: 'Comments',
+ scope: 'notes',
+ link: '/search?scope=notes&search=et',
+ count_link: '/search/count?scope=notes&search=et',
+ },
+ milestones: {
+ label: 'Milestones',
+ scope: 'milestones',
+ link: '/search?scope=milestones&search=et',
+ count_link: '/search/count?scope=milestones&search=et',
+ },
+ users: {
+ label: 'Users',
+ scope: 'users',
+ link: '/search?scope=users&search=et',
+ count_link: '/search/count?scope=users&search=et',
+ },
+};
+
+export const MOCK_NAVIGATION_DATA = {
+ projects: {
+ label: 'Projects',
+ scope: 'projects',
+ link: '/search?scope=projects&search=et',
+ count_link: '/search/count?scope=projects&search=et',
+ },
+};
+
+export const MOCK_ENDPOINT_RESPONSE = { count: '13' };
+
+export const MOCK_DATA_FOR_NAVIGATION_ACTION_MUTATION = {
+ projects: {
+ count: '13',
+ label: 'Projects',
+ scope: 'projects',
+ link: '/search?scope=projects&search=et',
+ count_link: '/search/count?scope=projects&search=et',
+ },
+};
+
+export const MOCK_NAVIGATION_ACTION_MUTATION = {
+ type: types.RECEIVE_NAVIGATION_COUNT,
+ payload: { key: 'projects', count: '13' },
+};
diff --git a/spec/frontend/search/sidebar/components/app_spec.js b/spec/frontend/search/sidebar/components/app_spec.js
index 89959feec39..b4e3388f067 100644
--- a/spec/frontend/search/sidebar/components/app_spec.js
+++ b/spec/frontend/search/sidebar/components/app_spec.js
@@ -1,11 +1,9 @@
-import { GlButton, GlLink } from '@gitlab/ui';
import { shallowMount } from '@vue/test-utils';
import Vue from 'vue';
import Vuex from 'vuex';
import { MOCK_QUERY } from 'jest/search/mock_data';
import GlobalSearchSidebar from '~/search/sidebar/components/app.vue';
-import ConfidentialityFilter from '~/search/sidebar/components/confidentiality_filter.vue';
-import StatusFilter from '~/search/sidebar/components/status_filter.vue';
+import ResultsFilters from '~/search/sidebar/components/results_filters.vue';
Vue.use(Vuex);
@@ -35,118 +33,49 @@ describe('GlobalSearchSidebar', () => {
wrapper.destroy();
});
- const findSidebarForm = () => wrapper.find('form');
- const findStatusFilter = () => wrapper.findComponent(StatusFilter);
- const findConfidentialityFilter = () => wrapper.findComponent(ConfidentialityFilter);
- const findApplyButton = () => wrapper.findComponent(GlButton);
- const findResetLinkButton = () => wrapper.findComponent(GlLink);
+ const findSidebarSection = () => wrapper.find('section');
+ const findFilters = () => wrapper.findComponent(ResultsFilters);
- describe('template', () => {
+ describe('renders properly', () => {
describe('scope=projects', () => {
beforeEach(() => {
createComponent({ urlQuery: { ...MOCK_QUERY, scope: 'projects' } });
});
- it("doesn't render StatusFilter", () => {
- expect(findStatusFilter().exists()).toBe(false);
+ it('shows section', () => {
+ expect(findSidebarSection().exists()).toBe(true);
});
- it("doesn't render ConfidentialityFilter", () => {
- expect(findConfidentialityFilter().exists()).toBe(false);
- });
-
- it("doesn't render ApplyButton", () => {
- expect(findApplyButton().exists()).toBe(false);
- });
- });
-
- describe('scope=issues', () => {
- beforeEach(() => {
- createComponent({ urlQuery: MOCK_QUERY });
- });
- it('renders StatusFilter', () => {
- expect(findStatusFilter().exists()).toBe(true);
- });
-
- it('renders ConfidentialityFilter', () => {
- expect(findConfidentialityFilter().exists()).toBe(true);
- });
-
- it('renders ApplyButton', () => {
- expect(findApplyButton().exists()).toBe(true);
- });
- });
- });
-
- describe('ApplyButton', () => {
- describe('when sidebarDirty is false', () => {
- beforeEach(() => {
- createComponent({ sidebarDirty: false });
- });
-
- it('disables the button', () => {
- expect(findApplyButton().attributes('disabled')).toBe('true');
+ it("doesn't shows filters", () => {
+ expect(findFilters().exists()).toBe(false);
});
});
- describe('when sidebarDirty is true', () => {
+ describe('scope=merge_requests', () => {
beforeEach(() => {
- createComponent({ sidebarDirty: true });
+ createComponent({ urlQuery: { ...MOCK_QUERY, scope: 'merge_requests' } });
});
- it('enables the button', () => {
- expect(findApplyButton().attributes('disabled')).toBe(undefined);
- });
- });
- });
-
- describe('ResetLinkButton', () => {
- describe('with no filter selected', () => {
- beforeEach(() => {
- createComponent({ urlQuery: {} });
+ it('shows section', () => {
+ expect(findSidebarSection().exists()).toBe(true);
});
- it('does not render', () => {
- expect(findResetLinkButton().exists()).toBe(false);
+ it('shows filters', () => {
+ expect(findFilters().exists()).toBe(true);
});
});
- describe('with filter selected', () => {
+ describe('scope=issues', () => {
beforeEach(() => {
createComponent({ urlQuery: MOCK_QUERY });
});
-
- it('does render', () => {
- expect(findResetLinkButton().exists()).toBe(true);
- });
- });
-
- describe('with filter selected and user updated query back to default', () => {
- beforeEach(() => {
- createComponent({ urlQuery: MOCK_QUERY, query: {} });
+ it('shows section', () => {
+ expect(findSidebarSection().exists()).toBe(true);
});
- it('does render', () => {
- expect(findResetLinkButton().exists()).toBe(true);
+ it('shows filters', () => {
+ expect(findFilters().exists()).toBe(true);
});
});
});
-
- describe('actions', () => {
- beforeEach(() => {
- createComponent({});
- });
-
- it('clicking ApplyButton calls applyQuery', () => {
- findSidebarForm().trigger('submit');
-
- expect(actionSpies.applyQuery).toHaveBeenCalled();
- });
-
- it('clicking ResetLinkButton calls resetQuery', () => {
- findResetLinkButton().vm.$emit('click');
-
- expect(actionSpies.resetQuery).toHaveBeenCalled();
- });
- });
});
diff --git a/spec/frontend/search/sidebar/components/filters_spec.js b/spec/frontend/search/sidebar/components/filters_spec.js
new file mode 100644
index 00000000000..4f217709297
--- /dev/null
+++ b/spec/frontend/search/sidebar/components/filters_spec.js
@@ -0,0 +1,132 @@
+import { GlButton, GlLink } from '@gitlab/ui';
+import { shallowMount } from '@vue/test-utils';
+import Vue from 'vue';
+import Vuex from 'vuex';
+import { MOCK_QUERY } from 'jest/search/mock_data';
+import ResultsFilters from '~/search/sidebar/components/results_filters.vue';
+import ConfidentialityFilter from '~/search/sidebar/components/confidentiality_filter.vue';
+import StatusFilter from '~/search/sidebar/components/status_filter.vue';
+
+Vue.use(Vuex);
+
+describe('GlobalSearchSidebarFilters', () => {
+ let wrapper;
+
+ const actionSpies = {
+ applyQuery: jest.fn(),
+ resetQuery: jest.fn(),
+ };
+
+ const createComponent = (initialState) => {
+ const store = new Vuex.Store({
+ state: {
+ urlQuery: MOCK_QUERY,
+ ...initialState,
+ },
+ actions: actionSpies,
+ });
+
+ wrapper = shallowMount(ResultsFilters, {
+ store,
+ });
+ };
+
+ afterEach(() => {
+ wrapper.destroy();
+ });
+
+ const findSidebarForm = () => wrapper.find('form');
+ const findStatusFilter = () => wrapper.findComponent(StatusFilter);
+ const findConfidentialityFilter = () => wrapper.findComponent(ConfidentialityFilter);
+ const findApplyButton = () => wrapper.findComponent(GlButton);
+ const findResetLinkButton = () => wrapper.findComponent(GlLink);
+
+ describe('Renders correctly', () => {
+ beforeEach(() => {
+ createComponent({ urlQuery: MOCK_QUERY });
+ });
+ it('renders StatusFilter', () => {
+ expect(findStatusFilter().exists()).toBe(true);
+ });
+
+ it('renders ConfidentialityFilter', () => {
+ expect(findConfidentialityFilter().exists()).toBe(true);
+ });
+
+ it('renders ApplyButton', () => {
+ expect(findApplyButton().exists()).toBe(true);
+ });
+ });
+
+ describe('ApplyButton', () => {
+ describe('when sidebarDirty is false', () => {
+ beforeEach(() => {
+ createComponent({ sidebarDirty: false });
+ });
+
+ it('disables the button', () => {
+ expect(findApplyButton().attributes('disabled')).toBe('true');
+ });
+ });
+
+ describe('when sidebarDirty is true', () => {
+ beforeEach(() => {
+ createComponent({ sidebarDirty: true });
+ });
+
+ it('enables the button', () => {
+ expect(findApplyButton().attributes('disabled')).toBe(undefined);
+ });
+ });
+ });
+
+ describe('ResetLinkButton', () => {
+ describe('with no filter selected', () => {
+ beforeEach(() => {
+ createComponent({ urlQuery: {} });
+ });
+
+ it('does not render', () => {
+ expect(findResetLinkButton().exists()).toBe(false);
+ });
+ });
+
+ describe('with filter selected', () => {
+ beforeEach(() => {
+ createComponent({ urlQuery: MOCK_QUERY });
+ });
+
+ it('does render', () => {
+ expect(findResetLinkButton().exists()).toBe(true);
+ });
+ });
+
+ describe('with filter selected and user updated query back to default', () => {
+ beforeEach(() => {
+ createComponent({ urlQuery: MOCK_QUERY, query: {} });
+ });
+
+ it('does render', () => {
+ expect(findResetLinkButton().exists()).toBe(true);
+ });
+ });
+ });
+
+ describe('actions', () => {
+ beforeEach(() => {
+ createComponent({});
+ });
+
+ it('clicking ApplyButton calls applyQuery', () => {
+ findSidebarForm().trigger('submit');
+
+ expect(actionSpies.applyQuery).toHaveBeenCalled();
+ });
+
+ it('clicking ResetLinkButton calls resetQuery', () => {
+ findResetLinkButton().vm.$emit('click');
+
+ expect(actionSpies.resetQuery).toHaveBeenCalled();
+ });
+ });
+});
diff --git a/spec/frontend/search/sidebar/components/scope_navigation_spec.js b/spec/frontend/search/sidebar/components/scope_navigation_spec.js
new file mode 100644
index 00000000000..6262a52e01a
--- /dev/null
+++ b/spec/frontend/search/sidebar/components/scope_navigation_spec.js
@@ -0,0 +1,80 @@
+import { GlNav, GlNavItem } from '@gitlab/ui';
+import { shallowMount } from '@vue/test-utils';
+import Vue from 'vue';
+import Vuex from 'vuex';
+import { MOCK_QUERY, MOCK_NAVIGATION } from 'jest/search/mock_data';
+import ScopeNavigation from '~/search/sidebar/components/scope_navigation.vue';
+
+Vue.use(Vuex);
+
+describe('ScopeNavigation', () => {
+ let wrapper;
+
+ const actionSpies = {
+ fetchSidebarCount: jest.fn(),
+ };
+
+ const createComponent = (initialState) => {
+ const store = new Vuex.Store({
+ state: {
+ urlQuery: MOCK_QUERY,
+ navigation: MOCK_NAVIGATION,
+ ...initialState,
+ },
+ actions: actionSpies,
+ });
+
+ wrapper = shallowMount(ScopeNavigation, {
+ store,
+ });
+ };
+
+ afterEach(() => {
+ wrapper.destroy();
+ });
+
+ const findNavElement = () => wrapper.find('nav');
+ const findGlNav = () => wrapper.findComponent(GlNav);
+ const findGlNavItems = () => wrapper.findAllComponents(GlNavItem);
+ const findGlNavItemActive = () => findGlNavItems().wrappers.filter((w) => w.attributes('active'));
+ const findGlNavItemActiveCount = () => findGlNavItemActive().at(0).findAll('span').at(1);
+
+ describe('scope navigation', () => {
+ beforeEach(() => {
+ createComponent();
+ });
+
+ it('renders section', () => {
+ expect(findNavElement().exists()).toBe(true);
+ });
+
+ it('renders nav component', () => {
+ expect(findGlNav().exists()).toBe(true);
+ });
+
+ it('renders all nav item components', () => {
+ expect(findGlNavItems()).toHaveLength(9);
+ });
+
+ it('nav items have proper links', () => {
+ const linkAtPosition = 3;
+ const { link } = MOCK_NAVIGATION[Object.keys(MOCK_NAVIGATION)[linkAtPosition]];
+
+ expect(findGlNavItems().at(linkAtPosition).attributes('href')).toBe(link);
+ });
+ });
+
+ describe('scope navigation sets proper state', () => {
+ beforeEach(() => {
+ createComponent();
+ });
+
+ it('sets proper class to active item', () => {
+ expect(findGlNavItemActive()).toHaveLength(1);
+ });
+
+ it('active item', () => {
+ expect(findGlNavItemActiveCount().text()).toBe('2.4K');
+ });
+ });
+});
diff --git a/spec/frontend/search/store/actions_spec.js b/spec/frontend/search/store/actions_spec.js
index c442ffa521d..3d19b27ff86 100644
--- a/spec/frontend/search/store/actions_spec.js
+++ b/spec/frontend/search/store/actions_spec.js
@@ -2,6 +2,7 @@ import MockAdapter from 'axios-mock-adapter';
import testAction from 'helpers/vuex_action_helper';
import Api from '~/api';
import { createAlert } from '~/flash';
+import * as logger from '~/lib/logger';
import axios from '~/lib/utils/axios_utils';
import * as urlUtils from '~/lib/utils/url_utility';
import * as actions from '~/search/store/actions';
@@ -23,6 +24,9 @@ import {
MOCK_FRESH_DATA_RES,
PRELOAD_EXPECTED_MUTATIONS,
PROMISE_ALL_EXPECTED_MUTATIONS,
+ MOCK_NAVIGATION_DATA,
+ MOCK_NAVIGATION_ACTION_MUTATION,
+ MOCK_ENDPOINT_RESPONSE,
} from '../mock_data';
jest.mock('~/flash');
@@ -31,6 +35,9 @@ jest.mock('~/lib/utils/url_utility', () => ({
joinPaths: jest.fn().mockReturnValue(''),
visitUrl: jest.fn(),
}));
+jest.mock('~/lib/logger', () => ({
+ logError: jest.fn(),
+}));
describe('Global Search Store Actions', () => {
let mock;
@@ -260,4 +267,32 @@ describe('Global Search Store Actions', () => {
);
});
});
+
+ describe.each`
+ action | axiosMock | type | scope | expectedMutations | errorLogs
+ ${actions.fetchSidebarCount} | ${{ method: 'onGet', code: 200 }} | ${'success'} | ${'issues'} | ${[MOCK_NAVIGATION_ACTION_MUTATION]} | ${0}
+ ${actions.fetchSidebarCount} | ${{ method: null, code: 0 }} | ${'success'} | ${'projects'} | ${[]} | ${0}
+ ${actions.fetchSidebarCount} | ${{ method: 'onGet', code: 500 }} | ${'error'} | ${'issues'} | ${[]} | ${1}
+ `('fetchSidebarCount', ({ action, axiosMock, type, expectedMutations, scope, errorLogs }) => {
+ describe(`on ${type}`, () => {
+ beforeEach(() => {
+ state.navigation = MOCK_NAVIGATION_DATA;
+ state.urlQuery = {
+ scope,
+ };
+
+ if (axiosMock.method) {
+ mock[axiosMock.method]().reply(axiosMock.code, MOCK_ENDPOINT_RESPONSE);
+ }
+ });
+
+ it(`should ${expectedMutations.length === 0 ? 'NOT ' : ''}dispatch ${
+ expectedMutations.length === 0 ? '' : 'the correct '
+ }mutations for ${scope}`, () => {
+ return testAction({ action, state, expectedMutations }).then(() => {
+ expect(logger.logError).toHaveBeenCalledTimes(errorLogs);
+ });
+ });
+ });
+ });
});
diff --git a/spec/frontend/search/store/mutations_spec.js b/spec/frontend/search/store/mutations_spec.js
index 25f9b692955..a79ec8f70b0 100644
--- a/spec/frontend/search/store/mutations_spec.js
+++ b/spec/frontend/search/store/mutations_spec.js
@@ -1,13 +1,20 @@
import * as types from '~/search/store/mutation_types';
import mutations from '~/search/store/mutations';
import createState from '~/search/store/state';
-import { MOCK_QUERY, MOCK_GROUPS, MOCK_PROJECTS } from '../mock_data';
+import {
+ MOCK_QUERY,
+ MOCK_GROUPS,
+ MOCK_PROJECTS,
+ MOCK_NAVIGATION_DATA,
+ MOCK_NAVIGATION_ACTION_MUTATION,
+ MOCK_DATA_FOR_NAVIGATION_ACTION_MUTATION,
+} from '../mock_data';
describe('Global Search Store Mutations', () => {
let state;
beforeEach(() => {
- state = createState({ query: MOCK_QUERY });
+ state = createState({ query: MOCK_QUERY, navigation: MOCK_NAVIGATION_DATA });
});
describe('REQUEST_GROUPS', () => {
@@ -90,4 +97,15 @@ describe('Global Search Store Mutations', () => {
expect(state.frequentItems[payload.key]).toStrictEqual(payload.data);
});
});
+
+ describe('RECEIVE_NAVIGATION_COUNT', () => {
+ it('sets frequentItems[key] to data', () => {
+ const { payload } = MOCK_NAVIGATION_ACTION_MUTATION;
+ mutations[types.RECEIVE_NAVIGATION_COUNT](state, payload);
+
+ expect(state.navigation[payload.key]).toStrictEqual(
+ MOCK_DATA_FOR_NAVIGATION_ACTION_MUTATION[payload.key],
+ );
+ });
+ });
});
diff --git a/spec/helpers/search_helper_spec.rb b/spec/helpers/search_helper_spec.rb
index 4348a57d055..a844d65157d 100644
--- a/spec/helpers/search_helper_spec.rb
+++ b/spec/helpers/search_helper_spec.rb
@@ -1023,6 +1023,7 @@ RSpec.describe SearchHelper do
describe '.search_navigation_json' do
using RSpec::Parameterized::TableSyntax
+
context 'with data' do
example_data_1 = {
projects: { label: _("Projects"), condition: true },
@@ -1041,13 +1042,13 @@ RSpec.describe SearchHelper do
}
where(:data, :matcher) do
- example_data_1 | -> { include("projects") }
- example_data_2 | -> { eq("{}") }
- example_data_3 | -> { include("projects", "blobs", "epics") }
+ example_data_1 | -> { include("projects") }
+ example_data_2 | -> { eq("{}") }
+ example_data_3 | -> { include("projects", "blobs", "epics") }
end
with_them do
- it 'converts correctly' do
+ it 'renders data correctly' do
allow(self).to receive(:search_navigation).with(no_args).and_return(data)
expect(search_navigation_json).to instance_exec(&matcher)
@@ -1056,6 +1057,23 @@ RSpec.describe SearchHelper do
end
end
+ describe '.search_navigation_json with .search_navigation' do
+ before do
+ allow(self).to receive(:current_user).and_return(build(:user))
+ allow(self).to receive(:can?).and_return(true)
+ allow(self).to receive(:project_search_tabs?).and_return(true)
+ allow(self).to receive(:feature_flag_tab_enabled?).and_return(true)
+ allow(search_service).to receive(:show_elasticsearch_tabs?).and_return(true)
+ allow(self).to receive(:feature_flag_tab_enabled?).and_return(true)
+ @show_snippets = true
+ @project = nil
+ end
+
+ it 'test search navigation item order for CE all options enabled' do
+ expect(Gitlab::Json.parse(search_navigation_json).keys).to eq(%w[projects blobs issues merge_requests wiki_blobs commits notes milestones users snippet_titles])
+ end
+ end
+
describe '.search_filter_link_json' do
using RSpec::Parameterized::TableSyntax
diff --git a/spec/models/ci/bridge_spec.rb b/spec/models/ci/bridge_spec.rb
index 3df278a49dd..fce5a3bc7bb 100644
--- a/spec/models/ci/bridge_spec.rb
+++ b/spec/models/ci/bridge_spec.rb
@@ -37,18 +37,8 @@ RSpec.describe Ci::Bridge do
describe '#retryable?' do
let(:bridge) { create(:ci_bridge, :success) }
- it 'returns true' do
- expect(bridge.retryable?).to eq(true)
- end
-
- context 'without ci_recreate_downstream_pipeline ff' do
- before do
- stub_feature_flags(ci_recreate_downstream_pipeline: false)
- end
-
- it 'returns false' do
- expect(bridge.retryable?).to eq(false)
- end
+ it 'returns false' do
+ expect(bridge.retryable?).to eq(false)
end
end
diff --git a/spec/models/ci/processable_spec.rb b/spec/models/ci/processable_spec.rb
index 261eba73424..535999f211d 100644
--- a/spec/models/ci/processable_spec.rb
+++ b/spec/models/ci/processable_spec.rb
@@ -286,12 +286,6 @@ RSpec.describe Ci::Processable do
end
end
- context 'when the processable is a bridge' do
- subject(:processable) { create(:ci_bridge, pipeline: pipeline) }
-
- it_behaves_like 'retryable processable'
- end
-
context 'when the processable is a build' do
subject(:processable) { create(:ci_build, pipeline: pipeline) }
diff --git a/spec/services/ci/retry_job_service_spec.rb b/spec/services/ci/retry_job_service_spec.rb
index 5737303aaf8..540e700efa6 100644
--- a/spec/services/ci/retry_job_service_spec.rb
+++ b/spec/services/ci/retry_job_service_spec.rb
@@ -27,22 +27,6 @@ RSpec.describe Ci::RetryJobService do
project.add_reporter(reporter)
end
- shared_context 'retryable bridge' do
- let_it_be(:downstream_project) { create(:project, :repository) }
-
- let_it_be_with_refind(:job) do
- create(:ci_bridge, :success,
- pipeline: pipeline, downstream: downstream_project, description: 'a trigger job', ci_stage: stage
- )
- end
-
- let_it_be(:job_to_clone) { job }
-
- before do
- job.update!(retried: false)
- end
- end
-
shared_context 'retryable build' do
let_it_be_with_reload(:job) do
create(:ci_build, :success, pipeline: pipeline, ci_stage: stage)
@@ -211,20 +195,6 @@ RSpec.describe Ci::RetryJobService do
expect { service.clone!(create(:ci_build).present) }.to raise_error(TypeError)
end
- context 'when the job to be cloned is a bridge' do
- include_context 'retryable bridge'
-
- it_behaves_like 'clones the job'
-
- context 'when given variables' do
- let(:new_job) { service.clone!(job, variables: job_variables_attributes) }
-
- it 'does not give variables to the new bridge' do
- expect { new_job }.not_to raise_error
- end
- end
- end
-
context 'when the job to be cloned is a build' do
include_context 'retryable build'
@@ -331,20 +301,6 @@ RSpec.describe Ci::RetryJobService do
subject { service.execute(job) }
- context 'when the job to be retried is a bridge' do
- include_context 'retryable bridge'
-
- it_behaves_like 'retries the job'
-
- context 'when given variables' do
- let(:new_job) { service.clone!(job, variables: job_variables_attributes) }
-
- it 'does not give variables to the new bridge' do
- expect { new_job }.not_to raise_error
- end
- end
- end
-
context 'when the job to be retried is a build' do
include_context 'retryable build'
diff --git a/spec/views/shared/deploy_tokens/_form.html.haml_spec.rb b/spec/views/shared/deploy_tokens/_form.html.haml_spec.rb
deleted file mode 100644
index 74ad0ccb77a..00000000000
--- a/spec/views/shared/deploy_tokens/_form.html.haml_spec.rb
+++ /dev/null
@@ -1,62 +0,0 @@
-# frozen_string_literal: true
-
-require 'spec_helper'
-
-RSpec.describe 'shared/deploy_tokens/_form.html.haml' do
- using RSpec::Parameterized::TableSyntax
-
- let_it_be(:user) { create(:user) }
- let_it_be(:token) { build(:deploy_token) }
-
- RSpec.shared_examples "display deploy token settings" do |role, shows_package_registry_permissions|
- before do
- subject.add_member(user, role)
- allow(view).to receive(:current_user).and_return(user)
- stub_config(packages: { enabled: packages_enabled })
- end
-
- it "correctly renders the form" do
- render 'shared/deploy_tokens/form', token: token, group_or_project: subject
-
- if shows_package_registry_permissions
- expect(rendered).to have_content('Allows read-only access to the package registry.')
- else
- expect(rendered).not_to have_content('Allows read-only access to the package registry.')
- end
- end
- end
-
- context "when the subject is a project" do
- let_it_be(:subject, refind: true) { create(:project, :private) }
-
- where(:packages_enabled, :feature_enabled, :role, :shows_package_registry_permissions) do
- true | true | :maintainer | true
- false | true | :maintainer | false
- true | false | :maintainer | false
- false | false | :maintainer | false
- end
-
- with_them do
- before do
- subject.update!(packages_enabled: feature_enabled)
- end
-
- it_behaves_like 'display deploy token settings', params[:role], params[:shows_package_registry_permissions]
- end
- end
-
- context "when the subject is a group" do
- let_it_be(:subject, refind: true) { create(:group, :private) }
-
- where(:packages_enabled, :role, :shows_package_registry_permissions) do
- true | :owner | true
- false | :owner | false
- true | :maintainer | true
- false | :maintainer | false
- end
-
- with_them do
- it_behaves_like 'display deploy token settings', params[:role], params[:shows_package_registry_permissions]
- end
- end
-end