From 05b83be3ee097da8e71c8655d8f9f2c179cc3f7c Mon Sep 17 00:00:00 2001 From: GitLab Bot Date: Fri, 7 May 2021 15:10:39 +0000 Subject: [PATCH] Add latest changes from gitlab-org/gitlab@master --- .../components/preview_dropdown.vue | 14 +- .../components/toolbar_button.vue | 2 +- .../content_editor/components/top_toolbar.vue | 21 +++ .../javascripts/content_editor/constants.js | 3 + .../diffs/components/commit_item.vue | 2 +- .../javascripts/lib/utils/common_utils.js | 3 - app/models/ci/build_dependencies.rb | 2 - app/workers/all_queues.yml | 27 ++-- app/workers/concerns/chaos_queue.rb | 1 + app/workers/hashed_storage/migrator_worker.rb | 1 + .../hashed_storage/project_migrate_worker.rb | 1 + .../hashed_storage/project_rollback_worker.rb | 1 + .../hashed_storage/rollbacker_worker.rb | 1 + ...-mrs-have-dark-grey-text-on-slightly-l.yml | 5 + ...lidate_build_dependencies-feature-flag.yml | 5 + .../ph-296082-singleFileDraftPreviewClick.yml | 5 + .../ci_validate_build_dependencies.yml | 8 - ...i_validate_build_dependencies_override.yml | 8 - .../active_record_renamed_table.rb | 5 + doc/administration/job_artifacts.md | 36 ----- doc/ci/yaml/README.md | 4 - .../avoiding_downtime_in_migrations.md | 6 + .../database/rename_database_tables.md | 140 ++++++++++++++++++ doc/development/elasticsearch.md | 8 +- doc/raketasks/backup_restore.md | 5 +- lib/gitlab/ci/features.rb | 5 - lib/gitlab/database.rb | 8 + lib/gitlab/database/migration_helpers.rb | 1 + lib/gitlab/database/rename_table_helpers.rb | 33 +++++ .../schema_cache_with_renamed_table.rb | 55 +++++++ locale/gitlab.pot | 36 +++++ .../components/preview_dropdown_spec.js | 71 +++++++++ .../components/toolbar_button_spec.js | 4 +- .../components/top_toolbar_spec.js | 43 +++++- .../lib/gitlab/ci/pipeline/chain/seed_spec.rb | 9 +- .../schema_cache_with_renamed_table_spec.rb | 83 +++++++++++ spec/models/ci/build_dependencies_spec.rb | 12 -- spec/models/ci/build_spec.rb | 41 ++--- spec/services/ci/register_job_service_spec.rb | 36 +---- 39 files changed, 578 insertions(+), 173 deletions(-) create mode 100644 changelogs/unreleased/329891-dark-mode-commit-messages-in-mrs-have-dark-grey-text-on-slightly-l.yml create mode 100644 changelogs/unreleased/cleanup-ci_validate_build_dependencies-feature-flag.yml create mode 100644 changelogs/unreleased/ph-296082-singleFileDraftPreviewClick.yml delete mode 100644 config/feature_flags/development/ci_validate_build_dependencies.yml delete mode 100644 config/feature_flags/development/ci_validate_build_dependencies_override.yml create mode 100644 config/initializers/active_record_renamed_table.rb create mode 100644 doc/development/database/rename_database_tables.md create mode 100644 lib/gitlab/database/rename_table_helpers.rb create mode 100644 lib/gitlab/database/schema_cache_with_renamed_table.rb create mode 100644 spec/frontend/batch_comments/components/preview_dropdown_spec.js create mode 100644 spec/lib/gitlab/database/schema_cache_with_renamed_table_spec.rb diff --git a/app/assets/javascripts/batch_comments/components/preview_dropdown.vue b/app/assets/javascripts/batch_comments/components/preview_dropdown.vue index fb643d441ec..625cd9858fb 100644 --- a/app/assets/javascripts/batch_comments/components/preview_dropdown.vue +++ b/app/assets/javascripts/batch_comments/components/preview_dropdown.vue @@ -1,6 +1,6 @@ @@ -35,7 +44,8 @@ export default { diff --git a/app/assets/javascripts/content_editor/components/toolbar_button.vue b/app/assets/javascripts/content_editor/components/toolbar_button.vue index 2a5f4375c2b..0af12812f3b 100644 --- a/app/assets/javascripts/content_editor/components/toolbar_button.vue +++ b/app/assets/javascripts/content_editor/components/toolbar_button.vue @@ -45,7 +45,7 @@ export default { this.tiptapEditor.chain()[this.editorCommand]().focus().run(); } - this.$emit('click', { contentType }); + this.$emit('execute', { contentType }); }, }, }; diff --git a/app/assets/javascripts/content_editor/components/top_toolbar.vue b/app/assets/javascripts/content_editor/components/top_toolbar.vue index dcb41cbc4df..b18649d4e57 100644 --- a/app/assets/javascripts/content_editor/components/top_toolbar.vue +++ b/app/assets/javascripts/content_editor/components/top_toolbar.vue @@ -1,19 +1,34 @@ diff --git a/app/assets/javascripts/content_editor/constants.js b/app/assets/javascripts/content_editor/constants.js index eb6deff434d..d0d2102a999 100644 --- a/app/assets/javascripts/content_editor/constants.js +++ b/app/assets/javascripts/content_editor/constants.js @@ -3,3 +3,6 @@ import { s__ } from '~/locale'; export const PROVIDE_SERIALIZER_OR_RENDERER_ERROR = s__( 'ContentEditor|You have to provide a renderMarkdown function or a custom serializer', ); + +export const CONTENT_EDITOR_TRACKING_LABEL = 'content_editor'; +export const TOOLBAR_CONTROL_TRACKING_ACTION = 'execute_toolbar_control'; diff --git a/app/assets/javascripts/diffs/components/commit_item.vue b/app/assets/javascripts/diffs/components/commit_item.vue index bc0f2fb0b69..63239728390 100644 --- a/app/assets/javascripts/diffs/components/commit_item.vue +++ b/app/assets/javascripts/diffs/components/commit_item.vue @@ -173,7 +173,7 @@ export default {

     
diff --git a/app/assets/javascripts/lib/utils/common_utils.js b/app/assets/javascripts/lib/utils/common_utils.js
index fb257228597..8666d325c1b 100644
--- a/app/assets/javascripts/lib/utils/common_utils.js
+++ b/app/assets/javascripts/lib/utils/common_utils.js
@@ -645,9 +645,6 @@ export const convertObjectPropsToCamelCase = (obj = {}, options = {}) =>
 export const convertObjectPropsToSnakeCase = (obj = {}, options = {}) =>
   convertObjectProps(convertToSnakeCase, obj, options);
 
-export const imagePath = (imgUrl) =>
-  `${gon.asset_host || ''}${gon.relative_url_root || ''}/assets/${imgUrl}`;
-
 export const addSelectOnFocusBehaviour = (selector = '.js-select-on-focus') => {
   // Click a .js-select-on-focus field, select the contents
   // Prevent a mouseup event from deselecting the input
diff --git a/app/models/ci/build_dependencies.rb b/app/models/ci/build_dependencies.rb
index e7406e009b8..38fc5c18732 100644
--- a/app/models/ci/build_dependencies.rb
+++ b/app/models/ci/build_dependencies.rb
@@ -105,8 +105,6 @@ module Ci
     end
 
     def valid_local?
-      return true unless Gitlab::Ci::Features.validate_build_dependencies?(project)
-
       local.all?(&:valid_dependency?)
     end
 
diff --git a/app/workers/all_queues.yml b/app/workers/all_queues.yml
index 8e120811b3e..40ff568c80b 100644
--- a/app/workers/all_queues.yml
+++ b/app/workers/all_queues.yml
@@ -65,7 +65,8 @@
   :resource_boundary: :unknown
   :weight: 2
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: chaos:chaos_db_spin
   :worker_name: Chaos::DbSpinWorker
   :feature_category: :not_owned
@@ -74,7 +75,8 @@
   :resource_boundary: :unknown
   :weight: 2
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: chaos:chaos_kill
   :worker_name: Chaos::KillWorker
   :feature_category: :not_owned
@@ -83,7 +85,8 @@
   :resource_boundary: :unknown
   :weight: 2
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: chaos:chaos_leak_mem
   :worker_name: Chaos::LeakMemWorker
   :feature_category: :not_owned
@@ -92,7 +95,8 @@
   :resource_boundary: :unknown
   :weight: 2
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: chaos:chaos_sleep
   :worker_name: Chaos::SleepWorker
   :feature_category: :not_owned
@@ -101,7 +105,8 @@
   :resource_boundary: :unknown
   :weight: 2
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: container_repository:cleanup_container_repository
   :worker_name: CleanupContainerRepositoryWorker
   :feature_category: :container_registry
@@ -1014,7 +1019,8 @@
   :resource_boundary: :unknown
   :weight: 1
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: hashed_storage:hashed_storage_project_migrate
   :worker_name: HashedStorage::ProjectMigrateWorker
   :feature_category: :source_code_management
@@ -1023,7 +1029,8 @@
   :resource_boundary: :unknown
   :weight: 1
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: hashed_storage:hashed_storage_project_rollback
   :worker_name: HashedStorage::ProjectRollbackWorker
   :feature_category: :source_code_management
@@ -1032,7 +1039,8 @@
   :resource_boundary: :unknown
   :weight: 1
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: hashed_storage:hashed_storage_rollbacker
   :worker_name: HashedStorage::RollbackerWorker
   :feature_category: :source_code_management
@@ -1041,7 +1049,8 @@
   :resource_boundary: :unknown
   :weight: 1
   :idempotent:
-  :tags: []
+  :tags:
+  - :exclude_from_gitlab_com
 - :name: incident_management:clusters_applications_check_prometheus_health
   :worker_name: Clusters::Applications::CheckPrometheusHealthWorker
   :feature_category: :incident_management
diff --git a/app/workers/concerns/chaos_queue.rb b/app/workers/concerns/chaos_queue.rb
index a9c557f0175..2ccd55157c6 100644
--- a/app/workers/concerns/chaos_queue.rb
+++ b/app/workers/concerns/chaos_queue.rb
@@ -6,5 +6,6 @@ module ChaosQueue
   included do
     queue_namespace :chaos
     feature_category_not_owned!
+    tags :exclude_from_gitlab_com
   end
 end
diff --git a/app/workers/hashed_storage/migrator_worker.rb b/app/workers/hashed_storage/migrator_worker.rb
index 7c8055cd647..735d8a2447a 100644
--- a/app/workers/hashed_storage/migrator_worker.rb
+++ b/app/workers/hashed_storage/migrator_worker.rb
@@ -8,6 +8,7 @@ module HashedStorage
 
     queue_namespace :hashed_storage
     feature_category :source_code_management
+    tags :exclude_from_gitlab_com
 
     # @param [Integer] start initial ID of the batch
     # @param [Integer] finish last ID of the batch
diff --git a/app/workers/hashed_storage/project_migrate_worker.rb b/app/workers/hashed_storage/project_migrate_worker.rb
index 11bcf4d7589..0659c8a6a46 100644
--- a/app/workers/hashed_storage/project_migrate_worker.rb
+++ b/app/workers/hashed_storage/project_migrate_worker.rb
@@ -8,6 +8,7 @@ module HashedStorage
 
     queue_namespace :hashed_storage
     loggable_arguments 1
+    tags :exclude_from_gitlab_com
 
     attr_reader :project_id
 
diff --git a/app/workers/hashed_storage/project_rollback_worker.rb b/app/workers/hashed_storage/project_rollback_worker.rb
index e411cea2593..a5ee8b35176 100644
--- a/app/workers/hashed_storage/project_rollback_worker.rb
+++ b/app/workers/hashed_storage/project_rollback_worker.rb
@@ -8,6 +8,7 @@ module HashedStorage
 
     queue_namespace :hashed_storage
     loggable_arguments 1
+    tags :exclude_from_gitlab_com
 
     attr_reader :project_id
 
diff --git a/app/workers/hashed_storage/rollbacker_worker.rb b/app/workers/hashed_storage/rollbacker_worker.rb
index de8b4966c44..447bdfa6220 100644
--- a/app/workers/hashed_storage/rollbacker_worker.rb
+++ b/app/workers/hashed_storage/rollbacker_worker.rb
@@ -8,6 +8,7 @@ module HashedStorage
 
     queue_namespace :hashed_storage
     feature_category :source_code_management
+    tags :exclude_from_gitlab_com
 
     # @param [Integer] start initial ID of the batch
     # @param [Integer] finish last ID of the batch
diff --git a/changelogs/unreleased/329891-dark-mode-commit-messages-in-mrs-have-dark-grey-text-on-slightly-l.yml b/changelogs/unreleased/329891-dark-mode-commit-messages-in-mrs-have-dark-grey-text-on-slightly-l.yml
new file mode 100644
index 00000000000..9542c8dba2b
--- /dev/null
+++ b/changelogs/unreleased/329891-dark-mode-commit-messages-in-mrs-have-dark-grey-text-on-slightly-l.yml
@@ -0,0 +1,5 @@
+---
+title: Fix commit messages text color in dark mode
+merge_request: 61082
+author:
+type: fixed
diff --git a/changelogs/unreleased/cleanup-ci_validate_build_dependencies-feature-flag.yml b/changelogs/unreleased/cleanup-ci_validate_build_dependencies-feature-flag.yml
new file mode 100644
index 00000000000..5a723f8d121
--- /dev/null
+++ b/changelogs/unreleased/cleanup-ci_validate_build_dependencies-feature-flag.yml
@@ -0,0 +1,5 @@
+---
+title: Validate CI pipeline jobs dependencies
+merge_request: 60999
+author:
+type: changed
diff --git a/changelogs/unreleased/ph-296082-singleFileDraftPreviewClick.yml b/changelogs/unreleased/ph-296082-singleFileDraftPreviewClick.yml
new file mode 100644
index 00000000000..1f063a79070
--- /dev/null
+++ b/changelogs/unreleased/ph-296082-singleFileDraftPreviewClick.yml
@@ -0,0 +1,5 @@
+---
+title: Fixed preview review comment not working with single file diff mode
+merge_request: 61032
+author:
+type: fixed
diff --git a/config/feature_flags/development/ci_validate_build_dependencies.yml b/config/feature_flags/development/ci_validate_build_dependencies.yml
deleted file mode 100644
index 885bdcf0c20..00000000000
--- a/config/feature_flags/development/ci_validate_build_dependencies.yml
+++ /dev/null
@@ -1,8 +0,0 @@
----
-name: ci_validate_build_dependencies
-introduced_by_url: https://gitlab.com/gitlab-org/gitlab-foss/-/merge_requests/14009
-rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/257852
-milestone: '10.3'
-type: development
-group: group::continuous integration
-default_enabled: true
diff --git a/config/feature_flags/development/ci_validate_build_dependencies_override.yml b/config/feature_flags/development/ci_validate_build_dependencies_override.yml
deleted file mode 100644
index bce4b88ca39..00000000000
--- a/config/feature_flags/development/ci_validate_build_dependencies_override.yml
+++ /dev/null
@@ -1,8 +0,0 @@
----
-name: ci_validate_build_dependencies_override
-introduced_by_url: https://gitlab.com/gitlab-org/gitlab-foss/-/merge_requests/14009
-rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/257852
-milestone: '10.3'
-type: development
-group: group::continuous integration
-default_enabled: false
diff --git a/config/initializers/active_record_renamed_table.rb b/config/initializers/active_record_renamed_table.rb
new file mode 100644
index 00000000000..948ef8790c8
--- /dev/null
+++ b/config/initializers/active_record_renamed_table.rb
@@ -0,0 +1,5 @@
+# frozen_string_literal: true
+
+ActiveSupport.on_load(:active_record) do
+  ActiveRecord::ConnectionAdapters::SchemaCache.prepend(Gitlab::Database::SchemaCacheWithRenamedTable)
+end
diff --git a/doc/administration/job_artifacts.md b/doc/administration/job_artifacts.md
index bec1fa6ad05..5c99a4d32b7 100644
--- a/doc/administration/job_artifacts.md
+++ b/doc/administration/job_artifacts.md
@@ -370,42 +370,6 @@ steps below.
 If the `expire` directive is not set explicitly in your pipeline, artifacts expire per the
 default artifacts expiration setting, which you can find in the [CI/CD Administration settings](../user/admin_area/settings/continuous_integration.md).
 
-## Validation for dependencies
-
-> Introduced in GitLab 10.3.
-
-To disable [the dependencies validation](../ci/yaml/README.md#when-a-dependent-job-fails),
-you can enable the `ci_validate_build_dependencies_override` feature flag from a Rails console.
-
-**In Omnibus installations:**
-
-1. Enter the Rails console:
-
-   ```shell
-   sudo gitlab-rails console
-   ```
-
-1. Enable the feature flag to disable the validation:
-
-   ```ruby
-   Feature.enable(:ci_validate_build_dependencies_override)
-   ```
-
-**In installations from source:**
-
-1. Enter the Rails console:
-
-   ```shell
-   cd /home/git/gitlab
-   sudo -u git -H bundle exec rails console -e production
-   ```
-
-1. Enable the feature flag to disable the validation:
-
-   ```ruby
-   Feature.enable(:ci_validate_build_dependencies_override)
-   ```
-
 ## Set the maximum file size of the artifacts
 
 If artifacts are enabled, you can change the maximum file size of the
diff --git a/doc/ci/yaml/README.md b/doc/ci/yaml/README.md
index 858e738e750..48df512fb42 100644
--- a/doc/ci/yaml/README.md
+++ b/doc/ci/yaml/README.md
@@ -3264,10 +3264,6 @@ If the artifacts of the job that is set as a dependency are
 [deleted](../pipelines/job_artifacts.md#delete-job-artifacts), then
 the dependent job fails.
 
-You can ask your administrator to
-[flip this switch](../../administration/job_artifacts.md#validation-for-dependencies)
-and bring back the old behavior.
-
 #### `artifacts:exclude`
 
 > - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/15122) in GitLab 13.1
diff --git a/doc/development/avoiding_downtime_in_migrations.md b/doc/development/avoiding_downtime_in_migrations.md
index d8981ce0999..6b6c47cfece 100644
--- a/doc/development/avoiding_downtime_in_migrations.md
+++ b/doc/development/avoiding_downtime_in_migrations.md
@@ -365,6 +365,12 @@ if the application no longer uses the table.
 Renaming tables requires downtime as an application may continue
 using the old table name during/after a database migration.
 
+If the table and the ActiveRecord model is not in use yet, removing the old
+table and creating a new one is the preferred way to "rename" the table.
+
+Renaming a table is possible without downtime by following our multi-release
+[rename table process](database/rename_database_tables.md#rename-table-without-downtime).
+
 ## Adding Foreign Keys
 
 Adding foreign keys usually works in 3 steps:
diff --git a/doc/development/database/rename_database_tables.md b/doc/development/database/rename_database_tables.md
new file mode 100644
index 00000000000..743558fae19
--- /dev/null
+++ b/doc/development/database/rename_database_tables.md
@@ -0,0 +1,140 @@
+---
+stage: Enablement
+group: Database
+info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://about.gitlab.com/handbook/engineering/ux/technical-writing/#assignments
+---
+
+# Rename table without downtime
+
+> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/54354) in GitLab 13.12.
+
+With our database helper methods built into GitLab, it's possible to rename a database table without downtime.
+
+The technique builds on top of database views, using the following steps:
+
+1. Rename the database table.
+1. Create a database view using the old table name by pointing to the new table name.
+1. Add workaround for ActiveRecord's schema cache.
+
+For example, consider that we are renaming the `issues` table name to `tickets`. Run:
+
+```sql
+BEGIN;
+  ALTER TABLE issues RENAME TO tickets;
+  CREATE VIEW issues AS SELECT * FROM tickets;
+COMMIT;
+```
+
+As database views do not expose the underlying table schema (default values, not null
+constraints, and indexes), we need further steps to update the application to use the new
+table name. ActiveRecord heavily relies on this data, for example, to initialize new
+models.
+
+To work around this limitation, we need to tell ActiveRecord to acquire this information
+from a different table using the new table name.
+
+## Migration strategy breakdown
+
+### Release N.M: Mark the ActiveRecord model's table
+
+Consider the current release as "Release N.M".
+
+In this release, register the database table so that it instructs ActiveRecord to fetch the
+database table information (for `SchemaCache`) using the new table name (if it's present). Otherwise, fall back
+to the old table name. This is necessary to avoid errors during a zero-downtime deployment.
+
+1. Edit the `TABLES_TO_BE_RENAMED` constant in: `lib/gitlab/database.rb`
+
+   ```ruby
+   TABLES_TO_BE_RENAMED = {
+     'issues' => 'tickets'
+   }.freeze
+   ```
+
+Note that, in this release (N.M), the `tickets` database table does not exist yet. This step is preparing for the actual table rename in release N.M+1.
+
+### Release N.M+1: Rename the database table
+
+Consider the next release as "Release N.M".
+
+Execute a standard migration (not a post-migration):
+
+```ruby
+  include Gitlab::Database::MigrationHelpers
+
+  def up
+    rename_table_safely(:issues, :tickets)
+  end
+
+  def down
+    undo_rename_table_safely(:issues, :tickets)
+  end
+```
+
+**Important notes:**
+
+- Let other developers know that the table is going to be renamed.
+  - Ping the `@gl-database` group in your merge request.
+  - Add a note in the Engineering Week-in-Review document: `table_name` is going to be renamed in N.M. Modifications to this table are not allowed in release N.M and N.M+1.
+- The helper method uses the standard `rename_table` helper from Rails for renaming the table.
+- The helper renames the sequence and the indexes. Sometimes it diverges from the standard Rails convention
+when naming indexes, so there is a possibility that not all indexes are properly renamed. After running
+the migration locally, check if there are inconsistently named indexes (`db/structure.sql`). Those can be
+renamed manually in a separate migration, which can be also part of the release M.N+1.
+- Foreign key columns might still contain the old table name. For smaller tables, follow our [standard column 
+rename process](../avoiding_downtime_in_migrations.md#renaming-columns)
+- Avoid renaming database tables which are using with triggers.
+- Table modifications (add or remove columns) are not allowed during the rename process, please make sure that all changes to the table happen before the rename migration is started (or in the next release).
+- As the index names might change, verify that the model does not use bulk insert
+(for example, `insert_all` and `upsert_all`) with the `unique_by: index_name` option.
+Renaming an index while using these methods may break functionality.
+- Modify the model code to point to the new database table. Do this by
+renaming the model directly or setting the `self.table_name` variable.
+
+At this point, we don't have applications using the old database table name in their queries.
+
+1. Remove the database view through a post-migration:
+
+   ```ruby
+     include Gitlab::Database::MigrationHelpers
+
+     def up
+       finalize_table_rename(:issues, :tickets)
+     end
+
+     def down
+       undo_finalize_table_rename(:issues, :tickets)
+     end
+   ```
+
+1. Additionally the table definition from `TABLES_TO_BE_RENAMED` **must** be removed.
+
+To do so, edit the `TABLES_TO_BE_RENAMED` constant in `lib/gitlab/database.rb`:
+
+   From:
+
+   ```ruby
+   TABLES_TO_BE_RENAMED = {
+     'issues' => 'tickets'
+   }.freeze
+   ```
+
+   To:
+
+   ```ruby
+   TABLES_TO_BE_RENAMED = {}.freeze
+   ```
+
+#### Zero-downtime deployments
+
+When the application is upgraded without downtime, there can be application instances
+running the old code. The old code still references the old database table. The queries
+still function without any problems, because the backward-compatible database view is
+in place.
+
+In case the old version of the application needs to be restarted or reconnected to the
+database, ActiveRecord fetches the column information again. At this time, our previously
+marked table (`TABLES_TO_BE_RENAMED`) instructs ActiveRecord to use the new database table name
+when fetching the database table information.
+
+The new version of the application will use the new database table.
diff --git a/doc/development/elasticsearch.md b/doc/development/elasticsearch.md
index 3e466512c79..6b829faf74d 100644
--- a/doc/development/elasticsearch.md
+++ b/doc/development/elasticsearch.md
@@ -316,11 +316,11 @@ choose to remove the migration code and tests so that:
   anymore.
 
 To be extra safe, we will not delete migrations that were created in the last
-minor version before the major upgrade. So, if the we are upgrading to `%14.0`,
-we should not delete migrations that were only added in `%13.11`. This is an
+minor version before the major upgrade. So, if we are upgrading to `%14.0`,
+we should not delete migrations that were only added in `%13.12`. This is an
 extra safety net as we expect there are migrations that get merged that may
 take multiple weeks to finish on GitLab.com. It would be bad if we upgraded
-GitLab.com to `%14.0` before the migrations in `%13.11` were finished. Since
+GitLab.com to `%14.0` before the migrations in `%13.12` were finished. Since
 our deployments to GitLab.com are automated and we currently don't have
 automated checks to prevent this, the extra precaution is warranted.
 Additionally, even if we did have automated checks to prevent it, we wouldn't
@@ -340,7 +340,7 @@ being upgraded to, we do the following:
    def migrate
      log_raise "Migration has been deleted in the last major version upgrade." \
        "Migrations are supposed to be finished before upgrading major version https://docs.gitlab.com/ee/update/#upgrading-to-a-new-major-version ." \
-       "In order to correct this issue you will need to reacreate your index from scratch https://docs.gitlab.com/ee/integration/elasticsearch.html#last-resort-to-recreate-an-index ."
+       "To correct this issue, recreate your index from scratch: https://docs.gitlab.com/ee/integration/elasticsearch.html#last-resort-to-recreate-an-index."
    end
 
    def completed?
diff --git a/doc/raketasks/backup_restore.md b/doc/raketasks/backup_restore.md
index e182ecc48bc..74e254d864e 100644
--- a/doc/raketasks/backup_restore.md
+++ b/doc/raketasks/backup_restore.md
@@ -339,7 +339,8 @@ sudo -u git -H GITLAB_ASSUME_YES=1 bundle exec rake gitlab:backup:restore RAILS_
 
 > [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/37158) in GitLab 13.3.
 
-Repositories can be backed up concurrently to help fully use CPU time. The
+When using [multiple repository storages](../administration/repository_storage_paths.md),
+repositories can be backed up concurrently to help fully use CPU time. The
 following variables are available to modify the default behavior of the Rake
 task:
 
@@ -349,7 +350,7 @@ task:
   back up at the same time on each storage. This allows the repository backups
   to be spread across storages. Defaults to `1`.
 
-For example, for Omnibus GitLab installations:
+For example, for Omnibus GitLab installations with 4 repository storages:
 
 ```shell
 sudo gitlab-backup create GITLAB_BACKUP_MAX_CONCURRENCY=4 GITLAB_BACKUP_MAX_STORAGE_CONCURRENCY=1
diff --git a/lib/gitlab/ci/features.rb b/lib/gitlab/ci/features.rb
index 162dbc4bcc7..f6ecbe80ceb 100644
--- a/lib/gitlab/ci/features.rb
+++ b/lib/gitlab/ci/features.rb
@@ -47,11 +47,6 @@ module Gitlab
         ::Feature.enabled?(:ci_trace_log_invalid_chunks, project, type: :ops, default_enabled: false)
       end
 
-      def self.validate_build_dependencies?(project)
-        ::Feature.enabled?(:ci_validate_build_dependencies, project, default_enabled: :yaml) &&
-          ::Feature.disabled?(:ci_validate_build_dependencies_override, project)
-      end
-
       def self.display_quality_on_mr_diff?(project)
         ::Feature.enabled?(:codequality_mr_diff, project, default_enabled: false)
       end
diff --git a/lib/gitlab/database.rb b/lib/gitlab/database.rb
index 2f6c3cc46fb..43c06068296 100644
--- a/lib/gitlab/database.rb
+++ b/lib/gitlab/database.rb
@@ -2,6 +2,14 @@
 
 module Gitlab
   module Database
+    # This constant is used when renaming tables concurrently.
+    # If you plan to rename a table using the `rename_table_safely` method, add your table here one milestone before the rename.
+    # Example:
+    # TABLES_TO_BE_RENAMED = {
+    #   'old_name' => 'new_name'
+    # }.freeze
+    TABLES_TO_BE_RENAMED = {}.freeze
+
     # Minimum PostgreSQL version requirement per documentation:
     # https://docs.gitlab.com/ee/install/requirements.html#postgresql-requirements
     MINIMUM_POSTGRES_VERSION = 11
diff --git a/lib/gitlab/database/migration_helpers.rb b/lib/gitlab/database/migration_helpers.rb
index 1c10959c875..3a94e109d2a 100644
--- a/lib/gitlab/database/migration_helpers.rb
+++ b/lib/gitlab/database/migration_helpers.rb
@@ -5,6 +5,7 @@ module Gitlab
     module MigrationHelpers
       include Migrations::BackgroundMigrationHelpers
       include DynamicModelHelpers
+      include Migrations::RenameTableHelpers
 
       # https://www.postgresql.org/docs/current/sql-syntax-lexical.html#SQL-SYNTAX-IDENTIFIERS
       MAX_IDENTIFIER_NAME_LENGTH = 63
diff --git a/lib/gitlab/database/rename_table_helpers.rb b/lib/gitlab/database/rename_table_helpers.rb
new file mode 100644
index 00000000000..7f5af038c6d
--- /dev/null
+++ b/lib/gitlab/database/rename_table_helpers.rb
@@ -0,0 +1,33 @@
+# frozen_string_literal: true
+
+module Gitlab
+  module Database
+    module RenameTableHelpers
+      def rename_table_safely(old_table_name, new_table_name)
+        with_lock_retries do
+          rename_table(old_table_name, new_table_name)
+          execute("CREATE VIEW #{old_table_name} AS SELECT * FROM #{new_table_name}")
+        end
+      end
+
+      def undo_rename_table_safely(old_table_name, new_table_name)
+        with_lock_retries do
+          execute("DROP VIEW IF EXISTS #{old_table_name}")
+          rename_table(new_table_name, old_table_name)
+        end
+      end
+
+      def finalize_table_rename(old_table_name, new_table_name)
+        with_lock_retries do
+          execute("DROP VIEW IF EXISTS #{old_table_name}")
+        end
+      end
+
+      def undo_finalize_table_rename(old_table_name, new_table_name)
+        with_lock_retries do
+          execute("CREATE VIEW #{old_table_name} AS SELECT * FROM #{new_table_name}")
+        end
+      end
+    end
+  end
+end
diff --git a/lib/gitlab/database/schema_cache_with_renamed_table.rb b/lib/gitlab/database/schema_cache_with_renamed_table.rb
new file mode 100644
index 00000000000..28123edd708
--- /dev/null
+++ b/lib/gitlab/database/schema_cache_with_renamed_table.rb
@@ -0,0 +1,55 @@
+# frozen_string_literal: true
+
+module Gitlab
+  module Database
+    module SchemaCacheWithRenamedTable
+      # Override methods in ActiveRecord::ConnectionAdapters::SchemaCache
+
+      def clear!
+        super
+
+        clear_renamed_tables_cache!
+      end
+
+      def clear_data_source_cache!(name)
+        super(name)
+
+        clear_renamed_tables_cache!
+      end
+
+      def primary_keys(table_name)
+        super(underlying_table(table_name))
+      end
+
+      def columns(table_name)
+        super(underlying_table(table_name))
+      end
+
+      def columns_hash(table_name)
+        super(underlying_table(table_name))
+      end
+
+      def indexes(table_name)
+        super(underlying_table(table_name))
+      end
+
+      private
+
+      def underlying_table(table_name)
+        renamed_tables_cache.fetch(table_name, table_name)
+      end
+
+      def renamed_tables_cache
+        @renamed_tables ||= begin
+          Gitlab::Database::TABLES_TO_BE_RENAMED.select do |old_name, new_name|
+            ActiveRecord::Base.connection.view_exists?(old_name)
+          end
+        end
+      end
+
+      def clear_renamed_tables_cache!
+        @renamed_tables = nil # rubocop:disable Gitlab/ModuleWithInstanceVariables
+      end
+    end
+  end
+end
diff --git a/locale/gitlab.pot b/locale/gitlab.pot
index 244f4d94d84..c6fa42e17eb 100644
--- a/locale/gitlab.pot
+++ b/locale/gitlab.pot
@@ -5040,6 +5040,12 @@ msgstr ""
 msgid "BillingPlan|Upgrade for free"
 msgstr ""
 
+msgid "Billings|As a user on a free or trial namespace, you'll need to verify your account with a credit card to run pipelines. This is required to help prevent cryptomining attacks on GitLab infrastructure. %{strongStart}GitLab will not charge or store your credit card, it will only be used for validation.%{strongEnd} %{linkStart}Learn more%{linkEnd}."
+msgstr ""
+
+msgid "Billings|User Verification Required"
+msgstr ""
+
 msgid "Billings|Verify User Account"
 msgstr ""
 
@@ -11265,6 +11271,9 @@ msgstr ""
 msgid "DevopsAdoption|Adopted"
 msgstr ""
 
+msgid "DevopsAdoption|Adoption"
+msgstr ""
+
 msgid "DevopsAdoption|An error occurred while removing the group. Please try again."
 msgstr ""
 
@@ -26999,6 +27008,9 @@ msgstr ""
 msgid "Remove user from project"
 msgstr ""
 
+msgid "Remove..."
+msgstr ""
+
 msgid "Removed"
 msgstr ""
 
@@ -30656,15 +30668,33 @@ msgstr ""
 msgid "StatusCheck|API to check"
 msgstr ""
 
+msgid "StatusCheck|Add status check"
+msgstr ""
+
+msgid "StatusCheck|An error occurred fetching the status checks."
+msgstr ""
+
+msgid "StatusCheck|Check for a status response in Merge Requests. Failures do not block merges. %{link_start}Learn more%{link_end}."
+msgstr ""
+
 msgid "StatusCheck|Invoke an external API as part of the approvals"
 msgstr ""
 
+msgid "StatusCheck|No status checks are defined yet."
+msgstr ""
+
 msgid "StatusCheck|Remove status check"
 msgstr ""
 
 msgid "StatusCheck|Remove status check?"
 msgstr ""
 
+msgid "StatusCheck|Service name"
+msgstr ""
+
+msgid "StatusCheck|Status checks"
+msgstr ""
+
 msgid "StatusCheck|Status to check"
 msgstr ""
 
@@ -31747,6 +31777,9 @@ msgstr ""
 msgid "The \"Require approval from CODEOWNERS\" setting was moved to %{banner_link_start}Protected Branches%{banner_link_end}"
 msgstr ""
 
+msgid "The %{featureName} feature is part of your GitLab Ultimate trial."
+msgstr ""
+
 msgid "The %{link_start}true-up model%{link_end} allows having more users, and additional users will incur a retroactive charge on renewal."
 msgstr ""
 
@@ -38207,6 +38240,9 @@ msgid_plural "merge requests"
 msgstr[0] ""
 msgstr[1] ""
 
+msgid "merge request approvals"
+msgstr ""
+
 msgid "merged %{timeAgo}"
 msgstr ""
 
diff --git a/spec/frontend/batch_comments/components/preview_dropdown_spec.js b/spec/frontend/batch_comments/components/preview_dropdown_spec.js
new file mode 100644
index 00000000000..41be04d0b7e
--- /dev/null
+++ b/spec/frontend/batch_comments/components/preview_dropdown_spec.js
@@ -0,0 +1,71 @@
+import Vue from 'vue';
+import Vuex from 'vuex';
+import { shallowMountExtended } from 'helpers/vue_test_utils_helper';
+import PreviewDropdown from '~/batch_comments/components/preview_dropdown.vue';
+
+Vue.use(Vuex);
+
+let wrapper;
+
+const toggleActiveFileByHash = jest.fn();
+const scrollToDraft = jest.fn();
+
+function factory({ viewDiffsFileByFile = false, draftsCount = 1, sortedDrafts = [] } = {}) {
+  const store = new Vuex.Store({
+    modules: {
+      diffs: {
+        namespaced: true,
+        actions: {
+          toggleActiveFileByHash,
+        },
+        state: {
+          viewDiffsFileByFile,
+        },
+      },
+      batchComments: {
+        namespaced: true,
+        actions: { scrollToDraft },
+        getters: { draftsCount: () => draftsCount, sortedDrafts: () => sortedDrafts },
+      },
+    },
+  });
+
+  wrapper = shallowMountExtended(PreviewDropdown, {
+    store,
+  });
+}
+
+describe('Batch comments preview dropdown', () => {
+  afterEach(() => {
+    wrapper.destroy();
+  });
+
+  describe('clicking draft', () => {
+    it('it toggles active file when viewDiffsFileByFile is true', async () => {
+      factory({
+        viewDiffsFileByFile: true,
+        sortedDrafts: [{ id: 1, file_hash: 'hash' }],
+      });
+
+      wrapper.findByTestId('preview-item').vm.$emit('click');
+
+      await Vue.nextTick();
+
+      expect(toggleActiveFileByHash).toHaveBeenCalledWith(expect.anything(), 'hash');
+      expect(scrollToDraft).toHaveBeenCalledWith(expect.anything(), { id: 1, file_hash: 'hash' });
+    });
+
+    it('calls scrollToDraft', async () => {
+      factory({
+        viewDiffsFileByFile: false,
+        sortedDrafts: [{ id: 1 }],
+      });
+
+      wrapper.findByTestId('preview-item').vm.$emit('click');
+
+      await Vue.nextTick();
+
+      expect(scrollToDraft).toHaveBeenCalledWith(expect.anything(), { id: 1 });
+    });
+  });
+});
diff --git a/spec/frontend/content_editor/components/toolbar_button_spec.js b/spec/frontend/content_editor/components/toolbar_button_spec.js
index 42fab2a5616..a49efa34017 100644
--- a/spec/frontend/content_editor/components/toolbar_button_spec.js
+++ b/spec/frontend/content_editor/components/toolbar_button_spec.js
@@ -83,7 +83,7 @@ describe('content_editor/components/toolbar_button', () => {
       await findButton().trigger('click');
 
       expect(toggleFooSpy).toHaveBeenCalled();
-      expect(wrapper.emitted().click).toHaveLength(1);
+      expect(wrapper.emitted().execute).toHaveLength(1);
     });
 
     it('does not executes the content type command when executeCommand = false', async () => {
@@ -92,7 +92,7 @@ describe('content_editor/components/toolbar_button', () => {
       await findButton().trigger('click');
 
       expect(toggleFooSpy).not.toHaveBeenCalled();
-      expect(wrapper.emitted().click).toHaveLength(1);
+      expect(wrapper.emitted().execute).toHaveLength(1);
     });
   });
 });
diff --git a/spec/frontend/content_editor/components/top_toolbar_spec.js b/spec/frontend/content_editor/components/top_toolbar_spec.js
index e7cdb8d0967..8f47be3f489 100644
--- a/spec/frontend/content_editor/components/top_toolbar_spec.js
+++ b/spec/frontend/content_editor/components/top_toolbar_spec.js
@@ -1,12 +1,17 @@
 import { shallowMount } from '@vue/test-utils';
+import { mockTracking } from 'helpers/tracking_helper';
 import { extendedWrapper } from 'helpers/vue_test_utils_helper';
 import TopToolbar from '~/content_editor/components/top_toolbar.vue';
+import {
+  TOOLBAR_CONTROL_TRACKING_ACTION,
+  CONTENT_EDITOR_TRACKING_LABEL,
+} from '~/content_editor/constants';
 import { createContentEditor } from '~/content_editor/services/create_content_editor';
 
 describe('content_editor/components/top_toolbar', () => {
   let wrapper;
   let contentEditor;
-
+  let trackingSpy;
   const buildEditor = () => {
     contentEditor = createContentEditor({ renderMarkdown: () => true });
   };
@@ -21,6 +26,10 @@ describe('content_editor/components/top_toolbar', () => {
     );
   };
 
+  beforeEach(() => {
+    trackingSpy = mockTracking(undefined, null, jest.spyOn);
+  });
+
   beforeEach(() => {
     buildEditor();
   });
@@ -29,7 +38,7 @@ describe('content_editor/components/top_toolbar', () => {
     wrapper.destroy();
   });
 
-  it.each`
+  describe.each`
     testId            | buttonProps
     ${'bold'}         | ${{ contentType: 'bold', iconName: 'bold', label: 'Bold text', editorCommand: 'toggleBold' }}
     ${'italic'}       | ${{ contentType: 'italic', iconName: 'italic', label: 'Italic text', editorCommand: 'toggleItalic' }}
@@ -37,11 +46,31 @@ describe('content_editor/components/top_toolbar', () => {
     ${'blockquote'}   | ${{ contentType: 'blockquote', iconName: 'quote', label: 'Insert a quote', editorCommand: 'toggleBlockquote' }}
     ${'bullet-list'}  | ${{ contentType: 'bulletList', iconName: 'list-bulleted', label: 'Add a bullet list', editorCommand: 'toggleBulletList' }}
     ${'ordered-list'} | ${{ contentType: 'orderedList', iconName: 'list-numbered', label: 'Add a numbered list', editorCommand: 'toggleOrderedList' }}
-  `('renders $testId button', ({ testId, buttonProps }) => {
-    buildWrapper();
-    expect(wrapper.findByTestId(testId).props()).toEqual({
-      ...buttonProps,
-      tiptapEditor: contentEditor.tiptapEditor,
+  `('given a $testId toolbar control', ({ testId, buttonProps }) => {
+    beforeEach(() => {
+      buildWrapper();
+    });
+
+    it('renders the toolbar control with the provided properties', () => {
+      expect(wrapper.findByTestId(testId).props()).toEqual({
+        ...buttonProps,
+        tiptapEditor: contentEditor.tiptapEditor,
+      });
+    });
+
+    it.each`
+      control         | eventData
+      ${'bold'}       | ${{ contentType: 'bold' }}
+      ${'blockquote'} | ${{ contentType: 'blockquote', value: 1 }}
+    `('tracks the execution of toolbar controls', ({ control, eventData }) => {
+      const { contentType, value } = eventData;
+      wrapper.findByTestId(control).vm.$emit('execute', eventData);
+
+      expect(trackingSpy).toHaveBeenCalledWith(undefined, TOOLBAR_CONTROL_TRACKING_ACTION, {
+        label: CONTENT_EDITOR_TRACKING_LABEL,
+        property: contentType,
+        value,
+      });
     });
   });
 });
diff --git a/spec/lib/gitlab/ci/pipeline/chain/seed_spec.rb b/spec/lib/gitlab/ci/pipeline/chain/seed_spec.rb
index 889c9d239a5..2e537f40692 100644
--- a/spec/lib/gitlab/ci/pipeline/chain/seed_spec.rb
+++ b/spec/lib/gitlab/ci/pipeline/chain/seed_spec.rb
@@ -218,15 +218,18 @@ RSpec.describe Gitlab::Ci::Pipeline::Chain::Seed do
     end
 
     context 'N+1 queries' do
-      it 'avoids N+1 queries when calculating variables of jobs' do
+      it 'avoids N+1 queries when calculating variables of jobs', :use_sql_query_cache do
+        warm_up_pipeline, warm_up_command = prepare_pipeline1
+        perform_seed(warm_up_pipeline, warm_up_command)
+
         pipeline1, command1 = prepare_pipeline1
         pipeline2, command2 = prepare_pipeline2
 
-        control = ActiveRecord::QueryRecorder.new do
+        control = ActiveRecord::QueryRecorder.new(skip_cached: false) do
           perform_seed(pipeline1, command1)
         end
 
-        expect { perform_seed(pipeline2, command2) }.not_to exceed_query_limit(
+        expect { perform_seed(pipeline2, command2) }.not_to exceed_all_query_limit(
           control.count + expected_extra_queries
         )
       end
diff --git a/spec/lib/gitlab/database/schema_cache_with_renamed_table_spec.rb b/spec/lib/gitlab/database/schema_cache_with_renamed_table_spec.rb
new file mode 100644
index 00000000000..8c0c4155ccc
--- /dev/null
+++ b/spec/lib/gitlab/database/schema_cache_with_renamed_table_spec.rb
@@ -0,0 +1,83 @@
+# frozen_string_literal: true
+
+require 'spec_helper'
+
+RSpec.describe Gitlab::Database::SchemaCacheWithRenamedTable do
+  let(:old_model) do
+    Class.new(ActiveRecord::Base) do
+      self.table_name = 'projects'
+    end
+  end
+
+  let(:new_model) do
+    Class.new(ActiveRecord::Base) do
+      self.table_name = 'projects_new'
+    end
+  end
+
+  before do
+    stub_const('Gitlab::Database::TABLES_TO_BE_RENAMED', { 'projects' => 'projects_new' })
+  end
+
+  context 'when table is not renamed yet' do
+    before do
+      old_model.reset_column_information
+      ActiveRecord::Base.connection.schema_cache.clear!
+    end
+
+    it 'uses the original table to look up metadata' do
+      expect(old_model.primary_key).to eq('id')
+    end
+  end
+
+  context 'when table is renamed' do
+    before do
+      ActiveRecord::Base.connection.execute("ALTER TABLE projects RENAME TO projects_new")
+      ActiveRecord::Base.connection.execute("CREATE VIEW projects AS SELECT * FROM projects_new")
+
+      old_model.reset_column_information
+      ActiveRecord::Base.connection.schema_cache.clear!
+    end
+
+    it 'uses the renamed table to look up metadata' do
+      expect(old_model.primary_key).to eq('id')
+    end
+
+    it 'has primary key' do
+      expect(old_model.primary_key).to eq('id')
+      expect(old_model.primary_key).to eq(new_model.primary_key)
+    end
+
+    it 'has the same column definitions' do
+      expect(old_model.columns).to eq(new_model.columns)
+    end
+
+    it 'has the same indexes' do
+      indexes_for_old_table = ActiveRecord::Base.connection.schema_cache.indexes('projects')
+      indexes_for_new_table = ActiveRecord::Base.connection.schema_cache.indexes('projects_new')
+
+      expect(indexes_for_old_table).to eq(indexes_for_new_table)
+    end
+
+    it 'has the same column_hash' do
+      columns_hash_for_old_table = ActiveRecord::Base.connection.schema_cache.columns_hash('projects')
+      columns_hash_for_new_table = ActiveRecord::Base.connection.schema_cache.columns_hash('projects_new')
+
+      expect(columns_hash_for_old_table).to eq(columns_hash_for_new_table)
+    end
+
+    describe 'when the table behind a model is actually a view' do
+      let(:group) { create(:group) }
+      let(:project_attributes) { attributes_for(:project, namespace_id: group.id).except(:creator) }
+      let(:record) { old_model.create!(project_attributes) }
+
+      it 'can persist records' do
+        expect(record.reload.attributes).to eq(new_model.find(record.id).attributes)
+      end
+
+      it 'can find records' do
+        expect(old_model.find_by_id(record.id)).not_to be_nil
+      end
+    end
+  end
+end
diff --git a/spec/models/ci/build_dependencies_spec.rb b/spec/models/ci/build_dependencies_spec.rb
index e576345f1ca..d00d88ae397 100644
--- a/spec/models/ci/build_dependencies_spec.rb
+++ b/spec/models/ci/build_dependencies_spec.rb
@@ -18,10 +18,6 @@ RSpec.describe Ci::BuildDependencies do
   let!(:rubocop_test) { create(:ci_build, pipeline: pipeline, name: 'rubocop', stage_idx: 1, stage: 'test') }
   let!(:staging) { create(:ci_build, pipeline: pipeline, name: 'staging', stage_idx: 2, stage: 'deploy') }
 
-  before do
-    stub_feature_flags(ci_validate_build_dependencies_override: false)
-  end
-
   context 'for local dependencies' do
     subject { described_class.new(job).all }
 
@@ -378,14 +374,6 @@ RSpec.describe Ci::BuildDependencies do
       end
 
       it { is_expected.to eq(false) }
-
-      context 'when ci_validate_build_dependencies_override feature flag is enabled' do
-        before do
-          stub_feature_flags(ci_validate_build_dependencies_override: job.project)
-        end
-
-        it { is_expected.to eq(true) }
-      end
     end
   end
 end
diff --git a/spec/models/ci/build_spec.rb b/spec/models/ci/build_spec.rb
index 9848ef30388..c7850b0bc16 100644
--- a/spec/models/ci/build_spec.rb
+++ b/spec/models/ci/build_spec.rb
@@ -3631,41 +3631,24 @@ RSpec.describe Ci::Build do
     end
 
     let!(:job) { create(:ci_build, :pending, pipeline: pipeline, stage_idx: 1, options: options) }
+    let!(:pre_stage_job) { create(:ci_build, :success, pipeline: pipeline, name: 'test', stage_idx: 0) }
 
-    context 'when validates for dependencies is enabled' do
-      before do
-        stub_feature_flags(ci_validate_build_dependencies_override: false)
-      end
+    context 'when "dependencies" keyword is not defined' do
+      let(:options) { {} }
 
-      let!(:pre_stage_job) { create(:ci_build, :success, pipeline: pipeline, name: 'test', stage_idx: 0) }
-
-      context 'when "dependencies" keyword is not defined' do
-        let(:options) { {} }
-
-        it { expect(job).to have_valid_build_dependencies }
-      end
-
-      context 'when "dependencies" keyword is empty' do
-        let(:options) { { dependencies: [] } }
-
-        it { expect(job).to have_valid_build_dependencies }
-      end
-
-      context 'when "dependencies" keyword is specified' do
-        let(:options) { { dependencies: ['test'] } }
-
-        it_behaves_like 'validation is active'
-      end
+      it { expect(job).to have_valid_build_dependencies }
     end
 
-    context 'when validates for dependencies is disabled' do
+    context 'when "dependencies" keyword is empty' do
+      let(:options) { { dependencies: [] } }
+
+      it { expect(job).to have_valid_build_dependencies }
+    end
+
+    context 'when "dependencies" keyword is specified' do
       let(:options) { { dependencies: ['test'] } }
 
-      before do
-        stub_feature_flags(ci_validate_build_dependencies_override: true)
-      end
-
-      it_behaves_like 'validation is not active'
+      it_behaves_like 'validation is active'
     end
   end
 
diff --git a/spec/services/ci/register_job_service_spec.rb b/spec/services/ci/register_job_service_spec.rb
index 65211632e3a..839a3c53f07 100644
--- a/spec/services/ci/register_job_service_spec.rb
+++ b/spec/services/ci/register_job_service_spec.rb
@@ -516,10 +516,6 @@ module Ci
             end
           end
 
-          before do
-            stub_feature_flags(ci_validate_build_dependencies_override: false)
-          end
-
           let!(:pre_stage_job) { create(:ci_build, :success, pipeline: pipeline, name: 'test', stage_idx: 0) }
 
           let!(:pending_job) do
@@ -530,37 +526,7 @@ module Ci
 
           subject { execute(specific_runner) }
 
-          context 'when validates for dependencies is enabled' do
-            before do
-              stub_feature_flags(ci_validate_build_dependencies_override: false)
-            end
-
-            it_behaves_like 'validation is active'
-
-            context 'when the main feature flag is enabled for a specific project' do
-              before do
-                stub_feature_flags(ci_validate_build_dependencies: pipeline.project)
-              end
-
-              it_behaves_like 'validation is active'
-            end
-
-            context 'when the main feature flag is enabled for a different project' do
-              before do
-                stub_feature_flags(ci_validate_build_dependencies: create(:project))
-              end
-
-              it_behaves_like 'validation is not active'
-            end
-          end
-
-          context 'when validates for dependencies is disabled' do
-            before do
-              stub_feature_flags(ci_validate_build_dependencies_override: true)
-            end
-
-            it_behaves_like 'validation is not active'
-          end
+          it_behaves_like 'validation is active'
         end
 
         context 'when build is degenerated' do