Add latest changes from gitlab-org/gitlab@master

This commit is contained in:
GitLab Bot 2025-04-01 18:12:45 +00:00
parent 3a045e1e08
commit 1d5ba345b1
98 changed files with 1330 additions and 355 deletions

View File

@ -278,17 +278,6 @@ export default {
'app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue',
'app/assets/javascripts/vue_merge_request_widget/widgets/accessibility/index.vue',
'app/assets/javascripts/vue_merge_request_widget/widgets/code_quality/index.vue',
'app/assets/javascripts/vue_shared/components/awards_list.vue',
'app/assets/javascripts/vue_shared/components/badges/beta_badge.vue',
'app/assets/javascripts/vue_shared/components/color_select_dropdown/dropdown_contents.vue',
'app/assets/javascripts/vue_shared/components/crud_component.vue',
'app/assets/javascripts/vue_shared/components/customizable_dashboard/customizable_dashboard.vue',
'app/assets/javascripts/vue_shared/components/diff_viewer/viewers/image_diff/swipe_viewer.vue',
'app/assets/javascripts/vue_shared/components/dropdown/dropdown_widget/dropdown_widget.vue',
'app/assets/javascripts/vue_shared/components/entity_select/entity_select.vue',
'app/assets/javascripts/vue_shared/components/filtered_search_bar/filtered_search_bar_root.vue',
'app/assets/javascripts/vue_shared/components/groups_list/group_list_item_prevent_delete_modal.vue',
'app/assets/javascripts/vue_shared/components/list_selector/index.vue',
'app/assets/javascripts/vue_shared/components/markdown_drawer/markdown_drawer.vue',
'app/assets/javascripts/vue_shared/components/mr_more_dropdown.vue',
'app/assets/javascripts/vue_shared/components/new_resource_dropdown/new_resource_dropdown.vue',
@ -358,7 +347,6 @@ export default {
'ee/app/assets/javascripts/approvals/mr_edit/app.vue',
'ee/app/assets/javascripts/approvals/project_settings/project_rules.vue',
'ee/app/assets/javascripts/audit_events/components/stream/stream_delete_modal.vue',
'ee/app/assets/javascripts/audit_events/components/stream/stream_destination_editor.vue',
'ee/app/assets/javascripts/billings/components/zuora_simple.vue',
'ee/app/assets/javascripts/billings/subscriptions/components/subscription_table.vue',
'ee/app/assets/javascripts/boards/components/board_form.vue',
@ -532,10 +520,9 @@ export default {
'ee/app/assets/javascripts/work_items/components/work_item_change_type_modal.vue',
'ee/app/assets/javascripts/work_items/components/work_item_custom_fields_multi_select.vue',
'ee/app/assets/javascripts/work_items/components/work_item_custom_fields_single_select.vue',
'ee/app/assets/javascripts/work_items/components/work_item_development/work_item_development_ff_item.vue',
'ee/app/assets/javascripts/work_items/components/work_item_health_status.vue',
'ee/app/assets/javascripts/work_items/components/work_item_iteration.vue',
'ee/app/assets/javascripts/work_items/components/work_item_links/work_item_rolled_up_health_status.vue'
'ee/app/assets/javascripts/work_items/components/work_item_links/work_item_rolled_up_health_status.vue',
],
rules: {
'vue/no-unused-properties': 'off',

View File

@ -1182,6 +1182,8 @@ Search/NamespacedClass:
- 'lib/gitlab/usage/metrics/instrumentations/**/*.rb'
- 'ee/lib/gitlab/usage/metrics/instrumentations/**/*.rb'
- 'lib/gitlab/sidekiq_middleware/pause_control/strategies/zoekt.rb'
- 'lib/tasks/**/*.rake'
- 'ee/lib/tasks/**/*.rake'
SidekiqLoadBalancing/WorkerDataConsistency:
Enabled: true
@ -1257,6 +1259,12 @@ Gitlab/TokenWithoutPrefix:
- 'ee/app/**/*'
- 'ee/lib/**/*'
Rake/TopLevelMethodDefinition:
Enabled: true
Include:
- 'lib/tasks/**/*.rake'
- 'ee/lib/tasks/**/*.rake'
Rails/StrongParams:
Enabled: true
SafeAutoCorrect: false

View File

@ -0,0 +1,49 @@
---
Rake/TopLevelMethodDefinition:
Details: grace period
Exclude:
- 'ee/lib/tasks/cloud_connector/keys.rake'
- 'ee/lib/tasks/duo_pro/bulk_user_assignment.rake'
- 'ee/lib/tasks/geo.rake'
- 'ee/lib/tasks/gitlab/duo_chat/completions.rake'
- 'ee/lib/tasks/gitlab/duo_chat/seed_failed_ci_jobs.rake'
- 'ee/lib/tasks/gitlab/elastic/test.rake'
- 'ee/lib/tasks/gitlab/license.rake'
- 'ee/lib/tasks/gitlab/seed/insights.rake'
- 'ee/lib/tasks/gitlab/seed/merge_trains/seed_project.rake'
- 'lib/tasks/bundler.rake'
- 'lib/tasks/config_lint.rake'
- 'lib/tasks/gems.rake'
- 'lib/tasks/gettext.rake'
- 'lib/tasks/gitlab/assets.rake'
- 'lib/tasks/gitlab/background_migrations.rake'
- 'lib/tasks/gitlab/backup.rake'
- 'lib/tasks/gitlab/cleanup.rake'
- 'lib/tasks/gitlab/click_house/migration.rake'
- 'lib/tasks/gitlab/container_registry.rake'
- 'lib/tasks/gitlab/dast_variables.rake'
- 'lib/tasks/gitlab/db.rake'
- 'lib/tasks/gitlab/db/validate_config.rake'
- 'lib/tasks/gitlab/docs/compile_windows.rake'
- 'lib/tasks/gitlab/feature_categories.rake'
- 'lib/tasks/gitlab/gitaly.rake'
- 'lib/tasks/gitlab/graphql.rake'
- 'lib/tasks/gitlab/keep_around.rake'
- 'lib/tasks/gitlab/populate_job_traces.rake'
- 'lib/tasks/gitlab/praefect.rake'
- 'lib/tasks/gitlab/seed.rake'
- 'lib/tasks/gitlab/seed/group_seed.rake'
- 'lib/tasks/gitlab/setup.rake'
- 'lib/tasks/gitlab/shell.rake'
- 'lib/tasks/gitlab/sidekiq.rake'
- 'lib/tasks/gitlab/snippets.rake'
- 'lib/tasks/gitlab/tw/codeowners.rake'
- 'lib/tasks/gitlab/two_factor.rake'
- 'lib/tasks/gitlab/update_templates.rake'
- 'lib/tasks/gitlab/web_hook.rake'
- 'lib/tasks/gitlab/x509/update.rake'
- 'lib/tasks/grape.rake'
- 'lib/tasks/rubocop.rake'
- 'lib/tasks/spec.rake'
- 'lib/tasks/tanuki_emoji.rake'
- 'lib/tasks/tokens.rake'

View File

@ -118,9 +118,9 @@ export default {
v-if="state !== $options.REGISTRATION_TOKEN_HIDDEN"
ref="runnerRegistrationDropdown"
:toggle-text="actionText"
toggle-class="!gl-px-3"
variant="default"
category="tertiary"
size="small"
v-bind="$attrs"
icon="ellipsis_v"
text-sr-only

View File

@ -11,6 +11,7 @@ import { OPERATORS_IS } from '~/vue_shared/components/filtered_search_bar/consta
import { ACCESS_LEVEL_OWNER_INTEGER } from '~/access_level/constants';
import projectCountsQuery from '~/projects/your_work/graphql/queries/project_counts.query.graphql';
import * as Sentry from '~/sentry/sentry_browser_wrapper';
import { InternalEvents } from '~/tracking';
import {
FILTERED_SEARCH_TOKEN_LANGUAGE,
FILTERED_SEARCH_TOKEN_MIN_ACCESS_LEVEL,
@ -20,6 +21,8 @@ import {
import userPreferencesUpdateMutation from '../graphql/mutations/user_preferences_update.mutation.graphql';
import TabView from './tab_view.vue';
const trackingMixin = InternalEvents.mixin();
// Will be made more generic to work with groups and projects in future commits
export default {
name: 'TabsWithList',
@ -33,6 +36,7 @@ export default {
TabView,
FilteredSearchAndSort,
},
mixins: [trackingMixin],
props: {
tabs: {
type: Array,
@ -87,6 +91,13 @@ export default {
return [];
},
},
eventTracking: {
type: Object,
required: false,
default() {
return {};
},
},
},
data() {
return {
@ -126,6 +137,9 @@ export default {
},
},
computed: {
activeTab() {
return this.tabs[this.activeTabIndex];
},
filteredSearchTokens() {
return [
{
@ -245,6 +259,12 @@ export default {
const tab = this.tabs[index] || this.tabs[0];
this.$router.push({ name: tab.value });
if (!this.eventTracking?.tabs) {
return;
}
this.trackEvent(this.eventTracking.tabs, { label: tab.text });
},
tabCount(tab) {
return this.counts[tab.value];
@ -265,16 +285,80 @@ export default {
updateSort(sort) {
this.pushQuery({ ...this.routeQueryWithoutPagination, sort });
this.userPreferencesUpdateMutate(sort);
if (!this.eventTracking?.sort) {
return;
}
this.trackEvent(this.eventTracking.sort, { label: this.activeTab.text, property: sort });
},
onFilter(filters) {
const { sort } = this.$route.query;
this.pushQuery({ sort, ...filters });
if (!this.eventTracking?.filteredSearch) {
return;
}
Object.entries(this.eventTracking.filteredSearch).forEach(([filter, event]) => {
const filterValues = filters[filter];
if (!filterValues) {
return;
}
// Don't record the value when using text search.
// Only record with pre-set values (e.g language or access level).
if (filter === this.filteredSearchTermKey) {
this.trackEvent(event, { label: this.activeTab.text });
return;
}
const filteredSearchToken = this.filteredSearchTokens.find(
(token) => token.type === filter,
);
if (!filteredSearchToken) {
return;
}
const optionTitles = filterValues.flatMap((filterValue) => {
const optionTitle = filteredSearchToken.options.find(
({ value }) => filterValue === value,
)?.title;
if (!optionTitle) {
return [];
}
return [optionTitle];
});
if (!optionTitles.length) {
return;
}
this.trackEvent(event, {
label: this.activeTab.text,
property: optionTitles.join(','),
});
});
},
onPageChange(pagination) {
this.pushQuery(
calculateGraphQLPaginationQueryParams({ ...pagination, routeQuery: this.$route.query }),
);
if (!this.eventTracking?.pagination) {
return;
}
this.trackEvent(this.eventTracking.pagination, {
label: this.activeTab.text,
property: pagination.startCursor === null ? 'next' : 'previous',
});
},
async userPreferencesUpdateMutate(sort) {
try {

View File

@ -85,44 +85,47 @@ export default {
<template>
<div>
<section class="gl-mt-5">
<identity-verification-required-alert
v-if="identityVerificationRequiredError"
:title="$options.i18n.REQUIRES_IDENTITY_VERIFICATION_TEXT"
class="gl-mb-5"
/>
<identity-verification-required-alert
v-if="identityVerificationRequiredError"
:title="$options.i18n.REQUIRES_IDENTITY_VERIFICATION_TEXT"
class="gl-mb-5"
/>
<gl-alert
v-if="genericError"
data-testid="error-alert"
variant="danger"
:dismissible="false"
class="gl-mb-5"
>
{{ errorMessage }}
</gl-alert>
<gl-alert
v-if="genericError"
data-testid="error-alert"
variant="danger"
:dismissible="false"
class="gl-mb-5"
>
{{ errorMessage }}
</gl-alert>
<gl-toggle
ref="sharedRunnersToggle"
:disabled="isDisabledAndUnoverridable"
:is-loading="isLoading"
:label="__('Enable instance runners for this project')"
:value="isSharedRunnerEnabled"
data-testid="toggle-shared-runners"
@change="toggleSharedRunners"
>
<template v-if="isDisabledAndUnoverridable" #help>
{{ s__('Runners|Instance runners are disabled in the group settings.') }}
<gl-sprintf
v-if="isGroupSettingsAvailable"
:message="s__('Runners|Go to %{groupLink} to enable them.')"
>
<template #groupLink>
<gl-link :href="groupSettingsPath">{{ groupName }}</gl-link>
</template>
</gl-sprintf>
</template>
</gl-toggle>
</section>
<gl-toggle
ref="sharedRunnersToggle"
:disabled="isDisabledAndUnoverridable"
:is-loading="isLoading"
label-position="left"
:value="isSharedRunnerEnabled"
data-testid="toggle-shared-runners"
@change="toggleSharedRunners"
>
<template #label>
<span class="gl-text-sm gl-font-normal gl-text-subtle">{{
__('Enable instance runners for this project')
}}</span>
</template>
<template v-if="isDisabledAndUnoverridable" #help>
{{ s__('Runners|Instance runners are disabled in the group settings.') }}
<gl-sprintf
v-if="isGroupSettingsAvailable"
:message="s__('Runners|Go to %{groupLink} to enable them.')"
>
<template #groupLink>
<gl-link :href="groupSettingsPath">{{ groupName }}</gl-link>
</template>
</gl-sprintf>
</template>
</gl-toggle>
</div>
</template>

View File

@ -34,6 +34,16 @@ export default {
[SORT_OPTION_CREATED.value]: TIMESTAMP_TYPE_CREATED_AT,
[SORT_OPTION_UPDATED.value]: TIMESTAMP_TYPE_LAST_ACTIVITY_AT,
},
eventTracking: {
filteredSearch: {
[FILTERED_SEARCH_TERM_KEY]: 'search_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_LANGUAGE]: 'filter_by_language_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_MIN_ACCESS_LEVEL]: 'filter_by_role_on_your_work_projects',
},
pagination: 'click_pagination_on_your_work_projects',
tabs: 'click_tab_on_your_work_projects',
sort: 'click_sort_on_your_work_projects',
},
name: 'YourWorkProjectsApp',
components: {
TabsWithList,
@ -64,5 +74,6 @@ export default {
:first-tab-route-names="$options.FIRST_TAB_ROUTE_NAMES"
:initial-sort="initialSort"
:programming-languages="programmingLanguages"
:event-tracking="$options.eventTracking"
/>
</template>

View File

@ -4,7 +4,6 @@ import { groupBy } from 'lodash';
import SafeHtml from '~/vue_shared/directives/safe_html';
import EmojiPicker from '~/emoji/components/picker.vue';
import { __, sprintf } from '~/locale';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
import { glEmojiTag } from '~/emoji';
import { EMOJI_THUMBS_UP, EMOJI_THUMBS_DOWN } from '~/emoji/constants';
@ -24,7 +23,6 @@ export default {
GlTooltip: GlTooltipDirective,
SafeHtml,
},
mixins: [glFeatureFlagsMixin()],
props: {
awards: {
type: Array,
@ -71,9 +69,6 @@ export default {
...Object.entries(rest).map(([name, list]) => this.createAwardList(name, list)),
];
},
isAuthoredByMe() {
return this.noteAuthorId === this.currentUserId;
},
},
mounted() {
this.virtualScrollerItem = this.$el.closest('.vue-recycle-scroller__item-view');

View File

@ -19,19 +19,6 @@ export default {
listItemNearCompletion: s__('BetaBadge|Have a near complete user experience.'),
listItemTestAgreement: s__('BetaBadge|Are subject to the GitLab Testing Agreement.'),
},
methods: {
target() {
/**
* BVPopover retrieves the target during the `beforeDestroy` hook to deregister attached
* events. Since during `beforeDestroy` refs are `undefined`, it throws a warning in the
* console because we're trying to access the `$el` property of `undefined`. Optional
* chaining is not working in templates, which is why the method is used.
*
* See more on https://gitlab.com/gitlab-org/gitlab/-/merge_requests/49628#note_464803276
*/
return this.$refs.badge?.$el;
},
},
};
</script>

View File

@ -37,7 +37,6 @@ export default {
},
data() {
return {
showDropdownContentsCreateView: false,
localSelectedColor: this.selectedColor,
isDirty: false,
};

View File

@ -160,13 +160,6 @@ export default {
this.isFormVisible = false;
this.$emit('hideForm');
},
toggleForm() {
if (this.isFormVisible) {
this.hideForm();
} else {
this.showForm();
}
},
getLocalStorageKeyName() {
return `crud-collapse-${this.anchorId}`;
},

View File

@ -210,6 +210,7 @@ export default {
this.$emit('save', this.dashboard.slug, this.dashboard);
},
// eslint-disable-next-line vue/no-unused-properties -- confirmDiscardIfChanged() is part of the component's public API.
async confirmDiscardIfChanged() {
// Implicityly confirm if no changes were made
if (!this.changesMade) return true;

View File

@ -35,9 +35,6 @@ export default {
swipeMaxPixelHeight() {
return pixeliseValue(this.swipeMaxHeight);
},
swipeWrapPixelWidth() {
return pixeliseValue(this.swipeWrapWidth);
},
swipeBarPixelPos() {
return pixeliseValue(this.swipeBarPos);
},

View File

@ -97,6 +97,7 @@ export default {
}
return this.selected && option.id && this.selected.id === option.id;
},
// eslint-disable-next-line vue/no-unused-properties -- showDropdown() is part of the component's public API.
showDropdown() {
this.$refs.dropdown.show();
},

View File

@ -85,7 +85,6 @@ export default {
searchString: '',
items: [],
page: 1,
errorMessage: '',
...this.setInitialSelected(),
};
},

View File

@ -108,7 +108,6 @@ export default {
},
data() {
return {
initialRender: true,
recentSearchesPromise: null,
recentSearches: [],
filterValue: this.initialFilterValue,

View File

@ -25,10 +25,6 @@ export default {
type: String,
required: true,
},
group: {
type: Object,
required: true,
},
},
CANCEL_PROPS: {
text: __('Cancel'),

View File

@ -197,7 +197,6 @@ export default {
v-if="group.isLinkedToSubscription"
:visible="isDeleteModalVisible"
:modal-id="modalId"
:group="group"
@change="onModalChange"
/>
<group-list-item-delete-modal

View File

@ -64,11 +64,6 @@ export default {
required: false,
default: null,
},
groupPath: {
type: String,
required: false,
default: null,
},
projectId: {
type: Number,
required: false,
@ -104,7 +99,6 @@ export default {
return {
searchValue: '',
isProjectNamespace: this.isProjectScoped ? 'true' : 'false',
selected: [],
items: [],
isLoading: false,
};

View File

@ -61,7 +61,6 @@ module UserSettings
:pronouns,
:pronunciation,
:public_email,
:role,
:skype,
:timezone,
:twitter,

View File

@ -113,6 +113,19 @@ module NamespacesHelper
def group_usage_quotas_url(group, *args)
Rails.application.routes.url_helpers.group_usage_quotas_url(group.root_ancestor, *args)
end
def permanent_deletion_date_formatted(container_or_date, format: '%F')
date =
if container_or_date.respond_to?(:self_deletion_scheduled_deletion_created_on)
container_or_date.self_deletion_scheduled_deletion_created_on
else
container_or_date
end
return unless date
::Gitlab::CurrentSettings.deletion_adjourned_period.days.since(date).strftime(format)
end
end
NamespacesHelper.prepend_mod_with('NamespacesHelper')

View File

@ -17,3 +17,5 @@ module Emails
end
end
end
Emails::Groups.prepend_mod

View File

@ -19,5 +19,9 @@ module CloudConnector
def expired?
expires_at.past?
end
def refresh_required?
expires_at < 2.days.from_now
end
end
end

View File

@ -4,9 +4,9 @@
= render ::Layouts::PageHeadingComponent.new(_('Projects')) do |c|
- c.with_actions do
= render Pajamas::ButtonComponent.new(href: starred_explore_projects_path, variant: :confirm, category: :tertiary) do
= render Pajamas::ButtonComponent.new(href: starred_explore_projects_path, variant: :confirm, category: :tertiary, button_options: { data: { event_tracking: 'click_explore_projects_on_your_work_projects' } }) do
= _("Explore projects")
- if current_user.can_create_project?
= render Pajamas::ButtonComponent.new(href: new_project_path, variant: :confirm, button_options: { data: { testid: 'new-project-button' } }) do
= render Pajamas::ButtonComponent.new(href: new_project_path, variant: :confirm, button_options: { data: { testid: 'new-project-button', event_tracking: 'click_new_project_on_your_work_projects' } }) do
= _("New project")

View File

@ -1,48 +1,38 @@
- link = link_to _('Runner API'), help_page_path('api/runners.md')
%h4
= _('Group runners')
= render Pajamas::AlertComponent.new(variant: :warning,
dismissible: false,
show_icon: false,
alert_options: { class: 'gl-mb-5' }) do |c|
- c.with_body do
= render ::Layouts::CrudComponent.new(s_('Runners|Group runners'),
icon: 'group',
count: @group_runners_count,
options: { data: { testid: 'group-runners' } }) do |c|
- c.with_description do
- link = link_to _('Runner API'), help_page_path('api/runners.md')
= _('These runners are shared across projects in this group.')
%br
%br
= _('Group runners can be managed with the %{link}.').html_safe % { link: link }
- if @project.group
- c.with_actions do
%br
%br
%div
- if @project.group_runners_enabled?
= link_button_to toggle_group_runners_project_runners_path(@project), method: :post do
= _('Disable group runners')
- if @project.group_runners_enabled?
= render Pajamas::ButtonComponent.new(href: toggle_group_runners_project_runners_path(@project), method: :post, size: :small) do
= _('Disable group runners')
- else
= render Pajamas::ButtonComponent.new(href: toggle_group_runners_project_runners_path(@project), variant: :confirm, category: :secondary, method: :post, size: :small) do
= _('Enable group runners')
%span.gl-text-sm.gl-text-subtle= _('for this project')
- c.with_body do
- if !@project.group
.gl-text-subtle= _('This project does not belong to a group and cannot make use of group runners.')
- elsif @group_runners.empty?
.gl-text-subtle
= _('This group does not have any group runners yet.')
- if can?(current_user, :register_group_runners, @project.group) || can?(current_user, :create_runner, @project.group)
- group_link_start = "<a href='#{group_runners_path(@project.group)}'>".html_safe
- group_link_end = '</a>'.html_safe
= s_("Runners|To register them, go to the %{link_start}group's Runners page%{link_end}.").html_safe % { link_start: group_link_start, link_end: group_link_end }
- else
= link_button_to toggle_group_runners_project_runners_path(@project), method: :post, variant: :confirm, category: :secondary do
= _('Enable group runners')
&nbsp;
= _('for this project')
= _('Ask your group owner to set up a group runner.')
- if !@project.group
= _('This project does not belong to a group and cannot make use of group runners.')
- elsif @group_runners.empty?
= _('This group does not have any group runners yet.')
- if can?(current_user, :register_group_runners, @project.group) || can?(current_user, :create_runner, @project.group)
- group_link_start = "<a href='#{group_runners_path(@project.group)}'>".html_safe
- group_link_end = '</a>'.html_safe
= s_("Runners|To register them, go to the %{link_start}group's Runners page%{link_end}.").html_safe % { link_start: group_link_start, link_end: group_link_end }
- else
= _('Ask your group owner to set up a group runner.')
- else
%div{ data: { testid: 'group-runners' } }
%h5.gl-mt-6.gl-mb-0
= _('Available group runners: %{runners}') % { runners: @group_runners_count }
%ul.bordered-list
= render partial: 'projects/runners/runner', collection: @group_runners, as: :runner
= paginate @group_runners, theme: "gitlab", param_name: "group_runners_page", params: { expand_runners: true, anchor: 'js-runners-settings' }
- else
%h3.gl-heading-5.gl-mt-5.gl-mb-0.gl-px-5
= _('Available group runners: %{runners}') % { runners: @group_runners_count }
%ul.content-list
= render partial: 'projects/runners/runner', collection: @group_runners, as: :runner
= paginate @group_runners, theme: "gitlab", param_name: "group_runners_page", params: { expand_runners: true, anchor: 'js-runners-settings' }

View File

@ -1,11 +1,11 @@
%h4
= s_('Runners|Project runners')
= render Pajamas::AlertComponent.new(dismissible: false, show_icon: false, alert_options: { class: 'gl-mb-5' }) do |c|
- c.with_body do
%p= s_('Runners|These runners are assigned to this project.')
= render ::Layouts::CrudComponent.new(s_('Runners|Project runners'),
icon: 'project',
count: @project_runners.count) do |c|
- c.with_description do
= s_('Runners|These runners are assigned to this project.')
- c.with_actions do
- if can?(current_user, :create_runner, @project)
= render Pajamas::ButtonComponent.new(href: new_project_runner_path(@project), variant: :confirm) do
= render Pajamas::ButtonComponent.new(href: new_project_runner_path(@project), size: :small) do
= s_('Runners|New project runner')
.gl-inline
#js-project-runner-registration-dropdown{ data: {
@ -13,19 +13,21 @@
registration_token: @project.runners_token,
project_id: @project.id
} }
- c.with_body do
- if can?(current_user, :create_runner, @project)
- if @project_runners.any?
%h3.gl-heading-5.gl-mt-5.gl-mb-0.gl-px-5= s_('Runners|Assigned project runners')
%ul.content-list{ data: { testid: 'assigned_project_runners' } }
= render partial: 'projects/runners/runner', collection: @project_runners, as: :runner
= paginate @project_runners, theme: "gitlab", param_name: "project_page", params: { expand_runners: true, anchor: 'js-runners-settings' }
- if @assignable_runners.any?
%h3.gl-heading-5.gl-mt-5.gl-mb-0.gl-px-5= _('Other available runners')
%ul.content-list{ data: { testid: 'available_project_runners' } }
= render partial: 'projects/runners/runner', collection: @assignable_runners, as: :runner
= paginate @assignable_runners, theme: "gitlab", param_name: "specific_page", :params => { :anchor => 'js-runners-settings'}
- else
= _('Please contact an admin to create runners.')
= link_to _('Learn more.'), help_page_path('administration/settings/continuous_integration.md', anchor: 'restrict-runner-registration-by-all-users-in-an-instance'), target: '_blank', rel: 'noopener noreferrer'
%hr
- if @project_runners.any?
%h4.underlined-title= s_('Runners|Assigned project runners')
%ul.bordered-list{ data: { testid: 'assigned_project_runners' } }
= render partial: 'projects/runners/runner', collection: @project_runners, as: :runner
= paginate @project_runners, theme: "gitlab", param_name: "project_page", params: { expand_runners: true, anchor: 'js-runners-settings' }
- if @assignable_runners.any?
%h4.underlined-title= _('Other available runners')
%ul.bordered-list{ data: { testid: 'available_project_runners' } }
= render partial: 'projects/runners/runner', collection: @assignable_runners, as: :runner
= paginate @assignable_runners, theme: "gitlab", param_name: "specific_page", :params => { :anchor => 'js-runners-settings'}
.gl-text-subtle
= s_('Runners|Please contact an admin to create runners.')
= link_to _('Learn more.'), help_page_path('administration/settings/continuous_integration.md', anchor: 'restrict-runner-registration-by-all-users-in-an-instance'), target: '_blank', rel: 'noopener noreferrer'

View File

@ -29,9 +29,9 @@
= render Pajamas::ButtonComponent.new(variant: :default, size: :small, type: :submit) do
= _('Enable for this project')
- if runner.description.present?
%p.gl-my-2
%p.gl-text-subtle.gl-my-0
= runner.description
- if runner.tags.present?
.gl-my-2
.gl-flex.gl-flex-wrap.gl-gap-2.gl-mt-3
- runner.tags.map(&:name).sort.each do |tag|
= gl_badge_tag tag, variant: :info

View File

@ -1,11 +1,7 @@
= render 'shared/runners/runner_description'
- if Feature.enabled?(:vue_project_runners_settings, @project)
#js-project-runners-settings
- else
.row
.col-sm-6
= render 'projects/runners/project_runners'
.col-sm-6
= render 'projects/runners/shared_runners'
= render 'projects/runners/group_runners'
.gl-flex.gl-flex-col.gl-gap-5.gl-mt-5
= render 'projects/runners/project_runners'
= render 'projects/runners/group_runners'
= render 'projects/runners/shared_runners'

View File

@ -1,13 +1,19 @@
= render 'shared/runners/shared_runners_description'
#toggle-shared-runners-form{ data: toggle_shared_runners_settings_data(@project) }
- if @shared_runners_count == 0
= _('This GitLab instance does not provide any instance runners yet. Administrators can register instance runners in the admin area.')
- else
%div{ data: { testid: 'available-shared-runners' } }
%h5.gl-mt-6.gl-mb-0
= s_('Runners|Available instance runners: %{count}') % {count: @shared_runners_count}
%ul.bordered-list
= render partial: 'projects/runners/runner', collection: @shared_runners, as: :runner
= paginate @shared_runners, theme: "gitlab", param_name: "shared_runners_page", params: { expand_runners: true, anchor: 'js-runners-settings' }
= render ::Layouts::CrudComponent.new(s_('Runners|Available instance runners'),
icon: 'users',
count: @shared_runners_count,
options: { data: { testid: 'available-shared-runners' } }) do |c|
- c.with_actions do
#toggle-shared-runners-form{ data: toggle_shared_runners_settings_data(@project) }
- c.with_description do
%span{ data: { testid: 'shared-runners-description' } }
- shared_link_start = '<a href="%{url}" target="_blank" rel="noopener noreferrer">'.html_safe % { url: help_page_path('ci/runners/runners_scope.md', anchor: 'instance-runners') }
= s_('Runners|%{link_start}These runners%{link_end} are available to all groups and projects.').html_safe % { link_start: shared_link_start, link_end: '</a>'.html_safe }
- if Gitlab::CurrentSettings.shared_runners_text.present?
#js-shared-runners-markdown= markdown(Gitlab::CurrentSettings.current_application_settings.shared_runners_text)
- c.with_body do
- if @shared_runners_count == 0
.gl-text-subtle= _('This GitLab instance does not provide any instance runners yet. Administrators can register instance runners in the admin area.')
- else
%ul.content-list
= render partial: 'projects/runners/runner', collection: @shared_runners, as: :runner
= paginate @shared_runners, theme: "gitlab", param_name: "shared_runners_page", params: { expand_runners: true, anchor: 'js-runners-settings' }

View File

@ -1,22 +0,0 @@
.light.gl-mt-3
%p
= s_("Runners|Register as many runners as you want. You can register runners as separate users, on separate servers, and on your local machine.")
%h5
= s_("Runners|How do runners pick up jobs?")
%p
= s_("Runners|Runners are either:")
%div
%ul
%li
= gl_badge_tag s_("Runners|active"), variant: :success
= _('- Available to run jobs.')
%li
= gl_badge_tag s_("Runners|paused"), variant: :danger
= _('- Not available to run jobs.')
%p
= s_("Runners|Tags control which type of jobs a runner can handle. By tagging a runner, you make sure runners only handle the jobs they are equipped to run.")
= link_to _("Learn more."), help_page_path("ci/runners/configure_runners.md", anchor: "how-the-runner-uses-tags"), target: '_blank'

View File

@ -1,12 +0,0 @@
- shared_link_start = '<a href="%{url}" target="_blank" rel="noopener noreferrer">'.html_safe % { url: help_page_path('ci/runners/runners_scope.md', anchor: 'instance-runners') }
%h4
= s_('Runners|Instance runners')
= render Pajamas::AlertComponent.new(dismissible: false,
show_icon: false,
alert_options: { class: 'instance-runners-info gl-mb-5', data: { testid: 'shared-runners-description' } }) do |c|
- c.with_body do
%p= s_('Runners|%{link_start}These runners%{link_end} are available to all groups and projects.').html_safe % { link_start: shared_link_start, link_end: '</a>'.html_safe }
- if Gitlab::CurrentSettings.shared_runners_text.present?
#js-shared-runners-markdown= markdown(Gitlab::CurrentSettings.current_application_settings.shared_runners_text)

View File

@ -0,0 +1,15 @@
---
description: Click Explore projects on Your work > Projects
internal_events: true
action: click_explore_projects_on_your_work_projects
identifiers:
- user
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,15 @@
---
description: Clicks New project on Your work > Projects
internal_events: true
action: click_new_project_on_your_work_projects
identifiers:
- user
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,20 @@
---
description: Uses pagination on Your work > Projects
internal_events: true
action: click_pagination_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
property:
description: Direction
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,20 @@
---
description: Uses sort on Your work > Projects
internal_events: true
action: click_sort_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
property:
description: Sort value
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,18 @@
---
description: User selects tab on Your work > Projects
internal_events: true
action: click_tab_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,20 @@
---
description: Use language filter on Your work > Projects
internal_events: true
action: filter_by_language_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
property:
description: Language
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,20 @@
---
description: Use role filter on Your work > Projects
internal_events: true
action: filter_by_role_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
property:
description: Role
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -0,0 +1,18 @@
---
description: Search on Your work > Projects
internal_events: true
action: search_on_your_work_projects
identifiers:
- user
additional_properties:
label:
description: Tab name (e.g. "Contributed")
product_group: organizations
product_categories:
- groups_and_projects
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
tiers:
- free
- premium
- ultimate

View File

@ -869,7 +869,7 @@ Gitlab.ee do
Settings.cron_jobs['sync_seat_link_worker']['cron'] ||= "#{rand(60)} #{rand(3..4)} * * * UTC"
Settings.cron_jobs['sync_seat_link_worker']['job_class'] = 'SyncSeatLinkWorker'
Settings.cron_jobs['sync_service_token_worker'] ||= {}
Settings.cron_jobs['sync_service_token_worker']['cron'] ||= "#{rand(60)} #{rand(5..6)} * * * UTC"
Settings.cron_jobs['sync_service_token_worker']['cron'] ||= "#{rand(60)} * * * * UTC"
Settings.cron_jobs['sync_service_token_worker']['job_class'] = '::CloudConnector::SyncServiceTokenWorker'
Settings.cron_jobs['users_create_statistics_worker'] ||= {}
Settings.cron_jobs['users_create_statistics_worker']['cron'] ||= '2 15 * * *'

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_click_explore_projects_on_your_work_projects
description: Count of unique users that click Explore projects on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: click_explore_projects_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_click_new_project_on_your_work_projects
description: Count of unique users that click New project on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: click_new_project_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_click_pagination_on_your_work_projects
description: Count of unique users that use pagination on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: click_pagination_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_click_sort_on_your_work_projects
description: Count of unique users that use sort on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: click_sort_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_click_tab_on_your_work_projects
description: Count of unique users that clicked tabs on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: click_tab_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_filter_by_role_on_your_work_projects
description: Count of unique users that use Role filter on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: filter_by_role_on_your_work_projects
unique: user.id

View File

@ -0,0 +1,23 @@
---
key_path: redis_hll_counters.count_distinct_user_id_from_search_on_your_work_projects
description: Count of unique users that search on Your work > Projects
product_group: organizations
product_categories:
- groups_and_projects
performance_indicator_type: []
value_type: number
status: active
milestone: '17.11'
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/186021
time_frame:
- 28d
- 7d
data_source: internal_events
data_category: optional
tiers:
- free
- premium
- ultimate
events:
- name: search_on_your_work_projects
unique: user.id

View File

@ -8,7 +8,8 @@ title: GitLab Duo Self-Hosted
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: GitLab Duo Self-Hosted configuration and authentication
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: Configure GitLab to access GitLab Duo Self-Hosted
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}
@ -55,7 +56,7 @@ Prerequisites:
- You must be an administrator.
- You must have an Ultimate license.
- You must have a Duo Enterprise license add-on.
- You must have a GitLab Duo Enterprise license add-on.
To configure a self-hosted model:
@ -92,7 +93,7 @@ Prerequisites:
- You must be an administrator.
- You must have an Ultimate license.
- You must have a Duo Enterprise license add-on.
- You must have a GitLab Duo Enterprise license add-on.
To enable self-hosted [beta](../../policy/development_stages_support.md#beta) models and features:
@ -116,7 +117,7 @@ Prerequisites:
- You must be an administrator.
- You must have an Ultimate license.
- You must have a Duo Enterprise license add-on.
- You must have a GitLab Duo Enterprise license add-on.
### View configured features

View File

@ -8,7 +8,8 @@ title: Enable logging for self-hosted models
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: GitLab Duo Self-Hosted supported platforms
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: Supported GitLab Duo Self-Hosted models and hardware requirements
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: Troubleshooting GitLab Duo Self-Hosted
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a GitLab Duo Enterprise trial on a paid Ultimate subscription](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: Self-Hosted model setup related topics
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab Self-Managed
- Status: Beta

View File

@ -12475,6 +12475,7 @@ Input type: `WorkItemCreateInput`
| <a id="mutationworkitemcreatenamespacepath"></a>`namespacePath` | [`ID`](#id) | Full path of the namespace(project or group) the work item is created in. |
| <a id="mutationworkitemcreateprojectpath"></a>`projectPath` {{< icon name="warning-solid" >}} | [`ID`](#id) | **Deprecated:** Please use namespacePath instead. That will cover for both projects and groups. Deprecated in GitLab 15.10. |
| <a id="mutationworkitemcreatestartandduedatewidget"></a>`startAndDueDateWidget` | [`WorkItemWidgetStartAndDueDateUpdateInput`](#workitemwidgetstartandduedateupdateinput) | Input for start and due date widget. |
| <a id="mutationworkitemcreatestatuswidget"></a>`statusWidget` {{< icon name="warning-solid" >}} | [`WorkItemWidgetStatusInput`](#workitemwidgetstatusinput) | **Deprecated:** **Status**: Experiment. Introduced in GitLab 17.11. |
| <a id="mutationworkitemcreatetitle"></a>`title` | [`String!`](#string) | Title of the work item. |
| <a id="mutationworkitemcreatevulnerabilityid"></a>`vulnerabilityId` {{< icon name="warning-solid" >}} | [`VulnerabilityID`](#vulnerabilityid) | **Deprecated:** **Status**: Experiment. Introduced in GitLab 17.9. |
| <a id="mutationworkitemcreateweightwidget"></a>`weightWidget` | [`WorkItemWidgetWeightInput`](#workitemwidgetweightinput) | Input for weight widget. |
@ -12680,6 +12681,7 @@ Input type: `WorkItemUpdateInput`
| <a id="mutationworkitemupdateprogresswidget"></a>`progressWidget` | [`WorkItemWidgetProgressInput`](#workitemwidgetprogressinput) | Input for progress widget. |
| <a id="mutationworkitemupdatestartandduedatewidget"></a>`startAndDueDateWidget` | [`WorkItemWidgetStartAndDueDateUpdateInput`](#workitemwidgetstartandduedateupdateinput) | Input for start and due date widget. |
| <a id="mutationworkitemupdatestateevent"></a>`stateEvent` | [`WorkItemStateEvent`](#workitemstateevent) | Close or reopen a work item. |
| <a id="mutationworkitemupdatestatuswidget"></a>`statusWidget` {{< icon name="warning-solid" >}} | [`WorkItemWidgetStatusInput`](#workitemwidgetstatusinput) | **Deprecated:** **Status**: Experiment. Introduced in GitLab 17.11. |
| <a id="mutationworkitemupdatetimetrackingwidget"></a>`timeTrackingWidget` | [`WorkItemWidgetTimeTrackingInput`](#workitemwidgettimetrackinginput) | Input for time tracking widget. |
| <a id="mutationworkitemupdatetitle"></a>`title` | [`String`](#string) | Title of the work item. |
| <a id="mutationworkitemupdateverificationstatuswidget"></a>`verificationStatusWidget` | [`VerificationStatusInput`](#verificationstatusinput) | Input for verification status widget. |
@ -46361,6 +46363,12 @@ A `WorkItemsRelatedWorkItemLinkID` is a global ID. It is encoded as a string.
An example `WorkItemsRelatedWorkItemLinkID` is: `"gid://gitlab/WorkItems::RelatedWorkItemLink/1"`.
### `WorkItemsStatusesStatusID`
A `WorkItemsStatusesStatusID` is a global ID. It is encoded as a string.
An example `WorkItemsStatusesStatusID` is: `"gid://gitlab/WorkItems::Statuses::Status/1"`.
### `WorkItemsTypeID`
A `WorkItemsTypeID` is a global ID. It is encoded as a string.
@ -48821,6 +48829,14 @@ Attributes for value stream stage.
| <a id="workitemwidgetstartandduedateupdateinputisfixed"></a>`isFixed` | [`Boolean`](#boolean) | Indicates if the work item is using fixed dates. |
| <a id="workitemwidgetstartandduedateupdateinputstartdate"></a>`startDate` | [`Date`](#date) | Start date for the work item. |
### `WorkItemWidgetStatusInput`
#### Arguments
| Name | Type | Description |
| ---- | ---- | ----------- |
| <a id="workitemwidgetstatusinputstatus"></a>`status` | [`WorkItemsStatusesStatusID`](#workitemsstatusesstatusid) | Status of the work item. |
### `WorkItemWidgetTimeTrackingInput`
#### Arguments

View File

@ -69,7 +69,7 @@ When documenting a GitLab Duo experiment:
`Experimental features` section.
- Document the feature near other similar features.
- Make sure you add history and status values, including any
[add-on information](styleguide/availability_details.md#gitlab-duo-pro-or-enterprise-add-on).
[add-on information](styleguide/availability_details.md#add-ons).
- For features that are part of the [Early Access Program](../../policy/early_access_program/_index.md#add-a-feature-to-the-program)
in the `#developer-relations-early-access-program` Slack channel,
post a comment that mentions the feature and its status.
@ -81,7 +81,7 @@ When a GitLab Duo experiment moves to beta:
- On the [top-level GitLab Duo page](../../user/gitlab_duo/_index.md), move the topic from the
`Experimental features` to the `Beta features` section.
- Make sure you update the history and status values, including any
[add-on information](styleguide/availability_details.md#gitlab-duo-pro-or-enterprise-add-on).
[add-on information](styleguide/availability_details.md#add-ons).
- For features that are part of the [Early Access Program](../../policy/early_access_program/_index.md#add-a-feature-to-the-program)
in the `#developer-relations-early-access-program` Slack channel,
post a comment that mentions the feature and its status.
@ -93,7 +93,7 @@ When a GitLab Duo feature becomes generally available:
- On the [top-level GitLab Duo page](../../user/gitlab_duo/_index.md), move the topic from the
`Beta features` or `Experimental features` section to the `Generally available features` section.
- Make sure you update the history and status values, including any
[add-on information](styleguide/availability_details.md#gitlab-duo-pro-or-enterprise-add-on).
[add-on information](styleguide/availability_details.md#add-ons).
- For features that are part of the [Early Access Program](../../policy/early_access_program/_index.md#add-a-feature-to-the-program)
in the `#developer-relations-early-access-program` Slack channel,
post a comment that mentions the feature and its status.

View File

@ -35,7 +35,7 @@ title: 'Topic title'
## Available options
Use the following text for the tier, offering, status, and version history.
Use the following text for the tier, offering, add-on, status, and version history.
### Offering
@ -67,25 +67,23 @@ For tier, choose one:
- `Premium, Ultimate`
- `Ultimate`
#### GitLab Duo Pro or Enterprise add-on
Document add-ons by using the phrase `with` and the add-on.
For example, `with GitLab Duo Pro`.
The possibilities are:
```markdown
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise
- Tier: Ultimate with GitLab Duo Pro or Enterprise
- Tier: Ultimate with GitLab Duo Enterprise
```
{{< alert type="note" >}}
GitLab Dedicated always includes an Ultimate subscription.
{{< /alert >}}
#### Add-ons
For add-ons, the possibilities are:
```markdown
- Add-on: GitLab Duo Pro
- Add-on: GitLab Duo Enterprise
- Add-on: GitLab Duo Pro or Enterprise
- Add-on: GitLab Duo with Amazon Q
```
### Status
For status, choose one:

View File

@ -76,7 +76,8 @@ glab mr merge
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM: Anthropic [Claude 3 Haiku](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-haiku)

View File

@ -414,6 +414,9 @@ These errors may occur when indexing Git repository data.
Prerequisites:
- You must have administrator access to the instance.
- Configure the [number of shards per index](#number-of-elasticsearch-shards).
- Configure the [number of replicas per index](#number-of-elasticsearch-replicas).
- Optional. Prepare for [indexing large instances](#index-large-instances-efficiently).
To enable advanced search:
@ -938,7 +941,7 @@ The following are some available Rake tasks:
| [`sudo gitlab-rake gitlab:elastic:reindex_cluster`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Schedules a zero-downtime cluster reindexing task. |
| [`sudo gitlab-rake gitlab:elastic:mark_reindex_failed`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Mark the most recent reindex job as failed. |
| [`sudo gitlab-rake gitlab:elastic:list_pending_migrations`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | List pending migrations. Pending migrations include those that have not yet started, have started but not finished, and those that are halted. |
| [`sudo gitlab-rake gitlab:elastic:estimate_cluster_size`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Get an estimate of cluster size based on the total repository size. |
| [`sudo gitlab-rake gitlab:elastic:estimate_cluster_size`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Get an estimate of code and wiki index sizes and total cluster size based on the total repository size. |
| [`sudo gitlab-rake gitlab:elastic:estimate_shard_sizes`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Get an estimate of shard sizes for each index based on approximate database counts. This estimate does not include repository data (code, commits, and wikis). [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/146108) in GitLab 16.11. |
| [`sudo gitlab-rake gitlab:elastic:enable_search_with_elasticsearch`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Enables advanced search with Elasticsearch. |
| [`sudo gitlab-rake gitlab:elastic:disable_search_with_elasticsearch`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/lib/tasks/gitlab/elastic.rake) | Disables advanced search with Elasticsearch. |
@ -1006,7 +1009,7 @@ For basic guidance on choosing a cluster configuration you may refer to [Elastic
#### Number of Elasticsearch shards
For single-node clusters, set the number of Elasticsearch shards per index to the number of
CPU cores. Keep the average shard size between a few GB and 30 GB.
CPU cores on the Elasticsearch data nodes. Keep the average shard size between a few GB and 30 GB.
For multi-node clusters, set the number of Elasticsearch shards per index to at least `5`.
@ -1040,6 +1043,9 @@ For indices that contain repository data:
- `gitlab-production-wikis`
- `gitlab-production-commits`
Run the Rake task `gitlab:elastic:estimate_cluster_size` to determine the number of shards.
The task returns approximate index sizes for code (`gitlab-production`) and wiki (`gitlab-production-wikis`).
Keep the average shard size between a few GB and 30 GB.
If the average shard size grows to more than 30 GB, increase the shard size
for the index and trigger [zero-downtime reindexing](#zero-downtime-reindexing).

View File

@ -7,7 +7,8 @@ title: AI Gateway Solution
{{< details >}}
- Tier: Ultimate with GitLab Duo Pro or Enterprise
- Tier: Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -7,7 +7,8 @@ title: 'GitLab Duo Self-Hosted: Complete AWS/Google Cloud Deployment Guide with
{{< details >}}
- Tier: Ultimate with GitLab Duo Pro or Enterprise
- Tier: Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab Self-Managed
{{< /details >}}

View File

@ -217,7 +217,7 @@ Prerequisites:
{{< details >}}
- Tier: Premium
- Tier: Premium, Ultimate
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
{{< /details >}}

View File

@ -7,7 +7,8 @@ title: AI impact analytics
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed
{{< /details >}}

View File

@ -238,7 +238,8 @@ After you save a visualization, you can add it to a new or existing custom dashb
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com
- Status: Experiment

View File

@ -203,14 +203,3 @@ Additional details about the differences between the two solutions are outlined
| **Ability to apply one standard to multiple projects** | The same compliance framework label can be applied to multiple projects inside a group. | The same security policy project can be used for multiple projects across GitLab with no requirement of being located in the same group. |
Feedback is welcome on our vision for [unifying the user experience for these two features](https://gitlab.com/groups/gitlab-org/-/epics/7312)
## Custom security role
You can create a [custom role](../custom_roles/_index.md) for security team members who need access to application security features, such as vulnerability management, security policies, or dependencies. This approach allows organizations to follow the Principle of Least Privilege by providing security team members with the privileges they need without promoting them to Developer or Maintainer on a group or project.
For example, the custom security role may have the following [permissions](../custom_roles/abilities.md):
- Name: Custom Security Role
- Description: Manage vulnerabilities and link security policy projects.
- Base Role: Reporter (or any default role)
- Permissions: `admin_vulnerability`, `read_dependency`, `manage_security_policy_link`

View File

@ -39,7 +39,8 @@ the top of the vulnerability's page.
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM: Anthropic [Claude 3 Haiku](https://docs.anthropic.com/en/docs/about-claude/models#claude-3-a-new-generation-of-ai)
@ -106,7 +107,8 @@ The following data is shared with third-party AI APIs:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
- LLM for GitLab.com: Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet)
@ -245,7 +247,8 @@ The following data is shared with third-party AI APIs:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
{{< /details >}}

View File

@ -353,7 +353,8 @@ such as:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
- LLM for GitLab.com: Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet)

View File

@ -22,7 +22,7 @@ title: GitLab Duo with Amazon Q
{{< alert type="note" >}}
If you have a Duo Pro or Duo Enterprise add-on, this feature is not available.
If you have a GitLab Duo Pro or Duo Enterprise add-on, this feature is not available.
{{< /alert >}}

View File

@ -22,7 +22,7 @@ title: Set up GitLab Duo with Amazon Q
{{< alert type="note" >}}
If you have a Duo Pro or Duo Enterprise add-on, this feature is not available.
If you have a GitLab Duo Pro or Duo Enterprise add-on, this feature is not available.
{{< /alert >}}

View File

@ -12,7 +12,7 @@ It can help you troubleshoot your pipeline, write tests, address vulnerabilities
## Step 1: Ensure you have a subscription
Your organization has purchased a GitLab Duo add-on subscription: either Duo Pro or Duo Enterprise.
Your organization has purchased a GitLab Duo add-on subscription: either GitLab Duo Pro or Duo Enterprise.
Each subscription includes a set of AI-powered features to help improve your workflow.
After your organization purchases a subscription, an administrator must assign seats to users.

View File

@ -40,7 +40,7 @@ to help you:
- [Install the latest version of Python](https://www.python.org/downloads/) on your system.
You can ask Chat how to do that for your operating system.
- Make sure your organization has purchased a
[GitLab Duo add-on subscription (either Duo Pro or Duo Enterprise)](https://about.gitlab.com/gitlab-duo/#pricing),
[GitLab Duo add-on subscription (either GitLab Duo Pro or Duo Enterprise)](https://about.gitlab.com/gitlab-duo/#pricing),
and your administrator has [assigned you a seat](../../../subscriptions/subscription-add-ons.md#assign-gitlab-duo-seats).
- Install an extension in your preferred IDE:
- [Web IDE](../../project/web_ide/_index.md): Access through your GitLab instance

View File

@ -7,7 +7,8 @@ title: GitLab Duo Chat
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLMs: Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet), Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2), Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet), Anthropic [Claude 3.5 Haiku](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-haiku), and [Vertex AI Search](https://cloud.google.com/enterprise-search). The LLM depends on the question asked.

View File

@ -27,7 +27,8 @@ The example questions on this page, including the [slash commands](#gitlab-duo-c
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, and JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -61,7 +62,8 @@ To keep Chat up to date with the documentation, its knowledge base is updated da
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -98,7 +100,8 @@ For tips on how GitLab Duo Chat can improve your productivity with issues and ep
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -131,7 +134,8 @@ If the epic contains a large amount of text (more than 40,000 words), GitLab Duo
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -164,7 +168,8 @@ While in the merge request, open Chat and type your question. For example:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -188,7 +193,8 @@ You can ask about a specific GitLab commit. For example:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -213,7 +219,8 @@ You can ask about a specific GitLab pipeline job. For example:
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -259,7 +266,8 @@ In the GitLab UI, you can also explain code in:
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -333,7 +341,8 @@ Programming languages that require compiling the source code may throw cryptic e
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: VS Code, JetBrains IDEs
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet)
@ -386,7 +395,8 @@ You cannot use [Quick Chat](_index.md#in-gitlab-duo-quick-chat-in-the-editor-vie
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -421,7 +431,8 @@ You can include additional instructions to be considered. For example:
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -454,7 +465,8 @@ You can include additional instructions to be considered. For example:
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -489,7 +501,8 @@ For more information, see [Use GitLab Duo Chat in VS Code](_index.md#use-gitlab-
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -528,7 +541,8 @@ Alternatively, you can use GitLab Duo Root Cause Analysis to [troubleshoot faile
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -588,7 +602,8 @@ To troubleshoot a failed CI/CD job from the job log:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet V2](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet-v2)
@ -610,7 +625,8 @@ For more information, see [Explaining a vulnerability](../application_security/v
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com
- Editors: GitLab UI
@ -656,7 +672,8 @@ Use the commands to quickly accomplish specific tasks.
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI, Web IDE, VS Code, JetBrains IDEs
@ -684,7 +701,8 @@ On GitLab.com, in GitLab 17.10 and later, when having [multiple conversations](_
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise- [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: GitLab UI
@ -703,7 +721,8 @@ These commands are dynamic and are available only in the GitLab UI when using Du
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Editors: Web IDE, VS Code, JetBrains IDEs

View File

@ -66,8 +66,8 @@ Learn about [data usage when using GitLab Duo Chat](../gitlab_duo/data_usage.md)
You can [manually synchronize your subscription](../../subscriptions/self_managed/_index.md#manually-synchronize-subscription-data) if either:
- You have just purchased a subscription for the Premium or Ultimate tier, or have recently assigned seats for Duo Pro, and you have upgraded to GitLab 16.8.
- You already have a subscription for the Premium or Ultimate tier, or you have recently assigned seats for Duo Pro, and you have upgraded to GitLab 16.8.
- You have just purchased a subscription for the Premium or Ultimate tier, or have recently assigned seats for GitLab Duo Pro, and you have upgraded to GitLab 16.8.
- You already have a subscription for the Premium or Ultimate tier, or you have recently assigned seats for GitLab Duo Pro, and you have upgraded to GitLab 16.8.
Without the manual synchronization, it might take up to 24 hours to activate GitLab Duo Chat on your instance.

View File

@ -189,6 +189,7 @@ Users are notified of the following events:
| User added to project | User | Sent when user is added to project. |
| Group access expired | Group members | Sent when user's access to a group expires in seven days. _[Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/12704) in GitLab 16.3._ |
| Project access expired | Project members | Sent when user's access to a project expires in seven days. _[Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/12704) in GitLab 16.3._ |
| Group scheduled for deletion | Group Owners | Sent when group is scheduled for deletion. _[Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/522883) in GitLab 17.11_ |
## Notifications on issues, merge requests, and epics

View File

@ -47,7 +47,8 @@ To edit an issue:
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com
- Status: Experiment
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)

View File

@ -246,7 +246,8 @@ To change how a merge request shows changed lines:
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
- LLM for GitLab.com: Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet)

View File

@ -14,7 +14,8 @@ GitLab Duo is designed to provide contextually relevant information during the l
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed
- Status: Beta
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
@ -49,7 +50,8 @@ Provide feedback on this feature in [issue 443236](https://gitlab.com/gitlab-org
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Status: Beta
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
@ -108,7 +110,8 @@ Additional settings and configuration are planned. To that work, see
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- Status: Experiment
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
@ -141,7 +144,8 @@ Provide feedback on this experimental feature in [issue 408991](https://gitlab.c
{{< details >}}
- Tier: Ultimate with GitLab Duo Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Ultimate
- Add-on: GitLab Duo Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)

View File

@ -7,7 +7,8 @@ title: Explain code in a file
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLM for GitLab Self-Managed, GitLab Dedicated: Anthropic [Claude 3.5 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-5-sonnet)
- LLM for GitLab.com: Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet)

View File

@ -8,7 +8,8 @@ title: Code Suggestions
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
- LLMs: For code completion, Fireworks AI-hosted [`Qwen2.5 7B`](https://fireworks.ai/models/fireworks/qwen2p5-coder-7b) and Vertex AI Codey [`code-gecko`](https://console.cloud.google.com/vertex-ai/publishers/google/model-garden/code-gecko). For code generation, Anthropic [Claude 3.7 Sonnet](https://console.cloud.google.com/vertex-ai/publishers/anthropic/model-garden/claude-3-7-sonnet).

View File

@ -8,7 +8,8 @@ title: Repository X-Ray
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
{{< /details >}}
@ -164,12 +165,12 @@ job is run. To learn more about pipeline configuration and triggers, see the
When running Repository X-Ray, you might get an error that states `401: Unauthorized`.
A Duo Pro add-on is linked to a group when you buy that add-on. To solve the error, ensure
that your current project is part of a group with the Duo Pro add-on.
A GitLab Duo Pro add-on is linked to a group when you buy that add-on. To solve the error, ensure
that your current project is part of a group with the GitLab Duo Pro add-on.
This link can be either of the following:
- Direct, that is, the project is in a group that has the Duo Pro add-on.
- Indirect, for example, the parent group of the current project's group has the Duo Pro add-on.
- Direct, that is, the project is in a group that has the GitLab Duo Pro add-on.
- Indirect, for example, the parent group of the current project's group has the GitLab Duo Pro add-on.
<!--- end_remove -->

View File

@ -8,7 +8,8 @@ title: Supported extensions and languages
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
{{< /details >}}

View File

@ -8,7 +8,8 @@ title: Troubleshooting Code Suggestions
{{< details >}}
- Tier: Premium with GitLab Duo Pro, Ultimate with GitLab Duo Pro or Enterprise - [Start a trial](https://about.gitlab.com/solutions/gitlab-duo-pro/sales/?type=free-trial)
- Tier: Premium, Ultimate
- Add-on: GitLab Duo Pro or Enterprise
- Offering: GitLab.com, GitLab Self-Managed, GitLab Dedicated
{{< /details >}}

View File

@ -1813,9 +1813,6 @@ msgstr ""
msgid "- Add or remove a user."
msgstr ""
msgid "- Available to run jobs."
msgstr ""
msgid "- Create or close an issue."
msgstr ""
@ -1833,9 +1830,6 @@ msgstr ""
msgid "- List the visible events for %{project_name} using the Events API %{events_api_link}."
msgstr ""
msgid "- Not available to run jobs."
msgstr ""
msgid "- Push code to the repository."
msgstr ""
@ -15182,7 +15176,7 @@ msgstr ""
msgid "ComplianceFrameworks|Cancel"
msgstr ""
msgid "ComplianceFrameworks|Choose a standard control"
msgid "ComplianceFrameworks|Choose a GitLab control"
msgstr ""
msgid "ComplianceFrameworks|Compliance framework created"
@ -15314,6 +15308,9 @@ msgstr ""
msgid "ComplianceFrameworks|Optional"
msgstr ""
msgid "ComplianceFrameworks|Please enter a valid URL"
msgstr ""
msgid "ComplianceFrameworks|Policies"
msgstr ""
@ -15356,6 +15353,9 @@ msgstr ""
msgid "ComplianceFrameworks|Saved changes to compliance framework"
msgstr ""
msgid "ComplianceFrameworks|Secret token is required"
msgstr ""
msgid "ComplianceFrameworks|Select policies to enforce on all projects scoped to this framework."
msgstr ""
@ -28625,9 +28625,6 @@ msgstr ""
msgid "Group requires separate account"
msgstr ""
msgid "Group runners"
msgstr ""
msgid "Group runners can be managed with the %{link}."
msgstr ""
@ -30461,6 +30458,12 @@ msgstr ""
msgid "If this was a mistake you can leave the %{source_type}."
msgstr ""
msgid "If this was a mistake, you can %{link_start}retain the group%{link_end} before %{deletion_date}."
msgstr ""
msgid "If this was a mistake, you can retain the group before %{deletion_date}: %{retention_url}"
msgstr ""
msgid "If using GitHub, youll see pipeline statuses on GitHub for your commits and pull requests. %{more_info_link}"
msgstr ""
@ -44380,9 +44383,6 @@ msgstr ""
msgid "Please confirm your email address"
msgstr ""
msgid "Please contact an admin to create runners."
msgstr ""
msgid "Please contact your GitLab administrator if you think this is an error."
msgstr ""
@ -50523,7 +50523,7 @@ msgstr ""
msgid "Runners|Available"
msgstr ""
msgid "Runners|Available instance runners: %{count}"
msgid "Runners|Available instance runners"
msgstr ""
msgid "Runners|Available to all projects"
@ -50732,7 +50732,7 @@ msgstr ""
msgid "Runners|Group area Runners"
msgstr ""
msgid "Runners|How do runners pick up jobs?"
msgid "Runners|Group runners"
msgstr ""
msgid "Runners|How is this calculated?"
@ -50774,9 +50774,6 @@ msgstr ""
msgid "Runners|Instance"
msgstr ""
msgid "Runners|Instance runners"
msgstr ""
msgid "Runners|Instance runners are disabled in the group settings."
msgstr ""
@ -50994,6 +50991,9 @@ msgstr ""
msgid "Runners|Platform"
msgstr ""
msgid "Runners|Please contact an admin to create runners."
msgstr ""
msgid "Runners|Project"
msgstr ""
@ -51048,9 +51048,6 @@ msgstr ""
msgid "Runners|Register an instance runner"
msgstr ""
msgid "Runners|Register as many runners as you want. You can register runners as separate users, on separate servers, and on your local machine."
msgstr ""
msgid "Runners|Register runner"
msgstr ""
@ -51162,9 +51159,6 @@ msgstr ""
msgid "Runners|Runners"
msgstr ""
msgid "Runners|Runners are either:"
msgstr ""
msgid "Runners|Runners are grouped when they have the same authentication token. This happens when you re-use a runner configuration in more than one runner manager. %{linkStart}How does this work?%{linkEnd}"
msgstr ""
@ -51261,9 +51255,6 @@ msgstr ""
msgid "Runners|Tags"
msgstr ""
msgid "Runners|Tags control which type of jobs a runner can handle. By tagging a runner, you make sure runners only handle the jobs they are equipped to run."
msgstr ""
msgid "Runners|The %{boldStart}runner authentication token%{boldEnd} %{token} displays here %{boldStart}for a short time only%{boldEnd}. After you register the runner, this token is stored in the %{codeStart}config.toml%{codeEnd} and cannot be accessed again from the UI."
msgstr ""
@ -51478,15 +51469,9 @@ msgstr ""
msgid "Runners|Zone must have the right format."
msgstr ""
msgid "Runners|active"
msgstr ""
msgid "Runners|group"
msgstr ""
msgid "Runners|paused"
msgstr ""
msgid "Runners|project"
msgstr ""
@ -65272,6 +65257,9 @@ msgstr ""
msgid "View users statistics"
msgstr ""
msgid "View your group: %{group_url}"
msgstr ""
msgid "Viewed"
msgstr ""
@ -69247,6 +69235,9 @@ msgid_plural "Your free group is now limited to %d members"
msgstr[0] ""
msgstr[1] ""
msgid "Your group %{group_name} has been marked for deletion and will be removed in %{days}."
msgstr ""
msgid "Your instance has %{remaining_user_count} users remaining of the %{total_user_count} in your subscription. When there are no more seats, users cannot be invited or added to the instance."
msgstr ""
@ -71225,6 +71216,12 @@ msgstr ""
msgid "must belong to same project of the work item."
msgstr ""
msgid "must belong to the compliance requirement."
msgstr ""
msgid "must belong to the same namespace."
msgstr ""
msgid "must contain only a discord user ID."
msgstr ""
@ -71630,6 +71627,9 @@ msgstr ""
msgid "should have length between 16 to 24 characters."
msgstr ""
msgid "should have the compliance requirement's framework applied to it."
msgstr ""
msgid "should use only one of: %{requirements}"
msgstr ""

View File

@ -0,0 +1,113 @@
# frozen_string_literal: true
module RuboCop
module Cop
module Rake
# Checks for method, class, and module definitions in rake task files
# that could cause namespace collisions or code organization issues.
#
# This cop flags:
# 1. Method definitions directly inside rake namespaces
# 2. Any class definitions in rake files
# 3. Any module definitions in rake files
#
# The ideal pattern is to move all supporting code to standalone Ruby files
# rather than defining methods, classes or modules in rake files at all.
#
# @example
# # bad - method definition inside rake namespace
# namespace :gitlab do
# namespace :elastic do
# def task_executor_service
# Search::RakeTaskExecutorService.new(logger: stdout_logger)
# end
# end
# end
#
# # bad - class definition in rake file
# # Either inside namespaces or at top level
# class TaskHelper
# def self.task_executor_service
# Search::RakeTaskExecutorService.new(logger: stdout_logger)
# end
# end
#
# # bad - module definition in rake file
# # Either inside namespaces or at top level
# module Search
# module RakeTask
# module Elastic
# def self.task_executor_service
# Search::RakeTaskExecutorService.new(logger: stdout_logger)
# end
# end
# end
# end
#
# # good - use a separate Ruby file for supporting code
# # In ee/lib/search/rake_task/elastic.rb:
# module Search
# module RakeTask
# module Elastic
# def self.task_executor_service
# Search::RakeTaskExecutorService.new(logger: stdout_logger)
# end
# end
# end
# end
#
# # In the rake file, use the module:
# namespace :gitlab do
# namespace :elastic do
# desc 'GitLab | Elasticsearch | Info'
# task info: :environment do
# Gitlab::Search::RakeTask::Elastic.task_executor_service.execute(:info)
# end
# end
# end
class TopLevelMethodDefinition < RuboCop::Cop::Base
MSG = 'Methods defined in rake tasks share the same namespace and can cause collisions. ' \
'Please define it in a bounded contexts module in a separate Ruby file. ' \
'For example, Search::RakeTask::<Namespace>. ' \
'See https://github.com/rubocop/rubocop-rake/issues/42'
CLASS_MSG = 'Classes should not be defined in rake files. ' \
'Please define it in a bounded contexts module in a separate Ruby file. ' \
'For example, Search::RakeTask::<Namespace>. ' \
'See https://github.com/rubocop/rubocop-rake/issues/42'
MODULE_MSG = 'Modules should not be defined in rake files. ' \
'Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. ' \
'See https://github.com/rubocop/rubocop-rake/issues/42'
def on_def(node)
return unless in_rake_file?
add_offense(node)
end
def on_defs(node)
return unless in_rake_file?
add_offense(node)
end
def on_class(node)
return unless in_rake_file?
add_offense(node, message: CLASS_MSG)
end
def on_module(node)
return unless in_rake_file?
add_offense(node, message: MODULE_MSG)
end
private
def in_rake_file?
processed_source.file_path.end_with?('.rake')
end
end
end
end
end

View File

@ -6,7 +6,6 @@ FactoryBot.define do
name { generate(:name) }
username { generate(:username) }
password { User.random_password }
role { 'software_developer' }
confirmed_at { Time.now }
confirmation_token { nil }
can_create_group { true }

View File

@ -117,7 +117,12 @@ RSpec.describe 'Maintainer manages project runners', feature_category: :fleet_vi
visit project_runners_path(project)
within_testid 'available-shared-runners' do
expect(page).to have_content format(_('Available instance runners: %{count}'), { count: 2 })
within_testid 'crud-title' do
expect(page).to have_content _('Available instance runners')
end
within_testid 'crud-count' do
expect(page).to have_content 2
end
end
end
@ -179,7 +184,7 @@ RSpec.describe 'Maintainer manages project runners', feature_category: :fleet_vi
it 'user sees instance runners description' do
visit project_runners_path(project)
within_testid('shared-runners-description') do
within_testid('available-shared-runners') do
expect(page).not_to have_content('The same instance runner executes code from multiple projects')
expect(page).to have_content(shared_runners_html)
end

View File

@ -157,7 +157,18 @@ describe('RegistrationDropdown', () => {
});
expect(findDropdown().attributes()).toMatchObject({
toggleclass: '!gl-px-3',
autoclose: 'true',
category: 'tertiary',
icon: 'ellipsis_v',
items: '',
nocaret: 'true',
placement: 'bottom-start',
positioningstrategy: 'absolute',
size: 'small',
textsronly: 'true',
toggleid: 'dropdown-toggle-btn-30',
toggletext: 'Register an instance runner',
variant: 'default',
});
});
@ -306,7 +317,18 @@ describe('RegistrationDropdown', () => {
});
expect(findDropdown().attributes()).toMatchObject({
toggleclass: '!gl-px-3',
autoclose: 'true',
category: 'tertiary',
icon: 'ellipsis_v',
items: '',
nocaret: 'true',
placement: 'bottom-start',
positioningstrategy: 'absolute',
size: 'small',
textsronly: 'true',
toggleid: 'dropdown-toggle-btn-74',
toggletext: 'Register an instance runner',
variant: 'default',
});
});

View File

@ -47,6 +47,7 @@ import {
} from '~/vue_shared/components/resource_lists/constants';
import createMockApollo from 'helpers/mock_apollo_helper';
import waitForPromises from 'helpers/wait_for_promises';
import { useMockInternalEventsTracking } from 'helpers/tracking_internal_events_helper';
import { programmingLanguages } from './mock_data';
jest.mock('~/alert');
@ -77,8 +78,20 @@ const defaultPropsData = {
firstTabRouteNames: FIRST_TAB_ROUTE_NAMES,
initialSort: 'created_desc',
programmingLanguages,
eventTracking: {
filteredSearch: {
[FILTERED_SEARCH_TERM_KEY]: 'search_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_LANGUAGE]: 'filter_by_language_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_MIN_ACCESS_LEVEL]: 'filter_by_role_on_your_work_projects',
},
pagination: 'click_pagination_on_your_work_projects',
tabs: 'click_tab_on_your_work_projects',
sort: 'click_sort_on_your_work_projects',
},
};
const { bindInternalEventDocument } = useMockInternalEventsTracking();
const searchTerm = 'foo bar';
const mockEndCursor = 'mockEndCursor';
const mockStartCursor = 'mockStartCursor';
@ -220,21 +233,63 @@ describe('TabsWithList', () => {
describe('when filtered search bar is submitted', () => {
beforeEach(async () => {
await createComponent();
});
it('updates query string', async () => {
findFilteredSearchAndSort().vm.$emit('filter', {
[defaultPropsData.filteredSearchTermKey]: searchTerm,
});
await waitForPromises();
});
it('updates query string', () => {
expect(router.currentRoute.query).toEqual({
[defaultPropsData.filteredSearchTermKey]: searchTerm,
});
});
it('tracks all filter events when multiple filters are applied', async () => {
const { trackEventSpy } = bindInternalEventDocument(wrapper.element);
findFilteredSearchAndSort().vm.$emit('filter', {
[defaultPropsData.filteredSearchTermKey]: searchTerm,
[FILTERED_SEARCH_TOKEN_LANGUAGE]: ['5'],
[FILTERED_SEARCH_TOKEN_MIN_ACCESS_LEVEL]: ['50'],
});
await waitForPromises();
expect(trackEventSpy).toHaveBeenCalledWith(
'search_on_your_work_projects',
{ label: 'Contributed' },
undefined,
);
expect(trackEventSpy).toHaveBeenCalledWith(
'filter_by_language_on_your_work_projects',
{ label: 'Contributed', property: 'CSS' },
undefined,
);
expect(trackEventSpy).toHaveBeenCalledWith(
'filter_by_role_on_your_work_projects',
{ label: 'Contributed', property: 'Owner' },
undefined,
);
});
describe('when invalid filter option is used', () => {
it('does not track events', async () => {
const { trackEventSpy } = bindInternalEventDocument(wrapper.element);
findFilteredSearchAndSort().vm.$emit('filter', {
[FILTERED_SEARCH_TOKEN_LANGUAGE]: ['51'],
});
await waitForPromises();
expect(trackEventSpy).not.toHaveBeenCalled();
});
});
});
describe('when sort is changed', () => {
let trackEventSpy;
beforeEach(async () => {
await createComponent({
route: {
@ -246,6 +301,8 @@ describe('TabsWithList', () => {
},
});
trackEventSpy = bindInternalEventDocument(wrapper.element).trackEventSpy;
findFilteredSearchAndSort().vm.$emit('sort-by-change', SORT_OPTION_UPDATED.value);
await waitForPromises();
});
@ -266,9 +323,19 @@ describe('TabsWithList', () => {
it('does not call Sentry.captureException', () => {
expect(Sentry.captureException).not.toHaveBeenCalled();
});
it('tracks event', () => {
expect(trackEventSpy).toHaveBeenCalledWith(
'click_sort_on_your_work_projects',
{ label: 'Contributed', property: `${SORT_OPTION_UPDATED.value}_${SORT_DIRECTION_DESC}` },
undefined,
);
});
});
describe('when sort direction is changed', () => {
let trackEventSpy;
beforeEach(async () => {
await createComponent({
route: {
@ -280,6 +347,8 @@ describe('TabsWithList', () => {
},
});
trackEventSpy = bindInternalEventDocument(wrapper.element).trackEventSpy;
findFilteredSearchAndSort().vm.$emit('sort-direction-change', true);
await waitForPromises();
});
@ -300,6 +369,14 @@ describe('TabsWithList', () => {
it('does not call Sentry.captureException', () => {
expect(Sentry.captureException).not.toHaveBeenCalled();
});
it('tracks event', () => {
expect(trackEventSpy).toHaveBeenCalledWith(
'click_sort_on_your_work_projects',
{ label: 'Contributed', property: `${SORT_OPTION_CREATED.value}_${SORT_DIRECTION_ASC}` },
undefined,
);
});
});
});
@ -434,6 +511,18 @@ describe('TabsWithList', () => {
expect(router.push).toHaveBeenCalledWith({ name: PROJECT_DASHBOARD_TABS[2].value });
});
it('tracks event', () => {
const { trackEventSpy } = bindInternalEventDocument(wrapper.element);
findGlTabs().vm.$emit('input', 2);
expect(trackEventSpy).toHaveBeenCalledWith(
'click_tab_on_your_work_projects',
{ label: PERSONAL_TAB.text },
undefined,
);
});
});
describe('when tab is an invalid tab', () => {
@ -477,6 +566,8 @@ describe('TabsWithList', () => {
});
describe('when page is changed', () => {
let trackEventSpy;
describe('when going to next page', () => {
beforeEach(async () => {
await createComponent({
@ -485,6 +576,8 @@ describe('TabsWithList', () => {
await nextTick();
trackEventSpy = bindInternalEventDocument(wrapper.element).trackEventSpy;
findTabView().vm.$emit('page-change', {
endCursor: mockEndCursor,
startCursor: null,
@ -499,6 +592,14 @@ describe('TabsWithList', () => {
end_cursor: mockEndCursor,
});
});
it('tracks event', () => {
expect(trackEventSpy).toHaveBeenCalledWith(
'click_pagination_on_your_work_projects',
{ label: 'Contributed', property: 'next' },
undefined,
);
});
});
describe('when going to previous page', () => {
@ -515,6 +616,8 @@ describe('TabsWithList', () => {
await nextTick();
trackEventSpy = bindInternalEventDocument(wrapper.element).trackEventSpy;
findTabView().vm.$emit('page-change', {
endCursor: null,
startCursor: mockStartCursor,
@ -527,6 +630,14 @@ describe('TabsWithList', () => {
start_cursor: mockStartCursor,
});
});
it('tracks event', () => {
expect(trackEventSpy).toHaveBeenCalledWith(
'click_pagination_on_your_work_projects',
{ label: 'Contributed', property: 'previous' },
undefined,
);
});
});
});

View File

@ -60,7 +60,7 @@ describe('projects/settings/components/shared_runners', () => {
});
it('renders text explaining why the toggle is disabled', () => {
expect(findSharedRunnersToggle().text()).toEqual(
expect(findSharedRunnersToggle().text()).toContain(
'Instance runners are disabled in the group settings.',
);
});

View File

@ -55,6 +55,16 @@ describe('YourWorkProjectsApp', () => {
firstTabRouteNames: FIRST_TAB_ROUTE_NAMES,
initialSort: defaultPropsData.initialSort,
programmingLanguages: defaultPropsData.programmingLanguages,
eventTracking: {
filteredSearch: {
[FILTERED_SEARCH_TERM_KEY]: 'search_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_LANGUAGE]: 'filter_by_language_on_your_work_projects',
[FILTERED_SEARCH_TOKEN_MIN_ACCESS_LEVEL]: 'filter_by_role_on_your_work_projects',
},
pagination: 'click_pagination_on_your_work_projects',
tabs: 'click_tab_on_your_work_projects',
sort: 'click_sort_on_your_work_projects',
},
});
});
});

View File

@ -300,7 +300,6 @@ describe('GroupsListItem', () => {
it('displays prevent delete modal', () => {
expect(findPreventDeleteModal().props()).toMatchObject({
visible: true,
group: groupLinkedToSubscription,
});
});

View File

@ -271,4 +271,42 @@ RSpec.describe NamespacesHelper, feature_category: :groups_and_projects do
expect(helper.group_usage_quotas_url(subgroup1)).to eql(usage_quotas_pipelines_url)
end
end
describe '#permanent_deletion_date_formatted', :freeze_time do
before do
stub_application_setting(deletion_adjourned_period: 5)
end
context 'when container responds to :self_deletion_scheduled_deletion_created_on' do
context 'when container.self_deletion_scheduled_deletion_created_on returns nil' do
# FIXME: Replace `double` with `instance_double(Namespace` after https://gitlab.com/gitlab-org/gitlab/-/work_items/527085
let(:container) { double(self_deletion_scheduled_deletion_created_on: nil) } # rubocop:disable RSpec/VerifiedDoubles -- We'll solve this with the above task
it 'returns nil' do
expect(permanent_deletion_date_formatted(container)).to be_nil
end
end
context 'when container.self_deletion_scheduled_deletion_created_on returns a date' do
# FIXME: Replace `double` with `instance_double(Namespace` after https://gitlab.com/gitlab-org/gitlab/-/work_items/527085
let(:container) { double(self_deletion_scheduled_deletion_created_on: Date.yesterday) } # rubocop:disable RSpec/VerifiedDoubles -- We'll solve this with the above task
it 'returns the date formatted' do
expect(permanent_deletion_date_formatted(container)).to eq(4.days.from_now.strftime('%F'))
end
end
context 'when date is passed as argument' do
it 'returns the date formatted' do
expect(permanent_deletion_date_formatted(Date.current)).to eq(5.days.from_now.strftime('%F'))
end
end
end
context 'when a format is given' do
it 'returns the date formatted with the given format' do
expect(permanent_deletion_date_formatted(Date.current, format: Date::DATE_FORMATS[:medium])).to eq(5.days.from_now.strftime(Date::DATE_FORMATS[:medium]))
end
end
end
end

View File

@ -49,4 +49,21 @@ RSpec.describe CloudConnector::ServiceAccessToken, type: :model, feature_categor
expect(expired_token).to be_expired
end
end
describe '#refresh_required?', :freeze_time do
let_it_be(:active_long_lived_token) { create(:service_access_token, expires_at: 3.days.from_now) }
let_it_be(:active_short_lived_token) { create(:service_access_token, expires_at: 1.day.from_now) }
it 'returns false for a token that lives longer 2 days' do
expect(active_long_lived_token.refresh_required?).to be false
end
it 'returns true for a token that expires within 2 days' do
expect(active_short_lived_token.refresh_required?).to be true
end
it 'returns true for expired token' do
expect(expired_token.refresh_required?).to be true
end
end
end

View File

@ -436,7 +436,7 @@ RSpec.describe API::Invitations, feature_category: :user_profile do
emails = 'email3@example.com,email4@example.com,email5@example.com,email6@example.com,email7@example.com,' \
'EMAIL8@EXamPle.com'
unresolved_n_plus_ones = 82 # currently there are 10 queries added per email, checking if we should dispatch AuthorizationsAddedEvent makes 1 query per event (3 events dispatched)
unresolved_n_plus_ones = 84 # currently there are 10 queries added per email, checking if we should dispatch AuthorizationsAddedEvent makes 1 query per event (3 events dispatched)
expect do
post invitations_url(project, maintainer), params: { email: emails, access_level: Member::DEVELOPER }

View File

@ -0,0 +1,216 @@
# frozen_string_literal: true
require 'rubocop_spec_helper'
require_relative '../../../../rubocop/cop/rake/top_level_method_definition'
RSpec.describe RuboCop::Cop::Rake::TopLevelMethodDefinition, :aggregate_failures, :config, feature_category: :shared do
context 'in a rake file' do
let(:source_file) { 'elastic.rake' }
context 'when method definitions are inside rake namespaces' do
it 'registers an offense for method definitions' do
expect_offense(<<~RUBY, source_file)
namespace :gitlab do
namespace :elastic do
def task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
RUBY
end
it 'registers an offense for private method definitions' do
expect_offense(<<~RUBY, source_file)
namespace :gitlab do
namespace :elastic do
private
#{' '}
def task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
RUBY
end
it 'registers an offense for singleton method definitions' do
expect_offense(<<~RUBY, 'rakelib/some_task.rake')
namespace :gitlab do
namespace :elastic do
def self.task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
RUBY
end
end
context 'when class/module definitions are in rake files' do
it 'registers an offense for class definitions inside rake namespaces' do
expect_offense(<<~RUBY, source_file)
namespace :gitlab do
namespace :elastic do
class TaskHelper
^^^^^^^^^^^^^^^^ Classes should not be defined in rake files. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
def self.task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
end
RUBY
end
it 'registers an offense for module definitions inside rake namespaces' do
expect_offense(<<~RUBY, source_file)
namespace :gitlab do
namespace :elastic do
module TaskHelpers
^^^^^^^^^^^^^^^^^^ Modules should not be defined in rake files. Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
def self.task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
end
RUBY
end
it 'registers an offense for top-level class definitions' do
expect_offense(<<~RUBY, source_file)
class TaskHelper
^^^^^^^^^^^^^^^^ Classes should not be defined in rake files. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
def self.task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
namespace :gitlab do
namespace :elastic do
task info: :environment do
TaskHelper.task_executor_service.execute(:info)
end
end
end
RUBY
end
it 'registers an offense for top-level module definitions' do
expect_offense(<<~RUBY, source_file)
module Search
^^^^^^^^^^^^^ Modules should not be defined in rake files. Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
module RakeTask
^^^^^^^^^^^^^^^ Modules should not be defined in rake files. Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
module Elastic
^^^^^^^^^^^^^^ Modules should not be defined in rake files. Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
def self.task_executor_service
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
end
namespace :gitlab do
namespace :elastic do
task info: :environment do
Search::RakeTask::Elastic.task_executor_service.execute(:info)
end
end
end
RUBY
end
end
context 'with top-level method definitions outside rake namespaces' do
it 'registers offenses for top-level method definitions' do
expect_offense(<<~RUBY, source_file)
def top_level_method
^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
'some logic'
end
namespace :gitlab do
namespace :elastic do
# No method/class/module definitions here
task info: :environment do
# Only task logic here
end
end
end
RUBY
end
end
context 'with mixed method definitions' do
it 'registers offenses for all method definitions and the module' do
expect_offense(<<~RUBY, source_file)
# Top-level method - also gets an offense
def top_level_method
^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
'top level'
end
# Inside a module - the module gets flagged, not the method
module SomeModule
^^^^^^^^^^^^^^^^^ Modules should not be defined in rake files. Please define it in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
def module_method
^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
'in module'
end
end
namespace :gitlab do
# Method inside namespace - offense
def inside_namespace_method
^^^^^^^^^^^^^^^^^^^^^^^^^^^ Methods defined in rake tasks share the same namespace and can cause collisions. Please define it in a bounded contexts module in a separate Ruby file. For example, Search::RakeTask::<Namespace>. See https://github.com/rubocop/rubocop-rake/issues/42
'bad practice'
end
end
RUBY
end
end
end
context 'in a non-rake file' do
let(:source_file) { 'elastic.rb' }
it 'does not register an offense for method definitions outside modules' do
expect_no_offenses(<<~RUBY, source_file)
def task_executor_service
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
RUBY
end
it 'does not register an offense for method definitions inside blocks' do
expect_no_offenses(<<~RUBY, source_file)
something do
def task_executor_service
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
RUBY
end
it 'does not register an offense for class and module definitions' do
expect_no_offenses(<<~RUBY, source_file)
module SomeNamespace
class TaskHelper
def self.task_executor_service
Search::RakeTaskExecutorService.new(logger: stdout_logger)
end
end
end
RUBY
end
end
end

View File

@ -181,7 +181,7 @@ RSpec.describe 'Every Sidekiq worker', feature_category: :shared do
'Ci::UnlockPipelinesInQueueWorker' => 0,
'Ci::SyncReportsToReportApprovalRulesWorker' => 3,
'CleanupContainerRepositoryWorker' => 3,
'CloudConnector::SyncServiceTokenWorker' => 12,
'CloudConnector::SyncServiceTokenWorker' => 3,
'ClusterConfigureIstioWorker' => 3,
'ClusterInstallAppWorker' => 3,
'ClusterPatchAppWorker' => 3,