summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2023-05-16 15:07:40 +0000
committerGitLab Bot <gitlab-bot@gitlab.com>2023-05-16 15:07:40 +0000
commit0e1756ac5c275f8d548c06693b15578baf189d56 (patch)
tree095610add4bf2e78c66a2dec230438aaf599fdb2
parent0045970352e8729b2797591beb88a7df884d84f4 (diff)
downloadgitlab-ce-0e1756ac5c275f8d548c06693b15578baf189d56.tar.gz
Add latest changes from gitlab-org/gitlab@master
-rw-r--r--.gitlab/ci/reports.gitlab-ci.yml2
-rw-r--r--.rubocop_todo/layout/empty_line_after_magic_comment.yml1
-rw-r--r--.rubocop_todo/layout/line_length.yml1
-rw-r--r--.rubocop_todo/lint/unused_method_argument.yml1
-rw-r--r--.rubocop_todo/rspec/missing_feature_category.yml2
-rw-r--r--.rubocop_todo/rspec/verified_doubles.yml1
-rw-r--r--GITALY_SERVER_VERSION2
-rw-r--r--Gemfile1
-rw-r--r--Gemfile.lock4
-rw-r--r--app/assets/javascripts/notes/stores/modules/index.js52
-rw-r--r--app/assets/javascripts/notes/stores/state.js53
-rw-r--r--app/components/pajamas/alert_component.html.haml8
-rw-r--r--app/components/pajamas/alert_component.rb8
-rw-r--r--app/models/packages/package.rb6
-rw-r--r--app/models/users/callout.rb6
-rw-r--r--app/models/users/group_callout.rb6
-rw-r--r--config/feature_flags/development/members_with_shared_group_access.yml2
-rw-r--r--config/feature_flags/development/packages_display_last_pipeline.yml8
-rw-r--r--config/puma.example.development.rb4
-rw-r--r--config/puma.rb.example4
-rw-r--r--db/docs/batched_background_migrations/cleanup_personal_access_tokens_with_nil_expires_at.yml2
-rw-r--r--doc/api/graphql/reference/index.md5
-rw-r--r--doc/ci/pipeline_editor/index.md41
-rw-r--r--doc/user/project/quick_actions.md2
-rw-r--r--lib/gitlab/cluster/puma_worker_killer_initializer.rb51
-rw-r--r--lib/gitlab/cluster/puma_worker_killer_observer.rb22
-rw-r--r--lib/gitlab/quick_actions/work_item_actions.rb3
-rw-r--r--lib/gitlab/usage_data_counters/known_events/product_analytics.yml2
-rw-r--r--locale/gitlab.pot21
-rw-r--r--package.json1
-rw-r--r--rubocop/cop/rspec/avoid_conditional_statements.rb2
-rw-r--r--spec/components/pajamas/alert_component_spec.rb52
-rw-r--r--spec/features/projects/environments/environment_metrics_spec.rb2
-rw-r--r--spec/frontend/__helpers__/mocks/mr_notes/stores/index.js15
-rw-r--r--spec/frontend/batch_comments/components/preview_item_spec.js47
-rw-r--r--spec/frontend/diffs/components/compare_versions_spec.js51
-rw-r--r--spec/frontend/diffs/components/diff_line_note_form_spec.js119
-rw-r--r--spec/frontend/diffs/components/no_changes_spec.js57
-rw-r--r--spec/frontend/diffs/components/settings_dropdown_spec.js93
-rw-r--r--spec/frontend/diffs/store/actions_spec.js2
-rw-r--r--spec/frontend/issuable/components/issuable_header_warnings_spec.js17
-rw-r--r--spec/lib/gitlab/cluster/puma_worker_killer_initializer_spec.rb30
-rw-r--r--spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb25
-rw-r--r--spec/models/packages/package_spec.rb10
-rw-r--r--spec/services/quick_actions/interpret_service_spec.rb12
-rw-r--r--spec/support/rspec_order_todo.yml1
-rw-r--r--yarn.lock7
47 files changed, 424 insertions, 440 deletions
diff --git a/.gitlab/ci/reports.gitlab-ci.yml b/.gitlab/ci/reports.gitlab-ci.yml
index b072b3dc772..9158e02da94 100644
--- a/.gitlab/ci/reports.gitlab-ci.yml
+++ b/.gitlab/ci/reports.gitlab-ci.yml
@@ -87,7 +87,7 @@ yarn-audit-dependency_scanning:
extends: .default-retry
stage: test
image:
- name: ${REGISTRY_HOST}/${REGISTRY_GROUP}/security-products/package-hunter-cli:v1.3.3@sha256:1d3af9a61aa01549a62be17fa655fcf06271ac9e1b1e822c2a7930fa1d4a8a6b
+ name: ${REGISTRY_HOST}/${REGISTRY_GROUP}/security-products/package-hunter-cli:v2.1.0@sha256:1f1d31fdc81f6cf0ee305ff0291bfb56f22c5764fe042948ff1676f2f8c60352
entrypoint: [""]
variables:
HTR_user: '$PACKAGE_HUNTER_USER'
diff --git a/.rubocop_todo/layout/empty_line_after_magic_comment.yml b/.rubocop_todo/layout/empty_line_after_magic_comment.yml
index 93302cebaa1..536f13e3919 100644
--- a/.rubocop_todo/layout/empty_line_after_magic_comment.yml
+++ b/.rubocop_todo/layout/empty_line_after_magic_comment.yml
@@ -206,7 +206,6 @@ Layout/EmptyLineAfterMagicComment:
- 'ee/app/models/dependencies/dependency_list_export.rb'
- 'ee/app/models/ee/issue_assignee.rb'
- 'ee/app/models/geo/ci_secure_file_state.rb'
- - 'ee/app/models/namespaces/storage/limit_exclusion.rb'
- 'ee/app/models/project_security_setting.rb'
- 'ee/app/models/protected_environment.rb'
- 'ee/app/models/sbom/vulnerable_component_version.rb'
diff --git a/.rubocop_todo/layout/line_length.yml b/.rubocop_todo/layout/line_length.yml
index 339edfce783..13ed078563f 100644
--- a/.rubocop_todo/layout/line_length.yml
+++ b/.rubocop_todo/layout/line_length.yml
@@ -2729,7 +2729,6 @@ Layout/LineLength:
- 'lib/gitlab/ci/status/build/waiting_for_approval.rb'
- 'lib/gitlab/ci/variables/builder.rb'
- 'lib/gitlab/cleanup/project_uploads.rb'
- - 'lib/gitlab/cluster/puma_worker_killer_observer.rb'
- 'lib/gitlab/composer/version_index.rb'
- 'lib/gitlab/config/entry/configurable.rb'
- 'lib/gitlab/config/entry/validators.rb'
diff --git a/.rubocop_todo/lint/unused_method_argument.yml b/.rubocop_todo/lint/unused_method_argument.yml
index 45f18e605b7..dd5f6640abb 100644
--- a/.rubocop_todo/lint/unused_method_argument.yml
+++ b/.rubocop_todo/lint/unused_method_argument.yml
@@ -430,7 +430,6 @@ Lint/UnusedMethodArgument:
- 'lib/gitlab/cleanup/orphan_job_artifact_files.rb'
- 'lib/gitlab/cleanup/orphan_job_artifact_files_batch.rb'
- 'lib/gitlab/cleanup/project_upload_file_finder.rb'
- - 'lib/gitlab/cluster/puma_worker_killer_observer.rb'
- 'lib/gitlab/config/entry/composable_hash.rb'
- 'lib/gitlab/config/entry/node.rb'
- 'lib/gitlab/config/entry/validators.rb'
diff --git a/.rubocop_todo/rspec/missing_feature_category.yml b/.rubocop_todo/rspec/missing_feature_category.yml
index 0382b0ff43e..0a77e2d8b15 100644
--- a/.rubocop_todo/rspec/missing_feature_category.yml
+++ b/.rubocop_todo/rspec/missing_feature_category.yml
@@ -3356,8 +3356,6 @@ RSpec/MissingFeatureCategory:
- 'spec/lib/gitlab/closing_issue_extractor_spec.rb'
- 'spec/lib/gitlab/cluster/lifecycle_events_spec.rb'
- 'spec/lib/gitlab/cluster/mixins/puma_cluster_spec.rb'
- - 'spec/lib/gitlab/cluster/puma_worker_killer_initializer_spec.rb'
- - 'spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb'
- 'spec/lib/gitlab/cluster/rack_timeout_observer_spec.rb'
- 'spec/lib/gitlab/code_navigation_path_spec.rb'
- 'spec/lib/gitlab/color_schemes_spec.rb'
diff --git a/.rubocop_todo/rspec/verified_doubles.yml b/.rubocop_todo/rspec/verified_doubles.yml
index 88b6f302e56..704a426595c 100644
--- a/.rubocop_todo/rspec/verified_doubles.yml
+++ b/.rubocop_todo/rspec/verified_doubles.yml
@@ -456,7 +456,6 @@ RSpec/VerifiedDoubles:
- 'spec/lib/gitlab/cleanup/orphan_lfs_file_references_spec.rb'
- 'spec/lib/gitlab/cleanup/project_uploads_spec.rb'
- 'spec/lib/gitlab/cleanup/remote_uploads_spec.rb'
- - 'spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb'
- 'spec/lib/gitlab/cluster/rack_timeout_observer_spec.rb'
- 'spec/lib/gitlab/color_schemes_spec.rb'
- 'spec/lib/gitlab/conan_token_spec.rb'
diff --git a/GITALY_SERVER_VERSION b/GITALY_SERVER_VERSION
index 61d75e125be..097a2a36348 100644
--- a/GITALY_SERVER_VERSION
+++ b/GITALY_SERVER_VERSION
@@ -1 +1 @@
-0b0e46fe69e9b94e3def2a9318188fcc0f3f00c6
+c47a4d7d1ef1ecf3b0d78b9423e0ef28d8513979
diff --git a/Gemfile b/Gemfile
index 10c4d6dc8d8..f7331961af2 100644
--- a/Gemfile
+++ b/Gemfile
@@ -211,7 +211,6 @@ gem 'rack-timeout', '~> 0.6.3', require: 'rack/timeout/base'
group :puma do
gem 'puma', '~> 5.6.5', require: false
- gem 'puma_worker_killer', '~> 0.3.1', require: false
gem 'sd_notify', '~> 0.1.0', require: false
end
diff --git a/Gemfile.lock b/Gemfile.lock
index 199c806a854..cd882fce0f5 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -1162,9 +1162,6 @@ GEM
public_suffix (5.0.0)
puma (5.6.5)
nio4r (~> 2.0)
- puma_worker_killer (0.3.1)
- get_process_mem (~> 0.2)
- puma (>= 2.7)
pyu-ruby-sasl (0.0.3.3)
raabro (1.4.0)
racc (1.6.2)
@@ -1867,7 +1864,6 @@ DEPENDENCIES
pry-rails (~> 0.3.9)
pry-shell (~> 0.6.1)
puma (~> 5.6.5)
- puma_worker_killer (~> 0.3.1)
rack (~> 2.2.7)
rack-attack (~> 6.6.1)
rack-cors (~> 1.1.1)
diff --git a/app/assets/javascripts/notes/stores/modules/index.js b/app/assets/javascripts/notes/stores/modules/index.js
index 317fe6442d4..7eba491430b 100644
--- a/app/assets/javascripts/notes/stores/modules/index.js
+++ b/app/assets/javascripts/notes/stores/modules/index.js
@@ -1,58 +1,10 @@
-import { ASC, MR_FILTER_OPTIONS } from '../../constants';
import * as actions from '../actions';
import * as getters from '../getters';
import mutations from '../mutations';
+import createState from '../state';
export default () => ({
- state: {
- discussions: [],
- discussionSortOrder: ASC,
- persistSortOrder: true,
- convertedDisscussionIds: [],
- targetNoteHash: null,
- lastFetchedAt: null,
- currentDiscussionId: null,
- batchSuggestionsInfo: [],
- currentlyFetchingDiscussions: false,
- doneFetchingBatchDiscussions: false,
- /**
- * selectedCommentPosition & selectedCommentPositionHover structures are the same as `position.line_range`:
- * {
- * start: { line_code: string, new_line: number, old_line:number, type: string },
- * end: { line_code: string, new_line: number, old_line:number, type: string },
- * }
- */
- selectedCommentPosition: null,
- selectedCommentPositionHover: null,
-
- // View layer
- isToggleStateButtonLoading: false,
- isNotesFetched: false,
- isLoading: true,
- isLoadingDescriptionVersion: false,
- isPromoteCommentToTimelineEventInProgress: false,
-
- // holds endpoints and permissions provided through haml
- notesData: {
- markdownDocsPath: '',
- },
- userData: {},
- noteableData: {
- discussion_locked: false,
- confidential: false, // TODO: Move data like this to Issue Store, should not be apart of notes.
- current_user: {},
- preview_note_path: 'path/to/preview',
- },
- isResolvingDiscussion: false,
- commentsDisabled: false,
- resolvableDiscussionsCount: 0,
- unresolvedDiscussionsCount: 0,
- descriptionVersions: {},
- isTimelineEnabled: false,
- isFetching: false,
- isPollingInitialized: false,
- mergeRequestFilters: MR_FILTER_OPTIONS.map((f) => f.value),
- },
+ state: createState(),
actions,
getters,
mutations,
diff --git a/app/assets/javascripts/notes/stores/state.js b/app/assets/javascripts/notes/stores/state.js
new file mode 100644
index 00000000000..8e49cd861a1
--- /dev/null
+++ b/app/assets/javascripts/notes/stores/state.js
@@ -0,0 +1,53 @@
+import { ASC, MR_FILTER_OPTIONS } from '../constants';
+
+const createState = () => ({
+ discussions: [],
+ discussionSortOrder: ASC,
+ persistSortOrder: true,
+ convertedDisscussionIds: [],
+ targetNoteHash: null,
+ lastFetchedAt: null,
+ currentDiscussionId: null,
+ batchSuggestionsInfo: [],
+ currentlyFetchingDiscussions: false,
+ doneFetchingBatchDiscussions: false,
+ /**
+ * selectedCommentPosition & selectedCommentPositionHover structures are the same as `position.line_range`:
+ * {
+ * start: { line_code: string, new_line: number, old_line:number, type: string },
+ * end: { line_code: string, new_line: number, old_line:number, type: string },
+ * }
+ */
+ selectedCommentPosition: null,
+ selectedCommentPositionHover: null,
+
+ // View layer
+ isToggleStateButtonLoading: false,
+ isNotesFetched: false,
+ isLoading: true,
+ isLoadingDescriptionVersion: false,
+ isPromoteCommentToTimelineEventInProgress: false,
+
+ // holds endpoints and permissions provided through haml
+ notesData: {
+ markdownDocsPath: '',
+ },
+ userData: {},
+ noteableData: {
+ discussion_locked: false,
+ confidential: false, // TODO: Move data like this to Issue Store, should not be apart of notes.
+ current_user: {},
+ preview_note_path: 'path/to/preview',
+ },
+ isResolvingDiscussion: false,
+ commentsDisabled: false,
+ resolvableDiscussionsCount: 0,
+ unresolvedDiscussionsCount: 0,
+ descriptionVersions: {},
+ isTimelineEnabled: false,
+ isFetching: false,
+ isPollingInitialized: false,
+ mergeRequestFilters: MR_FILTER_OPTIONS.map((f) => f.value),
+});
+
+export default createState;
diff --git a/app/components/pajamas/alert_component.html.haml b/app/components/pajamas/alert_component.html.haml
index 13c458f05e9..a7be57311bb 100644
--- a/app/components/pajamas/alert_component.html.haml
+++ b/app/components/pajamas/alert_component.html.haml
@@ -2,10 +2,10 @@
- if @show_icon
= sprite_icon(icon, css_class: icon_classes)
- if @dismissible
- %button.btn.gl-dismiss-btn.btn-default.btn-sm.gl-button.btn-default-tertiary.btn-icon.js-close{ @close_button_options,
- type: 'button',
- aria: { label: _('Dismiss') } }
- = sprite_icon('close')
+ = render Pajamas::ButtonComponent.new(category: :tertiary,
+ icon: 'close',
+ size: :small,
+ button_options: dismissible_button_options)
.gl-alert-content{ role: 'alert' }
- if @title
%h4.gl-alert-title
diff --git a/app/components/pajamas/alert_component.rb b/app/components/pajamas/alert_component.rb
index 4475f4cde6e..008d624b7e2 100644
--- a/app/components/pajamas/alert_component.rb
+++ b/app/components/pajamas/alert_component.rb
@@ -50,5 +50,13 @@ module Pajamas
def icon_classes
"gl-alert-icon#{' gl-alert-icon-no-title' if @title.nil?}"
end
+
+ def dismissible_button_options
+ new_options = @close_button_options.deep_symbolize_keys # in case strings were used
+ new_options[:class] = "js-close gl-dismiss-btn #{new_options[:class]}"
+ new_options[:aria] ||= {}
+ new_options[:aria][:label] = _('Dismiss') # this will wipe out label if already present
+ new_options
+ end
end
end
diff --git a/app/models/packages/package.rb b/app/models/packages/package.rb
index c58ad92d7a6..82157e48b0b 100644
--- a/app/models/packages/package.rb
+++ b/app/models/packages/package.rb
@@ -300,11 +300,7 @@ class Packages::Package < ApplicationRecord
# TODO: rename the method https://gitlab.com/gitlab-org/gitlab/-/issues/410352
def original_build_info
strong_memoize(:original_build_info) do
- if Feature.enabled?(:packages_display_last_pipeline, project)
- build_infos.last
- else
- build_infos.first
- end
+ build_infos.last
end
end
diff --git a/app/models/users/callout.rb b/app/models/users/callout.rb
index 896cccfa0e5..1ec1fb2fdfd 100644
--- a/app/models/users/callout.rb
+++ b/app/models/users/callout.rb
@@ -65,7 +65,11 @@ module Users
artifacts_management_page_feedback_banner: 62,
# 63 and 64 were removed with https://gitlab.com/gitlab-org/gitlab/-/merge_requests/120233
branch_rules_info_callout: 65,
- create_runner_workflow_banner: 66
+ create_runner_workflow_banner: 66,
+ repository_storage_limit_banner_info_threshold: 67, # EE-only
+ repository_storage_limit_banner_warning_threshold: 68, # EE-only
+ repository_storage_limit_banner_alert_threshold: 69, # EE-only
+ repository_storage_limit_banner_error_threshold: 70 # EE-only
}
validates :feature_name,
diff --git a/app/models/users/group_callout.rb b/app/models/users/group_callout.rb
index 1cc9f1f50ad..03384b594d6 100644
--- a/app/models/users/group_callout.rb
+++ b/app/models/users/group_callout.rb
@@ -25,7 +25,11 @@ module Users
preview_usage_quota_free_plan_alert: 15, # EE-only
enforcement_at_limit_alert: 16, # EE-only
web_hook_disabled: 17, # EE-only
- unlimited_members_during_trial_alert: 18 # EE-only
+ unlimited_members_during_trial_alert: 18, # EE-only
+ repository_storage_limit_banner_info_threshold: 19, # EE-only
+ repository_storage_limit_banner_warning_threshold: 20, # EE-only
+ repository_storage_limit_banner_alert_threshold: 21, # EE-only
+ repository_storage_limit_banner_error_threshold: 22 # EE-only
}
validates :group, presence: true
diff --git a/config/feature_flags/development/members_with_shared_group_access.yml b/config/feature_flags/development/members_with_shared_group_access.yml
index 83d3ca62681..f9d9a4fede4 100644
--- a/config/feature_flags/development/members_with_shared_group_access.yml
+++ b/config/feature_flags/development/members_with_shared_group_access.yml
@@ -5,4 +5,4 @@ rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/398621
milestone: '15.11'
type: development
group: group::tenant scale
-default_enabled: false
+default_enabled: true
diff --git a/config/feature_flags/development/packages_display_last_pipeline.yml b/config/feature_flags/development/packages_display_last_pipeline.yml
deleted file mode 100644
index a90edb4bb86..00000000000
--- a/config/feature_flags/development/packages_display_last_pipeline.yml
+++ /dev/null
@@ -1,8 +0,0 @@
----
-name: packages_display_last_pipeline
-introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/120125
-rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/410362
-milestone: '16.0'
-type: development
-group: group::package registry
-default_enabled: false
diff --git a/config/puma.example.development.rb b/config/puma.example.development.rb
index 1b75238112f..1183e3d75cf 100644
--- a/config/puma.example.development.rb
+++ b/config/puma.example.development.rb
@@ -53,10 +53,6 @@ on_restart do
end
before_fork do
- # Signal to the puma killer
- enable_puma_worker_killer = !Gitlab::Utils.to_boolean(ENV['DISABLE_PUMA_WORKER_KILLER'])
- Gitlab::Cluster::PumaWorkerKillerInitializer.start(@config.options) if enable_puma_worker_killer
-
# Signal application hooks that we're about to fork
Gitlab::Cluster::LifecycleEvents.do_before_fork
end
diff --git a/config/puma.rb.example b/config/puma.rb.example
index d474fc70500..ac3adc1eeec 100644
--- a/config/puma.rb.example
+++ b/config/puma.rb.example
@@ -36,7 +36,6 @@ bind 'unix:///home/git/gitlab/tmp/sockets/gitlab.socket'
workers 3
require_relative "/home/git/gitlab/lib/gitlab/cluster/lifecycle_events"
-require_relative "/home/git/gitlab/lib/gitlab/cluster/puma_worker_killer_initializer"
on_restart do
# Signal application hooks that we're about to restart
@@ -44,9 +43,6 @@ on_restart do
end
before_fork do
- # Signal to the puma killer
- Gitlab::Cluster::PumaWorkerKillerInitializer.start @config.options unless ENV['DISABLE_PUMA_WORKER_KILLER']
-
# Signal application hooks that we're about to fork
Gitlab::Cluster::LifecycleEvents.do_before_fork
end
diff --git a/db/docs/batched_background_migrations/cleanup_personal_access_tokens_with_nil_expires_at.yml b/db/docs/batched_background_migrations/cleanup_personal_access_tokens_with_nil_expires_at.yml
index 630aeccd6e1..9746663277a 100644
--- a/db/docs/batched_background_migrations/cleanup_personal_access_tokens_with_nil_expires_at.yml
+++ b/db/docs/batched_background_migrations/cleanup_personal_access_tokens_with_nil_expires_at.yml
@@ -1,5 +1,5 @@
---
-migration_job_name: CleanupPersonalAccessTokensWithInvalidExpiresAt
+migration_job_name: CleanupPersonalAccessTokensWithNilExpiresAt
description: Updates value of expires_at column to 365 days from now when it's nil for PersonalAccessTokens
feature_category: system_access
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/120239
diff --git a/doc/api/graphql/reference/index.md b/doc/api/graphql/reference/index.md
index 9a7724932eb..c5668d4ae57 100644
--- a/doc/api/graphql/reference/index.md
+++ b/doc/api/graphql/reference/index.md
@@ -19023,6 +19023,7 @@ Represents a product analytics dashboard.
| <a id="productanalyticsdashboardpanels"></a>`panels` | [`ProductAnalyticsDashboardPanelConnection!`](#productanalyticsdashboardpanelconnection) | Panels shown on the dashboard. (see [Connections](#connections)) |
| <a id="productanalyticsdashboardslug"></a>`slug` | [`String!`](#string) | Slug of the dashboard. |
| <a id="productanalyticsdashboardtitle"></a>`title` | [`String!`](#string) | Title of the dashboard. |
+| <a id="productanalyticsdashboarduserdefined"></a>`userDefined` | [`Boolean!`](#boolean) | Indicates whether the dashboard is user-defined or provided by GitLab. |
### `ProductAnalyticsDashboardPanel`
@@ -25618,6 +25619,10 @@ Name of the feature that the callout is for.
| <a id="usercalloutfeaturenameenumprofile_personal_access_token_expiry"></a>`PROFILE_PERSONAL_ACCESS_TOKEN_EXPIRY` | Callout feature name for profile_personal_access_token_expiry. |
| <a id="usercalloutfeaturenameenumproject_quality_summary_feedback"></a>`PROJECT_QUALITY_SUMMARY_FEEDBACK` | Callout feature name for project_quality_summary_feedback. |
| <a id="usercalloutfeaturenameenumregistration_enabled_callout"></a>`REGISTRATION_ENABLED_CALLOUT` | Callout feature name for registration_enabled_callout. |
+| <a id="usercalloutfeaturenameenumrepository_storage_limit_banner_alert_threshold"></a>`REPOSITORY_STORAGE_LIMIT_BANNER_ALERT_THRESHOLD` | Callout feature name for repository_storage_limit_banner_alert_threshold. |
+| <a id="usercalloutfeaturenameenumrepository_storage_limit_banner_error_threshold"></a>`REPOSITORY_STORAGE_LIMIT_BANNER_ERROR_THRESHOLD` | Callout feature name for repository_storage_limit_banner_error_threshold. |
+| <a id="usercalloutfeaturenameenumrepository_storage_limit_banner_info_threshold"></a>`REPOSITORY_STORAGE_LIMIT_BANNER_INFO_THRESHOLD` | Callout feature name for repository_storage_limit_banner_info_threshold. |
+| <a id="usercalloutfeaturenameenumrepository_storage_limit_banner_warning_threshold"></a>`REPOSITORY_STORAGE_LIMIT_BANNER_WARNING_THRESHOLD` | Callout feature name for repository_storage_limit_banner_warning_threshold. |
| <a id="usercalloutfeaturenameenumsecurity_configuration_devops_alert"></a>`SECURITY_CONFIGURATION_DEVOPS_ALERT` | Callout feature name for security_configuration_devops_alert. |
| <a id="usercalloutfeaturenameenumsecurity_configuration_upgrade_banner"></a>`SECURITY_CONFIGURATION_UPGRADE_BANNER` | Callout feature name for security_configuration_upgrade_banner. |
| <a id="usercalloutfeaturenameenumsecurity_newsletter_callout"></a>`SECURITY_NEWSLETTER_CALLOUT` | Callout feature name for security_newsletter_callout. |
diff --git a/doc/ci/pipeline_editor/index.md b/doc/ci/pipeline_editor/index.md
index d920c34d90a..fcacc3b5d97 100644
--- a/doc/ci/pipeline_editor/index.md
+++ b/doc/ci/pipeline_editor/index.md
@@ -113,7 +113,7 @@ where:
with the linked configuration.
Using `!reference` tags can cause nested configuration that display with
-multiple hyphens (`-`) in the expanded view. This behavior is expected, and the extra
+multiple hyphens (`-`) at the start of the line in the expanded view. This behavior is expected, and the extra
hyphens do not affect the job's execution. For example, this configuration and
fully expanded version are both valid:
@@ -124,11 +124,27 @@ fully expanded version are both valid:
script:
- pip install pyflakes
+ .rule-01:
+ rules:
+ - if: $CI_MERGE_REQUEST_SOURCE_BRANCH_NAME =~ /^feature/
+ when: manual
+ allow_failure: true
+ - if: $CI_MERGE_REQUEST_SOURCE_BRANCH_NAME
+
+ .rule-02:
+ rules:
+ - if: $CI_COMMIT_BRANCH == "main"
+ when: manual
+ allow_failure: true
+
lint-python:
image: python:latest
script:
- !reference [.python-req, script]
- pyflakes python/
+ rules:
+ - !reference [.rule-01, rules]
+ - !reference [.rule-02, rules]
```
- Expanded configuration in **Full configuration** tab:
@@ -137,11 +153,30 @@ fully expanded version are both valid:
".python-req":
script:
- pip install pyflakes
+ ".rule-01":
+ rules:
+ - if: "$CI_MERGE_REQUEST_SOURCE_BRANCH_NAME =~ /^feature/"
+ when: manual
+ allow_failure: true
+ - if: "$CI_MERGE_REQUEST_SOURCE_BRANCH_NAME"
+ ".rule-02":
+ rules:
+ - if: $CI_COMMIT_BRANCH == "main"
+ when: manual
+ allow_failure: true
lint-python:
+ image: python:latest
script:
- - - pip install pyflakes # <- The extra hyphens do not affect the job's execution.
+ - - pip install pyflakes # <- The extra hyphens do not affect the job's execution.
- pyflakes python/
- image: python:latest
+ rules:
+ - - if: "$CI_MERGE_REQUEST_SOURCE_BRANCH_NAME =~ /^feature/" # <- The extra hyphens do not affect the job's execution.
+ when: manual
+ allow_failure: true
+ - if: "$CI_MERGE_REQUEST_SOURCE_BRANCH_NAME" # <- No extra hyphen but aligned with previous rule
+ - - if: $CI_COMMIT_BRANCH == "main" # <- The extra hyphens do not affect the job's execution.
+ when: manual
+ allow_failure: true
```
## Commit changes to CI configuration
diff --git a/doc/user/project/quick_actions.md b/doc/user/project/quick_actions.md
index 2c52a5d743a..8cd924a8c08 100644
--- a/doc/user/project/quick_actions.md
+++ b/doc/user/project/quick_actions.md
@@ -162,7 +162,7 @@ The following quick actions can be applied through the description field when ed
| `/clear_health_status` | **{check-circle}** Yes | **{dotted-circle}** Yes | **{dotted-circle}** Yes | Clear [health status](issues/managing_issues.md#health-status).
| `/weight <value>` | **{check-circle}** Yes | **{dotted-circle}** No | **{dotted-circle}** No | Set weight. Valid options for `<value>` include `0`, `1`, and `2`.
| `/clear_weight` | **{check-circle}** Yes | **{dotted-circle}** No | **{dotted-circle}** No | Clear weight.
-| `/type` | **{check-circle}** Yes | **{dotted-circle}** Yes | **{dotted-circle}** Yes | Converts work item to specified type. Available options for `<type>` include `Issue`, `Task`, `Objective` and `Key Result`. [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/385227) in GitLab 16.0 [with a flag](../../administration/feature_flags.md) named `work_items_mvc_2`. Disabled by default.
+| `/type` | **{check-circle}** Yes | **{dotted-circle}** Yes | **{dotted-circle}** Yes | Converts work item to specified type. Available options for `<type>` include `Issue`, `Task`, `Objective` and `Key Result`. [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/385227) in GitLab 16.0.
## Commit messages
diff --git a/lib/gitlab/cluster/puma_worker_killer_initializer.rb b/lib/gitlab/cluster/puma_worker_killer_initializer.rb
deleted file mode 100644
index 957faf797b5..00000000000
--- a/lib/gitlab/cluster/puma_worker_killer_initializer.rb
+++ /dev/null
@@ -1,51 +0,0 @@
-# frozen_string_literal: true
-
-module Gitlab
- module Cluster
- class PumaWorkerKillerInitializer
- def self.start(
- puma_options,
- puma_per_worker_max_memory_mb: 1200,
- puma_master_max_memory_mb: 950,
- additional_puma_dev_max_memory_mb: 200)
-
- # We are replacing PWK with Watchdog by using backward compatible RssMemoryLimit monitor by default.
- # https://gitlab.com/groups/gitlab-org/-/epics/9119
- return if Gitlab::Utils.to_boolean(ENV.fetch('GITLAB_MEMORY_WATCHDOG_ENABLED', true))
-
- require 'puma_worker_killer'
-
- PumaWorkerKiller.config do |config|
- worker_count = puma_options[:workers] || 1
- # The Puma Worker Killer checks the total memory used by the cluster,
- # i.e. both primary and worker processes.
- # https://github.com/schneems/puma_worker_killer/blob/v0.1.0/lib/puma_worker_killer/puma_memory.rb#L57
- #
- # Additional memory is added when running in `development`
- config.ram = puma_master_max_memory_mb +
- (worker_count * puma_per_worker_max_memory_mb) +
- (Rails.env.development? ? (1 + worker_count) * additional_puma_dev_max_memory_mb : 0)
-
- config.frequency = 20 # seconds
-
- # We just want to limit to a fixed maximum, unrelated to the total amount
- # of available RAM.
- config.percent_usage = 0.98
-
- # Ideally we'll never hit the maximum amount of memory. Restart the workers
- # regularly rather than rely on OOM behavior for periodic restarting.
- config.rolling_restart_frequency = 43200 # 12 hours in seconds.
-
- # Spread the rolling restarts out over 1 hour to avoid too many simultaneous
- # process startups.
- config.rolling_restart_splay_seconds = 0.0..3600.0 # 0 to 1 hour in seconds.
-
- observer = Gitlab::Cluster::PumaWorkerKillerObserver.new
- config.pre_term = observer.callback
- end
-
- PumaWorkerKiller.start
- end
- end
- end
-end
diff --git a/lib/gitlab/cluster/puma_worker_killer_observer.rb b/lib/gitlab/cluster/puma_worker_killer_observer.rb
deleted file mode 100644
index f53051c32ff..00000000000
--- a/lib/gitlab/cluster/puma_worker_killer_observer.rb
+++ /dev/null
@@ -1,22 +0,0 @@
-# frozen_string_literal: true
-
-module Gitlab
- module Cluster
- class PumaWorkerKillerObserver
- def initialize
- @counter = Gitlab::Metrics.counter(:puma_killer_terminations_total, 'Number of workers terminated by PumaWorkerKiller')
- end
-
- # returns the Proc to be used as the observer callback block
- def callback
- method(:log_termination)
- end
-
- private
-
- def log_termination(worker)
- @counter.increment
- end
- end
- end
-end
diff --git a/lib/gitlab/quick_actions/work_item_actions.rb b/lib/gitlab/quick_actions/work_item_actions.rb
index fa43308c9e2..69a49d214ff 100644
--- a/lib/gitlab/quick_actions/work_item_actions.rb
+++ b/lib/gitlab/quick_actions/work_item_actions.rb
@@ -12,9 +12,6 @@ module Gitlab
format(_("Converts work item to %{type}. Widgets not supported in new type are removed."), type: target_type)
end
types WorkItem
- condition do
- quick_action_target&.project&.work_items_mvc_2_feature_flag_enabled?
- end
params 'Task | Objective | Key Result | Issue'
command :type do |type_name|
work_item_type = ::WorkItems::Type.find_by_name(type_name)
diff --git a/lib/gitlab/usage_data_counters/known_events/product_analytics.yml b/lib/gitlab/usage_data_counters/known_events/product_analytics.yml
index 5a791c4b3c2..56a077763c8 100644
--- a/lib/gitlab/usage_data_counters/known_events/product_analytics.yml
+++ b/lib/gitlab/usage_data_counters/known_events/product_analytics.yml
@@ -2,3 +2,5 @@
aggregation: weekly
- name: project_initialized_product_analytics
aggregation: weekly
+- name: user_created_analytics_dashboard
+ aggregation: weekly
diff --git a/locale/gitlab.pot b/locale/gitlab.pot
index e39517033a1..a0eec5283e0 100644
--- a/locale/gitlab.pot
+++ b/locale/gitlab.pot
@@ -5076,6 +5076,9 @@ msgstr ""
msgid "Analytics|Add to Dashboard"
msgstr ""
+msgid "Analytics|Add visualizations"
+msgstr ""
+
msgid "Analytics|An error occurred while loading data"
msgstr ""
@@ -34153,6 +34156,9 @@ msgstr ""
msgid "ProductAnalytics|Compares page views of all pages against each other"
msgstr ""
+msgid "ProductAnalytics|Create a visualization"
+msgstr ""
+
msgid "ProductAnalytics|Creating your product analytics instance..."
msgstr ""
@@ -39610,12 +39616,6 @@ msgstr ""
msgid "ScanExecutionPolicy|%{rules} actions for the %{scopes} %{branches} %{agents} %{namespaces}"
msgstr ""
-msgid "ScanExecutionPolicy|%{thenLabelStart}Then%{thenLabelEnd} Run a %{scan} scan on runner that %{tags}"
-msgstr ""
-
-msgid "ScanExecutionPolicy|%{thenLabelStart}Then%{thenLabelEnd} Run a %{scan} scan with %{dastProfiles} with tags %{tags}"
-msgstr ""
-
msgid "ScanExecutionPolicy|A pipeline is run"
msgstr ""
@@ -39628,6 +39628,12 @@ msgstr ""
msgid "ScanExecutionPolicy|If the field is empty, the runner will be automatically selected"
msgstr ""
+msgid "ScanExecutionPolicy|Run a %{scan} scan on runner that %{tags}"
+msgstr ""
+
+msgid "ScanExecutionPolicy|Run a %{scan} scan with %{dastProfiles} with tags %{tags}"
+msgstr ""
+
msgid "ScanExecutionPolicy|Scanner profile"
msgstr ""
@@ -47423,9 +47429,6 @@ msgstr ""
msgid "Trial|Continue"
msgstr ""
-msgid "Trial|Dismiss"
-msgstr ""
-
msgid "Trial|Your GitLab Ultimate trial lasts for 30 days, but you can keep your free GitLab account forever. We just need some additional information to activate your trial."
msgstr ""
diff --git a/package.json b/package.json
index 30dafb88268..fed66bb53c5 100644
--- a/package.json
+++ b/package.json
@@ -279,6 +279,7 @@
"timezone-mock": "^1.0.8",
"vue-loader-vue3": "npm:vue-loader@17",
"vue-test-utils-compat": "0.0.13",
+ "vuex-mock-store": "^0.1.0",
"webpack-dev-server": "4.15.0",
"xhr-mock": "^2.5.1",
"yarn-check-webpack-plugin": "^1.2.0",
diff --git a/rubocop/cop/rspec/avoid_conditional_statements.rb b/rubocop/cop/rspec/avoid_conditional_statements.rb
index d03c3fb5d04..c24133f6469 100644
--- a/rubocop/cop/rspec/avoid_conditional_statements.rb
+++ b/rubocop/cop/rspec/avoid_conditional_statements.rb
@@ -7,6 +7,8 @@ module RuboCop
module RSpec
# This cop checks for the usage of conditional statements in specs.
#
+ # https://gitlab.com/gitlab-org/gitlab/-/issues/410138
+ #
# @example
#
# # bad
diff --git a/spec/components/pajamas/alert_component_spec.rb b/spec/components/pajamas/alert_component_spec.rb
index 8f02979357e..4b554564d6e 100644
--- a/spec/components/pajamas/alert_component_spec.rb
+++ b/spec/components/pajamas/alert_component_spec.rb
@@ -126,25 +126,45 @@ RSpec.describe Pajamas::AlertComponent, :aggregate_failures, type: :component do
end
context 'with dismissible content' do
- before do
- render_inline described_class.new(
- close_button_options: {
- class: '_close_button_class_',
- data: {
- testid: '_close_button_testid_'
- }
- }
- )
- end
+ context 'with no custom options' do
+ before do
+ render_inline described_class.new
+ end
- it 'does not have "not dismissible" class' do
- expect(page).not_to have_selector('.gl-alert-not-dismissible')
+ it 'does not have "not dismissible" class' do
+ expect(page).not_to have_selector('.gl-alert-not-dismissible')
+ end
+
+ it 'renders a dismiss button and data' do
+ expect(page).to have_selector('.gl-button.btn-sm.btn-icon.gl-button.gl-dismiss-btn.js-close')
+ expect(page).to have_selector("[data-testid='close-icon']")
+ expect(page).to have_selector('[aria-label="Dismiss"]')
+ end
end
- it 'renders a dismiss button and data' do
- expect(page).to have_selector('.gl-dismiss-btn.js-close._close_button_class_')
- expect(page).to have_selector("[data-testid='close-icon']")
- expect(page).to have_selector('[data-testid="_close_button_testid_"]')
+ context 'with custom options' do
+ before do
+ render_inline described_class.new(
+ close_button_options: {
+ aria: {
+ label: '_custom_aria_label_'
+ },
+ class: '_close_button_class_',
+ data: {
+ testid: '_close_button_testid_',
+ "custom-attribute": '_custom_data_'
+ }
+ }
+ )
+ end
+
+ it 'renders a dismiss button and data' do
+ expect(page).to have_selector('.gl-button.btn-sm.btn-icon.gl-dismiss-btn.js-close._close_button_class_')
+ expect(page).to have_selector("[data-testid='close-icon']")
+ expect(page).to have_selector('[data-testid="_close_button_testid_"]')
+ expect(page).to have_selector('[aria-label="Dismiss"]')
+ expect(page).to have_selector('[data-custom-attribute="_custom_data_"]')
+ end
end
end
diff --git a/spec/features/projects/environments/environment_metrics_spec.rb b/spec/features/projects/environments/environment_metrics_spec.rb
index e212d464029..335866a7d75 100644
--- a/spec/features/projects/environments/environment_metrics_spec.rb
+++ b/spec/features/projects/environments/environment_metrics_spec.rb
@@ -6,7 +6,7 @@ RSpec.describe 'Environment > Metrics', feature_category: :projects do
include PrometheusHelpers
let(:user) { create(:user) }
- let(:project) { create(:project, :with_prometheus_integration, :repository) }
+ let_it_be(:project) { create(:project, :with_prometheus_integration, :repository) }
let(:pipeline) { create(:ci_pipeline, project: project) }
let(:build) { create(:ci_build, pipeline: pipeline) }
let(:environment) { create(:environment, project: project) }
diff --git a/spec/frontend/__helpers__/mocks/mr_notes/stores/index.js b/spec/frontend/__helpers__/mocks/mr_notes/stores/index.js
new file mode 100644
index 00000000000..a983edbbb72
--- /dev/null
+++ b/spec/frontend/__helpers__/mocks/mr_notes/stores/index.js
@@ -0,0 +1,15 @@
+import { Store } from 'vuex-mock-store';
+import createDiffState from 'ee_else_ce/diffs/store/modules/diff_state';
+import createNotesState from '~/notes/stores/state';
+
+const store = new Store({
+ state: {
+ diffs: createDiffState(),
+ notes: createNotesState(),
+ },
+ spy: {
+ create: (handler) => jest.fn(handler).mockImplementation(() => Promise.resolve()),
+ },
+});
+
+export default store;
diff --git a/spec/frontend/batch_comments/components/preview_item_spec.js b/spec/frontend/batch_comments/components/preview_item_spec.js
index a19a72af813..191586e44cc 100644
--- a/spec/frontend/batch_comments/components/preview_item_spec.js
+++ b/spec/frontend/batch_comments/components/preview_item_spec.js
@@ -1,29 +1,33 @@
import { mount } from '@vue/test-utils';
import PreviewItem from '~/batch_comments/components/preview_item.vue';
-import { createStore } from '~/batch_comments/stores';
-import diffsModule from '~/diffs/store/modules';
-import notesModule from '~/notes/stores/modules';
+import store from '~/mr_notes/stores';
import { createDraft } from '../mock_data';
jest.mock('~/behaviors/markdown/render_gfm');
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
describe('Batch comments draft preview item component', () => {
let wrapper;
let draft;
- function createComponent(isLast = false, extra = {}, extendStore = () => {}) {
- const store = createStore();
- store.registerModule('diffs', diffsModule());
- store.registerModule('notes', notesModule());
+ beforeEach(() => {
+ store.reset();
- extendStore(store);
+ store.getters.getDiscussion = jest.fn(() => null);
+ });
+ function createComponent(isLast = false, extra = {}) {
draft = {
...createDraft(),
...extra,
};
- wrapper = mount(PreviewItem, { store, propsData: { draft, isLast } });
+ wrapper = mount(PreviewItem, {
+ mocks: {
+ $store: store,
+ },
+ propsData: { draft, isLast },
+ });
}
it('renders text content', () => {
@@ -87,18 +91,19 @@ describe('Batch comments draft preview item component', () => {
describe('for thread', () => {
beforeEach(() => {
- createComponent(false, { discussion_id: '1', resolve_discussion: true }, (store) => {
- store.state.notes.discussions.push({
- id: '1',
- notes: [
- {
- author: {
- name: "Author 'Nick' Name",
- },
+ store.getters.getDiscussion.mockReturnValue({
+ id: '1',
+ notes: [
+ {
+ author: {
+ name: "Author 'Nick' Name",
},
- ],
- });
+ },
+ ],
});
+ store.getters.isDiscussionResolved = jest.fn().mockReturnValue(false);
+
+ createComponent(false, { discussion_id: '1', resolve_discussion: true });
});
it('renders title', () => {
@@ -114,9 +119,7 @@ describe('Batch comments draft preview item component', () => {
describe('for new comment', () => {
it('renders title', () => {
- createComponent(false, {}, (store) => {
- store.state.notes.discussions.push({});
- });
+ createComponent();
expect(wrapper.find('.review-preview-item-header-text').text()).toContain('Your new comment');
});
diff --git a/spec/frontend/diffs/components/compare_versions_spec.js b/spec/frontend/diffs/components/compare_versions_spec.js
index 47a266c2e36..cbbfd88260b 100644
--- a/spec/frontend/diffs/components/compare_versions_spec.js
+++ b/spec/frontend/diffs/components/compare_versions_spec.js
@@ -1,15 +1,14 @@
import { mount } from '@vue/test-utils';
-import Vue, { nextTick } from 'vue';
-import Vuex from 'vuex';
+import { nextTick } from 'vue';
import getDiffWithCommit from 'test_fixtures/merge_request_diffs/with_commit.json';
import setWindowLocation from 'helpers/set_window_location_helper';
import { TEST_HOST } from 'helpers/test_constants';
import { trimText } from 'helpers/text_helper';
import CompareVersionsComponent from '~/diffs/components/compare_versions.vue';
-import { createStore } from '~/mr_notes/stores';
+import store from '~/mr_notes/stores';
import diffsMockData from '../mock_data/merge_request_diffs';
-Vue.use(Vuex);
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
const NEXT_COMMIT_URL = `${TEST_HOST}/?commit_id=next`;
const PREV_COMMIT_URL = `${TEST_HOST}/?commit_id=prev`;
@@ -20,8 +19,6 @@ beforeEach(() => {
describe('CompareVersions', () => {
let wrapper;
- let store;
- let dispatchMock;
const targetBranchName = 'tmp-wine-dev';
const { commit } = getDiffWithCommit;
@@ -30,10 +27,10 @@ describe('CompareVersions', () => {
store.state.diffs.commit = { ...store.state.diffs.commit, ...commitArgs };
}
- dispatchMock = jest.spyOn(store, 'dispatch');
-
wrapper = mount(CompareVersionsComponent, {
- store,
+ mocks: {
+ $store: store,
+ },
propsData: {
mergeRequestDiffs: diffsMockData,
diffFilesCountText: '1',
@@ -50,8 +47,25 @@ describe('CompareVersions', () => {
getCommitNavButtonsElement().find('.btn-group > *:first-child');
beforeEach(() => {
- store = createStore();
+ store.reset();
+
const mergeRequestDiff = diffsMockData[0];
+ const version = {
+ ...mergeRequestDiff,
+ href: `${TEST_HOST}/latest/version`,
+ versionName: 'latest version',
+ };
+ store.getters['diffs/diffCompareDropdownSourceVersions'] = [version];
+ store.getters['diffs/diffCompareDropdownTargetVersions'] = [
+ {
+ ...version,
+ selected: true,
+ versionName: targetBranchName,
+ },
+ ];
+ store.getters['diffs/whichCollapsedTypes'] = { any: false };
+ store.getters['diffs/isInlineView'] = false;
+ store.getters['diffs/isParallelView'] = false;
store.state.diffs.addedLines = 10;
store.state.diffs.removedLines = 20;
@@ -104,7 +118,6 @@ describe('CompareVersions', () => {
it('should not render Tree List toggle button when there are no changes', () => {
createWrapper();
-
const treeListBtn = wrapper.find('.js-toggle-tree-list');
expect(treeListBtn.exists()).toBe(false);
@@ -118,7 +131,10 @@ describe('CompareVersions', () => {
const viewTypeBtn = wrapper.find('#inline-diff-btn');
viewTypeBtn.trigger('click');
- expect(window.location.toString()).toContain('?view=inline');
+ expect(store.dispatch).toHaveBeenCalledWith(
+ 'diffs/setInlineDiffViewType',
+ expect.any(MouseEvent),
+ );
});
});
@@ -128,13 +144,16 @@ describe('CompareVersions', () => {
const viewTypeBtn = wrapper.find('#parallel-diff-btn');
viewTypeBtn.trigger('click');
- expect(window.location.toString()).toContain('?view=parallel');
+ expect(store.dispatch).toHaveBeenCalledWith(
+ 'diffs/setParallelDiffViewType',
+ expect.any(MouseEvent),
+ );
});
});
describe('commit', () => {
beforeEach(() => {
- store.state.diffs.commit = getDiffWithCommit.commit;
+ store.state.diffs.commit = commit;
createWrapper();
});
@@ -218,7 +237,7 @@ describe('CompareVersions', () => {
link.trigger('click');
await nextTick();
- expect(dispatchMock).toHaveBeenCalledWith('diffs/moveToNeighboringCommit', {
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/moveToNeighboringCommit', {
direction: 'previous',
});
});
@@ -248,7 +267,7 @@ describe('CompareVersions', () => {
link.trigger('click');
await nextTick();
- expect(dispatchMock).toHaveBeenCalledWith('diffs/moveToNeighboringCommit', {
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/moveToNeighboringCommit', {
direction: 'next',
});
});
diff --git a/spec/frontend/diffs/components/diff_line_note_form_spec.js b/spec/frontend/diffs/components/diff_line_note_form_spec.js
index eb895bd9057..e42b98e4d68 100644
--- a/spec/frontend/diffs/components/diff_line_note_form_spec.js
+++ b/spec/frontend/diffs/components/diff_line_note_form_spec.js
@@ -1,8 +1,7 @@
import { shallowMount } from '@vue/test-utils';
import { nextTick } from 'vue';
-import Vuex from 'vuex';
import DiffLineNoteForm from '~/diffs/components/diff_line_note_form.vue';
-import { createModules } from '~/mr_notes/stores';
+import store from '~/mr_notes/stores';
import NoteForm from '~/notes/components/note_form.vue';
import MultilineCommentForm from '~/notes/components/multiline_comment_form.vue';
import { confirmAction } from '~/lib/utils/confirm_via_gl_modal/confirm_via_gl_modal';
@@ -10,51 +9,25 @@ import { noteableDataMock } from 'jest/notes/mock_data';
import { getDiffFileMock } from '../mock_data/diff_file';
jest.mock('~/lib/utils/confirm_via_gl_modal/confirm_via_gl_modal');
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
describe('DiffLineNoteForm', () => {
let wrapper;
let diffFile;
let diffLines;
- let actions;
- let store;
- const getSelectedLine = () => {
- const lineCode = diffLines[1].line_code;
- return diffFile.highlighted_diff_lines.find((l) => l.line_code === lineCode);
- };
-
- const createStore = (state) => {
- const modules = createModules();
- modules.diffs.actions = {
- ...modules.diffs.actions,
- saveDiffDiscussion: jest.fn(() => Promise.resolve()),
- };
- modules.diffs.getters = {
- ...modules.diffs.getters,
- diffCompareDropdownTargetVersions: jest.fn(),
- diffCompareDropdownSourceVersions: jest.fn(),
- selectedSourceIndex: jest.fn(),
- };
- modules.notes.getters = {
- ...modules.notes.getters,
- noteableType: jest.fn(),
- };
- actions = modules.diffs.actions;
+ beforeEach(() => {
+ diffFile = getDiffFileMock();
+ diffLines = diffFile.highlighted_diff_lines;
- store = new Vuex.Store({ modules });
- store.state.notes.userData.id = 1;
store.state.notes.noteableData = noteableDataMock;
- store.replaceState({ ...store.state, ...state });
- };
+ store.getters.isLoggedIn = jest.fn().mockReturnValue(true);
+ store.getters['diffs/getDiffFileByHash'] = jest.fn().mockReturnValue(diffFile);
+ });
- const createComponent = ({ props, state } = {}) => {
+ const createComponent = ({ props } = {}) => {
wrapper?.destroy();
- diffFile = getDiffFileMock();
- diffLines = diffFile.highlighted_diff_lines;
-
- createStore(state);
- store.state.diffs.diffFiles = [diffFile];
const propsData = {
diffFileHash: diffFile.file_hash,
@@ -66,7 +39,9 @@ describe('DiffLineNoteForm', () => {
};
wrapper = shallowMount(DiffLineNoteForm, {
- store,
+ mocks: {
+ $store: store,
+ },
propsData,
});
};
@@ -129,7 +104,10 @@ describe('DiffLineNoteForm', () => {
expect(confirmAction).toHaveBeenCalled();
await nextTick();
- expect(getSelectedLine().hasForm).toBe(false);
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/cancelCommentForm', {
+ lineCode: diffLines[1].line_code,
+ fileHash: diffFile.file_hash,
+ });
});
});
@@ -157,6 +135,10 @@ describe('DiffLineNoteForm', () => {
});
describe('saving note', () => {
+ beforeEach(() => {
+ store.getters.noteableType = 'merge-request';
+ });
+
it('should save original line', async () => {
const lineRange = {
start: {
@@ -172,20 +154,65 @@ describe('DiffLineNoteForm', () => {
old_line: null,
},
};
- await findNoteForm().vm.$emit('handleFormUpdate', 'note body');
- expect(actions.saveDiffDiscussion.mock.calls[0][1].formData).toMatchObject({
- lineRange,
+
+ const noteBody = 'note body';
+ await findNoteForm().vm.$emit('handleFormUpdate', noteBody);
+
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/saveDiffDiscussion', {
+ note: noteBody,
+ formData: {
+ noteableData: noteableDataMock,
+ noteableType: store.getters.noteableType,
+ noteTargetLine: diffLines[1],
+ diffViewType: store.state.diffs.diffViewType,
+ diffFile,
+ linePosition: '',
+ lineRange,
+ },
+ });
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/cancelCommentForm', {
+ lineCode: diffLines[1].line_code,
+ fileHash: diffFile.file_hash,
});
});
it('should save selected line from the store', async () => {
const lineCode = 'test';
store.state.notes.selectedCommentPosition = { start: { line_code: lineCode } };
- createComponent({ state: store.state });
- await findNoteForm().vm.$emit('handleFormUpdate', 'note body');
- expect(actions.saveDiffDiscussion.mock.calls[0][1].formData.lineRange.start.line_code).toBe(
- lineCode,
- );
+ createComponent();
+ const noteBody = 'note body';
+
+ await findNoteForm().vm.$emit('handleFormUpdate', noteBody);
+
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/saveDiffDiscussion', {
+ note: noteBody,
+ formData: {
+ noteableData: noteableDataMock,
+ noteableType: store.getters.noteableType,
+ noteTargetLine: diffLines[1],
+ diffViewType: store.state.diffs.diffViewType,
+ diffFile,
+ linePosition: '',
+ lineRange: {
+ start: {
+ line_code: lineCode,
+ new_line: undefined,
+ old_line: undefined,
+ type: undefined,
+ },
+ end: {
+ line_code: diffLines[1].line_code,
+ new_line: diffLines[1].new_line,
+ old_line: diffLines[1].old_line,
+ type: diffLines[1].type,
+ },
+ },
+ },
+ });
+ expect(store.dispatch).toHaveBeenCalledWith('diffs/cancelCommentForm', {
+ lineCode: diffLines[1].line_code,
+ fileHash: diffFile.file_hash,
+ });
});
});
});
diff --git a/spec/frontend/diffs/components/no_changes_spec.js b/spec/frontend/diffs/components/no_changes_spec.js
index e637b1dd43d..fd89d52a59e 100644
--- a/spec/frontend/diffs/components/no_changes_spec.js
+++ b/spec/frontend/diffs/components/no_changes_spec.js
@@ -1,55 +1,53 @@
import { GlButton } from '@gitlab/ui';
import { shallowMount, mount } from '@vue/test-utils';
-import Vue from 'vue';
-import Vuex from 'vuex';
import NoChanges from '~/diffs/components/no_changes.vue';
-import { createStore } from '~/mr_notes/stores';
+import store from '~/mr_notes/stores';
import diffsMockData from '../mock_data/merge_request_diffs';
-Vue.use(Vuex);
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
const TEST_TARGET_BRANCH = 'foo';
const TEST_SOURCE_BRANCH = 'dev/update';
+const latestVersionNumber = Math.max(...diffsMockData.map((version) => version.version_index));
describe('Diff no changes empty state', () => {
- let wrapper;
- let store;
-
- function createComponent(mountFn = shallowMount) {
- wrapper = mountFn(NoChanges, {
- store,
+ const createComponent = (mountFn = shallowMount) =>
+ mountFn(NoChanges, {
+ mocks: {
+ $store: store,
+ },
propsData: {
changesEmptyStateIllustration: '',
},
});
- }
beforeEach(() => {
- store = createStore();
- store.state.diffs.mergeRequestDiff = {};
- store.state.notes.noteableData = {
+ store.reset();
+
+ store.getters.getNoteableData = {
target_branch: TEST_TARGET_BRANCH,
source_branch: TEST_SOURCE_BRANCH,
};
- store.state.diffs.mergeRequestDiffs = diffsMockData;
+ store.getters['diffs/diffCompareDropdownSourceVersions'] = [];
+ store.getters['diffs/diffCompareDropdownTargetVersions'] = [];
});
- const findMessage = () => wrapper.find('[data-testid="no-changes-message"]');
+ const findMessage = (wrapper) => wrapper.find('[data-testid="no-changes-message"]');
it('prevents XSS', () => {
- store.state.notes.noteableData = {
+ store.getters.getNoteableData = {
source_branch: '<script>alert("test");</script>',
target_branch: '<script>alert("test");</script>',
};
- createComponent();
+ const wrapper = createComponent();
expect(wrapper.find('script').exists()).toBe(false);
});
describe('Renders', () => {
it('Show create commit button', () => {
- createComponent();
+ const wrapper = createComponent();
expect(wrapper.findComponent(GlButton).exists()).toBe(true);
});
@@ -64,15 +62,28 @@ describe('Diff no changes empty state', () => {
'renders text "$expectedText" (sourceIndex=$sourceIndex and targetIndex=$targetIndex)',
({ expectedText, targetIndex, sourceIndex }) => {
if (targetIndex !== null) {
- store.state.diffs.startVersion = { version_index: targetIndex };
+ store.getters['diffs/diffCompareDropdownTargetVersions'] = [
+ {
+ selected: true,
+ version_index: targetIndex,
+ versionName: `version ${targetIndex}`,
+ },
+ ];
}
if (sourceIndex !== null) {
- store.state.diffs.mergeRequestDiff.version_index = sourceIndex;
+ store.getters['diffs/diffCompareDropdownSourceVersions'] = [
+ {
+ isLatestVersion: sourceIndex === latestVersionNumber,
+ selected: true,
+ version_index: targetIndex,
+ versionName: `version ${sourceIndex}`,
+ },
+ ];
}
- createComponent(mount);
+ const wrapper = createComponent(mount);
- expect(findMessage().text()).toBe(expectedText);
+ expect(findMessage(wrapper).text()).toBe(expectedText);
},
);
});
diff --git a/spec/frontend/diffs/components/settings_dropdown_spec.js b/spec/frontend/diffs/components/settings_dropdown_spec.js
index 3d2bbe43746..cbd2ae3e525 100644
--- a/spec/frontend/diffs/components/settings_dropdown_spec.js
+++ b/spec/frontend/diffs/components/settings_dropdown_spec.js
@@ -5,44 +5,34 @@ import { extendedWrapper } from 'helpers/vue_test_utils_helper';
import SettingsDropdown from '~/diffs/components/settings_dropdown.vue';
import { PARALLEL_DIFF_VIEW_TYPE, INLINE_DIFF_VIEW_TYPE } from '~/diffs/constants';
import eventHub from '~/diffs/event_hub';
+import store from '~/mr_notes/stores';
-import createDiffsStore from '../create_diffs_store';
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
describe('Diff settings dropdown component', () => {
- let wrapper;
- let store;
-
- function createComponent(extendStore = () => {}) {
- store = createDiffsStore();
-
- extendStore(store);
-
- wrapper = extendedWrapper(
+ const createComponent = () =>
+ extendedWrapper(
mount(SettingsDropdown, {
- store,
+ mocks: {
+ $store: store,
+ },
}),
);
- }
function getFileByFileCheckbox(vueWrapper) {
return vueWrapper.findByTestId('file-by-file');
}
- function setup({ storeUpdater } = {}) {
- createComponent(storeUpdater);
- jest.spyOn(store, 'dispatch').mockImplementation(() => {});
- }
-
beforeEach(() => {
- setup();
- });
+ store.reset();
- afterEach(() => {
- store.dispatch.mockRestore();
+ store.getters['diffs/isInlineView'] = false;
+ store.getters['diffs/isParallelView'] = false;
});
describe('tree view buttons', () => {
it('list view button dispatches setRenderTreeList with false', () => {
+ const wrapper = createComponent();
wrapper.find('.js-list-view').trigger('click');
expect(store.dispatch).toHaveBeenCalledWith('diffs/setRenderTreeList', {
@@ -51,6 +41,7 @@ describe('Diff settings dropdown component', () => {
});
it('tree view button dispatches setRenderTreeList with true', () => {
+ const wrapper = createComponent();
wrapper.find('.js-tree-view').trigger('click');
expect(store.dispatch).toHaveBeenCalledWith('diffs/setRenderTreeList', {
@@ -59,19 +50,18 @@ describe('Diff settings dropdown component', () => {
});
it('sets list button as selected when renderTreeList is false', () => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { renderTreeList: false }),
- });
+ store.state.diffs = { renderTreeList: false };
+
+ const wrapper = createComponent();
expect(wrapper.find('.js-list-view').classes('selected')).toBe(true);
expect(wrapper.find('.js-tree-view').classes('selected')).toBe(false);
});
it('sets tree button as selected when renderTreeList is true', () => {
- setup({
- storeUpdater: (origStore) => Object.assign(origStore.state.diffs, { renderTreeList: true }),
- });
+ store.state.diffs = { renderTreeList: true };
+
+ const wrapper = createComponent();
expect(wrapper.find('.js-list-view').classes('selected')).toBe(false);
expect(wrapper.find('.js-tree-view').classes('selected')).toBe(true);
@@ -80,32 +70,36 @@ describe('Diff settings dropdown component', () => {
describe('compare changes', () => {
it('sets inline button as selected', () => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { diffViewType: INLINE_DIFF_VIEW_TYPE }),
- });
+ store.state.diffs = { diffViewType: INLINE_DIFF_VIEW_TYPE };
+ store.getters['diffs/isInlineView'] = true;
+
+ const wrapper = createComponent();
expect(wrapper.find('.js-inline-diff-button').classes('selected')).toBe(true);
expect(wrapper.find('.js-parallel-diff-button').classes('selected')).toBe(false);
});
it('sets parallel button as selected', () => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { diffViewType: PARALLEL_DIFF_VIEW_TYPE }),
- });
+ store.state.diffs = { diffViewType: PARALLEL_DIFF_VIEW_TYPE };
+ store.getters['diffs/isParallelView'] = true;
+
+ const wrapper = createComponent();
expect(wrapper.find('.js-inline-diff-button').classes('selected')).toBe(false);
expect(wrapper.find('.js-parallel-diff-button').classes('selected')).toBe(true);
});
it('calls setInlineDiffViewType when clicking inline button', () => {
+ const wrapper = createComponent();
+
wrapper.find('.js-inline-diff-button').trigger('click');
expect(store.dispatch).toHaveBeenCalledWith('diffs/setInlineDiffViewType', expect.anything());
});
it('calls setParallelDiffViewType when clicking parallel button', () => {
+ const wrapper = createComponent();
+
wrapper.find('.js-parallel-diff-button').trigger('click');
expect(store.dispatch).toHaveBeenCalledWith(
@@ -117,23 +111,23 @@ describe('Diff settings dropdown component', () => {
describe('whitespace toggle', () => {
it('does not set as checked when showWhitespace is false', () => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { showWhitespace: false }),
- });
+ store.state.diffs = { showWhitespace: false };
+
+ const wrapper = createComponent();
expect(wrapper.findByTestId('show-whitespace').element.checked).toBe(false);
});
it('sets as checked when showWhitespace is true', () => {
- setup({
- storeUpdater: (origStore) => Object.assign(origStore.state.diffs, { showWhitespace: true }),
- });
+ store.state.diffs = { showWhitespace: true };
+
+ const wrapper = createComponent();
expect(wrapper.findByTestId('show-whitespace').element.checked).toBe(true);
});
it('calls setShowWhitespace on change', async () => {
+ const wrapper = createComponent();
const checkbox = wrapper.findByTestId('show-whitespace');
const { checked } = checkbox.element;
@@ -157,10 +151,9 @@ describe('Diff settings dropdown component', () => {
`(
'sets the checkbox to { checked: $checked } if the fileByFile setting is $fileByFile',
({ fileByFile, checked }) => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { viewDiffsFileByFile: fileByFile }),
- });
+ store.state.diffs = { viewDiffsFileByFile: fileByFile };
+
+ const wrapper = createComponent();
expect(getFileByFileCheckbox(wrapper).element.checked).toBe(checked);
},
@@ -173,11 +166,9 @@ describe('Diff settings dropdown component', () => {
`(
'when the file by file setting starts as $start, toggling the checkbox should call setFileByFile with $setting',
async ({ start, setting }) => {
- setup({
- storeUpdater: (origStore) =>
- Object.assign(origStore.state.diffs, { viewDiffsFileByFile: start }),
- });
+ store.state.diffs = { viewDiffsFileByFile: start };
+ const wrapper = createComponent();
await getFileByFileCheckbox(wrapper).setChecked(setting);
expect(store.dispatch).toHaveBeenCalledWith('diffs/setFileByFile', {
diff --git a/spec/frontend/diffs/store/actions_spec.js b/spec/frontend/diffs/store/actions_spec.js
index f883aea764f..f084458b5c7 100644
--- a/spec/frontend/diffs/store/actions_spec.js
+++ b/spec/frontend/diffs/store/actions_spec.js
@@ -707,6 +707,7 @@ describe('DiffsStoreActions', () => {
[{ type: types.SET_DIFF_VIEW_TYPE, payload: INLINE_DIFF_VIEW_TYPE }],
[],
);
+ expect(window.location.toString()).toContain('?view=inline');
expect(Cookies.get('diff_view')).toEqual(INLINE_DIFF_VIEW_TYPE);
});
});
@@ -720,6 +721,7 @@ describe('DiffsStoreActions', () => {
[{ type: types.SET_DIFF_VIEW_TYPE, payload: PARALLEL_DIFF_VIEW_TYPE }],
[],
);
+ expect(window.location.toString()).toContain('?view=parallel');
expect(Cookies.get(DIFF_VIEW_COOKIE_NAME)).toEqual(PARALLEL_DIFF_VIEW_TYPE);
});
});
diff --git a/spec/frontend/issuable/components/issuable_header_warnings_spec.js b/spec/frontend/issuable/components/issuable_header_warnings_spec.js
index ff772040d22..cbe2810a443 100644
--- a/spec/frontend/issuable/components/issuable_header_warnings_spec.js
+++ b/spec/frontend/issuable/components/issuable_header_warnings_spec.js
@@ -1,15 +1,13 @@
-import Vue from 'vue';
-import Vuex from 'vuex';
import { createMockDirective, getBinding } from 'helpers/vue_mock_directive';
import { shallowMountExtended } from 'helpers/vue_test_utils_helper';
-import { createStore as createMrStore } from '~/mr_notes/stores';
+import mrStore from '~/mr_notes/stores';
import createIssueStore from '~/notes/stores';
import IssuableHeaderWarnings from '~/issuable/components/issuable_header_warnings.vue';
const ISSUABLE_TYPE_ISSUE = 'issue';
const ISSUABLE_TYPE_MR = 'merge_request';
-Vue.use(Vuex);
+jest.mock('~/mr_notes/stores', () => jest.requireActual('helpers/mocks/mr_notes/stores'));
describe('IssuableHeaderWarnings', () => {
let wrapper;
@@ -22,7 +20,9 @@ describe('IssuableHeaderWarnings', () => {
const createComponent = ({ store, provide }) => {
wrapper = shallowMountExtended(IssuableHeaderWarnings, {
- store,
+ mocks: {
+ $store: store,
+ },
provide,
directives: {
GlTooltip: createMockDirective('gl-tooltip'),
@@ -47,9 +47,14 @@ describe('IssuableHeaderWarnings', () => {
`(
`when locked=$lockStatus, confidential=$confidentialStatus, and hidden=$hiddenStatus`,
({ lockStatus, confidentialStatus, hiddenStatus }) => {
- const store = issuableType === ISSUABLE_TYPE_ISSUE ? createIssueStore() : createMrStore();
+ const store = issuableType === ISSUABLE_TYPE_ISSUE ? createIssueStore() : mrStore;
beforeEach(() => {
+ // TODO: simplify to single assignment after issue store is mock
+ if (store === mrStore) {
+ store.getters.getNoteableData = {};
+ }
+
store.getters.getNoteableData.confidential = confidentialStatus;
store.getters.getNoteableData.discussion_locked = lockStatus;
store.getters.getNoteableData.targetType = issuableType;
diff --git a/spec/lib/gitlab/cluster/puma_worker_killer_initializer_spec.rb b/spec/lib/gitlab/cluster/puma_worker_killer_initializer_spec.rb
deleted file mode 100644
index cb13a711857..00000000000
--- a/spec/lib/gitlab/cluster/puma_worker_killer_initializer_spec.rb
+++ /dev/null
@@ -1,30 +0,0 @@
-# frozen_string_literal: true
-
-require 'fast_spec_helper'
-require 'puma_worker_killer'
-
-RSpec.describe Gitlab::Cluster::PumaWorkerKillerInitializer do
- describe '.start' do
- context 'when GITLAB_MEMORY_WATCHDOG_ENABLED is false' do
- before do
- stub_env('GITLAB_MEMORY_WATCHDOG_ENABLED', 'false')
- end
-
- it 'configures and start PumaWorkerKiller' do
- expect(PumaWorkerKiller).to receive(:config)
- expect(PumaWorkerKiller).to receive(:start)
-
- described_class.start({})
- end
- end
-
- context 'when GITLAB_MEMORY_WATCHDOG_ENABLED is not set' do
- it 'configures and start PumaWorkerKiller' do
- expect(PumaWorkerKiller).not_to receive(:config)
- expect(PumaWorkerKiller).not_to receive(:start)
-
- described_class.start({})
- end
- end
- end
-end
diff --git a/spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb b/spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb
deleted file mode 100644
index cf532cf7be6..00000000000
--- a/spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb
+++ /dev/null
@@ -1,25 +0,0 @@
-# frozen_string_literal: true
-
-require 'fast_spec_helper'
-
-RSpec.describe Gitlab::Cluster::PumaWorkerKillerObserver do
- let(:counter) { Gitlab::Metrics::NullMetric.instance }
-
- before do
- allow(Gitlab::Metrics).to receive(:counter)
- .with(any_args)
- .and_return(counter)
- end
-
- describe '#callback' do
- subject { described_class.new }
-
- it 'increments timeout counter' do
- worker = double(index: 0)
-
- expect(counter).to receive(:increment)
-
- subject.callback.call(worker)
- end
- end
-end
diff --git a/spec/models/packages/package_spec.rb b/spec/models/packages/package_spec.rb
index e79459e0c7c..6e312dbeb4d 100644
--- a/spec/models/packages/package_spec.rb
+++ b/spec/models/packages/package_spec.rb
@@ -1251,16 +1251,6 @@ RSpec.describe Packages::Package, type: :model, feature_category: :package_regis
it 'returns the last build info' do
expect(package.original_build_info).to eq(second_build_info)
end
-
- context 'with packages_display_last_pipeline disabled' do
- before do
- stub_feature_flags(packages_display_last_pipeline: false)
- end
-
- it 'returns the first build info' do
- expect(package.original_build_info).to eq(first_build_info)
- end
- end
end
end
diff --git a/spec/services/quick_actions/interpret_service_spec.rb b/spec/services/quick_actions/interpret_service_spec.rb
index 966782aca98..2f65441dd01 100644
--- a/spec/services/quick_actions/interpret_service_spec.rb
+++ b/spec/services/quick_actions/interpret_service_spec.rb
@@ -2875,18 +2875,6 @@ RSpec.describe QuickActions::InterpretService, feature_category: :team_planning
expect(explanations)
.to contain_exactly("Converts work item to Issue. Widgets not supported in new type are removed.")
end
-
- context 'when feature flag work_items_mvc_2 is disabled' do
- before do
- stub_feature_flags(work_items_mvc_2: false)
- end
-
- it 'does not have the command available' do
- _, explanations = service.explain(command, work_item)
-
- expect(explanations).to be_empty
- end
- end
end
describe 'relate command' do
diff --git a/spec/support/rspec_order_todo.yml b/spec/support/rspec_order_todo.yml
index 82dc6659dbf..ee0854c2483 100644
--- a/spec/support/rspec_order_todo.yml
+++ b/spec/support/rspec_order_todo.yml
@@ -6033,7 +6033,6 @@
- './spec/lib/gitlab/closing_issue_extractor_spec.rb'
- './spec/lib/gitlab/cluster/lifecycle_events_spec.rb'
- './spec/lib/gitlab/cluster/mixins/puma_cluster_spec.rb'
-- './spec/lib/gitlab/cluster/puma_worker_killer_observer_spec.rb'
- './spec/lib/gitlab/cluster/rack_timeout_observer_spec.rb'
- './spec/lib/gitlab/code_navigation_path_spec.rb'
- './spec/lib/gitlab/color_schemes_spec.rb'
diff --git a/yarn.lock b/yarn.lock
index 9c9a98d4184..645a7f2b97f 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -12826,6 +12826,13 @@ vuedraggable@^2.23.0:
dependencies:
sortablejs "^1.9.0"
+vuex-mock-store@^0.1.0:
+ version "0.1.0"
+ resolved "https://registry.yarnpkg.com/vuex-mock-store/-/vuex-mock-store-0.1.0.tgz#eddd85d32184e93926b3693866ab43efdba95c9d"
+ integrity sha512-NWbZcw91sxDiCsFt4v6jSF6lr7GUBaVmdLvkYOIXIKtfbEUIN3OO+LuByaAzjmrskr5Xg7QQLueteQZoFLMBoA==
+ dependencies:
+ lodash.clonedeep "^4.5.0"
+
"vuex-vue3@npm:vuex@4.0.0":
version "4.0.0"
resolved "https://registry.yarnpkg.com/vuex/-/vuex-4.0.0.tgz#ac877aa76a9c45368c979471e461b520d38e6cf5"