summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.haml-lint.yml1
-rw-r--r--GITALY_SERVER_VERSION2
-rw-r--r--app/assets/javascripts/design_management/components/design_notes/design_note.vue7
-rw-r--r--app/assets/javascripts/diffs/components/diff_discussions.vue1
-rw-r--r--app/assets/javascripts/diffs/components/image_diff_overlay.vue1
-rw-r--r--app/assets/javascripts/diffs/components/inline_diff_table_row.vue1
-rw-r--r--app/assets/javascripts/diffs/components/parallel_diff_table_row.vue2
-rw-r--r--app/assets/javascripts/emoji/components/picker.vue1
-rw-r--r--app/assets/javascripts/error_tracking/components/error_tracking_actions.vue2
-rw-r--r--app/assets/javascripts/ide/components/jobs/detail/scroll_button.vue1
-rw-r--r--app/assets/javascripts/projects/commit/store/actions.js4
-rw-r--r--app/assets/javascripts/search/topbar/components/searchable_dropdown.vue8
-rw-r--r--app/assets/javascripts/vue_merge_request_widget/components/deployment/deployment_action_button.vue1
-rw-r--r--app/assets/javascripts/vue_shared/components/help_popover.vue2
-rw-r--r--app/assets/javascripts/vue_shared/components/rich_content_editor/toolbar_item.vue6
-rw-r--r--app/finders/concerns/packages/finder_helper.rb14
-rw-r--r--app/finders/packages/maven/package_finder.rb2
-rw-r--r--app/models/concerns/issuable.rb8
-rw-r--r--app/models/concerns/milestoneable.rb4
-rw-r--r--app/models/packages/package.rb2
-rw-r--r--app/services/issuable/bulk_update_service.rb13
-rw-r--r--app/services/merge_requests/base_service.rb8
-rw-r--r--app/services/merge_requests/refresh_service.rb9
-rw-r--r--app/views/layouts/_flash.html.haml2
-rw-r--r--app/views/shared/blob/_markdown_buttons.html.haml2
-rw-r--r--app/workers/all_queues.yml8
-rw-r--r--app/workers/merge_requests/create_pipeline_worker.rb28
-rw-r--r--changelogs/unreleased/21068-optimize-issueable-updates.yml5
-rw-r--r--changelogs/unreleased/220680-update-gatsby-project-template.yml5
-rw-r--r--changelogs/unreleased/326099-enabled-by-default.yml5
-rw-r--r--changelogs/unreleased/327064-fix-revert-query.yml5
-rw-r--r--changelogs/unreleased/cngo-add-aria-labels-to-icon-only-buttons-3.yml5
-rw-r--r--changelogs/unreleased/move_pipeline_creation_async.yml5
-rw-r--r--config/feature_flags/development/code_review_async_pipeline_creation.yml8
-rw-r--r--config/feature_flags/development/maven_packages_group_level_improvements.yml2
-rw-r--r--config/feature_flags/development/packages_finder_helper_deploy_token.yml8
-rw-r--r--doc/update/index.md2
-rw-r--r--lib/api/maven_packages.rb2
-rw-r--r--spec/factories/services.rb3
-rw-r--r--spec/finders/concerns/packages/finder_helper_spec.rb209
-rw-r--r--spec/frontend/vue_shared/components/help_popover_spec.js1
-rw-r--r--spec/models/concerns/issuable_spec.rb17
-rw-r--r--spec/models/concerns/milestoneable_spec.rb14
-rw-r--r--spec/requests/api/maven_packages_spec.rb2
-rw-r--r--spec/services/merge_requests/refresh_service_spec.rb16
-rw-r--r--spec/workers/merge_requests/create_pipeline_worker_spec.rb61
-rw-r--r--vendor/project_templates/gatsby.tar.gzbin79051 -> 377283 bytes
47 files changed, 373 insertions, 142 deletions
diff --git a/.haml-lint.yml b/.haml-lint.yml
index 39090a48d1c..efbf14b2e22 100644
--- a/.haml-lint.yml
+++ b/.haml-lint.yml
@@ -137,7 +137,6 @@ linters:
- Style/ParenthesesAroundCondition
- Style/RedundantParentheses
- Style/SelfAssignment
- - Style/Semicolon
- Style/TernaryParentheses
- Style/TrailingCommaInHashLiteral
- Style/UnlessElse
diff --git a/GITALY_SERVER_VERSION b/GITALY_SERVER_VERSION
index a9d42925fc7..1b3658930d2 100644
--- a/GITALY_SERVER_VERSION
+++ b/GITALY_SERVER_VERSION
@@ -1 +1 @@
-4ea88e921af65ba0577c40f8b54830c97adaa56c
+8752fc1097114316889560502579ddf477a20a2d
diff --git a/app/assets/javascripts/design_management/components/design_notes/design_note.vue b/app/assets/javascripts/design_management/components/design_notes/design_note.vue
index 2b867217327..833d7081a2c 100644
--- a/app/assets/javascripts/design_management/components/design_notes/design_note.vue
+++ b/app/assets/javascripts/design_management/components/design_notes/design_note.vue
@@ -1,6 +1,7 @@
<script>
import { GlTooltipDirective, GlIcon, GlLink, GlSafeHtmlDirective } from '@gitlab/ui';
import { ApolloMutation } from 'vue-apollo';
+import { __ } from '~/locale';
import TimelineEntryItem from '~/vue_shared/components/notes/timeline_entry_item.vue';
import TimeAgoTooltip from '~/vue_shared/components/time_ago_tooltip.vue';
import UserAvatarLink from '~/vue_shared/components/user_avatar/user_avatar_link.vue';
@@ -10,6 +11,9 @@ import { findNoteId, extractDesignNoteId } from '../../utils/design_management_u
import DesignReplyForm from './design_reply_form.vue';
export default {
+ i18n: {
+ editCommentLabel: __('Edit comment'),
+ },
components: {
UserAvatarLink,
TimelineEntryItem,
@@ -113,7 +117,8 @@ export default {
v-if="isEditButtonVisible"
v-gl-tooltip
type="button"
- :title="__('Edit comment')"
+ :title="$options.i18n.editCommentLabel"
+ :aria-label="$options.i18n.editCommentLabel"
class="note-action-button js-note-edit btn btn-transparent qa-note-edit-button"
@click="isEditing = true"
>
diff --git a/app/assets/javascripts/diffs/components/diff_discussions.vue b/app/assets/javascripts/diffs/components/diff_discussions.vue
index d0d457d8582..5e05ec87f84 100644
--- a/app/assets/javascripts/diffs/components/diff_discussions.vue
+++ b/app/assets/javascripts/diffs/components/diff_discussions.vue
@@ -68,6 +68,7 @@ export default {
}"
type="button"
class="js-diff-notes-toggle"
+ :aria-label="__('Show comments')"
@click="toggleDiscussion({ discussionId: discussion.id })"
>
<gl-icon v-if="discussion.expanded" name="collapse" class="collapse-icon" />
diff --git a/app/assets/javascripts/diffs/components/image_diff_overlay.vue b/app/assets/javascripts/diffs/components/image_diff_overlay.vue
index 3d05202fb2d..5572338908f 100644
--- a/app/assets/javascripts/diffs/components/image_diff_overlay.vue
+++ b/app/assets/javascripts/diffs/components/image_diff_overlay.vue
@@ -122,6 +122,7 @@ export default {
:disabled="!shouldToggleDiscussion"
class="js-image-badge"
type="button"
+ :aria-label="__('Show comments')"
@click="clickedToggle(discussion)"
>
<gl-icon v-if="showCommentIcon" name="image-comment-dark" :size="24" />
diff --git a/app/assets/javascripts/diffs/components/inline_diff_table_row.vue b/app/assets/javascripts/diffs/components/inline_diff_table_row.vue
index fd6c69e22c6..25403b1547e 100644
--- a/app/assets/javascripts/diffs/components/inline_diff_table_row.vue
+++ b/app/assets/javascripts/diffs/components/inline_diff_table_row.vue
@@ -146,6 +146,7 @@ export default {
type="button"
class="add-diff-note note-button js-add-diff-note-button"
:disabled="line.commentsDisabled"
+ :aria-label="addCommentTooltip"
@click="handleCommentButton"
>
<gl-icon :size="12" name="comment" />
diff --git a/app/assets/javascripts/diffs/components/parallel_diff_table_row.vue b/app/assets/javascripts/diffs/components/parallel_diff_table_row.vue
index 147741fa2bb..96946d0fd88 100644
--- a/app/assets/javascripts/diffs/components/parallel_diff_table_row.vue
+++ b/app/assets/javascripts/diffs/components/parallel_diff_table_row.vue
@@ -195,6 +195,7 @@ export default {
type="button"
class="add-diff-note note-button js-add-diff-note-button qa-diff-comment"
:disabled="line.left.commentsDisabled"
+ :aria-label="addCommentTooltipLeft"
@click="handleCommentButton(line.left)"
>
<gl-icon :size="12" name="comment" />
@@ -252,6 +253,7 @@ export default {
type="button"
class="add-diff-note note-button js-add-diff-note-button qa-diff-comment"
:disabled="line.right.commentsDisabled"
+ :aria-label="addCommentTooltipRight"
@click="handleCommentButton(line.right)"
>
<gl-icon :size="12" name="comment" />
diff --git a/app/assets/javascripts/emoji/components/picker.vue b/app/assets/javascripts/emoji/components/picker.vue
index 156bbb28ce6..cbcc5dcff3a 100644
--- a/app/assets/javascripts/emoji/components/picker.vue
+++ b/app/assets/javascripts/emoji/components/picker.vue
@@ -105,6 +105,7 @@ export default {
}"
type="button"
class="gl-border-0 gl-border-b-2 gl-border-b-solid gl-flex-fill-1 gl-text-gray-300 gl-pt-3 gl-pb-3 gl-bg-transparent emoji-picker-category-tab"
+ :aria-label="category.name"
@click="scrollToCategory(category.name)"
>
<gl-icon :name="category.icon" :size="12" />
diff --git a/app/assets/javascripts/error_tracking/components/error_tracking_actions.vue b/app/assets/javascripts/error_tracking/components/error_tracking_actions.vue
index db61957d452..9438900c736 100644
--- a/app/assets/javascripts/error_tracking/components/error_tracking_actions.vue
+++ b/app/assets/javascripts/error_tracking/components/error_tracking_actions.vue
@@ -51,6 +51,7 @@ export default {
v-gl-tooltip.hover
class="gl-display-block gl-mb-4 mb-md-0 gl-w-full"
:title="ignoreBtn.title"
+ :aria-label="ignoreBtn.title"
@click="$emit('update-issue-status', { errorId: error.id, status: ignoreBtn.status })"
>
<gl-icon class="gl-display-none d-md-inline gl-m-0" :name="ignoreBtn.icon" :size="12" />
@@ -62,6 +63,7 @@ export default {
v-gl-tooltip.hover
class="gl-display-block gl-mb-4 mb-md-0 gl-w-full"
:title="resolveBtn.title"
+ :aria-label="resolveBtn.title"
@click="$emit('update-issue-status', { errorId: error.id, status: resolveBtn.status })"
>
<gl-icon class="gl-display-none d-md-inline gl-m-0" :name="resolveBtn.icon" :size="12" />
diff --git a/app/assets/javascripts/ide/components/jobs/detail/scroll_button.vue b/app/assets/javascripts/ide/components/jobs/detail/scroll_button.vue
index f4859b9f312..6e1929a1948 100644
--- a/app/assets/javascripts/ide/components/jobs/detail/scroll_button.vue
+++ b/app/assets/javascripts/ide/components/jobs/detail/scroll_button.vue
@@ -55,6 +55,7 @@ export default {
:disabled="disabled"
class="btn-scroll btn-transparent btn-blank"
type="button"
+ :aria-label="tooltipTitle"
@click="clickedScroll"
>
<gl-icon :name="iconName" />
diff --git a/app/assets/javascripts/projects/commit/store/actions.js b/app/assets/javascripts/projects/commit/store/actions.js
index c72704303ca..2b25082eced 100644
--- a/app/assets/javascripts/projects/commit/store/actions.js
+++ b/app/assets/javascripts/projects/commit/store/actions.js
@@ -22,8 +22,8 @@ export const fetchBranches = ({ commit, dispatch, state }, query) => {
.get(state.branchesEndpoint, {
params: { search: query },
})
- .then(({ data }) => {
- commit(types.RECEIVE_BRANCHES_SUCCESS, data.Branches || []);
+ .then(({ data = [] }) => {
+ commit(types.RECEIVE_BRANCHES_SUCCESS, data.Branches?.length ? data.Branches : data);
})
.catch(() => {
createFlash({ message: PROJECT_BRANCHES_ERROR });
diff --git a/app/assets/javascripts/search/topbar/components/searchable_dropdown.vue b/app/assets/javascripts/search/topbar/components/searchable_dropdown.vue
index 5fb7217db74..d16850cd889 100644
--- a/app/assets/javascripts/search/topbar/components/searchable_dropdown.vue
+++ b/app/assets/javascripts/search/topbar/components/searchable_dropdown.vue
@@ -9,10 +9,13 @@ import {
GlSkeletonLoader,
GlTooltipDirective,
} from '@gitlab/ui';
-
+import { __ } from '~/locale';
import { ANY_OPTION } from '../constants';
export default {
+ i18n: {
+ clearLabel: __('Clear'),
+ },
name: 'SearchableDropdown',
components: {
GlDropdown,
@@ -96,7 +99,8 @@ export default {
v-gl-tooltip
name="clear"
category="tertiary"
- :title="__('Clear')"
+ :title="$options.i18n.clearLabel"
+ :aria-label="$options.i18n.clearLabel"
class="gl-p-0! gl-mr-2"
@keydown.enter.stop="resetDropdown"
@click.stop="resetDropdown"
diff --git a/app/assets/javascripts/vue_merge_request_widget/components/deployment/deployment_action_button.vue b/app/assets/javascripts/vue_merge_request_widget/components/deployment/deployment_action_button.vue
index cc3efae565a..b25c0cc0d96 100644
--- a/app/assets/javascripts/vue_merge_request_widget/components/deployment/deployment_action_button.vue
+++ b/app/assets/javascripts/vue_merge_request_widget/components/deployment/deployment_action_button.vue
@@ -68,6 +68,7 @@ export default {
category="primary"
size="small"
:title="buttonTitle"
+ :aria-label="buttonTitle"
:loading="isLoading"
:disabled="isActionInProgress"
:class="`inline gl-ml-2 ${containerClasses}`"
diff --git a/app/assets/javascripts/vue_shared/components/help_popover.vue b/app/assets/javascripts/vue_shared/components/help_popover.vue
index 7222bd82df0..f36b9107a6e 100644
--- a/app/assets/javascripts/vue_shared/components/help_popover.vue
+++ b/app/assets/javascripts/vue_shared/components/help_popover.vue
@@ -25,7 +25,7 @@ export default {
</script>
<template>
<span>
- <gl-button ref="popoverTrigger" variant="link" icon="question" tabindex="0" />
+ <gl-button ref="popoverTrigger" variant="link" icon="question" :aria-label="__('Help')" />
<gl-popover :target="() => $refs.popoverTrigger.$el" v-bind="options">
<template v-if="options.title" #title>
<span v-safe-html="options.title"></span>
diff --git a/app/assets/javascripts/vue_shared/components/rich_content_editor/toolbar_item.vue b/app/assets/javascripts/vue_shared/components/rich_content_editor/toolbar_item.vue
index 4271f6053ed..85a67c087bb 100644
--- a/app/assets/javascripts/vue_shared/components/rich_content_editor/toolbar_item.vue
+++ b/app/assets/javascripts/vue_shared/components/rich_content_editor/toolbar_item.vue
@@ -21,7 +21,11 @@ export default {
};
</script>
<template>
- <button v-gl-tooltip="{ title: tooltip }" class="p-0 gl-display-flex toolbar-button">
+ <button
+ v-gl-tooltip="{ title: tooltip }"
+ :aria-label="tooltip"
+ class="p-0 gl-display-flex toolbar-button"
+ >
<gl-icon class="gl-mx-auto gl-align-self-center" :name="icon" />
</button>
</template>
diff --git a/app/finders/concerns/packages/finder_helper.rb b/app/finders/concerns/packages/finder_helper.rb
index 244bd7f6f86..39c018818d1 100644
--- a/app/finders/concerns/packages/finder_helper.rb
+++ b/app/finders/concerns/packages/finder_helper.rb
@@ -13,7 +13,7 @@ module Packages
return ::Packages::Package.none unless within_group
return ::Packages::Package.none unless Ability.allowed?(user, :read_group, within_group)
- projects = projects_visible_to_reporters(user, within_group.self_and_descendants.select(:id))
+ projects = projects_visible_to_reporters(user, within_group: within_group)
::Packages::Package.for_projects(projects.select(:id))
end
@@ -21,12 +21,16 @@ module Packages
return ::Project.none unless within_group
return ::Project.none unless Ability.allowed?(user, :read_group, within_group)
- projects_visible_to_reporters(user, within_group.self_and_descendants.select(:id))
+ projects_visible_to_reporters(user, within_group: within_group)
end
- def projects_visible_to_reporters(user, namespace_ids)
- ::Project.in_namespace(namespace_ids)
- .public_or_visible_to_user(user, ::Gitlab::Access::REPORTER)
+ def projects_visible_to_reporters(user, within_group:)
+ if user.is_a?(DeployToken) && Feature.enabled?(:packages_finder_helper_deploy_token)
+ user.accessible_projects
+ else
+ within_group.all_projects
+ .public_or_visible_to_user(user, ::Gitlab::Access::REPORTER)
+ end
end
def package_type
diff --git a/app/finders/packages/maven/package_finder.rb b/app/finders/packages/maven/package_finder.rb
index 973496ca9c4..eefcdaba3c8 100644
--- a/app/finders/packages/maven/package_finder.rb
+++ b/app/finders/packages/maven/package_finder.rb
@@ -76,7 +76,7 @@ module Packages
def group_level_improvements?
strong_memoize(:group_level_improvements) do
- Feature.enabled?(:maven_packages_group_level_improvements)
+ Feature.enabled?(:maven_packages_group_level_improvements, default_enabled: :yaml)
end
end
end
diff --git a/app/models/concerns/issuable.rb b/app/models/concerns/issuable.rb
index 1e44321e148..478c7cd156f 100644
--- a/app/models/concerns/issuable.rb
+++ b/app/models/concerns/issuable.rb
@@ -137,14 +137,6 @@ module Issuable
scope :references_project, -> { references(:project) }
scope :non_archived, -> { join_project.where(projects: { archived: false }) }
- scope :includes_for_bulk_update, -> do
- associations = %i[author assignees epic group labels metrics project source_project target_project].select do |association|
- reflect_on_association(association)
- end
-
- includes(*associations)
- end
-
attr_mentionable :title, pipeline: :single_line
attr_mentionable :description
diff --git a/app/models/concerns/milestoneable.rb b/app/models/concerns/milestoneable.rb
index d42417bb6c1..ccb334343ff 100644
--- a/app/models/concerns/milestoneable.rb
+++ b/app/models/concerns/milestoneable.rb
@@ -39,13 +39,11 @@ module Milestoneable
private
def milestone_is_valid
- errors.add(:milestone_id, 'is invalid') if respond_to?(:milestone_id) && !milestone_available?
+ errors.add(:milestone_id, 'is invalid') if respond_to?(:milestone_id) && milestone_id.present? && !milestone_available?
end
end
def milestone_available?
- return true if milestone_id.blank?
-
project_id == milestone&.project_id || project.ancestors_upto.compact.include?(milestone&.group)
end
diff --git a/app/models/packages/package.rb b/app/models/packages/package.rb
index 08e9f06a6a1..e510432be8f 100644
--- a/app/models/packages/package.rb
+++ b/app/models/packages/package.rb
@@ -138,7 +138,7 @@ class Packages::Package < ApplicationRecord
after_commit :update_composer_cache, on: :destroy, if: -> { composer? }
def self.for_projects(projects)
- unless Feature.enabled?(:maven_packages_group_level_improvements)
+ unless Feature.enabled?(:maven_packages_group_level_improvements, default_enabled: :yaml)
return none unless projects.any?
end
diff --git a/app/services/issuable/bulk_update_service.rb b/app/services/issuable/bulk_update_service.rb
index 13e289716ef..d3d543edcd7 100644
--- a/app/services/issuable/bulk_update_service.rb
+++ b/app/services/issuable/bulk_update_service.rb
@@ -15,7 +15,7 @@ module Issuable
set_update_params(type)
items = update_issuables(type, ids)
- response_success(payload: { count: items.size })
+ response_success(payload: { count: items.count })
rescue ArgumentError => e
response_error(e.message, 422)
end
@@ -59,17 +59,10 @@ module Issuable
def find_issuables(parent, model_class, ids)
if parent.is_a?(Project)
- projects = parent
+ model_class.id_in(ids).of_projects(parent)
elsif parent.is_a?(Group)
- projects = parent.all_projects
- else
- return
+ model_class.id_in(ids).of_projects(parent.all_projects)
end
-
- model_class
- .id_in(ids)
- .of_projects(projects)
- .includes_for_bulk_update
end
def response_success(message: nil, payload: nil)
diff --git a/app/services/merge_requests/base_service.rb b/app/services/merge_requests/base_service.rb
index 0c0b6764019..3a3765355d8 100644
--- a/app/services/merge_requests/base_service.rb
+++ b/app/services/merge_requests/base_service.rb
@@ -143,8 +143,12 @@ module MergeRequests
merge_request, merge_request.project, current_user, old_reviewers)
end
- def create_pipeline_for(merge_request, user)
- MergeRequests::CreatePipelineService.new(project, user).execute(merge_request)
+ def create_pipeline_for(merge_request, user, async: false)
+ if async
+ MergeRequests::CreatePipelineWorker.perform_async(project.id, user.id, merge_request.id)
+ else
+ MergeRequests::CreatePipelineService.new(project, user).execute(merge_request)
+ end
end
def abort_auto_merge(merge_request, reason)
diff --git a/app/services/merge_requests/refresh_service.rb b/app/services/merge_requests/refresh_service.rb
index 0fb16597aff..e04c5168cef 100644
--- a/app/services/merge_requests/refresh_service.rb
+++ b/app/services/merge_requests/refresh_service.rb
@@ -162,9 +162,12 @@ module MergeRequests
end
def refresh_pipelines_on_merge_requests(merge_request)
- create_pipeline_for(merge_request, current_user)
-
- UpdateHeadPipelineForMergeRequestWorker.perform_async(merge_request.id)
+ if Feature.enabled?(:code_review_async_pipeline_creation, project, default_enabled: :yaml)
+ create_pipeline_for(merge_request, current_user, async: true)
+ else
+ create_pipeline_for(merge_request, current_user, async: false)
+ UpdateHeadPipelineForMergeRequestWorker.perform_async(merge_request.id)
+ end
end
def abort_auto_merges(merge_request)
diff --git a/app/views/layouts/_flash.html.haml b/app/views/layouts/_flash.html.haml
index 35fefe40d39..433337602f1 100644
--- a/app/views/layouts/_flash.html.haml
+++ b/app/views/layouts/_flash.html.haml
@@ -1,5 +1,5 @@
-# We currently only support `alert`, `notice`, `success`, 'toast'
-- icons = {'alert' => 'error', 'notice' => 'information-o', 'success' => 'check-circle'};
+- icons = {'alert' => 'error', 'notice' => 'information-o', 'success' => 'check-circle'}
.flash-container.flash-container-page.sticky{ data: { qa_selector: 'flash_container' } }
- flash.each do |key, value|
- if key == 'toast' && value
diff --git a/app/views/shared/blob/_markdown_buttons.html.haml b/app/views/shared/blob/_markdown_buttons.html.haml
index 085206714c6..73f3d2a8fcd 100644
--- a/app/views/shared/blob/_markdown_buttons.html.haml
+++ b/app/views/shared/blob/_markdown_buttons.html.haml
@@ -1,4 +1,4 @@
-- modifier_key = client_js_flags[:isMac] ? '⌘' : s_('KeyboardKey|Ctrl+');
+- modifier_key = client_js_flags[:isMac] ? '⌘' : s_('KeyboardKey|Ctrl+')
.md-header-toolbar.active
= markdown_toolbar_button({ icon: "bold",
diff --git a/app/workers/all_queues.yml b/app/workers/all_queues.yml
index ef7b5eb026e..f14497509e1 100644
--- a/app/workers/all_queues.yml
+++ b/app/workers/all_queues.yml
@@ -1227,6 +1227,14 @@
:weight: 4
:idempotent:
:tags: []
+- :name: pipeline_creation:merge_requests_create_pipeline
+ :feature_category: :continuous_integration
+ :has_external_dependencies:
+ :urgency: :high
+ :resource_boundary: :cpu
+ :weight: 4
+ :idempotent: true
+ :tags: []
- :name: pipeline_creation:run_pipeline_schedule
:feature_category: :continuous_integration
:has_external_dependencies:
diff --git a/app/workers/merge_requests/create_pipeline_worker.rb b/app/workers/merge_requests/create_pipeline_worker.rb
new file mode 100644
index 00000000000..244ba1af300
--- /dev/null
+++ b/app/workers/merge_requests/create_pipeline_worker.rb
@@ -0,0 +1,28 @@
+# frozen_string_literal: true
+
+module MergeRequests
+ class CreatePipelineWorker
+ include ApplicationWorker
+ include PipelineQueue
+
+ queue_namespace :pipeline_creation
+ feature_category :continuous_integration
+ urgency :high
+ worker_resource_boundary :cpu
+ idempotent!
+
+ def perform(project_id, user_id, merge_request_id)
+ project = Project.find_by_id(project_id)
+ return unless project
+
+ user = User.find_by_id(user_id)
+ return unless user
+
+ merge_request = MergeRequest.find_by_id(merge_request_id)
+ return unless merge_request
+
+ MergeRequests::CreatePipelineService.new(project, user).execute(merge_request)
+ merge_request.update_head_pipeline
+ end
+ end
+end
diff --git a/changelogs/unreleased/21068-optimize-issueable-updates.yml b/changelogs/unreleased/21068-optimize-issueable-updates.yml
deleted file mode 100644
index 214fd3fe0ab..00000000000
--- a/changelogs/unreleased/21068-optimize-issueable-updates.yml
+++ /dev/null
@@ -1,5 +0,0 @@
----
-title: Optimize issuable updates
-merge_request: 58114
-author:
-type: performance
diff --git a/changelogs/unreleased/220680-update-gatsby-project-template.yml b/changelogs/unreleased/220680-update-gatsby-project-template.yml
new file mode 100644
index 00000000000..d3bbe24b992
--- /dev/null
+++ b/changelogs/unreleased/220680-update-gatsby-project-template.yml
@@ -0,0 +1,5 @@
+---
+title: Update gatsby project template to address the pipeline failure
+merge_request: 37410
+author: Takuya Noguchi
+type: fixed
diff --git a/changelogs/unreleased/326099-enabled-by-default.yml b/changelogs/unreleased/326099-enabled-by-default.yml
new file mode 100644
index 00000000000..e73620bfc76
--- /dev/null
+++ b/changelogs/unreleased/326099-enabled-by-default.yml
@@ -0,0 +1,5 @@
+---
+title: Reduce the number of SQL queries executed on Maven file API endpoints
+merge_request: 59136
+author:
+type: performance
diff --git a/changelogs/unreleased/327064-fix-revert-query.yml b/changelogs/unreleased/327064-fix-revert-query.yml
new file mode 100644
index 00000000000..0235c022a1c
--- /dev/null
+++ b/changelogs/unreleased/327064-fix-revert-query.yml
@@ -0,0 +1,5 @@
+---
+title: Fix revert commit query
+merge_request: 59356
+author:
+type: fixed
diff --git a/changelogs/unreleased/cngo-add-aria-labels-to-icon-only-buttons-3.yml b/changelogs/unreleased/cngo-add-aria-labels-to-icon-only-buttons-3.yml
new file mode 100644
index 00000000000..8e72b9c9d7c
--- /dev/null
+++ b/changelogs/unreleased/cngo-add-aria-labels-to-icon-only-buttons-3.yml
@@ -0,0 +1,5 @@
+---
+title: Add aria labels to icon-only buttons
+merge_request: 59037
+author:
+type: fixed
diff --git a/changelogs/unreleased/move_pipeline_creation_async.yml b/changelogs/unreleased/move_pipeline_creation_async.yml
new file mode 100644
index 00000000000..2017a518f29
--- /dev/null
+++ b/changelogs/unreleased/move_pipeline_creation_async.yml
@@ -0,0 +1,5 @@
+---
+title: Create the pipelines asynchronously when refreshing merge requests
+merge_request: 58542
+author:
+type: performance
diff --git a/config/feature_flags/development/code_review_async_pipeline_creation.yml b/config/feature_flags/development/code_review_async_pipeline_creation.yml
new file mode 100644
index 00000000000..d0e5a3286aa
--- /dev/null
+++ b/config/feature_flags/development/code_review_async_pipeline_creation.yml
@@ -0,0 +1,8 @@
+---
+name: code_review_async_pipeline_creation
+introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/58542
+rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/327559
+milestone: '13.11'
+type: development
+group: group::code review
+default_enabled: false
diff --git a/config/feature_flags/development/maven_packages_group_level_improvements.yml b/config/feature_flags/development/maven_packages_group_level_improvements.yml
index 6b8a8ac5b11..8dfd5ab0f8b 100644
--- a/config/feature_flags/development/maven_packages_group_level_improvements.yml
+++ b/config/feature_flags/development/maven_packages_group_level_improvements.yml
@@ -5,4 +5,4 @@ rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/326099
milestone: '13.11'
type: development
group: group::package
-default_enabled: false
+default_enabled: true
diff --git a/config/feature_flags/development/packages_finder_helper_deploy_token.yml b/config/feature_flags/development/packages_finder_helper_deploy_token.yml
new file mode 100644
index 00000000000..fcc73cafd64
--- /dev/null
+++ b/config/feature_flags/development/packages_finder_helper_deploy_token.yml
@@ -0,0 +1,8 @@
+---
+name: packages_finder_helper_deploy_token
+introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/58497
+rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/326808
+milestone: '13.11'
+type: development
+group: group::package
+default_enabled: false
diff --git a/doc/update/index.md b/doc/update/index.md
index 5b62e0642c8..75bc1ef62f6 100644
--- a/doc/update/index.md
+++ b/doc/update/index.md
@@ -177,7 +177,7 @@ Find where your version sits in the upgrade path below, and upgrade GitLab
accordingly, while also consulting the
[version-specific upgrade instructions](#version-specific-upgrading-instructions):
-`8.11.Z` -> `8.12.0` -> `8.17.7` -> `9.5.10` -> `10.8.7` -> `11.11.8` -> `12.0.12` -> `12.1.17` -> `12.10.14` -> `13.0.14` -> `13.1.11` -> `13.5.4` - > [latest `13.Y.Z`](https://about.gitlab.com/releases/categories/releases/)
+`8.11.Z` -> `8.12.0` -> `8.17.7` -> `9.5.10` -> `10.8.7` -> `11.11.8` -> `12.0.12` -> `12.1.17` -> `12.10.14` -> `13.0.14` -> `13.1.11` -> [latest `13.Y.Z`](https://about.gitlab.com/releases/categories/releases/)
The following table, while not exhaustive, shows some examples of the supported
upgrade paths.
diff --git a/lib/api/maven_packages.rb b/lib/api/maven_packages.rb
index 5d255c309f7..879f1ea5d50 100644
--- a/lib/api/maven_packages.rb
+++ b/lib/api/maven_packages.rb
@@ -80,7 +80,7 @@ module API
def fetch_package(file_name:, project: nil, group: nil)
order_by_package_file = false
- if Feature.enabled?(:maven_packages_group_level_improvements)
+ if Feature.enabled?(:maven_packages_group_level_improvements, default_enabled: :yaml)
order_by_package_file = file_name.include?(::Packages::Maven::Metadata.filename) &&
!params[:path].include?(::Packages::Maven::FindOrCreatePackageService::SNAPSHOT_TERM)
end
diff --git a/spec/factories/services.rb b/spec/factories/services.rb
index 7b9d7bfb3e0..25ef75880bb 100644
--- a/spec/factories/services.rb
+++ b/spec/factories/services.rb
@@ -62,6 +62,7 @@ FactoryBot.define do
project_key { nil }
vulnerabilities_enabled { false }
vulnerabilities_issuetype { nil }
+ deployment_type { 'cloud' }
end
before(:create) do |service, evaluator|
@@ -72,7 +73,7 @@ FactoryBot.define do
jira_issue_transition_id: evaluator.jira_issue_transition_id,
username: evaluator.username, password: evaluator.password, issues_enabled: evaluator.issues_enabled,
project_key: evaluator.project_key, vulnerabilities_enabled: evaluator.vulnerabilities_enabled,
- vulnerabilities_issuetype: evaluator.vulnerabilities_issuetype
+ vulnerabilities_issuetype: evaluator.vulnerabilities_issuetype, deployment_type: evaluator.deployment_type
)
end
end
diff --git a/spec/finders/concerns/packages/finder_helper_spec.rb b/spec/finders/concerns/packages/finder_helper_spec.rb
index 73f77647573..c1740ee1796 100644
--- a/spec/finders/concerns/packages/finder_helper_spec.rb
+++ b/spec/finders/concerns/packages/finder_helper_spec.rb
@@ -6,7 +6,6 @@ RSpec.describe ::Packages::FinderHelper do
describe '#packages_visible_to_user' do
using RSpec::Parameterized::TableSyntax
- let_it_be(:user) { create(:user) }
let_it_be_with_reload(:group) { create(:group) }
let_it_be_with_reload(:project1) { create(:project, namespace: group) }
let_it_be(:package1) { create(:package, project: project1) }
@@ -44,41 +43,87 @@ RSpec.describe ::Packages::FinderHelper do
it { is_expected.to be_empty }
end
- where(:group_visibility, :subgroup_visibility, :project2_visibility, :user_role, :shared_example_name) do
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :maintainer | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :developer | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :guest | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :anonymous | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :maintainer | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :developer | 'returning both packages'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :guest | 'returning package1'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :anonymous | 'returning package1'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both packages'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both packages'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning package1'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning package1'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both packages'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both packages'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning no packages'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning no packages'
+ context 'with a user' do
+ let_it_be(:user) { create(:user) }
+
+ where(:group_visibility, :subgroup_visibility, :project2_visibility, :user_role, :shared_example_name) do
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :maintainer | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :developer | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :guest | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :anonymous | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :maintainer | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :developer | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :guest | 'returning package1'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :anonymous | 'returning package1'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both packages'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both packages'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning package1'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning package1'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both packages'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both packages'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning no packages'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning no packages'
+ end
+
+ with_them do
+ before do
+ unless user_role == :anonymous
+ group.send("add_#{user_role}", user)
+ subgroup.send("add_#{user_role}", user)
+ project1.send("add_#{user_role}", user)
+ project2.send("add_#{user_role}", user)
+ end
+
+ project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
+ subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
+ project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ end
+
+ it_behaves_like params[:shared_example_name]
+ end
end
- with_them do
- before do
- unless user_role == :anonymous
- group.send("add_#{user_role}", user)
- subgroup.send("add_#{user_role}", user)
- project1.send("add_#{user_role}", user)
- project2.send("add_#{user_role}", user)
+ context 'with a group deploy token' do
+ let_it_be(:user) { create(:deploy_token, :group, read_package_registry: true) }
+ let_it_be(:group_deploy_token) { create(:group_deploy_token, deploy_token: user, group: group) }
+
+ shared_examples 'handling all conditions' do
+ where(:group_visibility, :subgroup_visibility, :project2_visibility, :shared_example_name) do
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | 'returning both packages'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | 'returning both packages'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | 'returning both packages'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | 'returning both packages'
+ end
+
+ with_them do
+ before do
+ project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
+ subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
+ project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ end
+
+ it_behaves_like params[:shared_example_name]
+ end
+ end
+
+ context 'with packages_finder_helper_deploy_token enabled' do
+ before do
+ expect(group).not_to receive(:all_projects)
end
- project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
- subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
- project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
- group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ it_behaves_like 'handling all conditions'
end
- it_behaves_like params[:shared_example_name]
+ context 'with packages_finder_helper_deploy_token disabled' do
+ before do
+ stub_feature_flags(packages_finder_helper_deploy_token: false)
+ expect(group).to receive(:all_projects).and_call_original
+ end
+
+ it_behaves_like 'handling all conditions'
+ end
end
end
@@ -121,41 +166,87 @@ RSpec.describe ::Packages::FinderHelper do
it { is_expected.to be_empty }
end
- where(:group_visibility, :subgroup_visibility, :project2_visibility, :user_role, :shared_example_name) do
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :maintainer | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :developer | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :guest | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :anonymous | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :maintainer | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :developer | 'returning both projects'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :guest | 'returning project1'
- 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :anonymous | 'returning project1'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both projects'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both projects'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning project1'
- 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning project1'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both projects'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both projects'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning no project'
- 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning no project'
+ context 'with a user' do
+ let_it_be(:user) { create(:user) }
+
+ where(:group_visibility, :subgroup_visibility, :project2_visibility, :user_role, :shared_example_name) do
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :maintainer | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :developer | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :guest | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | :anonymous | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :maintainer | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :developer | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :guest | 'returning project1'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | :anonymous | 'returning project1'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both projects'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both projects'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning project1'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning project1'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :maintainer | 'returning both projects'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :developer | 'returning both projects'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :guest | 'returning no project'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | :anonymous | 'returning no project'
+ end
+
+ with_them do
+ before do
+ unless user_role == :anonymous
+ group.send("add_#{user_role}", user)
+ subgroup.send("add_#{user_role}", user)
+ project1.send("add_#{user_role}", user)
+ project2.send("add_#{user_role}", user)
+ end
+
+ project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
+ subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
+ project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ end
+
+ it_behaves_like params[:shared_example_name]
+ end
end
- with_them do
- before do
- unless user_role == :anonymous
- group.send("add_#{user_role}", user)
- subgroup.send("add_#{user_role}", user)
- project1.send("add_#{user_role}", user)
- project2.send("add_#{user_role}", user)
+ context 'with a group deploy token' do
+ let_it_be(:user) { create(:deploy_token, :group, read_package_registry: true) }
+ let_it_be(:group_deploy_token) { create(:group_deploy_token, deploy_token: user, group: group) }
+
+ shared_examples 'handling all conditions' do
+ where(:group_visibility, :subgroup_visibility, :project2_visibility, :shared_example_name) do
+ 'PUBLIC' | 'PUBLIC' | 'PUBLIC' | 'returning both projects'
+ 'PUBLIC' | 'PUBLIC' | 'PRIVATE' | 'returning both projects'
+ 'PUBLIC' | 'PRIVATE' | 'PRIVATE' | 'returning both projects'
+ 'PRIVATE' | 'PRIVATE' | 'PRIVATE' | 'returning both projects'
end
- project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
- subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
- project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
- group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ with_them do
+ before do
+ project2.update!(visibility_level: Gitlab::VisibilityLevel.const_get(project2_visibility, false))
+ subgroup.update!(visibility_level: Gitlab::VisibilityLevel.const_get(subgroup_visibility, false))
+ project1.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ group.update!(visibility_level: Gitlab::VisibilityLevel.const_get(group_visibility, false))
+ end
+
+ it_behaves_like params[:shared_example_name]
+ end
end
- it_behaves_like params[:shared_example_name]
+ context 'with packages_finder_helper_deploy_token enabled' do
+ before do
+ expect(group).not_to receive(:all_projects)
+ end
+
+ it_behaves_like 'handling all conditions'
+ end
+
+ context 'with packages_finder_helper_deploy_token disabled' do
+ before do
+ stub_feature_flags(packages_finder_helper_deploy_token: false)
+ expect(group).to receive(:all_projects).and_call_original
+ end
+
+ it_behaves_like 'handling all conditions'
+ end
end
end
end
diff --git a/spec/frontend/vue_shared/components/help_popover_spec.js b/spec/frontend/vue_shared/components/help_popover_spec.js
index cf5428ba4c3..30c6fa04032 100644
--- a/spec/frontend/vue_shared/components/help_popover_spec.js
+++ b/spec/frontend/vue_shared/components/help_popover_spec.js
@@ -34,7 +34,6 @@ describe('HelpPopover', () => {
icon: 'question',
variant: 'link',
});
- expect(findQuestionButton().attributes().tabindex).toBe('0');
});
it('renders popover that uses the question button as target', () => {
diff --git a/spec/models/concerns/issuable_spec.rb b/spec/models/concerns/issuable_spec.rb
index 14db9b530db..1df70f38707 100644
--- a/spec/models/concerns/issuable_spec.rb
+++ b/spec/models/concerns/issuable_spec.rb
@@ -65,23 +65,6 @@ RSpec.describe Issuable do
it { expect(issuable_class).to respond_to(:opened) }
it { expect(issuable_class).to respond_to(:closed) }
it { expect(issuable_class).to respond_to(:assigned) }
-
- describe '.includes_for_bulk_update' do
- before do
- stub_const('Example', Class.new(ActiveRecord::Base))
-
- Example.class_eval do
- include Issuable # adds :labels and :metrics, among others
-
- belongs_to :author
- has_many :assignees
- end
- end
-
- it 'includes available associations' do
- expect(Example.includes_for_bulk_update.includes_values).to eq([:author, :assignees, :labels, :metrics])
- end
- end
end
describe 'author_name' do
diff --git a/spec/models/concerns/milestoneable_spec.rb b/spec/models/concerns/milestoneable_spec.rb
index 961eac4710d..5fb3b39f734 100644
--- a/spec/models/concerns/milestoneable_spec.rb
+++ b/spec/models/concerns/milestoneable_spec.rb
@@ -50,13 +50,13 @@ RSpec.describe Milestoneable do
it 'returns true with a milestone from the issue project' do
milestone = create(:milestone, project: project)
- expect(build_milestoneable(milestone.id).milestone_available?).to be(true)
+ expect(build_milestoneable(milestone.id).milestone_available?).to be_truthy
end
it 'returns true with a milestone from the issue project group' do
milestone = create(:milestone, group: group)
- expect(build_milestoneable(milestone.id).milestone_available?).to be(true)
+ expect(build_milestoneable(milestone.id).milestone_available?).to be_truthy
end
it 'returns true with a milestone from the the parent of the issue project group' do
@@ -64,23 +64,19 @@ RSpec.describe Milestoneable do
group.update!(parent: parent)
milestone = create(:milestone, group: parent)
- expect(build_milestoneable(milestone.id).milestone_available?).to be(true)
- end
-
- it 'returns true with a blank milestone' do
- expect(build_milestoneable('').milestone_available?).to be(true)
+ expect(build_milestoneable(milestone.id).milestone_available?).to be_truthy
end
it 'returns false with a milestone from another project' do
milestone = create(:milestone)
- expect(build_milestoneable(milestone.id).milestone_available?).to be(false)
+ expect(build_milestoneable(milestone.id).milestone_available?).to be_falsey
end
it 'returns false with a milestone from another group' do
milestone = create(:milestone, group: create(:group))
- expect(build_milestoneable(milestone.id).milestone_available?).to be(false)
+ expect(build_milestoneable(milestone.id).milestone_available?).to be_falsey
end
end
end
diff --git a/spec/requests/api/maven_packages_spec.rb b/spec/requests/api/maven_packages_spec.rb
index 93310d3e90f..07c00a338f6 100644
--- a/spec/requests/api/maven_packages_spec.rb
+++ b/spec/requests/api/maven_packages_spec.rb
@@ -387,7 +387,7 @@ RSpec.describe API::MavenPackages do
subject
- status = Feature.enabled?(:maven_packages_group_level_improvements) ? :not_found : :forbidden
+ status = Feature.enabled?(:maven_packages_group_level_improvements, default_enabled: :yaml) ? :not_found : :forbidden
expect(response).to have_gitlab_http_status(status)
end
diff --git a/spec/services/merge_requests/refresh_service_spec.rb b/spec/services/merge_requests/refresh_service_spec.rb
index 2abe7a23bfe..f9b76db877b 100644
--- a/spec/services/merge_requests/refresh_service_spec.rb
+++ b/spec/services/merge_requests/refresh_service_spec.rb
@@ -198,7 +198,7 @@ RSpec.describe MergeRequests::RefreshService do
end
end
- describe 'Pipelines for merge requests' do
+ shared_examples 'Pipelines for merge requests' do
before do
stub_ci_pipeline_yaml_file(config)
end
@@ -256,7 +256,7 @@ RSpec.describe MergeRequests::RefreshService do
stub_feature_flags(ci_disallow_to_create_merge_request_pipelines_in_target_project: false)
end
- it 'creates detached merge request pipeline for fork merge request', :sidekiq_inline do
+ it 'creates detached merge request pipeline for fork merge request' do
expect { subject }
.to change { @fork_merge_request.pipelines_for_merge_request.count }.by(1)
@@ -364,6 +364,18 @@ RSpec.describe MergeRequests::RefreshService do
end
end
+ context 'when the code_review_async_pipeline_creation feature flag is on', :sidekiq_inline do
+ it_behaves_like 'Pipelines for merge requests'
+ end
+
+ context 'when the code_review_async_pipeline_creation feature flag is off', :sidekiq_inline do
+ before do
+ stub_feature_flags(code_review_async_pipeline_creation: false)
+ end
+
+ it_behaves_like 'Pipelines for merge requests'
+ end
+
context 'push to origin repo source branch' do
let(:refresh_service) { service.new(@project, @user) }
let(:notification_service) { spy('notification_service') }
diff --git a/spec/workers/merge_requests/create_pipeline_worker_spec.rb b/spec/workers/merge_requests/create_pipeline_worker_spec.rb
new file mode 100644
index 00000000000..8efce5220be
--- /dev/null
+++ b/spec/workers/merge_requests/create_pipeline_worker_spec.rb
@@ -0,0 +1,61 @@
+# frozen_string_literal: true
+
+require 'spec_helper'
+
+RSpec.describe MergeRequests::CreatePipelineWorker do
+ subject(:worker) { described_class.new }
+
+ describe '#perform' do
+ let(:user) { create(:user) }
+ let(:project) { create(:project) }
+ let(:merge_request) { create(:merge_request) }
+
+ context 'when the objects exist' do
+ it 'calls the merge request create pipeline service and calls update head pipeline' do
+ aggregate_failures do
+ expect_next_instance_of(MergeRequests::CreatePipelineService, project, user) do |service|
+ expect(service).to receive(:execute).with(merge_request)
+ end
+
+ expect(MergeRequest).to receive(:find_by_id).with(merge_request.id).and_return(merge_request)
+ expect(merge_request).to receive(:update_head_pipeline)
+
+ subject.perform(project.id, user.id, merge_request.id)
+ end
+ end
+ end
+
+ shared_examples 'when object does not exist' do
+ it 'does not call the create pipeline service' do
+ expect(MergeRequests::CreatePipelineService).not_to receive(:new)
+
+ expect { subject.perform(project.id, user.id, merge_request.id) }
+ .not_to raise_exception
+ end
+ end
+
+ context 'when the project does not exist' do
+ before do
+ project.destroy!
+ end
+
+ it_behaves_like 'when object does not exist'
+ end
+
+ context 'when the user does not exist' do
+ before do
+ user.destroy!
+ end
+
+ it_behaves_like 'when object does not exist'
+ end
+
+ context 'when the merge request does not exist' do
+ before do
+ merge_request.destroy!
+ end
+
+ it_behaves_like 'when object does not exist'
+ end
+ end
+end
diff --git a/vendor/project_templates/gatsby.tar.gz b/vendor/project_templates/gatsby.tar.gz
index a4ae5f99047..52bb056630e 100644
--- a/vendor/project_templates/gatsby.tar.gz
+++ b/vendor/project_templates/gatsby.tar.gz
Binary files differ