summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.rubocop_todo/layout/space_around_method_call_operator.yml32
-rw-r--r--GITALY_SERVER_VERSION2
-rw-r--r--app/assets/javascripts/commit/pipelines/pipelines_table.vue60
-rw-r--r--app/assets/javascripts/pipelines/components/performance_insights_modal.vue9
-rw-r--r--app/assets/javascripts/pipelines/mixins/pipelines_mixin.js13
-rw-r--r--app/graphql/resolvers/ci/runners_resolver.rb2
-rw-r--r--app/graphql/types/ci/runner_upgrade_status_enum.rb (renamed from app/graphql/types/ci/runner_upgrade_status_type_enum.rb)4
-rw-r--r--app/helpers/badges_helper.rb4
-rw-r--r--app/models/concerns/database_event_tracking.rb53
-rw-r--r--app/views/projects/merge_requests/show.html.haml4
-rw-r--r--config/feature_flags/development/product_intelligence_database_event_tracking.yml9
-rw-r--r--db/post_migrate/20220715185348_add_index_on_security_findings_id_and_partition_number.rb15
-rw-r--r--db/post_migrate/20220715185436_add_index_on_security_findings_unique_columns.rb15
-rw-r--r--db/post_migrate/20220715190612_drop_index_on_security_findings_uuid_and_scan_id.rb15
-rw-r--r--db/post_migrate/20220715191629_change_primary_key_of_security_findings_table.rb29
-rw-r--r--db/schema_migrations/202207151853481
-rw-r--r--db/schema_migrations/202207151854361
-rw-r--r--db/schema_migrations/202207151906121
-rw-r--r--db/schema_migrations/202207151916291
-rw-r--r--db/structure.sql4
-rw-r--r--doc/api/graphql/reference/index.md16
-rw-r--r--doc/development/fips_compliance.md8
-rw-r--r--doc/integration/jenkins_deprecated.md62
-rw-r--r--lib/gitlab/graphql/type_name_deprecations.rb6
-rw-r--r--locale/gitlab.pot35
-rw-r--r--package.json4
-rw-r--r--qa/qa/service/praefect_manager.rb4
-rw-r--r--qa/qa/specs/features/api/3_create/gitaly/praefect_replication_queue_spec.rb2
-rw-r--r--spec/features/merge_request/user_sees_pipelines_spec.rb11
-rw-r--r--spec/frontend/commit/pipelines/pipelines_table_spec.js39
-rw-r--r--spec/frontend/pipelines/performance_insights_modal_spec.js25
-rw-r--r--spec/graphql/types/base_field_spec.rb2
-rw-r--r--spec/graphql/types/ci/runner_upgrade_status_enum_spec.rb (renamed from spec/graphql/types/ci/runner_upgrade_status_type_enum_spec.rb)4
-rw-r--r--spec/lib/gitlab/ci/pipeline/chain/command_spec.rb4
-rw-r--r--spec/lib/gitlab/database/shared_model_spec.rb2
-rw-r--r--spec/lib/gitlab/diff/highlight_spec.rb2
-rw-r--r--spec/lib/gitlab/spamcheck/client_spec.rb2
-rw-r--r--spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb2
-rw-r--r--spec/models/concerns/database_event_tracking_spec.rb69
-rw-r--r--spec/models/integrations/chat_message/issue_message_spec.rb4
-rw-r--r--spec/models/milestone_spec.rb4
-rw-r--r--spec/presenters/alert_management/alert_presenter_spec.rb2
-rw-r--r--spec/requests/api/graphql/custom_emoji_query_spec.rb4
-rw-r--r--spec/support/shared_examples/controllers/snowplow_event_tracking_examples.rb18
-rw-r--r--spec/tasks/gitlab/db_rake_spec.rb2
-rw-r--r--spec/workers/concerns/limited_capacity/job_tracker_spec.rb2
-rw-r--r--yarn.lock20
47 files changed, 441 insertions, 188 deletions
diff --git a/.rubocop_todo/layout/space_around_method_call_operator.yml b/.rubocop_todo/layout/space_around_method_call_operator.yml
deleted file mode 100644
index bc174a43d77..00000000000
--- a/.rubocop_todo/layout/space_around_method_call_operator.yml
+++ /dev/null
@@ -1,32 +0,0 @@
----
-# Cop supports --auto-correct.
-Layout/SpaceAroundMethodCallOperator:
- # Offense count: 35
- # Temporarily disabled due to too many offenses
- Enabled: false
- Exclude:
- - 'app/helpers/badges_helper.rb'
- - 'app/services/google_cloud/create_service_accounts_service.rb'
- - 'app/services/google_cloud/enable_cloud_run_service.rb'
- - 'app/services/google_cloud/generate_pipeline_service.rb'
- - 'ee/spec/lib/gitlab/ci/config/entry/dast_configuration_spec.rb'
- - 'ee/spec/migrations/geo/set_resync_flag_for_retried_projects_spec.rb'
- - 'ee/spec/models/approval_project_rule_spec.rb'
- - 'ee/spec/models/integrations/github/status_message_spec.rb'
- - 'ee/spec/services/ee/boards/issues/move_service_spec.rb'
- - 'ee/spec/services/ee/issues/create_service_spec.rb'
- - 'ee/spec/services/geo/repository_base_sync_service_spec.rb'
- - 'ee/spec/services/requirements_management/create_requirement_service_spec.rb'
- - 'ee/spec/services/requirements_management/update_requirement_service_spec.rb'
- - 'spec/graphql/types/base_field_spec.rb'
- - 'spec/lib/gitlab/ci/pipeline/chain/command_spec.rb'
- - 'spec/lib/gitlab/database/shared_model_spec.rb'
- - 'spec/lib/gitlab/diff/highlight_spec.rb'
- - 'spec/lib/gitlab/spamcheck/client_spec.rb'
- - 'spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb'
- - 'spec/models/integrations/chat_message/issue_message_spec.rb'
- - 'spec/models/milestone_spec.rb'
- - 'spec/presenters/alert_management/alert_presenter_spec.rb'
- - 'spec/requests/api/graphql/custom_emoji_query_spec.rb'
- - 'spec/tasks/gitlab/db_rake_spec.rb'
- - 'spec/workers/concerns/limited_capacity/job_tracker_spec.rb'
diff --git a/GITALY_SERVER_VERSION b/GITALY_SERVER_VERSION
index 7cc7ed09682..c074ed50eee 100644
--- a/GITALY_SERVER_VERSION
+++ b/GITALY_SERVER_VERSION
@@ -1 +1 @@
-cef54e67714844049ec017b38cd6be2fd3db74b8
+0fa08d953e0d5497fe5366836d0ed54b9ff557d8
diff --git a/app/assets/javascripts/commit/pipelines/pipelines_table.vue b/app/assets/javascripts/commit/pipelines/pipelines_table.vue
index 4ff49433749..95ee3a0d90e 100644
--- a/app/assets/javascripts/commit/pipelines/pipelines_table.vue
+++ b/app/assets/javascripts/commit/pipelines/pipelines_table.vue
@@ -1,5 +1,6 @@
<script>
-import { GlButton, GlEmptyState, GlLoadingIcon, GlModal, GlLink } from '@gitlab/ui';
+import { GlButton, GlEmptyState, GlLoadingIcon, GlModal, GlLink, GlSprintf } from '@gitlab/ui';
+import { helpPagePath } from '~/helpers/help_page_helper';
import { getParameterByName } from '~/lib/utils/url_utility';
import PipelinesTableComponent from '~/pipelines/components/pipelines_list/pipelines_table.vue';
import { PipelineKeyOptions } from '~/pipelines/constants';
@@ -19,6 +20,7 @@ export default {
GlLink,
GlLoadingIcon,
GlModal,
+ GlSprintf,
PipelinesTableComponent,
TablePagination,
},
@@ -32,6 +34,10 @@ export default {
type: String,
required: true,
},
+ emptyStateSvgPath: {
+ type: String,
+ required: true,
+ },
viewType: {
type: String,
required: false,
@@ -83,6 +89,9 @@ export default {
shouldRenderErrorState() {
return this.hasError && !this.isLoading;
},
+ shouldRenderEmptyState() {
+ return this.state.pipelines.length === 0 && !this.shouldRenderErrorState;
+ },
/**
* The "Run pipeline" button can only be rendered when:
* - In MR view - we use `canCreatePipelineInTargetProject` for that purpose
@@ -185,6 +194,17 @@ export default {
},
},
},
+ i18n: {
+ runPipelinePopoverTitle: s__('Pipeline|Run merge request pipeline'),
+ runPipelinePopoverDescription: s__(
+ 'Pipeline|To run a merge request pipeline, the jobs in the CI/CD configuration file %{linkStart}must be configured%{linkEnd} to run in merge request pipelines.',
+ ),
+ runPipelineText: s__('Pipeline|Run pipeline'),
+ emptyStateTitle: s__('Pipelines|There are currently no pipelines.'),
+ },
+ mrPipelinesDocsPath: helpPagePath('ci/pipelines/merge_request_pipelines.md', {
+ anchor: 'prerequisites',
+ }),
};
</script>
<template>
@@ -203,7 +223,41 @@ export default {
s__(`Pipelines|There was an error fetching the pipelines.
Try again in a few moments or contact your support team.`)
"
+ data-testid="pipeline-error-empty-state"
/>
+ <template v-else-if="shouldRenderEmptyState">
+ <gl-empty-state
+ :svg-path="emptyStateSvgPath"
+ :title="$options.i18n.emptyStateTitle"
+ data-testid="pipeline-empty-state"
+ >
+ <template #description>
+ <gl-sprintf :message="$options.i18n.runPipelinePopoverDescription">
+ <template #link="{ content }">
+ <gl-link
+ :href="$options.mrPipelinesDocsPath"
+ target="_blank"
+ data-testid="mr-pipelines-docs-link"
+ >{{ content }}</gl-link
+ >
+ </template>
+ </gl-sprintf>
+ </template>
+
+ <template #actions>
+ <div class="gl-vertical-align-middle">
+ <gl-button
+ variant="confirm"
+ :loading="state.isRunningMergeRequestPipeline"
+ data-testid="run_pipeline_button"
+ @click="tryRunPipeline"
+ >
+ {{ $options.i18n.runPipelineText }}
+ </gl-button>
+ </div>
+ </template>
+ </gl-empty-state>
+ </template>
<div v-else-if="shouldRenderTable">
<gl-button
@@ -215,7 +269,7 @@ export default {
:loading="state.isRunningMergeRequestPipeline"
@click="tryRunPipeline"
>
- {{ s__('Pipeline|Run pipeline') }}
+ {{ $options.i18n.runPipelineText }}
</gl-button>
<pipelines-table-component
@@ -231,7 +285,7 @@ export default {
:loading="state.isRunningMergeRequestPipeline"
@click="tryRunPipeline"
>
- {{ s__('Pipeline|Run pipeline') }}
+ {{ $options.i18n.runPipelineText }}
</gl-button>
</div>
</template>
diff --git a/app/assets/javascripts/pipelines/components/performance_insights_modal.vue b/app/assets/javascripts/pipelines/components/performance_insights_modal.vue
index ae6b9186930..fdbf0ca19bc 100644
--- a/app/assets/javascripts/pipelines/components/performance_insights_modal.vue
+++ b/app/assets/javascripts/pipelines/components/performance_insights_modal.vue
@@ -97,13 +97,16 @@ export default {
<gl-loading-icon v-if="$apollo.queries.jobs.loading" size="lg" />
<template v-else>
- <gl-alert v-if="showLimitMessage" class="gl-mb-4" :dismissible="false">
- <p>{{ $options.i18n.insightsLimit }}</p>
+ <gl-alert class="gl-mb-4" :dismissible="false">
+ <p v-if="showLimitMessage" data-testid="limit-alert-text">
+ {{ $options.i18n.insightsLimit }}
+ </p>
<gl-link href="https://gitlab.com/gitlab-org/gitlab/-/issues/365902" class="gl-mt-5">
{{ $options.i18n.feeback }}
</gl-link>
</gl-alert>
- <div class="gl-display-flex gl-justify-content-space-between gl-mb-7">
+
+ <div class="gl-display-flex gl-justify-content-space-between gl-mt-2 gl-mb-7">
<gl-card class="gl-w-half gl-mr-7 gl-text-center">
<template #header>
<span class="gl-font-weight-bold">{{ $options.i18n.queuedCardHeader }}</span>
diff --git a/app/assets/javascripts/pipelines/mixins/pipelines_mixin.js b/app/assets/javascripts/pipelines/mixins/pipelines_mixin.js
index c4f7665c91d..e8e49cc652e 100644
--- a/app/assets/javascripts/pipelines/mixins/pipelines_mixin.js
+++ b/app/assets/javascripts/pipelines/mixins/pipelines_mixin.js
@@ -1,5 +1,6 @@
import Visibility from 'visibilityjs';
-import createFlash from '~/flash';
+import createFlash, { createAlert } from '~/flash';
+import { helpPagePath } from '~/helpers/help_page_helper';
import { historyPushState, buildUrlWithCurrentLocation } from '~/lib/utils/common_utils';
import httpStatusCodes from '~/lib/utils/http_status';
import Poll from '~/lib/utils/poll';
@@ -198,18 +199,20 @@ export default {
})
.catch((e) => {
const unauthorized = e.response.status === httpStatusCodes.UNAUTHORIZED;
- const badRequest = e.response.status === httpStatusCodes.BAD_REQUEST;
-
let errorMessage = __(
'An error occurred while trying to run a new pipeline for this merge request.',
);
- if (unauthorized || badRequest) {
+ if (unauthorized) {
errorMessage = __('You do not have permission to run a pipeline on this branch.');
}
- createFlash({
+ createAlert({
message: errorMessage,
+ primaryButton: {
+ text: __('Learn more'),
+ link: helpPagePath('ci/pipelines/merge_request_pipelines.md'),
+ },
});
})
.finally(() => this.store.toggleIsRunningPipeline(false));
diff --git a/app/graphql/resolvers/ci/runners_resolver.rb b/app/graphql/resolvers/ci/runners_resolver.rb
index 64738608b60..b52a4cc0ab4 100644
--- a/app/graphql/resolvers/ci/runners_resolver.rb
+++ b/app/graphql/resolvers/ci/runners_resolver.rb
@@ -36,7 +36,7 @@ module Resolvers
required: false,
description: 'Sort order of results.'
- argument :upgrade_status, ::Types::Ci::RunnerUpgradeStatusTypeEnum,
+ argument :upgrade_status, ::Types::Ci::RunnerUpgradeStatusEnum,
required: false,
description: 'Filter by upgrade status.'
diff --git a/app/graphql/types/ci/runner_upgrade_status_type_enum.rb b/app/graphql/types/ci/runner_upgrade_status_enum.rb
index 8e32eee5e6e..34a931c8f79 100644
--- a/app/graphql/types/ci/runner_upgrade_status_type_enum.rb
+++ b/app/graphql/types/ci/runner_upgrade_status_enum.rb
@@ -2,8 +2,8 @@
module Types
module Ci
- class RunnerUpgradeStatusTypeEnum < BaseEnum
- graphql_name 'CiRunnerUpgradeStatusType'
+ class RunnerUpgradeStatusEnum < BaseEnum
+ graphql_name 'CiRunnerUpgradeStatus'
::Ci::RunnerVersion::STATUS_DESCRIPTIONS.each do |status, description|
status_name_src =
diff --git a/app/helpers/badges_helper.rb b/app/helpers/badges_helper.rb
index 26ebe8a6470..46f0b043770 100644
--- a/app/helpers/badges_helper.rb
+++ b/app/helpers/badges_helper.rb
@@ -8,13 +8,13 @@ module BadgesHelper
success: "badge-success",
warning: "badge-warning",
danger: "badge-danger"
- }.tap { |hash| hash.default = hash.fetch(:muted) } .freeze
+ }.tap { |hash| hash.default = hash.fetch(:muted) }.freeze
SIZE_CLASSES = {
sm: "sm",
md: "md",
lg: "lg"
- }.tap { |hash| hash.default = hash.fetch(:md) } .freeze
+ }.tap { |hash| hash.default = hash.fetch(:md) }.freeze
GL_BADGE_CLASSES = %w[gl-badge badge badge-pill].freeze
diff --git a/app/models/concerns/database_event_tracking.rb b/app/models/concerns/database_event_tracking.rb
new file mode 100644
index 00000000000..04cefc7acf9
--- /dev/null
+++ b/app/models/concerns/database_event_tracking.rb
@@ -0,0 +1,53 @@
+# frozen_string_literal: true
+
+module DatabaseEventTracking
+ extend ActiveSupport::Concern
+
+ included do
+ after_create_commit :publish_database_create_event
+ after_destroy_commit :publish_database_destroy_event
+ after_update_commit :publish_database_update_event
+ end
+
+ def publish_database_create_event
+ publish_database_event('create')
+ end
+
+ def publish_database_destroy_event
+ publish_database_event('destroy')
+ end
+
+ def publish_database_update_event
+ publish_database_event('update')
+ end
+
+ def publish_database_event(name)
+ return unless Feature.enabled?(:product_intelligence_database_event_tracking)
+
+ # Gitlab::Tracking#event is triggering Snowplow event
+ # Snowplow events are sent with usage of
+ # https://snowplow.github.io/snowplow-ruby-tracker/SnowplowTracker/AsyncEmitter.html
+ # that reports data asynchronously and does not impact performance nor carries a risk of
+ # rollback in case of error
+
+ Gitlab::Tracking.event(
+ self.class.to_s,
+ "database_event_#{name}",
+ label: self.class.table_name,
+ namespace: try(:group) || try(:namespace),
+ property: name,
+ **filtered_record_attributes
+ )
+ rescue StandardError => err
+ # this rescue should be a dead code due to utilization of AsyncEmitter, however
+ # since this concern is expected to be included in every model, it is better to
+ # prevent against any unexpected outcome
+ Gitlab::ErrorTracking.track_and_raise_for_dev_exception(err)
+ end
+
+ def filtered_record_attributes
+ attributes.select do |key, _value|
+ self.class::SNOWPLOW_ATTRIBUTES.include?(key)
+ end
+ end
+end
diff --git a/app/views/projects/merge_requests/show.html.haml b/app/views/projects/merge_requests/show.html.haml
index 87e222754e5..4a79c7d5cbb 100644
--- a/app/views/projects/merge_requests/show.html.haml
+++ b/app/views/projects/merge_requests/show.html.haml
@@ -32,7 +32,7 @@
= tab_link_for @merge_request, :commits do
= _("Commits")
= gl_badge_tag @commits_count, { size: :sm }
- - if @number_of_pipelines.nonzero?
+ - if @project.builds_enabled?
= render "projects/merge_requests/tabs/tab", name: "pipelines", class: "pipelines-tab" do
= tab_link_for @merge_request, :pipelines do
= _("Pipelines")
@@ -80,7 +80,7 @@
= render "projects/merge_requests/tabs/pane", name: "commits", id: "commits", class: "commits" do
-# This tab is always loaded via AJAX
= render "projects/merge_requests/tabs/pane", name: "pipelines", id: "pipelines", class: "pipelines" do
- - if @number_of_pipelines.nonzero?
+ - if @project.builds_enabled?
= render 'projects/commit/pipelines_list', disable_initialization: true, endpoint: pipelines_project_merge_request_path(@project, @merge_request)
- params = request.query_parameters.merge(diff_head: true)
= render "projects/merge_requests/tabs/pane", name: "diffs", id: "js-diffs-app", class: "diffs", data: diffs_tab_pane_data(@project, @merge_request, params)
diff --git a/config/feature_flags/development/product_intelligence_database_event_tracking.yml b/config/feature_flags/development/product_intelligence_database_event_tracking.yml
new file mode 100644
index 00000000000..83a65398e87
--- /dev/null
+++ b/config/feature_flags/development/product_intelligence_database_event_tracking.yml
@@ -0,0 +1,9 @@
+---
+name: product_intelligence_database_event_tracking
+introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/92079
+rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/368976
+rollout_issue_url:
+milestone: '15.3'
+type: development
+group: group::product intelligence
+default_enabled: false
diff --git a/db/post_migrate/20220715185348_add_index_on_security_findings_id_and_partition_number.rb b/db/post_migrate/20220715185348_add_index_on_security_findings_id_and_partition_number.rb
new file mode 100644
index 00000000000..e867ef81381
--- /dev/null
+++ b/db/post_migrate/20220715185348_add_index_on_security_findings_id_and_partition_number.rb
@@ -0,0 +1,15 @@
+# frozen_string_literal: true
+
+class AddIndexOnSecurityFindingsIdAndPartitionNumber < Gitlab::Database::Migration[2.0]
+ INDEX_NAME = 'security_findings_partitioned_pkey'
+
+ disable_ddl_transaction!
+
+ def up
+ add_concurrent_index :security_findings, [:id, :partition_number], unique: true, name: INDEX_NAME
+ end
+
+ def down
+ remove_concurrent_index_by_name :security_findings, INDEX_NAME
+ end
+end
diff --git a/db/post_migrate/20220715185436_add_index_on_security_findings_unique_columns.rb b/db/post_migrate/20220715185436_add_index_on_security_findings_unique_columns.rb
new file mode 100644
index 00000000000..33b069a27d4
--- /dev/null
+++ b/db/post_migrate/20220715185436_add_index_on_security_findings_unique_columns.rb
@@ -0,0 +1,15 @@
+# frozen_string_literal: true
+
+class AddIndexOnSecurityFindingsUniqueColumns < Gitlab::Database::Migration[2.0]
+ INDEX_NAME = 'index_security_findings_on_unique_columns'
+
+ disable_ddl_transaction!
+
+ def up
+ add_concurrent_index :security_findings, [:uuid, :scan_id, :partition_number], unique: true, name: INDEX_NAME
+ end
+
+ def down
+ remove_concurrent_index_by_name :security_findings, INDEX_NAME
+ end
+end
diff --git a/db/post_migrate/20220715190612_drop_index_on_security_findings_uuid_and_scan_id.rb b/db/post_migrate/20220715190612_drop_index_on_security_findings_uuid_and_scan_id.rb
new file mode 100644
index 00000000000..a8a9bab2c84
--- /dev/null
+++ b/db/post_migrate/20220715190612_drop_index_on_security_findings_uuid_and_scan_id.rb
@@ -0,0 +1,15 @@
+# frozen_string_literal: true
+
+class DropIndexOnSecurityFindingsUuidAndScanId < Gitlab::Database::Migration[2.0]
+ INDEX_NAME = 'index_security_findings_on_uuid_and_scan_id'
+
+ disable_ddl_transaction!
+
+ def up
+ remove_concurrent_index_by_name :security_findings, INDEX_NAME
+ end
+
+ def down
+ add_concurrent_index :security_findings, [:uuid, :scan_id], unique: true, name: INDEX_NAME
+ end
+end
diff --git a/db/post_migrate/20220715191629_change_primary_key_of_security_findings_table.rb b/db/post_migrate/20220715191629_change_primary_key_of_security_findings_table.rb
new file mode 100644
index 00000000000..c2859c68c52
--- /dev/null
+++ b/db/post_migrate/20220715191629_change_primary_key_of_security_findings_table.rb
@@ -0,0 +1,29 @@
+# frozen_string_literal: true
+
+class ChangePrimaryKeyOfSecurityFindingsTable < Gitlab::Database::Migration[2.0]
+ enable_lock_retries!
+
+ def up
+ execute(<<~SQL)
+ ALTER TABLE security_findings DROP CONSTRAINT security_findings_pkey;
+ SQL
+
+ execute(<<~SQL)
+ ALTER TABLE security_findings ADD CONSTRAINT security_findings_pkey PRIMARY KEY USING index security_findings_partitioned_pkey;
+ SQL
+ end
+
+ def down
+ execute(<<~SQL)
+ ALTER TABLE security_findings DROP CONSTRAINT security_findings_pkey;
+ SQL
+
+ execute(<<~SQL)
+ ALTER TABLE security_findings ADD CONSTRAINT security_findings_pkey PRIMARY KEY (id);
+ SQL
+
+ execute(<<~SQL)
+ CREATE UNIQUE INDEX security_findings_partitioned_pkey ON security_findings USING btree(id, partition_number);
+ SQL
+ end
+end
diff --git a/db/schema_migrations/20220715185348 b/db/schema_migrations/20220715185348
new file mode 100644
index 00000000000..6df20d578f0
--- /dev/null
+++ b/db/schema_migrations/20220715185348
@@ -0,0 +1 @@
+5a8e178601b1b88bef0186269bc62f8e3b10eacb0fe8a9a11e322c244883cfde \ No newline at end of file
diff --git a/db/schema_migrations/20220715185436 b/db/schema_migrations/20220715185436
new file mode 100644
index 00000000000..31f9a069d31
--- /dev/null
+++ b/db/schema_migrations/20220715185436
@@ -0,0 +1 @@
+673e77eb5ffa49ab70088a7a43119c5f388d199e69504994c8c0a2a867ee1da3 \ No newline at end of file
diff --git a/db/schema_migrations/20220715190612 b/db/schema_migrations/20220715190612
new file mode 100644
index 00000000000..ffafb037b43
--- /dev/null
+++ b/db/schema_migrations/20220715190612
@@ -0,0 +1 @@
+bbb07db2554d2b1c7083341efcdc065a3a25ba4b042b0b3ea3cb26ec25e1e023 \ No newline at end of file
diff --git a/db/schema_migrations/20220715191629 b/db/schema_migrations/20220715191629
new file mode 100644
index 00000000000..88874ec93d3
--- /dev/null
+++ b/db/schema_migrations/20220715191629
@@ -0,0 +1 @@
+e300a6144e63f734e41b3a3ad40089dea5764ea2636ea11f5782fe86b6574229 \ No newline at end of file
diff --git a/db/structure.sql b/db/structure.sql
index 5d349c4450b..301b5b50871 100644
--- a/db/structure.sql
+++ b/db/structure.sql
@@ -25796,7 +25796,7 @@ ALTER TABLE ONLY scim_oauth_access_tokens
ADD CONSTRAINT scim_oauth_access_tokens_pkey PRIMARY KEY (id);
ALTER TABLE ONLY security_findings
- ADD CONSTRAINT security_findings_pkey PRIMARY KEY (id);
+ ADD CONSTRAINT security_findings_pkey PRIMARY KEY (id, partition_number);
ALTER TABLE ONLY security_orchestration_policy_configurations
ADD CONSTRAINT security_orchestration_policy_configurations_pkey PRIMARY KEY (id);
@@ -29692,7 +29692,7 @@ CREATE INDEX index_security_findings_on_scanner_id ON security_findings USING bt
CREATE INDEX index_security_findings_on_severity ON security_findings USING btree (severity);
-CREATE UNIQUE INDEX index_security_findings_on_uuid_and_scan_id ON security_findings USING btree (uuid, scan_id);
+CREATE UNIQUE INDEX index_security_findings_on_unique_columns ON security_findings USING btree (uuid, scan_id, partition_number);
CREATE INDEX index_security_scans_on_created_at ON security_scans USING btree (created_at);
diff --git a/doc/api/graphql/reference/index.md b/doc/api/graphql/reference/index.md
index 7ee604207a0..00c329253e5 100644
--- a/doc/api/graphql/reference/index.md
+++ b/doc/api/graphql/reference/index.md
@@ -387,7 +387,7 @@ four standard [pagination arguments](#connection-pagination-arguments):
| <a id="queryrunnersstatus"></a>`status` | [`CiRunnerStatus`](#cirunnerstatus) | Filter runners by status. |
| <a id="queryrunnerstaglist"></a>`tagList` | [`[String!]`](#string) | Filter by tags associated with the runner (comma-separated or array). |
| <a id="queryrunnerstype"></a>`type` | [`CiRunnerType`](#cirunnertype) | Filter runners by type. |
-| <a id="queryrunnersupgradestatus"></a>`upgradeStatus` | [`CiRunnerUpgradeStatusType`](#cirunnerupgradestatustype) | Filter by upgrade status. |
+| <a id="queryrunnersupgradestatus"></a>`upgradeStatus` | [`CiRunnerUpgradeStatus`](#cirunnerupgradestatus) | Filter by upgrade status. |
### `Query.snippets`
@@ -10244,7 +10244,7 @@ CI/CD variables for a project.
| <a id="cirunnershortsha"></a>`shortSha` | [`String`](#string) | First eight characters of the runner's token used to authenticate new job requests. Used as the runner's unique ID. |
| <a id="cirunnertaglist"></a>`tagList` | [`[String!]`](#string) | Tags associated with the runner. |
| <a id="cirunnertokenexpiresat"></a>`tokenExpiresAt` | [`Time`](#time) | Runner token expiration time. |
-| <a id="cirunnerupgradestatus"></a>`upgradeStatus` **{warning-solid}** | [`CiRunnerUpgradeStatusType`](#cirunnerupgradestatustype) | **Introduced** in 14.10. This feature is in Alpha. It can be changed or removed at any time. |
+| <a id="cirunnerupgradestatus"></a>`upgradeStatus` **{warning-solid}** | [`CiRunnerUpgradeStatus`](#cirunnerupgradestatus) | **Introduced** in 14.10. This feature is in Alpha. It can be changed or removed at any time. |
| <a id="cirunneruserpermissions"></a>`userPermissions` | [`RunnerPermissions!`](#runnerpermissions) | Permissions for the current user on the resource. |
| <a id="cirunnerversion"></a>`version` | [`String`](#string) | Version of the runner. |
@@ -12681,7 +12681,7 @@ four standard [pagination arguments](#connection-pagination-arguments):
| <a id="grouprunnersstatus"></a>`status` | [`CiRunnerStatus`](#cirunnerstatus) | Filter runners by status. |
| <a id="grouprunnerstaglist"></a>`tagList` | [`[String!]`](#string) | Filter by tags associated with the runner (comma-separated or array). |
| <a id="grouprunnerstype"></a>`type` | [`CiRunnerType`](#cirunnertype) | Filter runners by type. |
-| <a id="grouprunnersupgradestatus"></a>`upgradeStatus` | [`CiRunnerUpgradeStatusType`](#cirunnerupgradestatustype) | Filter by upgrade status. |
+| <a id="grouprunnersupgradestatus"></a>`upgradeStatus` | [`CiRunnerUpgradeStatus`](#cirunnerupgradestatus) | Filter by upgrade status. |
##### `Group.scanExecutionPolicies`
@@ -19124,14 +19124,14 @@ Values for sorting runners.
| <a id="cirunnertypeinstance_type"></a>`INSTANCE_TYPE` | A runner that is instance type. |
| <a id="cirunnertypeproject_type"></a>`PROJECT_TYPE` | A runner that is project type. |
-### `CiRunnerUpgradeStatusType`
+### `CiRunnerUpgradeStatus`
| Value | Description |
| ----- | ----------- |
-| <a id="cirunnerupgradestatustypeavailable"></a>`AVAILABLE` | Upgrade is available for the runner. |
-| <a id="cirunnerupgradestatustypeinvalid"></a>`INVALID` | Runner version is not valid. |
-| <a id="cirunnerupgradestatustypenot_available"></a>`NOT_AVAILABLE` | Upgrade is not available for the runner. |
-| <a id="cirunnerupgradestatustyperecommended"></a>`RECOMMENDED` | Upgrade is available and recommended for the runner. |
+| <a id="cirunnerupgradestatusavailable"></a>`AVAILABLE` | Upgrade is available for the runner. |
+| <a id="cirunnerupgradestatusinvalid"></a>`INVALID` | Runner version is not valid. |
+| <a id="cirunnerupgradestatusnot_available"></a>`NOT_AVAILABLE` | Upgrade is not available for the runner. |
+| <a id="cirunnerupgradestatusrecommended"></a>`RECOMMENDED` | Upgrade is available and recommended for the runner. |
### `CiVariableType`
diff --git a/doc/development/fips_compliance.md b/doc/development/fips_compliance.md
index d1c2520b496..44a3c0cb45d 100644
--- a/doc/development/fips_compliance.md
+++ b/doc/development/fips_compliance.md
@@ -40,15 +40,15 @@ when FIPS mode is enabled.
| Ubuntu 20.04 Libgcrypt Cryptographic Module | [3902](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/3902) | EC2 instances | `gpg`, `sshd` |
| Amazon Linux 2 Kernel Crypto API Cryptographic Module | [3709](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/3709) | EKS nodes | Linux kernel |
| Amazon Linux 2 OpenSSL Cryptographic Module | [3553](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/3553) | EKS nodes | NGINX |
-| RedHat Enterprise Linux 8 OpenSSL Cryptographic Module | [3852](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/3852) | EKS nodes | UBI containers: Workhorse, Pages, Container Registry, Rails (Puma/Sidekiq), Security Analyzers |
+| RedHat Enterprise Linux 8 OpenSSL Cryptographic Module | [4271](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/4271) | EKS nodes | UBI containers: Workhorse, Pages, Container Registry, Rails (Puma/Sidekiq), Security Analyzers |
| RedHat Enterprise Linux 8 Libgcrypt Cryptographic Module | [3784](https://csrc.nist.gov/projects/cryptographic-module-validation-program/certificate/3784) | EKS nodes | UBI containers: GitLab Shell, `gpg` |
### Supported Operating Systems
-The supported hybrid environments are:
+The supported hybrid platforms are:
-- Omnibus: Ubuntu 20.04 FIPS
-- EKS: Amazon Linux 2
+- Omnibus GitLab: Ubuntu 20.04 LTS
+- Cloud Native GitLab: Amazon Linux 2 (EKS)
### Unsupported features in FIPS mode
diff --git a/doc/integration/jenkins_deprecated.md b/doc/integration/jenkins_deprecated.md
index 57219b18047..5010545b73a 100644
--- a/doc/integration/jenkins_deprecated.md
+++ b/doc/integration/jenkins_deprecated.md
@@ -2,62 +2,12 @@
stage: Ecosystem
group: Integrations
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
+remove_date: '2022-10-29'
+redirect_to: 'jenkins.md'
---
-# Jenkins CI (deprecated) service **(FREE)**
+# Jenkins CI service (removed) **(FREE)**
-NOTE:
-In GitLab 8.3, Jenkins integration using the
-[GitLab Hook Plugin](https://wiki.jenkins.io/display/JENKINS/GitLab+Hook+Plugin)
-was deprecated in favor of the
-[GitLab Plugin](https://wiki.jenkins.io/display/JENKINS/GitLab+Plugin).
-Please use documentation for the new [Jenkins CI service](jenkins.md).
-
-NOTE:
-This service was [removed](https://gitlab.com/gitlab-org/gitlab/-/issues/1600) in GitLab 13.0
-
-Integration includes:
-
-- Trigger Jenkins build after push to repository
-- Show build status on Merge request page
-
-Requirements:
-
-- [Jenkins GitLab Hook plugin](https://wiki.jenkins.io/display/JENKINS/GitLab+Hook+Plugin)
-- Git clone access for Jenkins from GitLab repository (via SSH key)
-
-## Jenkins
-
-1. Install [GitLab Hook plugin](https://wiki.jenkins.io/display/JENKINS/GitLab+Hook+Plugin)
-1. Set up Jenkins project
-
-![screen](img/jenkins_project.png)
-
-## GitLab
-
-In GitLab, perform the following steps.
-
-### Read access to repository
-
-Jenkins needs read access to the GitLab repository. We already specified a
-private key to use in Jenkins, now we must add a public one to the GitLab
-project. For that case we need a Deploy key. Read the documentation on
-[how to set up a Deploy key](../user/project/deploy_keys/index.md).
-
-### Jenkins service
-
-Now navigate to GitLab services page and activate Jenkins
-
-![screen](img/jenkins_gitlab_service.png)
-
-Done! When you push to GitLab, it creates a build for Jenkins. You can view the
-merge request build status with a link to the Jenkins build.
-
-### Multi-project Configuration
-
-The GitLab Hook plugin in Jenkins supports the automatic creation of a project
-for each feature branch. After configuration GitLab triggers feature branch
-builds and a corresponding project is created in Jenkins.
-
-Configure the GitLab Hook plugin in Jenkins. Go to 'Manage Jenkins' and then
-'Configure System'. Find the 'GitLab Web Hook' section and configure as shown below.
+This feature was [removed](https://gitlab.com/gitlab-org/gitlab/-/issues/1600)
+in GitLab 13.0.
+Use the [Jenkins integration](jenkins.md) instead.
diff --git a/lib/gitlab/graphql/type_name_deprecations.rb b/lib/gitlab/graphql/type_name_deprecations.rb
index 4c75a0e7bd3..c27ad1d54f5 100644
--- a/lib/gitlab/graphql/type_name_deprecations.rb
+++ b/lib/gitlab/graphql/type_name_deprecations.rb
@@ -11,7 +11,11 @@ module Gitlab
# old_name: 'CiRunnerUpgradeStatusType', new_name: 'CiRunnerUpgradeStatus', milestone: '15.3'
# )
# ].freeze
- DEPRECATIONS = [].freeze
+ DEPRECATIONS = [
+ Gitlab::Graphql::DeprecationsBase::NameDeprecation.new(
+ old_name: 'CiRunnerUpgradeStatusType', new_name: 'CiRunnerUpgradeStatus', milestone: '15.3'
+ )
+ ].freeze
def self.map_graphql_name(name)
name
diff --git a/locale/gitlab.pot b/locale/gitlab.pot
index 193a8fffb77..a7a28880e63 100644
--- a/locale/gitlab.pot
+++ b/locale/gitlab.pot
@@ -966,6 +966,16 @@ msgid_plural "%{securityScanner} results are not available because a pipeline ha
msgstr[0] ""
msgstr[1] ""
+msgid "%{selectedLabelsCount} label"
+msgid_plural "%{selectedLabelsCount} labels"
+msgstr[0] ""
+msgstr[1] ""
+
+msgid "%{selectedProjectsCount} project"
+msgid_plural "%{selectedProjectsCount} projects"
+msgstr[0] ""
+msgstr[1] ""
+
msgid "%{size} %{unit}"
msgstr ""
@@ -29047,6 +29057,9 @@ msgstr ""
msgid "Pipeline|Run for branch name or tag"
msgstr ""
+msgid "Pipeline|Run merge request pipeline"
+msgstr ""
+
msgid "Pipeline|Run pipeline"
msgstr ""
@@ -29104,6 +29117,9 @@ msgstr ""
msgid "Pipeline|This pipeline ran on the contents of this merge request's source branch, not the target branch."
msgstr ""
+msgid "Pipeline|To run a merge request pipeline, the jobs in the CI/CD configuration file %{linkStart}must be configured%{linkEnd} to run in merge request pipelines."
+msgstr ""
+
msgid "Pipeline|Trigger author"
msgstr ""
@@ -36246,10 +36262,10 @@ msgstr ""
msgid "Showing version #%{versionNumber}"
msgstr ""
-msgid "Shows issues and %{labels_count} label for group '%{group_name}' from Nov 1, 2019 to Dec 31, 2019"
+msgid "Shows issues and 1 label for group '%{group_name}' from Nov 1, 2019 to Dec 31, 2019"
msgstr ""
-msgid "Shows issues and %{labels_count} labels for group '%{group_name}' from Nov 1, 2019 to Dec 31, 2019"
+msgid "Shows issues for group '%{group_name}' from Nov 1, 2019 to Dec 31, 2019"
msgstr ""
msgid "Side-by-side"
@@ -42650,11 +42666,6 @@ msgstr ""
msgid "ValueStreamAnalytics|%{stageCount}+ items"
msgstr ""
-msgid "ValueStreamAnalytics|%{subjectFilterText} and %{selectedLabelsCount} label"
-msgid_plural "ValueStreamAnalytics|%{subjectFilterText} and %{selectedLabelsCount} labels"
-msgstr[0] ""
-msgstr[1] ""
-
msgid "ValueStreamAnalytics|%{value}M"
msgstr ""
@@ -42709,10 +42720,16 @@ msgstr ""
msgid "ValueStreamAnalytics|Percentage of deployments that cause an incident in production."
msgstr ""
-msgid "ValueStreamAnalytics|Shows %{selectedFiltersDescription} for group '%{groupName}' and %{selectedProjectCount} projects from %{createdAfter} to %{createdBefore}"
+msgid "ValueStreamAnalytics|Shows %{selectedSubjectFilterText} and %{labelsCount} for group '%{groupName}' and %{projectsCount} from %{createdAfter} to %{createdBefore}"
+msgstr ""
+
+msgid "ValueStreamAnalytics|Shows %{selectedSubjectFilterText} and %{labelsCount} for group '%{groupName}' from %{createdAfter} to %{createdBefore}"
+msgstr ""
+
+msgid "ValueStreamAnalytics|Shows %{selectedSubjectFilterText} for group '%{groupName}' and %{projectsCount} from %{createdAfter} to %{createdBefore}"
msgstr ""
-msgid "ValueStreamAnalytics|Shows %{selectedFiltersDescription} for group '%{groupName}' from %{createdAfter} to %{createdBefore}"
+msgid "ValueStreamAnalytics|Shows %{selectedSubjectFilterText} for group '%{groupName}' from %{createdAfter} to %{createdBefore}"
msgstr ""
msgid "ValueStreamAnalytics|Tasks by type"
diff --git a/package.json b/package.json
index 92f7e48d668..4ba8caee76e 100644
--- a/package.json
+++ b/package.json
@@ -52,8 +52,8 @@
"@babel/preset-env": "^7.18.2",
"@gitlab/at.js": "1.5.7",
"@gitlab/favicon-overlay": "2.0.0",
- "@gitlab/svgs": "2.30.0",
- "@gitlab/ui": "42.24.0",
+ "@gitlab/svgs": "2.32.0",
+ "@gitlab/ui": "42.25.0",
"@gitlab/visual-review-tools": "1.7.3",
"@rails/actioncable": "6.1.4-7",
"@rails/ujs": "6.1.4-7",
diff --git a/qa/qa/service/praefect_manager.rb b/qa/qa/service/praefect_manager.rb
index 8563c3656a8..eab41572cda 100644
--- a/qa/qa/service/praefect_manager.rb
+++ b/qa/qa/service/praefect_manager.rb
@@ -30,7 +30,7 @@ module QA
wait_until_shell_command_matches(dataloss_command, /Outdated repositories/)
end
- def replicated?(project_id)
+ def replicated?(project_id, project_name_prefix = 'gitaly_cluster')
Support::Retrier.retry_until(raise_on_failure: false) do
replicas = wait_until_shell_command(%(docker exec #{@gitlab} bash -c 'gitlab-rake "gitlab:praefect:replicas[#{project_id}]"')) do |line|
QA::Runtime::Logger.debug(line.chomp)
@@ -40,7 +40,7 @@ module QA
# ----------------------------------------------------------------------------------------------------------------------------------------------------------------
# gitaly_cluster-3aff1f2bd14e6c98 | 23c4422629234d62b62adacafd0a33a8364e8619 | 23c4422629234d62b62adacafd0a33a8364e8619 | 23c4422629234d62b62adacafd0a33a8364e8619
#
- break line if line.start_with?('gitaly_cluster')
+ break line if line.start_with?(project_name_prefix)
break nil if line.include?('Something went wrong when getting replicas')
end
next false unless replicas
diff --git a/qa/qa/specs/features/api/3_create/gitaly/praefect_replication_queue_spec.rb b/qa/qa/specs/features/api/3_create/gitaly/praefect_replication_queue_spec.rb
index a68155ef0b2..fabcc3a862c 100644
--- a/qa/qa/specs/features/api/3_create/gitaly/praefect_replication_queue_spec.rb
+++ b/qa/qa/specs/features/api/3_create/gitaly/praefect_replication_queue_spec.rb
@@ -67,7 +67,7 @@ module QA
project.initialize_with_readme = true
end
- expect(praefect_manager.replicated?(new_project.id)).to be true
+ expect(praefect_manager.replicated?(new_project.id, new_project.name)).to be true
end
end
end
diff --git a/spec/features/merge_request/user_sees_pipelines_spec.rb b/spec/features/merge_request/user_sees_pipelines_spec.rb
index 16b1de0393f..11e542916f9 100644
--- a/spec/features/merge_request/user_sees_pipelines_spec.rb
+++ b/spec/features/merge_request/user_sees_pipelines_spec.rb
@@ -78,9 +78,18 @@ RSpec.describe 'Merge request > User sees pipelines', :js do
it 'user visits merge request page' do
page.within('.merge-request-tabs') do
- expect(page).to have_no_link('Pipelines')
+ expect(page).to have_link('Pipelines')
end
end
+
+ it 'shows empty state with run pipeline button' do
+ page.within('.merge-request-tabs') do
+ click_link('Pipelines')
+ end
+
+ expect(page).to have_content('There are currently no pipelines.')
+ expect(page.find('[data-testid="run_pipeline_button"]')).to have_text('Run pipeline')
+ end
end
end
diff --git a/spec/frontend/commit/pipelines/pipelines_table_spec.js b/spec/frontend/commit/pipelines/pipelines_table_spec.js
index 9b01af1e585..71ee12cf02d 100644
--- a/spec/frontend/commit/pipelines/pipelines_table_spec.js
+++ b/spec/frontend/commit/pipelines/pipelines_table_spec.js
@@ -1,4 +1,4 @@
-import { GlEmptyState, GlLoadingIcon, GlModal, GlTableLite } from '@gitlab/ui';
+import { GlLoadingIcon, GlModal, GlTableLite } from '@gitlab/ui';
import { mount } from '@vue/test-utils';
import MockAdapter from 'axios-mock-adapter';
import { nextTick } from 'vue';
@@ -8,7 +8,7 @@ import waitForPromises from 'helpers/wait_for_promises';
import Api from '~/api';
import PipelinesTable from '~/commit/pipelines/pipelines_table.vue';
import httpStatusCodes from '~/lib/utils/http_status';
-import createFlash from '~/flash';
+import { createAlert } from '~/flash';
import { TOAST_MESSAGE } from '~/pipelines/constants';
import axios from '~/lib/utils/axios_utils';
@@ -26,10 +26,12 @@ describe('Pipelines table in Commits and Merge requests', () => {
const findRunPipelineBtn = () => wrapper.findByTestId('run_pipeline_button');
const findRunPipelineBtnMobile = () => wrapper.findByTestId('run_pipeline_button_mobile');
const findLoadingState = () => wrapper.findComponent(GlLoadingIcon);
- const findEmptyState = () => wrapper.findComponent(GlEmptyState);
+ const findErrorEmptyState = () => wrapper.findByTestId('pipeline-error-empty-state');
+ const findEmptyState = () => wrapper.findByTestId('pipeline-empty-state');
const findTable = () => wrapper.findComponent(GlTableLite);
const findTableRows = () => wrapper.findAllByTestId('pipeline-table-row');
const findModal = () => wrapper.findComponent(GlModal);
+ const findMrPipelinesDocsLink = () => wrapper.findByTestId('mr-pipelines-docs-link');
const createComponent = (props = {}) => {
wrapper = extendedWrapper(
@@ -73,7 +75,18 @@ describe('Pipelines table in Commits and Merge requests', () => {
it('should render the empty state', () => {
expect(findTableRows()).toHaveLength(0);
expect(findLoadingState().exists()).toBe(false);
- expect(findEmptyState().exists()).toBe(false);
+ expect(findErrorEmptyState().exists()).toBe(false);
+ expect(findEmptyState().exists()).toBe(true);
+ });
+
+ it('should render correct empty state content', () => {
+ expect(findRunPipelineBtn().exists()).toBe(true);
+ expect(findMrPipelinesDocsLink().attributes('href')).toBe(
+ '/help/ci/pipelines/merge_request_pipelines.md#prerequisites',
+ );
+ expect(findEmptyState().text()).toContain(
+ 'To run a merge request pipeline, the jobs in the CI/CD configuration file must be configured to run in merge request pipelines.',
+ );
});
});
@@ -90,7 +103,7 @@ describe('Pipelines table in Commits and Merge requests', () => {
expect(findTable().exists()).toBe(true);
expect(findTableRows()).toHaveLength(1);
expect(findLoadingState().exists()).toBe(false);
- expect(findEmptyState().exists()).toBe(false);
+ expect(findErrorEmptyState().exists()).toBe(false);
});
describe('with pagination', () => {
@@ -226,12 +239,14 @@ describe('Pipelines table in Commits and Merge requests', () => {
describe('failure', () => {
const permissionsMsg = 'You do not have permission to run a pipeline on this branch.';
+ const defaultMsg =
+ 'An error occurred while trying to run a new pipeline for this merge request.';
it.each`
status | message
- ${httpStatusCodes.BAD_REQUEST} | ${permissionsMsg}
+ ${httpStatusCodes.BAD_REQUEST} | ${defaultMsg}
${httpStatusCodes.UNAUTHORIZED} | ${permissionsMsg}
- ${httpStatusCodes.INTERNAL_SERVER_ERROR} | ${'An error occurred while trying to run a new pipeline for this merge request.'}
+ ${httpStatusCodes.INTERNAL_SERVER_ERROR} | ${defaultMsg}
`('displays permissions error message', async ({ status, message }) => {
const response = { response: { status } };
@@ -243,7 +258,13 @@ describe('Pipelines table in Commits and Merge requests', () => {
await waitForPromises();
- expect(createFlash).toHaveBeenCalledWith({ message });
+ expect(createAlert).toHaveBeenCalledWith({
+ message,
+ primaryButton: {
+ text: 'Learn more',
+ link: '/help/ci/pipelines/merge_request_pipelines.md',
+ },
+ });
});
});
});
@@ -293,7 +314,7 @@ describe('Pipelines table in Commits and Merge requests', () => {
});
it('should render error state', () => {
- expect(findEmptyState().text()).toBe(
+ expect(findErrorEmptyState().text()).toBe(
'There was an error fetching the pipelines. Try again in a few moments or contact your support team.',
);
});
diff --git a/spec/frontend/pipelines/performance_insights_modal_spec.js b/spec/frontend/pipelines/performance_insights_modal_spec.js
index b745eb1d78e..8c802be7718 100644
--- a/spec/frontend/pipelines/performance_insights_modal_spec.js
+++ b/spec/frontend/pipelines/performance_insights_modal_spec.js
@@ -20,6 +20,7 @@ describe('Performance insights modal', () => {
const findModal = () => wrapper.findComponent(GlModal);
const findAlert = () => wrapper.findComponent(GlAlert);
const findLink = () => wrapper.findComponent(GlLink);
+ const findLimitText = () => wrapper.findByTestId('limit-alert-text');
const findQueuedCardData = () => wrapper.findByTestId('insights-queued-card-data');
const findQueuedCardLink = () => wrapper.findByTestId('insights-queued-card-link');
const findExecutedCardData = () => wrapper.findByTestId('insights-executed-card-data');
@@ -62,8 +63,19 @@ describe('Performance insights modal', () => {
expect(findModal().exists()).toBe(true);
});
- it('does not dispaly alert', () => {
- expect(findAlert().exists()).toBe(false);
+ it('displays alert', () => {
+ expect(findAlert().exists()).toBe(true);
+ });
+
+ it('displays feedback issue link', () => {
+ expect(findLink().text()).toBe('Feedback issue');
+ expect(findLink().attributes('href')).toBe(
+ 'https://gitlab.com/gitlab-org/gitlab/-/issues/365902',
+ );
+ });
+
+ it('does not display limit text', () => {
+ expect(findLimitText().exists()).toBe(false);
});
describe('queued duration card', () => {
@@ -107,16 +119,13 @@ describe('Performance insights modal', () => {
});
});
- describe('limit alert', () => {
- it('displays limit alert when there is a next page', async () => {
+ describe('with next page', () => {
+ it('displays limit text when there is a next page', async () => {
createComponent([[getPerformanceInsights, getPerformanceInsightsNextPageHandler]]);
await waitForPromises();
- expect(findAlert().exists()).toBe(true);
- expect(findLink().attributes('href')).toBe(
- 'https://gitlab.com/gitlab-org/gitlab/-/issues/365902',
- );
+ expect(findLimitText().exists()).toBe(true);
});
});
});
diff --git a/spec/graphql/types/base_field_spec.rb b/spec/graphql/types/base_field_spec.rb
index 439678e7e16..a3efc60ff5b 100644
--- a/spec/graphql/types/base_field_spec.rb
+++ b/spec/graphql/types/base_field_spec.rb
@@ -299,7 +299,7 @@ RSpec.describe Types::BaseField do
end
it 'returns the correct availability in the description' do
- expect(field.description). to eq expected_description
+ expect(field.description).to eq expected_description
end
end
end
diff --git a/spec/graphql/types/ci/runner_upgrade_status_type_enum_spec.rb b/spec/graphql/types/ci/runner_upgrade_status_enum_spec.rb
index 03c784dcbe7..ef378f3fc5a 100644
--- a/spec/graphql/types/ci/runner_upgrade_status_type_enum_spec.rb
+++ b/spec/graphql/types/ci/runner_upgrade_status_enum_spec.rb
@@ -2,13 +2,13 @@
require 'spec_helper'
-RSpec.describe Types::Ci::RunnerUpgradeStatusTypeEnum do
+RSpec.describe Types::Ci::RunnerUpgradeStatusEnum do
let(:model_only_enum_values) { %w[not_processed] }
let(:expected_graphql_source_values) do
Ci::RunnerVersion.statuses.keys - model_only_enum_values
end
- specify { expect(described_class.graphql_name).to eq('CiRunnerUpgradeStatusType') }
+ specify { expect(described_class.graphql_name).to eq('CiRunnerUpgradeStatus') }
it 'exposes all upgrade status values except not_processed' do
expect(described_class.values.keys).to match_array(
diff --git a/spec/lib/gitlab/ci/pipeline/chain/command_spec.rb b/spec/lib/gitlab/ci/pipeline/chain/command_spec.rb
index 0d78ce3440a..de43e759193 100644
--- a/spec/lib/gitlab/ci/pipeline/chain/command_spec.rb
+++ b/spec/lib/gitlab/ci/pipeline/chain/command_spec.rb
@@ -282,7 +282,7 @@ RSpec.describe Gitlab::Ci::Pipeline::Chain::Command do
subject { command.ambiguous_ref? }
context 'when ref is not ambiguous' do
- it { is_expected. to eq(false) }
+ it { is_expected.to eq(false) }
end
context 'when ref is ambiguous' do
@@ -291,7 +291,7 @@ RSpec.describe Gitlab::Ci::Pipeline::Chain::Command do
project.repository.add_branch(project.creator, 'ref', 'master')
end
- it { is_expected. to eq(true) }
+ it { is_expected.to eq(true) }
end
end
diff --git a/spec/lib/gitlab/database/shared_model_spec.rb b/spec/lib/gitlab/database/shared_model_spec.rb
index c88edc17817..7e0ba3397d1 100644
--- a/spec/lib/gitlab/database/shared_model_spec.rb
+++ b/spec/lib/gitlab/database/shared_model_spec.rb
@@ -106,7 +106,7 @@ RSpec.describe Gitlab::Database::SharedModel do
shared_model = shared_model_class.new
- expect(shared_model.connection_db_config). to eq(described_class.connection_db_config)
+ expect(shared_model.connection_db_config).to eq(described_class.connection_db_config)
end
end
end
diff --git a/spec/lib/gitlab/diff/highlight_spec.rb b/spec/lib/gitlab/diff/highlight_spec.rb
index 624160d2f48..c378ecb8134 100644
--- a/spec/lib/gitlab/diff/highlight_spec.rb
+++ b/spec/lib/gitlab/diff/highlight_spec.rb
@@ -117,7 +117,7 @@ RSpec.describe Gitlab::Diff::Highlight do
it 'reports to Sentry if configured' do
expect(Gitlab::ErrorTracking).to receive(:track_and_raise_for_dev_exception).and_call_original
- expect { subject }. to raise_exception(RangeError)
+ expect { subject }.to raise_exception(RangeError)
end
end
diff --git a/spec/lib/gitlab/spamcheck/client_spec.rb b/spec/lib/gitlab/spamcheck/client_spec.rb
index a6e7665569c..bb0b542b4f5 100644
--- a/spec/lib/gitlab/spamcheck/client_spec.rb
+++ b/spec/lib/gitlab/spamcheck/client_spec.rb
@@ -97,7 +97,7 @@ RSpec.describe Gitlab::Spamcheck::Client do
context: cxt)
expect(issue_pb.title).to eq issue.title
expect(issue_pb.description).to eq issue.description
- expect(issue_pb.user_in_project). to be false
+ expect(issue_pb.user_in_project).to be false
expect(issue_pb.project.project_id).to eq issue.project_id
expect(issue_pb.created_at).to eq timestamp_to_protobuf_timestamp(issue.created_at)
expect(issue_pb.updated_at).to eq timestamp_to_protobuf_timestamp(issue.updated_at)
diff --git a/spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb b/spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb
index 3478305bbad..a23f9995875 100644
--- a/spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb
+++ b/spec/migrations/20220128155251_remove_dangling_running_builds_spec.rb
@@ -47,6 +47,6 @@ RSpec.describe RemoveDanglingRunningBuilds, :suppress_gitlab_schemas_validate_co
migrate!
expect(running_metadata.reload).to be_present
- expect { failed_metadata.reload } .to raise_error(ActiveRecord::RecordNotFound)
+ expect { failed_metadata.reload }.to raise_error(ActiveRecord::RecordNotFound)
end
end
diff --git a/spec/models/concerns/database_event_tracking_spec.rb b/spec/models/concerns/database_event_tracking_spec.rb
new file mode 100644
index 00000000000..79be8654498
--- /dev/null
+++ b/spec/models/concerns/database_event_tracking_spec.rb
@@ -0,0 +1,69 @@
+# frozen_string_literal: true
+
+require 'spec_helper'
+
+RSpec.describe DatabaseEventTracking, :snowplow do
+ let(:test_class) do
+ Class.new(ActiveRecord::Base) do
+ include DatabaseEventTracking
+
+ self.table_name = 'application_setting_terms'
+
+ self::SNOWPLOW_ATTRIBUTES = %w[id].freeze # rubocop:disable Rspec/LeakyConstantDeclaration
+ end
+ end
+
+ subject(:create_test_class_record) { test_class.create!(id: 1, terms: "") }
+
+ context 'if event emmiter failed' do
+ before do
+ allow(Gitlab::Tracking).to receive(:event).and_raise(StandardError) # rubocop:disable Rspec/ExpectGitlabTracking
+ end
+
+ it 'tracks the exception' do
+ expect(Gitlab::ErrorTracking).to receive(:track_and_raise_for_dev_exception)
+
+ create_test_class_record
+ end
+ end
+
+ context 'if product_intelligence_database_event_tracking FF is off' do
+ before do
+ stub_feature_flags(product_intelligence_database_event_tracking: false)
+ end
+
+ it 'does not track the event' do
+ create_test_class_record
+
+ expect_no_snowplow_event
+ end
+ end
+
+ describe 'event tracking' do
+ let(:category) { test_class.to_s }
+ let(:event) { 'database_event' }
+
+ it 'when created' do
+ create_test_class_record
+
+ expect_snowplow_event(category: category, action: "#{event}_create", label: 'application_setting_terms',
+ property: 'create', namespace: nil, "id" => 1)
+ end
+
+ it 'when updated' do
+ create_test_class_record
+ test_class.first.update!(id: 3)
+
+ expect_snowplow_event(category: category, action: "#{event}_update", label: 'application_setting_terms',
+ property: 'update', namespace: nil, "id" => 3)
+ end
+
+ it 'when destroyed' do
+ create_test_class_record
+ test_class.first.destroy!
+
+ expect_snowplow_event(category: category, action: "#{event}_destroy", label: 'application_setting_terms',
+ property: 'destroy', namespace: nil, "id" => 1)
+ end
+ end
+end
diff --git a/spec/models/integrations/chat_message/issue_message_spec.rb b/spec/models/integrations/chat_message/issue_message_spec.rb
index 7026a314b78..4a86322cdaf 100644
--- a/spec/models/integrations/chat_message/issue_message_spec.rb
+++ b/spec/models/integrations/chat_message/issue_message_spec.rb
@@ -65,7 +65,7 @@ RSpec.describe Integrations::ChatMessage::IssueMessage do
end
it 'returns a message regarding closing of issues' do
- expect(subject.pretext). to eq(
+ expect(subject.pretext).to eq(
'[<http://somewhere.com|project_name>] Issue <http://url.com|#100 Issue title> closed by Test User (test.user)')
expect(subject.attachments).to be_empty
end
@@ -111,7 +111,7 @@ RSpec.describe Integrations::ChatMessage::IssueMessage do
end
it 'returns a message regarding closing of issues' do
- expect(subject.pretext). to eq(
+ expect(subject.pretext).to eq(
'[[project_name](http://somewhere.com)] Issue [#100 Issue title](http://url.com) closed by Test User (test.user)')
expect(subject.attachments).to be_empty
expect(subject.activity).to eq({
diff --git a/spec/models/milestone_spec.rb b/spec/models/milestone_spec.rb
index 72a57b6076a..af1383b68bf 100644
--- a/spec/models/milestone_spec.rb
+++ b/spec/models/milestone_spec.rb
@@ -257,7 +257,7 @@ RSpec.describe Milestone do
let(:milestone) { create(:milestone, title: 'foo', description: 'bar') }
it 'returns milestones with a matching title' do
- expect(described_class.search_title(milestone.title)) .to eq([milestone])
+ expect(described_class.search_title(milestone.title)).to eq([milestone])
end
it 'returns milestones with a partially matching title' do
@@ -272,7 +272,7 @@ RSpec.describe Milestone do
it 'searches only on the title and ignores milestones with a matching description' do
create(:milestone, title: 'bar', description: 'foo')
- expect(described_class.search_title(milestone.title)) .to eq([milestone])
+ expect(described_class.search_title(milestone.title)).to eq([milestone])
end
end
diff --git a/spec/presenters/alert_management/alert_presenter_spec.rb b/spec/presenters/alert_management/alert_presenter_spec.rb
index 21c0cb3fead..fe228f174fe 100644
--- a/spec/presenters/alert_management/alert_presenter_spec.rb
+++ b/spec/presenters/alert_management/alert_presenter_spec.rb
@@ -115,7 +115,7 @@ RSpec.describe AlertManagement::AlertPresenter do
it 'formats the start time of the alert' do
alert.started_at = Time.utc(2019, 5, 5)
- expect(presenter.start_time). to eq('05 May 2019, 12:00AM (UTC)')
+ expect(presenter.start_time).to eq('05 May 2019, 12:00AM (UTC)')
end
end
diff --git a/spec/requests/api/graphql/custom_emoji_query_spec.rb b/spec/requests/api/graphql/custom_emoji_query_spec.rb
index 874357d9eef..13b7a22e791 100644
--- a/spec/requests/api/graphql/custom_emoji_query_spec.rb
+++ b/spec/requests/api/graphql/custom_emoji_query_spec.rb
@@ -31,8 +31,8 @@ RSpec.describe 'getting custom emoji within namespace' do
post_graphql(custom_emoji_query(group), current_user: current_user)
expect(response).to have_gitlab_http_status(:ok)
- expect(graphql_data['group']['customEmoji']['nodes'].count). to eq(1)
- expect(graphql_data['group']['customEmoji']['nodes'].first['name']). to eq(custom_emoji.name)
+ expect(graphql_data['group']['customEmoji']['nodes'].count).to eq(1)
+ expect(graphql_data['group']['customEmoji']['nodes'].first['name']).to eq(custom_emoji.name)
end
it 'returns nil when unauthorised' do
diff --git a/spec/support/shared_examples/controllers/snowplow_event_tracking_examples.rb b/spec/support/shared_examples/controllers/snowplow_event_tracking_examples.rb
index fc88d37660b..91e043ffb4b 100644
--- a/spec/support/shared_examples/controllers/snowplow_event_tracking_examples.rb
+++ b/spec/support/shared_examples/controllers/snowplow_event_tracking_examples.rb
@@ -2,16 +2,18 @@
#
# Requires a context containing:
# - subject
-# - project
# - feature_flag_name
# - category
# - action
# - namespace
+# Optionaly, the context can contain:
+# - project
+# - property
# - user
+# - label
+# - **extra
shared_examples 'Snowplow event tracking' do
- let(:label) { nil }
-
it 'is not emitted if FF is disabled' do
stub_feature_flags(feature_flag_name => false)
@@ -21,13 +23,17 @@ shared_examples 'Snowplow event tracking' do
end
it 'is emitted' do
+ extra ||= {}
+
params = {
category: category,
action: action,
namespace: namespace,
- user: user,
- project: project,
- label: label
+ user: try(:user),
+ project: try(:project),
+ label: try(:label),
+ property: try(:property),
+ **extra
}.compact
subject
diff --git a/spec/tasks/gitlab/db_rake_spec.rb b/spec/tasks/gitlab/db_rake_spec.rb
index 74bec406947..8f8178cde4d 100644
--- a/spec/tasks/gitlab/db_rake_spec.rb
+++ b/spec/tasks/gitlab/db_rake_spec.rb
@@ -370,7 +370,7 @@ RSpec.describe 'gitlab:db namespace rake task', :silence_stdout do
it 'outputs changed message for automation after operations happen' do
allow(ActiveRecord::Base.connection.schema_migration).to receive(:table_exists?).and_return(schema_migration_table_exists)
allow_any_instance_of(ActiveRecord::MigrationContext).to receive(:needs_migration?).and_return(needs_migrations)
- expect { run_rake_task('gitlab:db:unattended') }. to output(/^#{rake_output}$/).to_stdout
+ expect { run_rake_task('gitlab:db:unattended') }.to output(/^#{rake_output}$/).to_stdout
end
end
end
diff --git a/spec/workers/concerns/limited_capacity/job_tracker_spec.rb b/spec/workers/concerns/limited_capacity/job_tracker_spec.rb
index eeccdbd0e2d..0e3fa350fcd 100644
--- a/spec/workers/concerns/limited_capacity/job_tracker_spec.rb
+++ b/spec/workers/concerns/limited_capacity/job_tracker_spec.rb
@@ -11,7 +11,7 @@ RSpec.describe LimitedCapacity::JobTracker, :clean_gitlab_redis_shared_state do
describe '#register' do
it 'adds jid to the set' do
- expect(job_tracker.register('a-job-id', max_jids)). to be true
+ expect(job_tracker.register('a-job-id', max_jids)).to be true
expect(job_tracker.running_jids).to contain_exactly('a-job-id')
end
diff --git a/yarn.lock b/yarn.lock
index 3f40c7805f4..ca755429f19 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -1059,19 +1059,19 @@
stylelint-declaration-strict-value "1.8.0"
stylelint-scss "4.2.0"
-"@gitlab/svgs@2.30.0":
- version "2.30.0"
- resolved "https://registry.yarnpkg.com/@gitlab/svgs/-/svgs-2.30.0.tgz#bb73b2d16868b17e7e2dbb73653b7ab84f3cbd05"
- integrity sha512-XtYXba8XMAMHJz66H/lVZpXy77Z+ATlvbuvsR9cvM479lUEbrIcdAVOPV6zjPJiIxCUA5Yx1lUfWhgAwLEvRgw==
+"@gitlab/svgs@2.32.0":
+ version "2.32.0"
+ resolved "https://registry.yarnpkg.com/@gitlab/svgs/-/svgs-2.32.0.tgz#eb66dc76cc6242d97d16e05acb0dbad4f56555a0"
+ integrity sha512-ElblTUE26pddJS6EzHHtMHPkZ7JPB7vt3C2RoY9W3JPPSrcsOudeeLN5oW7Pz3MoXR3G0U/Wg+Bhe4M1STD+tA==
-"@gitlab/ui@42.24.0":
- version "42.24.0"
- resolved "https://registry.yarnpkg.com/@gitlab/ui/-/ui-42.24.0.tgz#6263d3b59cc7791096723b63746add3a15cc116f"
- integrity sha512-krQcaGjskWUw/jqRu6V5kCP2yLy+drGitx0T+fIWy78wwQNfR8qgfeaGfPBwTYZ3zpLF8WBULIj37VnAqx2HIw==
+"@gitlab/ui@42.25.0":
+ version "42.25.0"
+ resolved "https://registry.yarnpkg.com/@gitlab/ui/-/ui-42.25.0.tgz#d79873347be9868c4d3d3123295ce1f12967f330"
+ integrity sha512-yxSQeLbhrPD4KKQPCo+glarlhoa4cj46j7mgQtTRbJFw2ZWPcpJ4xuujCb8GoyGPlHpWaS8VJyv3l+hwBQs3qg==
dependencies:
"@popperjs/core" "^2.11.2"
bootstrap-vue "2.20.1"
- dompurify "^2.3.9"
+ dompurify "^2.3.10"
echarts "^5.3.2"
iframe-resizer "^4.3.2"
lodash "^4.17.20"
@@ -4862,7 +4862,7 @@ dompurify@2.3.6:
resolved "https://registry.yarnpkg.com/dompurify/-/dompurify-2.3.6.tgz#2e019d7d7617aacac07cbbe3d88ae3ad354cf875"
integrity sha512-OFP2u/3T1R5CEgWCEONuJ1a5+MFKnOYpkywpUSxv/dj1LeBT1erK+JwM7zK0ROy2BRhqVCf0LRw/kHqKuMkVGg==
-dompurify@^2.3.10, dompurify@^2.3.9:
+dompurify@^2.3.10:
version "2.3.10"
resolved "https://registry.yarnpkg.com/dompurify/-/dompurify-2.3.10.tgz#901f7390ffe16a91a5a556b94043314cd4850385"
integrity sha512-o7Fg/AgC7p/XpKjf/+RC3Ok6k4St5F7Q6q6+Nnm3p2zGWioAY6dh0CbbuwOhH2UcSzKsdniE/YnE2/92JcsA+g==