Add latest changes from gitlab-org/gitlab@master
This commit is contained in:
parent
852aade153
commit
41bd3e161f
|
|
@ -596,13 +596,10 @@ lib/gitlab/checks/**
|
|||
/doc/administration/redis/ @axil
|
||||
/doc/administration/reference_architectures/ @axil
|
||||
/doc/administration/reply_by_email_postfix_setup.md @axil
|
||||
/doc/administration/reporting/ @phillipwells
|
||||
/doc/administration/reporting/spamcheck.md @axil
|
||||
/doc/administration/reporting/ @axil
|
||||
/doc/administration/repository_checks.md @eread
|
||||
/doc/administration/repository_storage_paths.md @eread
|
||||
/doc/administration/restart_gitlab.md @axil
|
||||
/doc/administration/review_abuse_reports.md @phillipwells
|
||||
/doc/administration/review_spam_logs.md @phillipwells
|
||||
/doc/administration/server_hooks.md @eread
|
||||
/doc/administration/settings/account_and_limit_settings.md @msedlakjakubowski
|
||||
/doc/administration/settings/continuous_integration.md @marcel.amirault @lyspin
|
||||
|
|
@ -621,6 +618,7 @@ lib/gitlab/checks/**
|
|||
/doc/administration/settings/package_registry_rate_limits.md @phillipwells
|
||||
/doc/administration/settings/project_integration_management.md @eread @ashrafkhamis
|
||||
/doc/administration/settings/push_event_activities_limit.md @msedlakjakubowski
|
||||
/doc/administration/settings/rate_limit_on_groups_api.md @lciutacu
|
||||
/doc/administration/settings/rate_limit_on_issues_creation.md @msedlakjakubowski
|
||||
/doc/administration/settings/rate_limit_on_members_api.md @lciutacu
|
||||
/doc/administration/settings/rate_limit_on_notes_creation.md @msedlakjakubowski
|
||||
|
|
@ -684,6 +682,8 @@ lib/gitlab/checks/**
|
|||
/doc/api/geo_nodes.md @axil
|
||||
/doc/api/geo_sites.md @axil
|
||||
/doc/api/google_cloud_integration.md @jglassman1
|
||||
/doc/api/graphql/audit_event_streaming_groups.md @eread
|
||||
/doc/api/graphql/audit_event_streaming_instances.md @eread
|
||||
/doc/api/graphql/audit_report.md @eread
|
||||
/doc/api/graphql/branch_rules.md @msedlakjakubowski
|
||||
/doc/api/graphql/custom_emoji.md @msedlakjakubowski
|
||||
|
|
@ -875,12 +875,9 @@ lib/gitlab/checks/**
|
|||
/doc/install/ @axil
|
||||
/doc/integration/ @jglassman1
|
||||
/doc/integration/advanced_search/ @ashrafkhamis
|
||||
/doc/integration/akismet.md @phillipwells
|
||||
/doc/integration/arkose.md @phillipwells
|
||||
/doc/integration/datadog.md @fneill
|
||||
/doc/integration/diffblue_cover.md @marcel.amirault @lyspin
|
||||
/doc/integration/external-issue-tracker.md @eread @ashrafkhamis
|
||||
/doc/integration/github.md @marcel.amirault @lyspin
|
||||
/doc/integration/gitpod.md @ashrafkhamis
|
||||
/doc/integration/gmail_action_buttons_for_gitlab.md @eread @ashrafkhamis
|
||||
/doc/integration/index.md @eread @ashrafkhamis
|
||||
|
|
@ -888,7 +885,6 @@ lib/gitlab/checks/**
|
|||
/doc/integration/jira/ @eread @ashrafkhamis
|
||||
/doc/integration/mattermost/ @axil
|
||||
/doc/integration/partner_marketplace.md @fneill
|
||||
/doc/integration/recaptcha.md @phillipwells
|
||||
/doc/integration/sourcegraph.md @msedlakjakubowski
|
||||
/doc/integration/trello_power_up.md @eread @ashrafkhamis
|
||||
/doc/integration/vault.md @phillipwells
|
||||
|
|
@ -898,8 +894,6 @@ lib/gitlab/checks/**
|
|||
/doc/raketasks/spdx.md @rdickenson
|
||||
/doc/raketasks/x509_signatures.md @msedlakjakubowski
|
||||
/doc/security/ @jglassman1
|
||||
/doc/security/email_verification.md @phillipwells
|
||||
/doc/security/identity_verification.md @phillipwells
|
||||
/doc/solutions/ @jfullam @brianwald @Darwinjs
|
||||
/doc/subscriptions/ @fneill
|
||||
/doc/subscriptions/gitlab_dedicated/ @lyspin
|
||||
|
|
@ -941,9 +935,10 @@ lib/gitlab/checks/**
|
|||
/doc/user/application_security/ @rdickenson
|
||||
/doc/user/asciidoc.md @msedlakjakubowski
|
||||
/doc/user/clusters/ @phillipwells
|
||||
/doc/user/compliance/ @rdickenson
|
||||
/doc/user/compliance/compliance_center/ @eread
|
||||
/doc/user/compliance/index.md @eread
|
||||
/doc/user/compliance/ @eread
|
||||
/doc/user/compliance/license_approval_policies.md @rdickenson
|
||||
/doc/user/compliance/license_list.md @rdickenson
|
||||
/doc/user/compliance/license_scanning_of_cyclonedx_files/ @rdickenson
|
||||
/doc/user/custom_roles.md @jglassman1
|
||||
/doc/user/custom_roles/ @jglassman1
|
||||
/doc/user/discussions/ @aqualls
|
||||
|
|
@ -971,9 +966,7 @@ lib/gitlab/checks/**
|
|||
/doc/user/group/issues_analytics/ @lciutacu
|
||||
/doc/user/group/iterations/ @msedlakjakubowski
|
||||
/doc/user/group/manage.md @lciutacu
|
||||
/doc/user/group/moderate_users.md @phillipwells
|
||||
/doc/user/group/planning_hierarchy/ @msedlakjakubowski
|
||||
/doc/user/group/reporting/ @phillipwells
|
||||
/doc/user/group/repositories_analytics/ @marcel.amirault @lyspin
|
||||
/doc/user/group/roadmap/ @msedlakjakubowski
|
||||
/doc/user/group/saml_sso/ @jglassman1
|
||||
|
|
@ -1054,7 +1047,6 @@ lib/gitlab/checks/**
|
|||
/doc/user/project/web_ide/ @ashrafkhamis
|
||||
/doc/user/project/working_with_projects.md @lciutacu
|
||||
/doc/user/public_access.md @lciutacu
|
||||
/doc/user/report_abuse.md @phillipwells
|
||||
/doc/user/reserved_names.md @lciutacu
|
||||
/doc/user/search/ @ashrafkhamis
|
||||
/doc/user/search/command_palette.md @sselhorn
|
||||
|
|
|
|||
|
|
@ -18,23 +18,6 @@ Layout/ArgumentAlignment:
|
|||
- 'app/graphql/mutations/work_items/delete.rb'
|
||||
- 'app/graphql/mutations/work_items/update.rb'
|
||||
- 'app/graphql/resolvers/admin/analytics/usage_trends/measurements_resolver.rb'
|
||||
- 'ee/app/graphql/ee/mutations/issues/create.rb'
|
||||
- 'ee/app/graphql/ee/mutations/issues/update.rb'
|
||||
- 'ee/app/graphql/ee/mutations/work_items/create.rb'
|
||||
- 'ee/app/graphql/ee/mutations/work_items/update.rb'
|
||||
- 'ee/app/graphql/ee/resolvers/issues/base_parent_resolver.rb'
|
||||
- 'ee/app/graphql/ee/resolvers/issues/base_resolver.rb'
|
||||
- 'ee/app/graphql/ee/resolvers/namespace_projects_resolver.rb'
|
||||
- 'ee/app/graphql/ee/resolvers/work_items_resolver.rb'
|
||||
- 'ee/app/graphql/ee/types/alert_management/http_integration_type.rb'
|
||||
- 'ee/app/graphql/ee/types/boards/board_issue_input_base_type.rb'
|
||||
- 'ee/app/graphql/ee/types/boards/board_issue_input_type.rb'
|
||||
- 'ee/app/graphql/ee/types/boards/negated_board_issue_input_type.rb'
|
||||
- 'ee/app/graphql/ee/types/branch_protections/base_access_level_type.rb'
|
||||
- 'ee/app/graphql/ee/types/branch_rules/branch_protection_type.rb'
|
||||
- 'ee/app/graphql/ee/types/ci/runner_countable_connection_type.rb'
|
||||
- 'ee/app/graphql/ee/types/deployment_type.rb'
|
||||
- 'ee/app/graphql/ee/types/environment_type.rb'
|
||||
- 'ee/app/graphql/mutations/iterations/cadences/destroy.rb'
|
||||
- 'ee/app/graphql/mutations/iterations/create.rb'
|
||||
- 'ee/app/graphql/mutations/iterations/update.rb'
|
||||
|
|
|
|||
|
|
@ -20,22 +20,6 @@ Layout/SpaceInLambdaLiteral:
|
|||
- 'app/models/namespace_statistics.rb'
|
||||
- 'app/models/note.rb'
|
||||
- 'app/models/note_diff_file.rb'
|
||||
- 'app/models/operations/feature_flags/user_list.rb'
|
||||
- 'app/models/packages/build_info.rb'
|
||||
- 'app/models/packages/maven/metadatum.rb'
|
||||
- 'app/models/packages/package.rb'
|
||||
- 'app/models/packages/tag.rb'
|
||||
- 'app/models/personal_access_token.rb'
|
||||
- 'app/models/project.rb'
|
||||
- 'app/models/project_daily_statistic.rb'
|
||||
- 'app/models/project_feature_usage.rb'
|
||||
- 'app/models/project_group_link.rb'
|
||||
- 'app/models/project_statistics.rb'
|
||||
- 'app/models/projects/import_export/relation_export.rb'
|
||||
- 'app/models/projects/topic.rb'
|
||||
- 'app/models/prometheus_alert.rb'
|
||||
- 'app/models/prometheus_alert_event.rb'
|
||||
- 'app/models/prometheus_metric.rb'
|
||||
- 'app/serializers/analytics/cycle_analytics/stage_entity.rb'
|
||||
- 'app/serializers/base_discussion_entity.rb'
|
||||
- 'app/serializers/blob_entity.rb'
|
||||
|
|
@ -79,28 +63,6 @@ Layout/SpaceInLambdaLiteral:
|
|||
- 'ee/app/models/concerns/ee/protected_ref.rb'
|
||||
- 'ee/app/models/concerns/filterable_by_test_reports.rb'
|
||||
- 'ee/app/models/concerns/issue_widgets/acts_like_requirement.rb'
|
||||
- 'ee/app/models/saml_group_link.rb'
|
||||
- 'ee/app/models/sca/license_compliance.rb'
|
||||
- 'ee/app/models/security/finding.rb'
|
||||
- 'ee/app/models/security/orchestration_policy_configuration.rb'
|
||||
- 'ee/app/models/security/scan.rb'
|
||||
- 'ee/app/models/security/training.rb'
|
||||
- 'ee/app/models/security/training_provider.rb'
|
||||
- 'ee/app/models/software_license.rb'
|
||||
- 'ee/app/models/software_license_policy.rb'
|
||||
- 'ee/app/models/vulnerabilities/external_issue_link.rb'
|
||||
- 'ee/app/models/vulnerabilities/feedback.rb'
|
||||
- 'ee/app/models/vulnerabilities/finding.rb'
|
||||
- 'ee/app/models/vulnerabilities/finding_link.rb'
|
||||
- 'ee/app/models/vulnerabilities/finding_remediation.rb'
|
||||
- 'ee/app/models/vulnerabilities/finding_signature.rb'
|
||||
- 'ee/app/models/vulnerabilities/historical_statistic.rb'
|
||||
- 'ee/app/models/vulnerabilities/identifier.rb'
|
||||
- 'ee/app/models/vulnerabilities/issue_link.rb'
|
||||
- 'ee/app/models/vulnerabilities/read.rb'
|
||||
- 'ee/app/models/vulnerabilities/remediation.rb'
|
||||
- 'ee/app/models/vulnerabilities/scanner.rb'
|
||||
- 'ee/app/models/vulnerabilities/statistic.rb'
|
||||
- 'ee/app/serializers/blocking_merge_request_entity.rb'
|
||||
- 'ee/app/serializers/clusters/environment_entity.rb'
|
||||
- 'ee/app/serializers/dashboard_operations_project_entity.rb'
|
||||
|
|
|
|||
|
|
@ -40,6 +40,7 @@ RSpec/FilePath:
|
|||
- 'spec/requests/api/issues/get_project_issues_spec.rb'
|
||||
- 'spec/requests/api/issues/issues_spec.rb'
|
||||
- 'spec/requests/api/issues/post_projects_issues_spec.rb'
|
||||
- 'ee/spec/requests/api/ee/issues/post_projects_issues_spec.rb'
|
||||
- 'spec/requests/api/issues/put_projects_issues_spec.rb'
|
||||
- 'spec/requests/api/pages/pages_spec.rb'
|
||||
- 'spec/services/ci/create_pipeline_service/*'
|
||||
|
|
|
|||
|
|
@ -1 +1 @@
|
|||
v17.1.0-rc3
|
||||
v17.1.0-rc5
|
||||
|
|
|
|||
2
Gemfile
2
Gemfile
|
|
@ -273,7 +273,7 @@ gem 're2', '2.7.0' # rubocop:todo Gemfile/MissingFeatureCategory
|
|||
|
||||
# Misc
|
||||
|
||||
gem 'semver_dialects', '~> 2.0', '>= 2.0.2', feature_category: :static_application_security_testing
|
||||
gem 'semver_dialects', '~> 2.0', '>= 2.0.2', feature_category: :software_composition_analysis
|
||||
gem 'version_sorter', '~> 2.3' # rubocop:todo Gemfile/MissingFeatureCategory
|
||||
gem 'csv_builder', path: 'gems/csv_builder' # rubocop:todo Gemfile/MissingFeatureCategory
|
||||
|
||||
|
|
|
|||
|
|
@ -551,7 +551,7 @@
|
|||
{"name":"redcarpet","version":"3.6.0","platform":"ruby","checksum":"8ad1889c0355ff4c47174af14edd06d62f45a326da1da6e8a121d59bdcd2e9e9"},
|
||||
{"name":"redis","version":"5.2.0","platform":"ruby","checksum":"336b975a56b166c6af4d4a1026c71dbed429ba5dc949aac373ef2fded07936b4"},
|
||||
{"name":"redis-actionpack","version":"5.4.0","platform":"ruby","checksum":"f10cf649ab05914716d63334d7f709221ecc883b87cf348f90ecfe0c35ea3540"},
|
||||
{"name":"redis-client","version":"0.22.1","platform":"ruby","checksum":"b411b3812e83f817069dc20651dd3b01d4d417a0cab0f04fbaf143d6de19107e"},
|
||||
{"name":"redis-client","version":"0.22.2","platform":"ruby","checksum":"31fee4b7cf04109b227327fabeaaf1fc5b652cf48a186a03bc607e40767bacc0"},
|
||||
{"name":"redis-cluster-client","version":"0.8.2","platform":"ruby","checksum":"1ced1b8a86e2bd57d297de35194e06f84da306f22c13cfbb7103e6458055eb80"},
|
||||
{"name":"redis-clustering","version":"5.2.0","platform":"ruby","checksum":"685f388e0bdd81091a96cce9a46e22e727213d5fa14ebfc5111e110440e0038e"},
|
||||
{"name":"redis-namespace","version":"1.11.0","platform":"ruby","checksum":"e91a1aa2b2d888b6dea1d4ab8d39e1ae6fac3426161feb9d91dd5cca598a2239"},
|
||||
|
|
|
|||
|
|
@ -1484,7 +1484,7 @@ GEM
|
|||
actionpack (>= 5, < 8)
|
||||
redis-rack (>= 2.1.0, < 4)
|
||||
redis-store (>= 1.1.0, < 2)
|
||||
redis-client (0.22.1)
|
||||
redis-client (0.22.2)
|
||||
connection_pool
|
||||
redis-cluster-client (0.8.2)
|
||||
redis-client (~> 0.22)
|
||||
|
|
|
|||
|
|
@ -105,7 +105,7 @@ export default {
|
|||
title: $options.i18n.moveCardText,
|
||||
boundary: 'viewport',
|
||||
}"
|
||||
class="move-to-position gl-display-block gl-mb-2 gl-ml-auto -gl-mt-3 gl-mr-n3 js-no-trigger"
|
||||
class="move-to-position gl-display-block gl-mb-2 gl-ml-auto -gl-mt-3 -gl-mr-3 js-no-trigger"
|
||||
category="tertiary"
|
||||
:items="$options.BOARD_CARD_MOVE_TO_POSITIONS_OPTIONS"
|
||||
icon="ellipsis_v"
|
||||
|
|
|
|||
|
|
@ -172,7 +172,7 @@ export default {
|
|||
v-if="node.attrs.showPreview"
|
||||
:contenteditable="false"
|
||||
data-testid="sandbox-preview"
|
||||
class="!-gl-mt-3 gl-ml-n4! gl-mr-n4! gl-mb-3 gl-bg-white! gl-p-4 gl-border-b-1 gl-border-b-solid gl-border-b-gray-100"
|
||||
class="!-gl-mt-3 gl-ml-n4! !-gl-mr-4 gl-mb-3 gl-bg-white! gl-p-4 gl-border-b-1 gl-border-b-solid gl-border-b-gray-100"
|
||||
>
|
||||
<sandboxed-mermaid v-if="node.attrs.language === 'mermaid'" :source="diagramSource" />
|
||||
<img v-else ref="diagramContainer" :src="diagramUrl" />
|
||||
|
|
@ -191,7 +191,7 @@ export default {
|
|||
data-testid="code-suggestion-box"
|
||||
>
|
||||
<div
|
||||
class="md-suggestion-header gl-flex-wrap gl-z-1 gl-w-full gl-border-none! gl-font-regular gl-px-4 gl-py-3 gl-border-b-1! gl-border-b-solid! gl-mr-n10!"
|
||||
class="md-suggestion-header gl-flex-wrap gl-z-1 gl-w-full gl-border-none! gl-font-regular gl-px-4 gl-py-3 gl-border-b-1! gl-border-b-solid!"
|
||||
>
|
||||
<div class="gl-font-weight-bold gl-pr-3">
|
||||
{{ __('Suggested change') }}
|
||||
|
|
|
|||
|
|
@ -309,7 +309,7 @@ export default {
|
|||
<imported-badge v-if="isImported" :importable-type="$options.TYPE_COMMENT" size="sm" />
|
||||
</span>
|
||||
</div>
|
||||
<div class="gl-display-flex gl-align-items-flex-start -gl-mt-2 gl-mr-n2">
|
||||
<div class="gl-display-flex gl-align-items-flex-start -gl-mt-2 -gl-mr-2">
|
||||
<slot name="resolve-discussion"></slot>
|
||||
<emoji-picker
|
||||
v-if="canAwardEmoji"
|
||||
|
|
|
|||
|
|
@ -191,7 +191,7 @@ export default {
|
|||
<div
|
||||
class="item-attributes-area gl-display-flex gl-align-items-center gl-flex-wrap gl-gap-3"
|
||||
>
|
||||
<span v-if="hasPipeline" class="mr-ci-status order-md-last gl-md-ml-3 gl-mr-n2">
|
||||
<span v-if="hasPipeline" class="mr-ci-status order-md-last gl-md-ml-3 -gl-mr-2">
|
||||
<ci-icon :status="pipelineStatus" />
|
||||
</span>
|
||||
|
||||
|
|
|
|||
|
|
@ -196,7 +196,7 @@ export default {
|
|||
<span
|
||||
v-if="isForked"
|
||||
v-gl-tooltip
|
||||
class="gl-align-middle gl-mr-n2"
|
||||
class="gl-align-middle -gl-mr-2"
|
||||
:title="__('The source project is a fork')"
|
||||
>
|
||||
<gl-icon name="fork" :size="12" class="gl-ml-1" />
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ import 'bootstrap/js/dist/collapse';
|
|||
import MirrorRepos from '~/mirrors/mirror_repos';
|
||||
import mountBranchRules from '~/projects/settings/repository/branch_rules/mount_branch_rules';
|
||||
import mountDefaultBranchSelector from '~/projects/settings/mount_default_branch_selector';
|
||||
import mountRepositoryMaintenance from '~/projects/settings/repository/maintenance/mount_repository_maintenance';
|
||||
|
||||
import initForm from '../form';
|
||||
|
||||
|
|
@ -12,3 +13,4 @@ if (mirrorReposContainer) new MirrorRepos(mirrorReposContainer).init();
|
|||
|
||||
mountBranchRules(document.getElementById('js-branch-rules'));
|
||||
mountDefaultBranchSelector(document.querySelector('.js-select-default-branch'));
|
||||
mountRepositoryMaintenance();
|
||||
|
|
|
|||
|
|
@ -335,7 +335,7 @@ export default {
|
|||
<div class="col-12">
|
||||
<gl-form-group :label="$options.i18n.title.label" label-for="wiki_title">
|
||||
<template v-if="!isTemplate" #description>
|
||||
<gl-icon class="gl-mr-n1" name="bulb" />
|
||||
<gl-icon class="-gl-mr-1" name="bulb" />
|
||||
{{ titleHelpText }}
|
||||
<gl-link :href="helpPath" target="_blank">
|
||||
{{ $options.i18n.title.helpText.learnMore }}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,14 @@
|
|||
import Vue from 'vue';
|
||||
import RemoveBlobs from '~/projects/settings/repository/maintenance/remove_blobs.vue';
|
||||
|
||||
export default function mountRepositoryMaintenance() {
|
||||
const removeBlobsEl = document.querySelector('.js-maintenance-remove-blobs');
|
||||
if (!removeBlobsEl) return false;
|
||||
|
||||
return new Vue({
|
||||
el: removeBlobsEl,
|
||||
render(createElement) {
|
||||
return createElement(RemoveBlobs);
|
||||
},
|
||||
});
|
||||
}
|
||||
|
|
@ -0,0 +1,111 @@
|
|||
<script>
|
||||
import { GlButton, GlDrawer, GlLink, GlFormTextarea, GlModal } from '@gitlab/ui';
|
||||
import { helpPagePath } from '~/helpers/help_page_helper';
|
||||
import { DRAWER_Z_INDEX } from '~/lib/utils/constants';
|
||||
import { getContentWrapperHeight } from '~/lib/utils/dom_utils';
|
||||
import { s__ } from '~/locale';
|
||||
|
||||
const i18n = {
|
||||
removeBlobs: s__('ProjectMaintenance|Remove blobs'),
|
||||
description: s__(
|
||||
'ProjectMaintenance|Enter a list of object IDs to be removed to reduce repository size.',
|
||||
),
|
||||
helpLink: s__('ProjectMaintenance|How do I get a list of object IDs?'),
|
||||
label: s__('ProjectMaintenance|Blob IDs to remove'),
|
||||
helpText: s__('ProjectMaintenance|Enter multiple entries on separate lines.'),
|
||||
modalPrimaryText: s__('ProjectMaintenance|Yes, remove blobs'),
|
||||
modalCancelText: s__('ProjectMaintenance|Cancel'),
|
||||
modalContent: s__(
|
||||
'ProjectMaintenance|Removing blobs by ID cannot be undone. Are you sure you want to continue?',
|
||||
),
|
||||
};
|
||||
|
||||
export default {
|
||||
i18n,
|
||||
DRAWER_Z_INDEX,
|
||||
removeBlobsHelpLink: helpPagePath('/user/project/repository/reducing_the_repo_size_using_git'),
|
||||
modalCancel: { text: i18n.modalCancelText },
|
||||
modalPrimary: { text: i18n.modalPrimaryText, attributes: { variant: 'danger' } },
|
||||
components: { GlButton, GlDrawer, GlLink, GlFormTextarea, GlModal },
|
||||
data() {
|
||||
return { isDrawerOpen: false, blobIDs: null, showConfirmationModal: false };
|
||||
},
|
||||
computed: {
|
||||
getDrawerHeaderHeight() {
|
||||
return getContentWrapperHeight();
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
openDrawer() {
|
||||
this.isDrawerOpen = true;
|
||||
},
|
||||
closeDrawer() {
|
||||
this.blobIDs = null;
|
||||
this.isDrawerOpen = false;
|
||||
},
|
||||
removeBlobs() {
|
||||
this.showConfirmationModal = true;
|
||||
},
|
||||
removeBlobsConfirm() {
|
||||
// TODO (follow-up MR): submit mutation + show alert/toast...
|
||||
this.closeDrawer();
|
||||
},
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div>
|
||||
<gl-button class="gl-mb-6" data-testid="drawer-trigger" @click="openDrawer">{{
|
||||
$options.i18n.removeBlobs
|
||||
}}</gl-button>
|
||||
|
||||
<gl-drawer
|
||||
:header-height="getDrawerHeaderHeight"
|
||||
:open="isDrawerOpen"
|
||||
:z-index="$options.DRAWER_Z_INDEX"
|
||||
@close="closeDrawer"
|
||||
>
|
||||
<template #title>
|
||||
<h4 class="gl-m-0">{{ $options.i18n.removeBlobs }}</h4>
|
||||
</template>
|
||||
|
||||
<div>
|
||||
<p class="gl-text-secondary">
|
||||
{{ $options.i18n.description }}
|
||||
<gl-link :href="$options.removeBlobsHelpLink" target="_blank">{{
|
||||
$options.i18n.helpLink
|
||||
}}</gl-link>
|
||||
</p>
|
||||
<label for="blobs">{{ $options.i18n.label }}</label>
|
||||
<gl-form-textarea
|
||||
id="blobs"
|
||||
v-model.trim="blobIDs"
|
||||
class="!gl-font-monospace gl-mb-3"
|
||||
autofocus
|
||||
/>
|
||||
|
||||
<p class="gl-text-gray-400">{{ $options.i18n.helpText }}</p>
|
||||
|
||||
<gl-button
|
||||
data-testid="remove-blobs"
|
||||
variant="danger"
|
||||
:disabled="!blobIDs"
|
||||
@click="removeBlobs"
|
||||
>{{ $options.i18n.removeBlobs }}</gl-button
|
||||
>
|
||||
</div>
|
||||
</gl-drawer>
|
||||
|
||||
<gl-modal
|
||||
v-model="showConfirmationModal"
|
||||
:title="$options.i18n.removeBlobs"
|
||||
modal-id="remove-blobs-confirmation-modal"
|
||||
:action-cancel="$options.modalCancel"
|
||||
:action-primary="$options.modalPrimary"
|
||||
@primary="removeBlobsConfirm"
|
||||
>
|
||||
{{ $options.i18n.modalContent }}
|
||||
</gl-modal>
|
||||
</div>
|
||||
</template>
|
||||
|
|
@ -127,8 +127,8 @@ export default {
|
|||
accessLevelTooltipDescription: s__(
|
||||
'SecretDetection|Only a project maintainer or owner can toggle this feature.',
|
||||
),
|
||||
toastMessageEnabled: s__('SecretDetection|Pre-receive Secret Detection is enabled'),
|
||||
toastMessageDisabled: s__('SecretDetection|Pre-receive Secret Detection is disabled'),
|
||||
toastMessageEnabled: s__('SecretDetection|Secret push protection is enabled'),
|
||||
toastMessageDisabled: s__('SecretDetection|Secret push protection is disabled'),
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
|
@ -188,7 +188,7 @@ export default {
|
|||
class="gl-mt-5"
|
||||
:disabled="isToggleDisabled"
|
||||
:value="toggleValue"
|
||||
:label="s__('SecurityConfiguration|Toggle Pre-receive secret detection')"
|
||||
:label="s__('SecurityConfiguration|Toggle secret push protection')"
|
||||
label-position="hidden"
|
||||
@change="togglePreReceiveSecretDetection"
|
||||
/>
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ export const CLUSTER_IMAGE_SCANNING_NAME = s__('ciReport|Cluster Image Scanning'
|
|||
|
||||
export const PRE_RECEIVE_SECRET_DETECTION = 'pre_receive_secret_detection';
|
||||
|
||||
export const PRE_RECEIVE_SECRET_DETECTION_NAME = __('Pre-receive Secret Detection');
|
||||
export const PRE_RECEIVE_SECRET_DETECTION_NAME = __('Secret push protection');
|
||||
|
||||
export const SCANNER_NAMES_MAP = {
|
||||
SAST: SAST_SHORT_NAME,
|
||||
|
|
|
|||
|
|
@ -126,12 +126,12 @@ export default {
|
|||
</script>
|
||||
|
||||
<template>
|
||||
<div class="gl-md-display-flex row-content-block">
|
||||
<!-- `gl-w-full gl-md-w-15` forces fixed width needed to prevent
|
||||
filtered component to grow beyond available width -->
|
||||
<div
|
||||
class="gl-display-flex gl-flex-direction-column gl-md-flex-direction-row gl-gap-3 row-content-block"
|
||||
>
|
||||
<gl-filtered-search
|
||||
v-model="internalFilter"
|
||||
class="gl-w-full gl-md-w-15 gl-mr-4 gl-flex-grow-1"
|
||||
class="gl-flex-grow-1 gl-min-w-0"
|
||||
:placeholder="__('Filter results')"
|
||||
:available-tokens="tokens"
|
||||
@submit="submitSearch"
|
||||
|
|
@ -139,10 +139,8 @@ export default {
|
|||
/>
|
||||
<gl-sorting
|
||||
data-testid="registry-sort-dropdown"
|
||||
class="gl-mt-3 gl-md-mt-0 gl-w-full gl-md-w-auto"
|
||||
dropdown-class="gl-w-full"
|
||||
dropdown-toggle-class="!gl-shadow-inner-1-gray-400"
|
||||
sort-direction-toggle-class="!gl-shadow-inner-1-gray-400"
|
||||
block
|
||||
:text="sortText"
|
||||
:is-ascending="isSortAscending"
|
||||
:sort-direction-tool-tip="sortDirectionData.tooltip"
|
||||
|
|
|
|||
|
|
@ -92,9 +92,12 @@
|
|||
.wiki-list {
|
||||
min-height: 30px;
|
||||
|
||||
&:hover {
|
||||
&:hover,
|
||||
&.active {
|
||||
background: var(--gray-50, $gray-50);
|
||||
}
|
||||
|
||||
&:hover {
|
||||
a {
|
||||
color: $black;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -35,7 +35,7 @@ module DiffHelper
|
|||
options[:paths] = params.values_at(:old_path, :new_path)
|
||||
options[:use_extra_viewer_as_main] = false
|
||||
|
||||
if Feature.enabled?(:large_ipynb_diffs, @project) && params[:file_identifier]&.include?('.ipynb')
|
||||
if params[:file_identifier]&.include?('.ipynb')
|
||||
options[:max_patch_bytes_for_file_extension] = {
|
||||
'.ipynb' => 1.megabyte
|
||||
}
|
||||
|
|
|
|||
|
|
@ -271,7 +271,7 @@ module MergeRequestsHelper
|
|||
def merge_request_source_branch(merge_request)
|
||||
fork_icon = if merge_request.for_fork?
|
||||
title = _('The source project is a fork')
|
||||
content_tag(:span, class: 'gl-align-middle gl-mr-n2 has-tooltip', title: title) do
|
||||
content_tag(:span, class: 'gl-align-middle -gl-mr-2 has-tooltip', title: title) do
|
||||
sprite_icon('fork', size: 12, css_class: 'gl-ml-1 has-tooltip')
|
||||
end
|
||||
else
|
||||
|
|
|
|||
|
|
@ -12,6 +12,24 @@ module Emails
|
|||
)
|
||||
end
|
||||
|
||||
def bulk_import_complete(user_id, bulk_import_id)
|
||||
user = User.find(user_id)
|
||||
@bulk_import = BulkImport.find(bulk_import_id)
|
||||
@bulk_import_entity = @bulk_import.entities.find_by(source_type: 'group_entity') # rubocop:disable CodeReuse/ActiveRecord -- Move this to BulkImport model
|
||||
@hostname = @bulk_import.configuration.url
|
||||
@source_group = @bulk_import_entity.source_full_path
|
||||
title = safe_format(
|
||||
s_('BulkImport|Import of %{source_group} from %{hostname}'),
|
||||
hostname: @hostname,
|
||||
source_group: @source_group
|
||||
)
|
||||
|
||||
email_with_layout(
|
||||
to: user.notification_email_or_default,
|
||||
subject: subject(title)
|
||||
)
|
||||
end
|
||||
|
||||
def bulk_import_csv_user_mapping(user_id, group_id, success_count, failed_count = 0)
|
||||
user = User.find(user_id)
|
||||
@group = Group.find(group_id)
|
||||
|
|
|
|||
|
|
@ -357,6 +357,12 @@ class NotifyPreview < ActionMailer::Preview
|
|||
Notify.github_gists_import_errors_email(user.id, { '12345' => 'Snippet maximum file count exceeded', '67890' => 'error message 2' }).message
|
||||
end
|
||||
|
||||
def bulk_import_complete
|
||||
bulk_import = BulkImport.last
|
||||
|
||||
Notify.bulk_import_complete(user.id, bulk_import.id)
|
||||
end
|
||||
|
||||
def bulk_import_csv_user_mapping_success
|
||||
Notify.bulk_import_csv_user_mapping(user.id, group.id, 94125, 0)
|
||||
end
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ module Operations
|
|||
|
||||
before_destroy :ensure_no_associated_strategies
|
||||
|
||||
scope :for_name_like, -> (query) do
|
||||
scope :for_name_like, ->(query) do
|
||||
fuzzy_search(query, [:name], use_minimum_char_limit: false)
|
||||
end
|
||||
|
||||
|
|
|
|||
|
|
@ -6,9 +6,9 @@ class Packages::BuildInfo < ApplicationRecord
|
|||
|
||||
scope :pluck_pipeline_ids, -> { pluck(:pipeline_id) }
|
||||
scope :without_empty_pipelines, -> { where.not(pipeline_id: nil) }
|
||||
scope :order_by_pipeline_id, -> (direction) { order(pipeline_id: direction) }
|
||||
scope :with_pipeline_id_less_than, -> (pipeline_id) { where("#{table_name}.pipeline_id < ?", pipeline_id) }
|
||||
scope :with_pipeline_id_greater_than, -> (pipeline_id) { where("#{table_name}.pipeline_id > ?", pipeline_id) }
|
||||
scope :order_by_pipeline_id, ->(direction) { order(pipeline_id: direction) }
|
||||
scope :with_pipeline_id_less_than, ->(pipeline_id) { where("#{table_name}.pipeline_id < ?", pipeline_id) }
|
||||
scope :with_pipeline_id_greater_than, ->(pipeline_id) { where("#{table_name}.pipeline_id > ?", pipeline_id) }
|
||||
|
||||
def self.supported_keyset_orderings
|
||||
{ id: [:desc] }
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ class Packages::Maven::Metadatum < ApplicationRecord
|
|||
|
||||
validate :maven_package_type
|
||||
|
||||
scope :for_package_ids, -> (package_ids) { where(package_id: package_ids) }
|
||||
scope :for_package_ids, ->(package_ids) { where(package_id: package_ids) }
|
||||
scope :with_path, ->(path) { where(path: path) }
|
||||
scope :order_created, -> { reorder('created_at ASC') }
|
||||
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ class Packages::Package < ApplicationRecord
|
|||
has_one :terraform_module_metadatum, inverse_of: :package, class_name: 'Packages::TerraformModule::Metadatum'
|
||||
has_many :build_infos, inverse_of: :package
|
||||
has_many :pipelines, through: :build_infos, disable_joins: true
|
||||
has_many :matching_package_protection_rules, -> (package) { where(package_type: package.package_type).for_package_name(package.name) }, through: :project, source: :package_protection_rules
|
||||
has_many :matching_package_protection_rules, ->(package) { where(package_type: package.package_type).for_package_name(package.name) }, through: :project, source: :package_protection_rules
|
||||
|
||||
accepts_nested_attributes_for :maven_metadatum
|
||||
|
||||
|
|
@ -126,7 +126,7 @@ class Packages::Package < ApplicationRecord
|
|||
|
||||
scope :search_by_name, ->(query) { fuzzy_search(query, [:name], use_minimum_char_limit: false) }
|
||||
scope :with_version, ->(version) { where(version: version) }
|
||||
scope :without_version_like, -> (version) { where.not(arel_table[:version].matches(version)) }
|
||||
scope :without_version_like, ->(version) { where.not(arel_table[:version].matches(version)) }
|
||||
scope :with_package_type, ->(package_type) { where(package_type: package_type) }
|
||||
scope :without_package_type, ->(package_type) { where.not(package_type: package_type) }
|
||||
scope :displayable, -> { with_status(DISPLAYABLE_STATUSES) }
|
||||
|
|
@ -136,7 +136,7 @@ class Packages::Package < ApplicationRecord
|
|||
scope :including_dependency_links, -> { includes(dependency_links: :dependency) }
|
||||
scope :including_dependency_links_with_nuget_metadatum, -> { includes(dependency_links: [:dependency, :nuget_metadatum]) }
|
||||
|
||||
scope :with_composer_target, -> (target) do
|
||||
scope :with_composer_target, ->(target) do
|
||||
includes(:composer_metadatum)
|
||||
.joins(:composer_metadatum)
|
||||
.where(Packages::Composer::Metadatum.table_name => { target_sha: target })
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ class Packages::Tag < ApplicationRecord
|
|||
NUGET_TAGS_SEPARATOR = ' ' # https://docs.microsoft.com/en-us/nuget/reference/nuspec#tags
|
||||
|
||||
scope :preload_package, -> { preload(:package) }
|
||||
scope :with_name, -> (name) { where(name: name) }
|
||||
scope :with_name, ->(name) { where(name: name) }
|
||||
|
||||
def self.for_package_ids(package_ids)
|
||||
where(package_id: package_ids)
|
||||
|
|
|
|||
|
|
@ -29,19 +29,19 @@ class PersonalAccessToken < ApplicationRecord
|
|||
scope :expiring_and_not_notified, ->(date) { where(["revoked = false AND expire_notification_delivered = false AND expires_at >= CURRENT_DATE AND expires_at <= ?", date]) }
|
||||
scope :expired_today_and_not_notified, -> { where(["revoked = false AND expires_at = CURRENT_DATE AND after_expiry_notification_delivered = false"]) }
|
||||
scope :inactive, -> { where("revoked = true OR expires_at < CURRENT_DATE") }
|
||||
scope :last_used_before_or_unused, -> (date) { where("personal_access_tokens.created_at < :date AND (last_used_at < :date OR last_used_at IS NULL)", date: date) }
|
||||
scope :last_used_before_or_unused, ->(date) { where("personal_access_tokens.created_at < :date AND (last_used_at < :date OR last_used_at IS NULL)", date: date) }
|
||||
scope :with_impersonation, -> { where(impersonation: true) }
|
||||
scope :without_impersonation, -> { where(impersonation: false) }
|
||||
scope :revoked, -> { where(revoked: true) }
|
||||
scope :not_revoked, -> { where(revoked: [false, nil]) }
|
||||
scope :for_user, -> (user) { where(user: user) }
|
||||
scope :for_users, -> (users) { where(user: users) }
|
||||
scope :for_user, ->(user) { where(user: user) }
|
||||
scope :for_users, ->(users) { where(user: users) }
|
||||
scope :preload_users, -> { preload(:user) }
|
||||
scope :order_expires_at_asc_id_desc, -> { reorder(expires_at: :asc, id: :desc) }
|
||||
scope :project_access_token, -> { includes(:user).references(:user).merge(User.project_bot) }
|
||||
scope :owner_is_human, -> { includes(:user).references(:user).merge(User.human) }
|
||||
scope :last_used_before, -> (date) { where("last_used_at <= ?", date) }
|
||||
scope :last_used_after, -> (date) { where("last_used_at >= ?", date) }
|
||||
scope :last_used_before, ->(date) { where("last_used_at <= ?", date) }
|
||||
scope :last_used_after, ->(date) { where("last_used_at >= ?", date) }
|
||||
scope :expiring_and_not_notified_without_impersonation, -> { where(["(revoked = false AND expire_notification_delivered = false AND expires_at >= CURRENT_DATE AND expires_at <= :date) and impersonation = false", { date: DAYS_TO_EXPIRE.days.from_now.to_date }]) }
|
||||
|
||||
validates :scopes, presence: true
|
||||
|
|
|
|||
|
|
@ -649,7 +649,7 @@ class Project < ApplicationRecord
|
|||
# Sometimes queries (e.g. using CTEs) require explicit disambiguation with table name
|
||||
scope :projects_order_id_asc, -> { reorder(self.arel_table['id'].asc) }
|
||||
scope :projects_order_id_desc, -> { reorder(self.arel_table['id'].desc) }
|
||||
scope :order_by_storage_size, -> (direction) do
|
||||
scope :order_by_storage_size, ->(direction) do
|
||||
build_keyset_order_on_joined_column(
|
||||
scope: joins(:statistics),
|
||||
attribute_name: 'project_statistics_storage_size',
|
||||
|
|
@ -659,7 +659,7 @@ class Project < ApplicationRecord
|
|||
)
|
||||
end
|
||||
|
||||
scope :sorted_by_similarity_desc, -> (search, full_path_only: false) do
|
||||
scope :sorted_by_similarity_desc, ->(search, full_path_only: false) do
|
||||
rules = if full_path_only
|
||||
[{ column: arel_table["path"], multiplier: 1 }]
|
||||
else
|
||||
|
|
@ -713,9 +713,9 @@ class Project < ApplicationRecord
|
|||
scope :with_group, -> { includes(:group) }
|
||||
scope :with_import_state, -> { includes(:import_state) }
|
||||
scope :include_project_feature, -> { includes(:project_feature) }
|
||||
scope :include_integration, -> (integration_association_name) { includes(integration_association_name) }
|
||||
scope :with_integration, -> (integration_class) { joins(:integrations).merge(integration_class.all) }
|
||||
scope :with_active_integration, -> (integration_class) { with_integration(integration_class).merge(integration_class.active) }
|
||||
scope :include_integration, ->(integration_association_name) { includes(integration_association_name) }
|
||||
scope :with_integration, ->(integration_class) { joins(:integrations).merge(integration_class.all) }
|
||||
scope :with_active_integration, ->(integration_class) { with_integration(integration_class).merge(integration_class.active) }
|
||||
scope :with_shared_runners_enabled, -> { where(shared_runners_enabled: true) }
|
||||
# .with_slack_integration can generate poorly performing queries. It is intended only for UsagePing.
|
||||
scope :with_slack_integration, -> { joins(:slack_integration) }
|
||||
|
|
@ -763,12 +763,12 @@ class Project < ApplicationRecord
|
|||
scope :with_package_registry_enabled, -> { with_feature_enabled(:package_registry) }
|
||||
scope :with_issues_available_for_user, ->(current_user) { with_feature_available_for_user(:issues, current_user) }
|
||||
scope :with_merge_requests_available_for_user, ->(current_user) { with_feature_available_for_user(:merge_requests, current_user) }
|
||||
scope :with_issues_or_mrs_available_for_user, -> (user) do
|
||||
scope :with_issues_or_mrs_available_for_user, ->(user) do
|
||||
with_issues_available_for_user(user).or(with_merge_requests_available_for_user(user))
|
||||
end
|
||||
scope :with_merge_requests_enabled, -> { with_feature_enabled(:merge_requests) }
|
||||
scope :with_remote_mirrors, -> { joins(:remote_mirrors).where(remote_mirrors: { enabled: true }) }
|
||||
scope :with_limit, -> (maximum) { limit(maximum) }
|
||||
scope :with_limit, ->(maximum) { limit(maximum) }
|
||||
|
||||
scope :with_group_runners_enabled, -> do
|
||||
joins(:ci_cd_settings)
|
||||
|
|
@ -788,14 +788,14 @@ class Project < ApplicationRecord
|
|||
preload(:project_feature, :route, namespace: [:route, :owner])
|
||||
}
|
||||
|
||||
scope :with_name, -> (name) { where(name: name) }
|
||||
scope :created_by, -> (user) { where(creator: user) }
|
||||
scope :imported_from, -> (type) { where(import_type: type) }
|
||||
scope :with_name, ->(name) { where(name: name) }
|
||||
scope :created_by, ->(user) { where(creator: user) }
|
||||
scope :imported_from, ->(type) { where(import_type: type) }
|
||||
scope :imported, -> { where.not(import_type: nil) }
|
||||
scope :with_enabled_error_tracking, -> { joins(:error_tracking_setting).where(project_error_tracking_settings: { enabled: true }) }
|
||||
scope :last_activity_before, -> (time) { where('projects.last_activity_at < ?', time) }
|
||||
scope :last_activity_before, ->(time) { where('projects.last_activity_at < ?', time) }
|
||||
|
||||
scope :with_service_desk_key, -> (key) do
|
||||
scope :with_service_desk_key, ->(key) do
|
||||
# project_key is not indexed for now
|
||||
# see https://gitlab.com/gitlab-org/gitlab/-/merge_requests/24063#note_282435524 for details
|
||||
joins(:service_desk_setting).where('service_desk_settings.project_key' => key)
|
||||
|
|
@ -815,8 +815,8 @@ class Project < ApplicationRecord
|
|||
.order(id: :desc)
|
||||
end
|
||||
|
||||
scope :in_organization, -> (organization) { where(organization: organization) }
|
||||
scope :by_project_namespace, -> (project_namespace) { where(project_namespace_id: project_namespace) }
|
||||
scope :in_organization, ->(organization) { where(organization: organization) }
|
||||
scope :by_project_namespace, ->(project_namespace) { where(project_namespace_id: project_namespace) }
|
||||
|
||||
scope :not_a_fork, -> {
|
||||
left_outer_joins(:fork_network_member).where(fork_network_member: { forked_from_project_id: nil })
|
||||
|
|
@ -945,7 +945,7 @@ class Project < ApplicationRecord
|
|||
|
||||
# We require an alias to the project_mirror_data_table in order to use import_state in our queries
|
||||
scope :joins_import_state, -> { joins("INNER JOIN project_mirror_data import_state ON import_state.project_id = projects.id") }
|
||||
scope :for_group, -> (group) { where(group: group) }
|
||||
scope :for_group, ->(group) { where(group: group) }
|
||||
scope :for_group_and_its_subgroups, ->(group) { where(namespace_id: group.self_and_descendants.select(:id)) }
|
||||
scope :for_group_and_its_ancestor_groups, ->(group) { where(namespace_id: group.self_and_ancestors.select(:id)) }
|
||||
scope :is_importing, -> { with_import_state.where(import_state: { status: %w[started scheduled] }) }
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ class ProjectDailyStatistic < ApplicationRecord
|
|||
|
||||
counter_attribute :fetch_count
|
||||
|
||||
scope :of_project, -> (project) { where(project: project) }
|
||||
scope :of_project, ->(project) { where(project: project) }
|
||||
scope :of_last_30_days, -> { where('date >= ?', 29.days.ago.utc.to_date) }
|
||||
scope :sorted_by_date_desc, -> { order(project_id: :desc, date: :desc) }
|
||||
scope :sum_fetch_count, -> { sum(:fetch_count) }
|
||||
|
|
|
|||
|
|
@ -50,7 +50,6 @@ class ProjectExportJob < ApplicationRecord
|
|||
private
|
||||
|
||||
def audit_project_exported
|
||||
return if Feature.disabled?(:export_audit_events, user)
|
||||
return if exported_by_admin? && Gitlab::CurrentSettings.silent_admin_exports_enabled?
|
||||
|
||||
audit_context = {
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ class ProjectFeatureUsage < ApplicationRecord
|
|||
belongs_to :project
|
||||
validates :project, presence: true
|
||||
|
||||
scope :with_jira_dvcs_integration_enabled, -> (cloud: true) do
|
||||
scope :with_jira_dvcs_integration_enabled, ->(cloud: true) do
|
||||
where.not(jira_dvcs_integration_field(cloud: cloud) => nil)
|
||||
end
|
||||
|
||||
|
|
|
|||
|
|
@ -15,8 +15,8 @@ class ProjectGroupLink < ApplicationRecord
|
|||
validate :different_group
|
||||
|
||||
scope :non_guests, -> { where('group_access > ?', Gitlab::Access::GUEST) }
|
||||
scope :in_group, -> (group_ids) { where(group_id: group_ids) }
|
||||
scope :for_projects, -> (project_ids) { where(project_id: project_ids) }
|
||||
scope :in_group, ->(group_ids) { where(group_id: group_ids) }
|
||||
scope :for_projects, ->(project_ids) { where(project_id: project_ids) }
|
||||
|
||||
alias_method :shared_with_group, :group
|
||||
alias_method :shared_from, :project
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ class ProjectStatistics < ApplicationRecord
|
|||
|
||||
scope :for_project_ids, ->(project_ids) { where(project_id: project_ids) }
|
||||
|
||||
scope :for_namespaces, -> (namespaces) { where(namespace: namespaces) }
|
||||
scope :for_namespaces, ->(namespaces) { where(namespace: namespaces) }
|
||||
|
||||
def total_repository_size
|
||||
repository_size + lfs_objects_size
|
||||
|
|
|
|||
|
|
@ -32,7 +32,7 @@ module Projects
|
|||
validates :relation, presence: true, length: { maximum: 255 }, uniqueness: { scope: :project_export_job_id }
|
||||
validates :status, numericality: { only_integer: true }, presence: true
|
||||
|
||||
scope :by_relation, -> (relation) { where(relation: relation) }
|
||||
scope :by_relation, ->(relation) { where(relation: relation) }
|
||||
|
||||
STATUS = {
|
||||
queued: 0,
|
||||
|
|
|
|||
|
|
@ -19,6 +19,14 @@ module Projects
|
|||
end
|
||||
|
||||
mount_uploader :export_file, ImportExportUploader
|
||||
|
||||
# This causes CarrierWave v1 and v3 (but not v2) to upload the file to
|
||||
# object storage *after* the database entry has been committed to the
|
||||
# database. This avoids idling in a transaction. Similar to `ImportExportUpload`.
|
||||
if Gitlab::Utils.to_boolean(ENV.fetch('ENABLE_STORE_EXPORT_FILE_AFTER_COMMIT', true))
|
||||
skip_callback :save, :after, :store_export_file!
|
||||
set_callback :commit, :after, :store_export_file!
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ module Projects
|
|||
|
||||
scope :without_assigned_projects, -> { where(total_projects_count: 0) }
|
||||
scope :order_by_non_private_projects_count, -> { order(non_private_projects_count: :desc).order(id: :asc) }
|
||||
scope :reorder_by_similarity, -> (search) do
|
||||
scope :reorder_by_similarity, ->(search) do
|
||||
order_expression = Gitlab::Database::SimilarityScore.build_expression(
|
||||
search: search,
|
||||
rules: [
|
||||
|
|
|
|||
|
|
@ -33,9 +33,9 @@ class PrometheusAlert < ApplicationRecord
|
|||
|
||||
delegate :title, :query, to: :prometheus_metric
|
||||
|
||||
scope :for_metric, -> (metric) { where(prometheus_metric: metric) }
|
||||
scope :for_project, -> (project) { where(project_id: project) }
|
||||
scope :for_environment, -> (environment) { where(environment_id: environment) }
|
||||
scope :for_metric, ->(metric) { where(prometheus_metric: metric) }
|
||||
scope :for_project, ->(project) { where(project_id: project) }
|
||||
scope :for_environment, ->(environment) { where(environment_id: environment) }
|
||||
scope :get_environment_id, -> { select(:environment_id).pluck(:environment_id) }
|
||||
|
||||
def self.distinct_projects
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ class PrometheusAlertEvent < ApplicationRecord
|
|||
|
||||
delegate :title, :prometheus_metric_id, to: :prometheus_alert
|
||||
|
||||
scope :for_environment, -> (environment) do
|
||||
scope :for_environment, ->(environment) do
|
||||
joins(:prometheus_alert).where(prometheus_alerts: { environment_id: environment })
|
||||
end
|
||||
|
||||
|
|
|
|||
|
|
@ -18,13 +18,13 @@ class PrometheusMetric < ApplicationRecord
|
|||
validates :project, presence: true, unless: :common?
|
||||
validates :project, absence: true, if: :common?
|
||||
|
||||
scope :for_dashboard_path, -> (dashboard_path) { where(dashboard_path: dashboard_path) }
|
||||
scope :for_project, -> (project) { where(project: project) }
|
||||
scope :for_group, -> (group) { where(group: group) }
|
||||
scope :for_title, -> (title) { where(title: title) }
|
||||
scope :for_y_label, -> (y_label) { where(y_label: y_label) }
|
||||
scope :for_identifier, -> (identifier) { where(identifier: identifier) }
|
||||
scope :not_identifier, -> (identifier) { where.not(identifier: identifier) }
|
||||
scope :for_dashboard_path, ->(dashboard_path) { where(dashboard_path: dashboard_path) }
|
||||
scope :for_project, ->(project) { where(project: project) }
|
||||
scope :for_group, ->(group) { where(group: group) }
|
||||
scope :for_title, ->(title) { where(title: title) }
|
||||
scope :for_y_label, ->(y_label) { where(y_label: y_label) }
|
||||
scope :for_identifier, ->(identifier) { where(identifier: identifier) }
|
||||
scope :not_identifier, ->(identifier) { where.not(identifier: identifier) }
|
||||
scope :common, -> { where(common: true) }
|
||||
scope :ordered, -> { reorder(created_at: :asc) }
|
||||
|
||||
|
|
|
|||
|
|
@ -112,7 +112,6 @@ module Groups
|
|||
end
|
||||
|
||||
def audit_export
|
||||
return if Feature.disabled?(:export_audit_events, current_user)
|
||||
return if exported_by_admin && Gitlab::CurrentSettings.silent_admin_exports_enabled?
|
||||
|
||||
audit_context = {
|
||||
|
|
|
|||
|
|
@ -6,6 +6,8 @@ module Issues
|
|||
include IncidentManagement::UsageData
|
||||
include IssueTypeHelpers
|
||||
|
||||
EpicAssignmentError = Class.new(::ArgumentError)
|
||||
|
||||
def hook_data(issue, action, old_associations: {})
|
||||
hook_data = issue.to_hook_data(current_user, old_associations: old_associations)
|
||||
hook_data[:object_attributes][:action] = action
|
||||
|
|
|
|||
|
|
@ -17,12 +17,11 @@
|
|||
.form-group{ data: { testid: 'bulk-import' } }
|
||||
= f.label :bulk_import, s_('AdminSettings|Allow migrating GitLab groups and projects by direct transfer'), class: 'gl-font-weight-bold'
|
||||
= f.gitlab_ui_checkbox_component :bulk_import_enabled, s_('AdminSettings|Enabled')
|
||||
- if Feature.enabled?(:export_audit_events, current_user)
|
||||
.form-group{ data: { testid: 'silent-admin-exports' } }
|
||||
- tag_pair_silent_admin_exports = tag_pair(link_to('', help_page_path('administration/settings/import_and_export_settings', anchor: 'enable-silent-admin-exports'), target: '_blank', rel: 'noopener noreferrer'), :silent_admin_exports_link_start, :silent_admin_exports_link_end)
|
||||
- silent_admin_exports_label_text = safe_format(s_('AdminSettings|Silent exports by admins %{silent_admin_exports_link_start}%{icon}%{silent_admin_exports_link_end}'), tag_pair_silent_admin_exports, icon: sprite_icon('question-o'))
|
||||
= f.label :silent_admin_exports_enabled, silent_admin_exports_label_text, class: 'gl-font-weight-bold'
|
||||
= f.gitlab_ui_checkbox_component :silent_admin_exports_enabled, s_('AdminSettings|Enabled')
|
||||
.form-group{ data: { testid: 'silent-admin-exports' } }
|
||||
- tag_pair_silent_admin_exports = tag_pair(link_to('', help_page_path('administration/settings/import_and_export_settings', anchor: 'enable-silent-admin-exports'), target: '_blank', rel: 'noopener noreferrer'), :silent_admin_exports_link_start, :silent_admin_exports_link_end)
|
||||
- silent_admin_exports_label_text = safe_format(s_('AdminSettings|Silent exports by admins %{silent_admin_exports_link_start}%{icon}%{silent_admin_exports_link_end}'), tag_pair_silent_admin_exports, icon: sprite_icon('question-o'))
|
||||
= f.label :silent_admin_exports_enabled, silent_admin_exports_label_text, class: 'gl-font-weight-bold'
|
||||
= f.gitlab_ui_checkbox_component :silent_admin_exports_enabled, s_('AdminSettings|Enabled')
|
||||
.form-group
|
||||
= f.label :max_export_size, _('Maximum export size (MiB)'), class: 'label-light'
|
||||
= f.number_field :max_export_size, class: 'form-control gl-form-input', title: _('Maximum size of export files.'), data: { toggle: 'tooltip', container: 'body' }
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
= gl_tabs_nav({ class: 'gl-flex-grow-1 gl-border-0', data: { testid: 'admin-users-tabs' } }) do
|
||||
= gl_tab_link_to s_('AdminUsers|Users'), admin_users_path
|
||||
= render_if_exists 'admin/users/role_promotion_requests_tab'
|
||||
= gl_tab_link_to s_('AdminUsers|Cohorts'), admin_cohorts_path
|
||||
|
|
|
|||
|
|
@ -0,0 +1,24 @@
|
|||
- header_style = 'font-size:24px; text-align:center; line-height:30px;'
|
||||
- text_style = 'font-size:16px; text-align:center; line-height:24px; margin-top: 24px;'
|
||||
- button_style = 'border: 1px solid #694cc0; border-radius: 4px; font-size: 14px; padding: 8px 16px; background-color: #7b58cf; color: #fff; cursor: pointer;'
|
||||
|
||||
- strong_tag_pair = tag_pair(tag.strong, :strong_open, :strong_close)
|
||||
- strong_color_tag_pair = tag_pair(tag.strong(style: 'color: #7b58cf'), :strong_color_open, :strong_color_close)
|
||||
|
||||
- destination_group = @bulk_import_entity.full_path_with_fallback
|
||||
|
||||
%h1{ style: header_style }
|
||||
= s_('BulkImport|Import completed')
|
||||
|
||||
%p{ style: text_style }
|
||||
= safe_format(s_('BulkImport|The import of %{strong_open}%{source_group}%{strong_close} from %{strong_open}%{hostname}%{strong_close} to %{strong_color_open}%{destination_group}%{strong_color_close} is complete. You can view the results of the import.'),
|
||||
strong_tag_pair,
|
||||
strong_color_tag_pair,
|
||||
source_group: @source_group,
|
||||
hostname: @hostname,
|
||||
destination_group: destination_group)
|
||||
|
||||
%p{ style: text_style }
|
||||
= link_to history_import_bulk_import_url(@bulk_import.id), target: '_blank', rel: 'noopener noreferrer' do
|
||||
%button{ type: 'button', style: button_style }
|
||||
= s_('BulkImport|View import results')
|
||||
|
|
@ -0,0 +1,7 @@
|
|||
<% destination_group = @bulk_import_entity.full_path_with_fallback %>
|
||||
|
||||
<%= s_('BulkImport|Import completed') %>
|
||||
|
||||
<%= safe_format(s_('BulkImport|The import of %{strong_open}%{source_group}%{strong_close} from %{strong_open}%{hostname}%{strong_close} to %{strong_color_open}%{destination_group}%{strong_color_close} is complete. You can view the results of the import.'), strong_open: '', strong_close: '', strong_color_open: '', strong_color_close: '', source_group: @source_group, hostname: @hostname, destination_group: destination_group) %>
|
||||
|
||||
<%= s_('BulkImport|View import results') %>: <%= history_import_bulk_import_url(@bulk_import.id) %>
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
- header_style = 'font-size:24px; text-align:center; line-height:30px;'
|
||||
- text_style = 'font-size:16px; text-align:center; line-height:24px; margin-top: 24px;'
|
||||
- error_style = 'color:#c91c00;'
|
||||
- button_style = 'border-color: #694cc0; border-style: solid; border-width: 1px; border-radius: 4px; font-size: 14px; padding: 8px 16px; background-color: #7b58cf; color: #fff; cursor: pointer;'
|
||||
- button_style = 'border: 1px solid #694cc0; border-radius: 4px; font-size: 14px; padding: 8px 16px; background-color: #7b58cf; color: #fff; cursor: pointer;'
|
||||
|
||||
- strong_tag_pair = tag_pair(tag.strong(style: 'color: #7b58cf'), :strong_open, :strong_close)
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
%h4.gl-heading-4= _('Repository cleanup')
|
||||
%h5.gl-heading-4= _('Repository cleanup')
|
||||
%p.gl-text-secondary
|
||||
- link_start = '<a href="%{url}" target="_blank" rel="noopener noreferrer">'.html_safe
|
||||
- git_filter_link_start = link_start % { url: 'https://github.com/newren/git-filter-repo' }
|
||||
|
|
@ -17,7 +17,7 @@
|
|||
= gitlab_ui_form_for @project, url: url, method: :post, authenticity_token: true, html: { class: 'js-requires-input' } do |f|
|
||||
%fieldset.gl-mt-0.gl-mb-3
|
||||
.gl-mb-3
|
||||
%h5.gl-mt-0
|
||||
%h6.gl-mt-0
|
||||
= _("Upload commit-map file")
|
||||
= render Pajamas::ButtonComponent.new(button_options: { class: 'js-choose-file' }) do
|
||||
= _("Choose a file")
|
||||
|
|
|
|||
|
|
@ -0,0 +1,8 @@
|
|||
%h5.gl-heading-4= s_('ProjectMaintenance|Remove blobs')
|
||||
%p.gl-text-secondary
|
||||
= s_('ProjectMaintenance|Provide a list of blob object IDs to be removed.')
|
||||
= link_to s_('ProjectMaintenance|How do I get a list of object IDs?'), help_page_path('user/project/repository/reducing_the_repo_size_using_git')
|
||||
%p.gl-text-secondary
|
||||
= s_('ProjectMaintenance|Housekeeping will need to be triggered manually afterwards to remove old versions of the file.')
|
||||
|
||||
.js-maintenance-remove-blobs
|
||||
|
|
@ -15,4 +15,7 @@
|
|||
- link_end = '</a>'.html_safe
|
||||
= s_('ProjectMaintenance| To ensure that a full backup is available in case changes need to be restored, you should make an %{docs_link_start}export of the project%{docs_link_end}.').html_safe % { docs_link_start: docs_link_start, docs_link_end: link_end }
|
||||
|
||||
- if current_user.can?(:owner_access, @project) && Feature.enabled?(:rewrite_history_ui, @project)
|
||||
= render "projects/maintenance/remove_blobs"
|
||||
|
||||
= render "projects/maintenance/cleanup"
|
||||
|
|
|
|||
|
|
@ -78,7 +78,7 @@
|
|||
= sprite_icon('issues', size: 14, css_class: 'gl-mr-2')
|
||||
= badge_count(project.open_issues_count)
|
||||
|
||||
.gl-display-flex.gl-align-items-center.gl-gap-2.gl-mr-n2
|
||||
.gl-display-flex.gl-align-items-center.gl-gap-2.-gl-mr-2
|
||||
- if show_pipeline_status_icon && last_pipeline.present?
|
||||
- pipeline_path = pipelines_project_commit_path(project.pipeline_status.project, project.pipeline_status.sha, ref: project.pipeline_status.ref)
|
||||
%span.icon-wrapper.pipeline-status
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
- wiki_path = wiki_page_path(@wiki, wiki_page)
|
||||
|
||||
%li{ class: active_when(params[:id] == wiki_page.slug) }
|
||||
.gl-relative.gl-flex.gl-items-center.js-wiki-list-toggle.wiki-list.gl-px-3.gl-rounded-base{ data: { testid: 'wiki-list' } }
|
||||
%li
|
||||
.gl-relative.gl-flex.gl-items-center.js-wiki-list-toggle.wiki-list.gl-px-3.gl-rounded-base{ data: { testid: 'wiki-list' }, class: active_when(params[:id] == wiki_page.slug) }
|
||||
= link_to wiki_path, class: 'gl-str-truncated', data: { testid: 'wiki-page-link', qa_page_name: wiki_page.human_title } do
|
||||
= wiki_page.human_title
|
||||
- plus_tooltip_title = safe_format(s_('Wiki|Create a new page under "%{page_title}"'), { page_title: wiki_page.human_title })
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
- wiki_path = wiki_page_path(@wiki, wiki_directory)
|
||||
|
||||
%li{ data: { testid: 'wiki-directory-content' } }
|
||||
.gl-relative.gl-flex.gl-items-center.js-wiki-list-toggle.wiki-list.gl-px-3.gl-rounded-base.gl-cursor-pointer{ data: { testid: 'wiki-list' } }<
|
||||
.gl-relative.gl-flex.gl-items-center.js-wiki-list-toggle.wiki-list.gl-px-3.gl-rounded-base.gl-cursor-pointer{ data: { testid: 'wiki-list' }, class: active_when(params[:id] == wiki_directory.slug) }
|
||||
= link_to wiki_path, data: { testid: 'wiki-dir-page-link', qa_page_name: wiki_directory.title }, class: 'gl-str-truncated ' do
|
||||
= wiki_directory.title
|
||||
- plus_tooltip_title = safe_format(s_('Wiki|Create a new page under "%{page_title}"'), { page_title: wiki_directory.title })
|
||||
|
|
|
|||
|
|
@ -1,9 +1,9 @@
|
|||
---
|
||||
name: export_audit_events
|
||||
feature_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/294168
|
||||
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/151278
|
||||
rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/458597
|
||||
milestone: '17.0'
|
||||
group: group::import and integrate
|
||||
type: wip
|
||||
name: rewrite_history_ui
|
||||
feature_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/450701
|
||||
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/153824
|
||||
rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/462999
|
||||
milestone: '17.1'
|
||||
group: group::source code
|
||||
type: beta
|
||||
default_enabled: false
|
||||
|
|
@ -1,8 +0,0 @@
|
|||
---
|
||||
name: large_ipynb_diffs
|
||||
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/113370
|
||||
rollout_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/393886
|
||||
milestone: '15.10'
|
||||
type: development
|
||||
group: group::incubation
|
||||
default_enabled: false
|
||||
|
|
@ -1,75 +0,0 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
require 'redis-client'
|
||||
|
||||
# This patch can be dropped once https://github.com/redis-rb/redis-client/pull/197
|
||||
# is released and merged.
|
||||
if Gem::Version.new(RedisClient::VERSION) > Gem::Version.new('0.22.1') # rubocop:disable Style/GuardClause -- This is easier to read
|
||||
raise 'New version of redis-client detected, please remove this file'
|
||||
end
|
||||
|
||||
# rubocop:disable Gitlab/ModuleWithInstanceVariables -- This is an upstream gem
|
||||
# rubocop:disable Style/GuardClause -- This is an upstream gem
|
||||
class RedisClient
|
||||
module ConnectionMixin
|
||||
def call(command, timeout)
|
||||
@pending_reads += 1
|
||||
write(command)
|
||||
result = read(connection_timeout(timeout))
|
||||
@pending_reads -= 1
|
||||
if result.is_a?(Error)
|
||||
result._set_command(command)
|
||||
result._set_config(config)
|
||||
raise result
|
||||
else
|
||||
result
|
||||
end
|
||||
end
|
||||
|
||||
def call_pipelined(commands, timeouts, exception: true)
|
||||
first_exception = nil
|
||||
|
||||
size = commands.size
|
||||
results = Array.new(commands.size)
|
||||
@pending_reads += size
|
||||
write_multi(commands)
|
||||
|
||||
size.times do |index|
|
||||
timeout = timeouts && timeouts[index]
|
||||
result = read(connection_timeout(timeout))
|
||||
@pending_reads -= 1
|
||||
|
||||
# A multi/exec command can return an array of results.
|
||||
# An error from a multi/exec command is handled in Multi#_coerce!.
|
||||
if result.is_a?(Array)
|
||||
result.each do |res|
|
||||
res._set_config(config) if res.is_a?(Error)
|
||||
end
|
||||
elsif result.is_a?(Error)
|
||||
result._set_command(commands[index])
|
||||
result._set_config(config)
|
||||
first_exception ||= result
|
||||
end
|
||||
|
||||
results[index] = result
|
||||
end
|
||||
|
||||
if first_exception && exception
|
||||
raise first_exception
|
||||
else
|
||||
results
|
||||
end
|
||||
end
|
||||
|
||||
def connection_timeout(timeout)
|
||||
return timeout unless timeout && timeout > 0
|
||||
|
||||
# Can't use the command timeout argument as the connection timeout
|
||||
# otherwise it would be very racy. So we add the regular read_timeout on top
|
||||
# to account for the network delay.
|
||||
timeout + config.read_timeout
|
||||
end
|
||||
end
|
||||
end
|
||||
# rubocop:enable Gitlab/ModuleWithInstanceVariables
|
||||
# rubocop:enable Style/GuardClause
|
||||
|
|
@ -6,3 +6,4 @@ introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/128010
|
|||
milestone: '16.8'
|
||||
queued_migration_version: 20240105144908
|
||||
finalize_after: '2024-02-22'
|
||||
finalized_by: 20240516140819
|
||||
|
|
|
|||
|
|
@ -3,7 +3,7 @@ table_name: push_event_payloads
|
|||
classes:
|
||||
- PushEventPayload
|
||||
feature_categories:
|
||||
- user_profile
|
||||
- source_code_management
|
||||
description: Stores log of push events
|
||||
introduced_by_url: https://gitlab.com/gitlab-org/gitlab-foss/-/merge_requests/12463
|
||||
milestone: '9.5'
|
||||
|
|
|
|||
|
|
@ -1,10 +1,11 @@
|
|||
---
|
||||
table_name: work_item_related_link_restrictions
|
||||
classes:
|
||||
- WorkItems::RelatedLinkRestriction
|
||||
- WorkItems::RelatedLinkRestriction
|
||||
feature_categories:
|
||||
- portfolio_management
|
||||
- portfolio_management
|
||||
description: Restrictions applied to related links.
|
||||
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/133044
|
||||
milestone: '16.5'
|
||||
gitlab_schema: gitlab_main
|
||||
sharding_key_issue_url: https://gitlab.com/gitlab-org/gitlab/-/issues/463469
|
||||
|
|
|
|||
|
|
@ -0,0 +1,16 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
# See https://docs.gitlab.com/ee/development/migration_style_guide.html
|
||||
# for more information on how to write migrations for GitLab.
|
||||
|
||||
class UpdateSubscriptionAddOnPurchasesStartedAtPrecision < Gitlab::Database::Migration[2.2]
|
||||
milestone '17.1'
|
||||
|
||||
def up
|
||||
change_column :subscription_add_on_purchases, :started_at, :date
|
||||
end
|
||||
|
||||
def down
|
||||
change_column :subscription_add_on_purchases, :started_at, :datetime_with_timezone
|
||||
end
|
||||
end
|
||||
|
|
@ -0,0 +1,27 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
# See https://docs.gitlab.com/ee/development/migration_style_guide.html
|
||||
# for more information on how to write migrations for GitLab.
|
||||
|
||||
class FinalizeBackfillIssueSearchDataNamespaceId < Gitlab::Database::Migration[2.2]
|
||||
milestone '17.1'
|
||||
|
||||
disable_ddl_transaction!
|
||||
restrict_gitlab_migration gitlab_schema: :gitlab_main
|
||||
|
||||
MIGRATION = "BackfillIssueSearchDataNamespaceId"
|
||||
|
||||
def up
|
||||
ensure_batched_background_migration_is_finished(
|
||||
job_class_name: MIGRATION,
|
||||
table_name: :issues,
|
||||
column_name: :id,
|
||||
job_arguments: [],
|
||||
finalize: true
|
||||
)
|
||||
end
|
||||
|
||||
def down
|
||||
# no-op
|
||||
end
|
||||
end
|
||||
|
|
@ -0,0 +1 @@
|
|||
613d939f0d13e2045b001a95e7ee2ec885368f8503218a8ccd23a26cf4f1b9af
|
||||
|
|
@ -0,0 +1 @@
|
|||
5e5b9c56e5421deb38e06530c8acdf706145d18400a2e26090f7aab453795e40
|
||||
|
|
@ -16717,7 +16717,7 @@ CREATE TABLE subscription_add_on_purchases (
|
|||
purchase_xid text NOT NULL,
|
||||
last_assigned_users_refreshed_at timestamp with time zone,
|
||||
trial boolean DEFAULT false NOT NULL,
|
||||
started_at timestamp with time zone,
|
||||
started_at date,
|
||||
CONSTRAINT check_3313c4d200 CHECK ((char_length(purchase_xid) <= 255))
|
||||
);
|
||||
|
||||
|
|
|
|||
|
|
@ -408,7 +408,7 @@ Audit event types belong to the following product categories.
|
|||
|
||||
| Name | Description | Saved to database | Streamed | Introduced in | Scope |
|
||||
|:------------|:------------|:------------------|:---------|:--------------|:--------------|
|
||||
| [`skip_pre_receive_secret_detection`](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/147855) | Triggered when pre-receive secret detection is skipped by the user| **{check-circle}** Yes | **{check-circle}** Yes | GitLab [16.11](https://gitlab.com/gitlab-org/gitlab/-/issues/441185) | Project |
|
||||
| [`skip_pre_receive_secret_detection`](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/147855) | Triggered when secret push protection is skipped by the user| **{check-circle}** Yes | **{check-circle}** Yes | GitLab [16.11](https://gitlab.com/gitlab-org/gitlab/-/issues/441185) | Project |
|
||||
|
||||
### Security policy management
|
||||
|
||||
|
|
|
|||
|
|
@ -69,11 +69,9 @@ The same setting
|
|||
## Enable silent admin exports
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/151278) in GitLab 17.0 [with a flag](../../administration/feature_flags.md) named `export_audit_events`. Disabled by default.
|
||||
> - [Generally available](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/153351) in GitLab 17.1. Feature flag `export_audit_events` removed.
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/152143) for file export downloads in GitLab 17.1.
|
||||
|
||||
FLAG:
|
||||
The availability of this feature is controlled by a feature flag. For more information, see the history.
|
||||
|
||||
Enable silent admin exports to prevent [audit events](../audit_event_reports.md) when
|
||||
instance administrators trigger a [project or group file export](../../user/project/settings/import_export.md) or download the export file.
|
||||
Exports from non-administrators still generate audit events.
|
||||
|
|
|
|||
|
|
@ -8266,7 +8266,7 @@ Input type: `SetContainerScanningForRegistryInput`
|
|||
|
||||
### `Mutation.setPreReceiveSecretDetection`
|
||||
|
||||
Enable/disable pre-receive secret detection for the given project.
|
||||
Enable/disable secret push protection for the given project.
|
||||
|
||||
Input type: `SetPreReceiveSecretDetectionInput`
|
||||
|
||||
|
|
@ -8275,7 +8275,7 @@ Input type: `SetPreReceiveSecretDetectionInput`
|
|||
| Name | Type | Description |
|
||||
| ---- | ---- | ----------- |
|
||||
| <a id="mutationsetprereceivesecretdetectionclientmutationid"></a>`clientMutationId` | [`String`](#string) | A unique identifier for the client performing the mutation. |
|
||||
| <a id="mutationsetprereceivesecretdetectionenable"></a>`enable` | [`Boolean!`](#boolean) | Desired status for pre-receive secret detection feature. |
|
||||
| <a id="mutationsetprereceivesecretdetectionenable"></a>`enable` | [`Boolean!`](#boolean) | Desired status for secret push protection feature. |
|
||||
| <a id="mutationsetprereceivesecretdetectionnamespacepath"></a>`namespacePath` | [`ID!`](#id) | Full path of the namespace (project). |
|
||||
|
||||
#### Fields
|
||||
|
|
|
|||
|
|
@ -177,7 +177,7 @@ The CI/CD template migration involves the following steps:
|
|||
- The name of the template should follow the `go` command, for example `format.yml`, `build.yml`, and `test.yml`.
|
||||
- Create a new project, initialize a Git repository, add/commit all changes, set a remote origin and push.
|
||||
Modify the URL for your CI/CD component project path.
|
||||
- Create additional files to follow [best practice](index.md#best-practices):
|
||||
- Create additional files as outlined in the guidance to [write a component](index.md#write-a-component):
|
||||
`README.md`, `LICENSE.md`, `.gitlab-ci.yml`, `.gitignore`. The following shell commands
|
||||
initialize the Go component structure:
|
||||
|
||||
|
|
@ -336,7 +336,7 @@ Follow the remaining steps in the [converting a CI/CD template into a component]
|
|||
section to complete the migration:
|
||||
|
||||
1. Commit and push the changes, and verify the CI/CD pipeline results.
|
||||
1. Follow [documentation best practices](index.md#best-practices) to update the `README.md` and `LICENSE.md` files.
|
||||
1. Follow the guidance on [writing a component](index.md#write-a-component) to update the `README.md` and `LICENSE.md` files.
|
||||
1. [Release the component](index.md#publish-a-new-release) and verify it in the CI/CD catalog.
|
||||
1. Add the CI/CD component into your staging/production environment.
|
||||
|
||||
|
|
|
|||
|
|
@ -210,141 +210,7 @@ In this example, referencing the component with:
|
|||
Pre-release versions are never fetched when referencing a version range. To fetch
|
||||
a pre-release version, specify the full version, for example `1.0.1-rc`.
|
||||
|
||||
## CI/CD Catalog
|
||||
|
||||
DETAILS:
|
||||
**Tier:** Free, Premium, Ultimate
|
||||
**Offering:** GitLab.com, Self-managed, GitLab Dedicated
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/407249) as an [experiment](../../policy/experiment-beta-support.md#experiment) in GitLab 16.1.
|
||||
> - [Moved](https://gitlab.com/gitlab-org/gitlab/-/issues/432045) to [beta](../../policy/experiment-beta-support.md#beta) in GitLab 16.7.
|
||||
> - [Made generally available](https://gitlab.com/gitlab-org/gitlab/-/issues/454306) in GitLab 17.0.
|
||||
|
||||
The CI/CD Catalog is a list of projects with published CI/CD components you can use
|
||||
to extend your CI/CD workflow.
|
||||
|
||||
Anyone can [create a component project](#create-a-component-project) and add it to
|
||||
the CI/CD Catalog, or contribute to an existing project to improve the available components.
|
||||
|
||||
For a click-through demo, see [the CI/CD Catalog beta Product Tour](https://gitlab.navattic.com/cicd-catalog).
|
||||
<!-- Demo published on 2024-01-24 -->
|
||||
|
||||
### View the CI/CD Catalog
|
||||
|
||||
To access the CI/CD Catalog and view the published components that are available to you:
|
||||
|
||||
1. On the left sidebar, select **Search or go to**.
|
||||
1. Select **Explore**.
|
||||
1. Select **CI/CD Catalog**.
|
||||
|
||||
Alternatively, if you are already in the [pipeline editor](../pipeline_editor/index.md)
|
||||
in your project, you can select **Browse CI/CD Catalog**.
|
||||
|
||||
Visibility of components in the CI/CD catalog follows the component source project's
|
||||
[visibility setting](../../user/public_access.md). Components with source projects set to:
|
||||
|
||||
- Private are visible only to users assigned at least the Guest role in the source component project.
|
||||
- Internal are visible only to users logged into the GitLab instance.
|
||||
- Public are visible to anyone with access to the GitLab instance.
|
||||
|
||||
### Publish a component project
|
||||
|
||||
To publish a component project in the CI/CD catalog, you must:
|
||||
|
||||
1. Set the project as a catalog project.
|
||||
1. Publish a new release.
|
||||
|
||||
#### Set a component project as a catalog project
|
||||
|
||||
To make published versions of a component project visible in the CI/CD catalog,
|
||||
you must set the project as a catalog project.
|
||||
|
||||
Prerequisites:
|
||||
|
||||
- You must have the Owner role in the project.
|
||||
|
||||
To set the project as a catalog project:
|
||||
|
||||
1. On the left sidebar, select **Search or go to** and find your project.
|
||||
1. Select **Settings > General**.
|
||||
1. Expand **Visibility, project features, permissions**.
|
||||
1. Turn on the **CI/CD Catalog project** toggle.
|
||||
|
||||
The project only becomes findable in the catalog after you publish a new release.
|
||||
|
||||
#### Publish a new release
|
||||
|
||||
CI/CD components can be [used](#use-a-component) without being listed in the CI/CD catalog.
|
||||
However, publishing a component's releases in the catalog makes it discoverable to other users.
|
||||
|
||||
Prerequisites:
|
||||
|
||||
- The project must:
|
||||
- Be set as a [catalog project](#set-a-component-project-as-a-catalog-project).
|
||||
- Have a [project description](../../user/project/working_with_projects.md#edit-project-name-description-and-avatar) defined.
|
||||
- Have a `README.md` file in the root directory for the commit SHA of the tag being released.
|
||||
- Have at least one [CI/CD component in the `templates/` directory](#directory-structure)
|
||||
for the commit SHA of the tag being released.
|
||||
|
||||
To publish a new version of the component to the catalog:
|
||||
|
||||
1. Add a job to the project's `.gitlab-ci.yml` file that uses the [`release`](../yaml/index.md#release)
|
||||
keyword to create the new release when a tag is created.
|
||||
You should configure the tag pipeline to [test the components](#test-the-component) before
|
||||
running the release job. For example:
|
||||
|
||||
```yaml
|
||||
create-release:
|
||||
stage: release
|
||||
image: registry.gitlab.com/gitlab-org/release-cli:latest
|
||||
script: echo "Creating release $CI_COMMIT_TAG"
|
||||
rules:
|
||||
- if: $CI_COMMIT_TAG
|
||||
release:
|
||||
tag_name: $CI_COMMIT_TAG
|
||||
description: "Release $CI_COMMIT_TAG of components in $CI_PROJECT_PATH"
|
||||
```
|
||||
|
||||
1. Create a [new tag](../../user/project/repository/tags/index.md#create-a-tag) for the release,
|
||||
which should trigger a tag pipeline that contains the job responsible for creating the release.
|
||||
The tag must use [semantic versioning](#semantic-versioning).
|
||||
|
||||
After the release job completes successfully, the release is created and the new version
|
||||
is published to the CI/CD catalog.
|
||||
|
||||
#### Semantic versioning
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/427286) in GitLab 16.10.
|
||||
|
||||
When tagging and [releasing new versions](#publish-a-new-release) of components to the Catalog,
|
||||
you must use [semantic versioning](https://semver.org). Semantic versioning is the standard
|
||||
for communicating that a change is a major, minor, patch, or other kind of change.
|
||||
|
||||
For example, `1.0.0`, `2.3.4`, and `1.0.0-alpha` are all valid semantic versions.
|
||||
|
||||
### Unpublish a component project
|
||||
|
||||
To remove a component project from the catalog, turn off the [**CI/CD Catalog resource**](#set-a-component-project-as-a-catalog-project)
|
||||
toggle in the project settings.
|
||||
|
||||
WARNING:
|
||||
This action destroys the metadata about the component project and its versions published
|
||||
in the catalog. The project and its repository still exist, but are not visible in the catalog.
|
||||
|
||||
To publish the component project in the catalog again, you need to [publish a new release](#publish-a-new-release).
|
||||
|
||||
### Verified component creators
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/433443) in GitLab 16.11
|
||||
|
||||
Some CI/CD components are badged with an icon to show that the component was created
|
||||
and is maintained by users verified by GitLab:
|
||||
|
||||
- GitLab-maintained (**{tanuki-verified}**): Components that are created and maintained by GitLab.
|
||||
- GitLab Partner (**{partner-verified}**): Components that are created and maintained by
|
||||
a GitLab-verified partner.
|
||||
|
||||
## Best practices
|
||||
## Write a component
|
||||
|
||||
This section describes some best practices for creating high quality component projects.
|
||||
|
||||
|
|
@ -459,6 +325,18 @@ during component testing.
|
|||
|
||||
You can learn more in [examples for testing a component](examples.md#test-a-component).
|
||||
|
||||
### Avoid hard-coding instance or project-specific values
|
||||
|
||||
When [using another component](#use-a-component) in your component, use `$CI_SERVER_FQDN`
|
||||
instead of your instance's Fully Qualified Domain Name (like `gitlab.com`).
|
||||
|
||||
When accessing the GitLab API in your component, use the `$CI_API_V4_URL` instead of the
|
||||
full URL and path for your instance (like `https://gitlab.com/api/v4`).
|
||||
|
||||
These [predefined variables](../variables/predefined_variables.md)
|
||||
ensure that your component also works when used on another instance, for example when using
|
||||
[a GitLab.com component in a self-managed instance](#use-a-gitlabcom-component-in-a-self-managed-instance).
|
||||
|
||||
### Avoid using global keywords
|
||||
|
||||
Avoid using [global keywords](../yaml/index.md#global-keywords) in a component.
|
||||
|
|
@ -601,6 +479,140 @@ In other cases, CI/CD variables might still be preferred. For example:
|
|||
a component to match a user's project.
|
||||
- Ask users to store sensitive values as [masked or protected CI/CD variables in project settings](../variables/index.md#define-a-cicd-variable-in-the-ui).
|
||||
|
||||
## CI/CD Catalog
|
||||
|
||||
DETAILS:
|
||||
**Tier:** Free, Premium, Ultimate
|
||||
**Offering:** GitLab.com, Self-managed, GitLab Dedicated
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/407249) as an [experiment](../../policy/experiment-beta-support.md#experiment) in GitLab 16.1.
|
||||
> - [Moved](https://gitlab.com/gitlab-org/gitlab/-/issues/432045) to [beta](../../policy/experiment-beta-support.md#beta) in GitLab 16.7.
|
||||
> - [Made Generally Available](https://gitlab.com/gitlab-org/gitlab/-/issues/454306) in GitLab 17.0.
|
||||
|
||||
The CI/CD Catalog is a list of projects with published CI/CD components you can use
|
||||
to extend your CI/CD workflow.
|
||||
|
||||
Anyone can [create a component project](#create-a-component-project) and add it to
|
||||
the CI/CD Catalog, or contribute to an existing project to improve the available components.
|
||||
|
||||
For a click-through demo, see [the CI/CD Catalog beta Product Tour](https://gitlab.navattic.com/cicd-catalog).
|
||||
<!-- Demo published on 2024-01-24 -->
|
||||
|
||||
### View the CI/CD Catalog
|
||||
|
||||
To access the CI/CD Catalog and view the published components that are available to you:
|
||||
|
||||
1. On the left sidebar, select **Search or go to**.
|
||||
1. Select **Explore**.
|
||||
1. Select **CI/CD Catalog**.
|
||||
|
||||
Alternatively, if you are already in the [pipeline editor](../pipeline_editor/index.md)
|
||||
in your project, you can select **Browse CI/CD Catalog**.
|
||||
|
||||
Visibility of components in the CI/CD catalog follows the component source project's
|
||||
[visibility setting](../../user/public_access.md). Components with source projects set to:
|
||||
|
||||
- Private are visible only to users assigned at least the Guest role in the source component project.
|
||||
- Internal are visible only to users logged into the GitLab instance.
|
||||
- Public are visible to anyone with access to the GitLab instance.
|
||||
|
||||
### Publish a component project
|
||||
|
||||
To publish a component project in the CI/CD catalog, you must:
|
||||
|
||||
1. Set the project as a catalog project.
|
||||
1. Publish a new release.
|
||||
|
||||
#### Set a component project as a catalog project
|
||||
|
||||
To make published versions of a component project visible in the CI/CD catalog,
|
||||
you must set the project as a catalog project.
|
||||
|
||||
Prerequisites:
|
||||
|
||||
- You must have the Owner role in the project.
|
||||
|
||||
To set the project as a catalog project:
|
||||
|
||||
1. On the left sidebar, select **Search or go to** and find your project.
|
||||
1. Select **Settings > General**.
|
||||
1. Expand **Visibility, project features, permissions**.
|
||||
1. Turn on the **CI/CD Catalog project** toggle.
|
||||
|
||||
The project only becomes findable in the catalog after you publish a new release.
|
||||
|
||||
#### Publish a new release
|
||||
|
||||
CI/CD components can be [used](#use-a-component) without being listed in the CI/CD catalog.
|
||||
However, publishing a component's releases in the catalog makes it discoverable to other users.
|
||||
|
||||
Prerequisites:
|
||||
|
||||
- The project must:
|
||||
- Be set as a [catalog project](#set-a-component-project-as-a-catalog-project).
|
||||
- Have a [project description](../../user/project/working_with_projects.md#edit-project-name-description-and-avatar) defined.
|
||||
- Have a `README.md` file in the root directory for the commit SHA of the tag being released.
|
||||
- Have at least one [CI/CD component in the `templates/` directory](#directory-structure)
|
||||
for the commit SHA of the tag being released.
|
||||
|
||||
To publish a new version of the component to the catalog:
|
||||
|
||||
1. Add a job to the project's `.gitlab-ci.yml` file that uses the [`release`](../yaml/index.md#release)
|
||||
keyword to create the new release when a tag is created.
|
||||
You should configure the tag pipeline to [test the components](#test-the-component) before
|
||||
running the release job. For example:
|
||||
|
||||
```yaml
|
||||
create-release:
|
||||
stage: release
|
||||
image: registry.gitlab.com/gitlab-org/release-cli:latest
|
||||
script: echo "Creating release $CI_COMMIT_TAG"
|
||||
rules:
|
||||
- if: $CI_COMMIT_TAG
|
||||
release:
|
||||
tag_name: $CI_COMMIT_TAG
|
||||
description: "Release $CI_COMMIT_TAG of components in $CI_PROJECT_PATH"
|
||||
```
|
||||
|
||||
1. Create a [new tag](../../user/project/repository/tags/index.md#create-a-tag) for the release,
|
||||
which should trigger a tag pipeline that contains the job responsible for creating the release.
|
||||
The tag must use [semantic versioning](#semantic-versioning).
|
||||
|
||||
After the release job completes successfully, the release is created and the new version
|
||||
is published to the CI/CD catalog.
|
||||
|
||||
#### Semantic versioning
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/427286) in GitLab 16.10.
|
||||
|
||||
When tagging and [releasing new versions](#publish-a-new-release) of components to the Catalog,
|
||||
you must use [semantic versioning](https://semver.org). Semantic versioning is the standard
|
||||
for communicating that a change is a major, minor, patch, or other kind of change.
|
||||
|
||||
For example, `1.0.0`, `2.3.4`, and `1.0.0-alpha` are all valid semantic versions.
|
||||
|
||||
### Unpublish a component project
|
||||
|
||||
To remove a component project from the catalog, turn off the [**CI/CD Catalog resource**](#set-a-component-project-as-a-catalog-project)
|
||||
toggle in the project settings.
|
||||
|
||||
WARNING:
|
||||
This action destroys the metadata about the component project and its versions published
|
||||
in the catalog. The project and its repository still exist, but are not visible in the catalog.
|
||||
|
||||
To publish the component project in the catalog again, you need to [publish a new release](#publish-a-new-release).
|
||||
|
||||
### Verified component creators
|
||||
|
||||
> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/433443) in GitLab 16.11
|
||||
|
||||
Some CI/CD components are badged with an icon to show that the component was created
|
||||
and is maintained by users verified by GitLab:
|
||||
|
||||
- GitLab-maintained (**{tanuki-verified}**): Components that are created and maintained by GitLab.
|
||||
- GitLab Partner (**{partner-verified}**): Components that are created and maintained by
|
||||
a GitLab-verified partner.
|
||||
|
||||
## Convert a CI/CD template to a component
|
||||
|
||||
Any existing CI/CD template that you use in projects by using the `include:` syntax
|
||||
|
|
@ -611,7 +623,7 @@ can be converted to a CI/CD component:
|
|||
1. Create a YAML file in the component project according to the [directory structure](index.md#directory-structure).
|
||||
1. Copy the content of the original template YAML file into the new component YAML file.
|
||||
1. Refactor the new component's configuration to:
|
||||
- Follow the [best practices](index.md#best-practices) for components.
|
||||
- Follow the guidance on [writing a component](#write-a-component).
|
||||
- Improve the configuration, for example by enabling [merge request pipelines](../pipelines/merge_request_pipelines.md)
|
||||
or making it [more efficient](../pipelines/pipeline_efficiency.md).
|
||||
1. Leverage the `.gitlab-ci.yml` in the components repository to [test changes to the component](index.md#test-the-component).
|
||||
|
|
|
|||
|
|
@ -513,3 +513,39 @@ flow of how we construct a Chat prompt:
|
|||
context to the request. It loops to up to 10 times until a final answer is reached.
|
||||
|
||||
(`*`) indicates that this step is part of the actual construction of the prompt
|
||||
|
||||
## Interpreting GitLab Duo Chat error codes
|
||||
|
||||
GitLab Duo Chat has error codes with specified meanings to assist in debugging.
|
||||
Currently, they are only logged, but in the future, they will be displayed on the UI.
|
||||
|
||||
When developing for GitLab Duo Chat, please include these error codes when returning an error, especially a user-facing error.
|
||||
|
||||
### Error Code Format
|
||||
|
||||
The error codes follow the format: `<Layer Identifier><Four-digit Series Number>`.
|
||||
|
||||
For example:
|
||||
|
||||
- `M1001`: A network communication error in the monolith layer.
|
||||
- `G2005`: A data formatting/processing error in the AI gateway layer.
|
||||
- `A3010`: An authentication or data access permissions error in a third-party API.
|
||||
|
||||
### Error Code Layer Identifier
|
||||
|
||||
| Code | Layer |
|
||||
|------|-----------------|
|
||||
| M | Monolith |
|
||||
| G | AI Gateway |
|
||||
| A | Third-party API |
|
||||
|
||||
### Error Series
|
||||
|
||||
| Series | Type |
|
||||
|--------|------------------------------------------------------------------------------|
|
||||
| 1000 | Network communication errors |
|
||||
| 2000 | Data formatting/processing errors |
|
||||
| 3000 | Authentication and/or data access permission errors |
|
||||
| 4000 | Code execution exceptions |
|
||||
| 5000 | Bad configuration or bad parameters errors |
|
||||
| 6000 | Semantic or inference errors (the model does not understand or hallucinates) |
|
||||
|
|
|
|||
|
|
@ -52,7 +52,7 @@ in the catalog.
|
|||
or ask one of the group owners to create an empty project for you.
|
||||
1. Follow the [standard guide for creating components](../../ci/components/index.md).
|
||||
1. Add a concise project description that clearly describes the capabilities offered by the component project.
|
||||
1. Ensure that the [general best practices](../../ci/components/index.md#best-practices) are followed as well as
|
||||
1. Ensure to follow the general guidance to [write a component](../../ci/components/index.md#write-a-component) as well as
|
||||
[those for the official components](#best-practices-for-official-components).
|
||||
1. Add a `LICENSE.md` file with the MIT license.
|
||||
1. The project must have a `.gitlab-ci.yml` file that:
|
||||
|
|
@ -103,7 +103,7 @@ Requirements for becoming a maintainer:
|
|||
|
||||
- Have a an in-depth understanding of the [CI/CD YAML syntax](../../ci/yaml/index.md) and features.
|
||||
- Understand how CI components work and demonstrate experience developing them.
|
||||
- Have a solid understanding of the components [best practices](../../ci/components/index.md#best-practices).
|
||||
- Have a solid understanding of how to [write a component](../../ci/components/index.md#write-a-component).
|
||||
|
||||
How to join the `gitlab-components` group of general maintainers:
|
||||
|
||||
|
|
|
|||
|
|
@ -681,9 +681,8 @@ We also run our test suite against PostgreSQL 13 upon specific database library
|
|||
| Merge requests | 14 (default version), 13 for DB library changes | 3.1 (default version) |
|
||||
| `master` branch commits | 14 (default version), 13 for DB library changes | 3.1 (default version) |
|
||||
| `maintenance` scheduled pipelines for the `master` branch (every even-numbered hour at XX:05) | 14 (default version), 13 for DB library changes | 3.1 (default version) |
|
||||
| `maintenance` scheduled pipelines for the `ruby3_0` branch (every odd-numbered hour at XX:40) | 14 (default version), 13 for DB library changes | 3.0 |
|
||||
| `maintenance` scheduled pipelines for the `ruby3_2` branch (every odd-numbered hour at XX:10) | 14 (default version), 13 for DB library changes | 3.2 |
|
||||
| `nightly` scheduled pipelines for the `master` branch | 14 (default version), 13, 15, 16 | 3.1 (default version) |
|
||||
| `nightly` scheduled pipelines for the `master` branch | 14 (default version), 13, 15, 16 | 3.1 (default version) |
|
||||
|
||||
For each current Ruby versions we're testing against with, we run
|
||||
maintenance scheduled pipelines every 2 hours on their respective `ruby\d_\d`
|
||||
|
|
@ -753,7 +752,8 @@ In general, pipelines for an MR fall into one of the following types (from short
|
|||
|
||||
A "pipeline type" is an abstract term that mostly describes the "critical path" (for example, the chain of jobs for which the sum
|
||||
of individual duration equals the pipeline's duration).
|
||||
We use these "pipeline types" in [metrics dashboards](https://app.periscopedata.com/app/gitlab/858266/GitLab-Pipeline-Durations) to detect what types and jobs need to be optimized first.
|
||||
We use these "pipeline types" in [metrics dashboards](https://10az.online.tableau.com/#/site/gitlab/views/GitlabPipelineDurations/SuccessfulMergeRequestPipelineDurationHistogramsbyTypes?:iid=1)
|
||||
to detect what types and jobs need to be optimized first.
|
||||
|
||||
An MR that touches multiple areas would be associated with the longest type applicable. For instance, an MR that touches backend
|
||||
and frontend would fall into the "Frontend" pipeline type since this type takes longer to finish than the "Backend" pipeline type.
|
||||
|
|
|
|||
|
|
@ -344,11 +344,15 @@ On the **Child issues and epics** section, under each epic name, hover over the
|
|||
The number indicates all epics associated with the project, including issues
|
||||
you might not have permission to.
|
||||
|
||||
### Add a new issue to an epic
|
||||
### Add an issue to an epic
|
||||
|
||||
> - Maximum number of child issues and epics [changed](https://gitlab.com/gitlab-org/gitlab/-/issues/452111) to 100 in GitLab 17.0.
|
||||
|
||||
Add an existing issue to an epic, or create a new issue that's automatically
|
||||
added to the epic.
|
||||
|
||||
The maximum number of direct child issues and epics is 100.
|
||||
|
||||
#### Add an existing issue to an epic
|
||||
|
||||
> - Minimum required role for the project [changed](https://gitlab.com/gitlab-org/gitlab/-/issues/382506) from Reporter to Guest in GitLab 15.8.
|
||||
|
|
|
|||
|
|
@ -216,8 +216,8 @@ For members with `Minimal Access` in the selected group, their `Max Role` and `S
|
|||
|
||||
## User cap for groups
|
||||
|
||||
> - Behind a [feature flag](../../administration/feature_flags.md) named `saas_user_caps`. Disabled by default.
|
||||
> - [Enabled on GitLab.com](https://gitlab.com/groups/gitlab-org/-/epics/9263) in GitLab 16.3.
|
||||
> - [Generally available](https://gitlab.com/gitlab-org/gitlab/-/issues/421693) in GitLab 17.1 Feature flag `saas_user_caps` removed.
|
||||
|
||||
For more information about user caps for GitLab self-managed, see [User cap](../../administration/settings/sign_up_restrictions.md#user-cap).
|
||||
|
||||
|
|
|
|||
|
|
@ -257,6 +257,9 @@ For example, in the following diagram:
|
|||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TB
|
||||
accTitle: Automatic member removal
|
||||
accDescr: How group membership of users is determined before sign in if group sync is set up.
|
||||
|
||||
subgraph SAML users
|
||||
SAMLUserA[Sidney Jones]
|
||||
SAMLUserB[Zhang Wei]
|
||||
|
|
@ -283,6 +286,9 @@ graph TB
|
|||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TB
|
||||
accTitle: Automatic member removal
|
||||
accDescr: User membership for Sidney when she has not signed into group C, and group B has not configured group links.
|
||||
|
||||
subgraph GitLab users
|
||||
GitLabUserA[Sidney Jones]
|
||||
GitLabUserB[Zhang Wei]
|
||||
|
|
@ -306,7 +312,11 @@ graph TB
|
|||
```
|
||||
|
||||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TB
|
||||
accTitle: Automatic member removal
|
||||
accDescr: How membership of Alex Garcia works once she has signed into a group that has group links enabled.
|
||||
|
||||
subgraph GitLab users
|
||||
GitLabUserA[Sidney Jones]
|
||||
GitLabUserB[Zhang Wei]
|
||||
|
|
|
|||
|
|
@ -226,7 +226,11 @@ During the synchronization process, all new users:
|
|||
The following diagram describes what happens when you add users to your SCIM app:
|
||||
|
||||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TD
|
||||
accTitle: Adding users to your SCIM application
|
||||
accDescr: How GitLab determines whether or not to associate a SCIM identity with a user.
|
||||
|
||||
A[Add User to SCIM app] -->|IdP sends user info to GitLab| B(GitLab: Does the email exist?)
|
||||
B -->|No| C[GitLab creates user with SCIM identity]
|
||||
B -->|Yes| D(GitLab: Is the user part of the group?)
|
||||
|
|
@ -285,7 +289,11 @@ NOTE:
|
|||
Deprovisioning does not delete the GitLab user account.
|
||||
|
||||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TD
|
||||
accTitle: Deprovisioning users
|
||||
accDescr: How removing users from your SCIM app removes them from GitLab groups.
|
||||
|
||||
A[Remove User from SCIM app] -->|IdP sends request to GitLab| B(GitLab: Is the user part of the group?)
|
||||
B -->|No| C[Nothing to do]
|
||||
B -->|Yes| D[GitLab removes user from GitLab group]
|
||||
|
|
|
|||
|
|
@ -33,7 +33,11 @@ Subgroups can:
|
|||
For example:
|
||||
|
||||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
graph TD
|
||||
accTitle: Parent and subgroup nesting
|
||||
accDescr: How parent groups, subgroups, and projects nest.
|
||||
|
||||
subgraph "Parent group"
|
||||
subgraph "Subgroup A"
|
||||
subgraph "Subgroup A1"
|
||||
|
|
@ -136,7 +140,11 @@ Subgroup members can be:
|
|||
1. [Indirect members](../../project/members/index.md#indirect-membership) include [inherited members](../../project/members/index.md#inherited-membership) and members of a group that was [invited to the subgroup or its ancestors](../manage.md#share-a-group-with-another-group).
|
||||
|
||||
```mermaid
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
flowchart RL
|
||||
accTitle: Subgroup membership
|
||||
accDescr: How users become members of a subgroup - through direct, indirect, or inherited membership.
|
||||
|
||||
subgraph Group A
|
||||
A(Direct member)
|
||||
B{{Shared member}}
|
||||
|
|
|
|||
|
|
@ -51,10 +51,11 @@ Product analytics uses the following tools:
|
|||
The following diagram illustrates the product analytics flow:
|
||||
|
||||
```mermaid
|
||||
---
|
||||
title: Product Analytics flow
|
||||
---
|
||||
%%{init: { "fontFamily": "GitLab Sans" }}%%
|
||||
flowchart TB
|
||||
accTitle: Product Analytics flow
|
||||
accDescr: How data is collected, processed, and visualized in dashboards.
|
||||
|
||||
subgraph Event collection
|
||||
A([SDK]) --Send user data--> B[Snowplow Collector]
|
||||
B --Pass data--> C[Snowplow Enricher]
|
||||
|
|
|
|||
|
|
@ -248,3 +248,29 @@ The error can be avoided by:
|
|||
- Using a reverse proxy to direct all requests from the source instance to the primary Geo node.
|
||||
- Adding a local `hosts` file entry on the source to force the target host name to resolve to the Geo primary node's IP address.
|
||||
- Configuring a pull mirror on the target instead.
|
||||
|
||||
## Pull or push mirror fails to update: `The project is not mirrored`
|
||||
|
||||
Pull and push mirrors fail to update when [GitLab Silent Mode](../../../../administration/silent_mode/index.md) is enabled.
|
||||
When this happens, the option to allow mirroring on the UI is disabled.
|
||||
|
||||
An administrator can check to confirm that GitLab Silent Mode is disabled.
|
||||
|
||||
When mirroring fails due to Silent Mode the following are the debug steps:
|
||||
|
||||
- [Triggering the mirror using the API](pull.md#trigger-pipelines-for-mirror-updates) shows: `The project is not mirrored`.
|
||||
|
||||
- If pull or push mirror was already set up but there are no further updates on the mirrored repository,
|
||||
confirm the [project's pull and push mirror details ans status](../../../../api/projects.md#get-a-projects-pull-mirror-details) are not recent as shown below. This indicates mirroring was paused and disabling GitLab Silent Mode restarts it automatically.
|
||||
|
||||
For example, if Silent Mode is what is impeding your imports, the output is similar to the following:
|
||||
|
||||
```json
|
||||
"id": 1,
|
||||
"update_status": "finished",
|
||||
"url": "https://test.git"
|
||||
"last_error": null,
|
||||
"last_update_at": null,
|
||||
"last_update_started_at": "2023-12-12T00:01:02.222Z",
|
||||
"last_successful_update_at": null
|
||||
```
|
||||
|
|
|
|||
|
|
@ -288,6 +288,8 @@ module API
|
|||
end
|
||||
rescue ::ActiveRecord::RecordNotUnique
|
||||
render_api_error!('Duplicated issue', 409)
|
||||
rescue ::Issues::BaseService::EpicAssignmentError => error
|
||||
render_api_error!(error.message, 422)
|
||||
end
|
||||
end
|
||||
|
||||
|
|
|
|||
|
|
@ -70,9 +70,9 @@ module Gitlab
|
|||
type: 'container_scanning'
|
||||
},
|
||||
pre_receive_secret_detection: {
|
||||
name: _('Pre-receive Secret Detection'),
|
||||
name: _('Secret push protection'),
|
||||
description: _('Block secrets such as keys and API tokens from being pushed to your repositories. ' \
|
||||
'Pre-receive secret detection is triggered when commits are pushed to a repository. ' \
|
||||
'Secret push protection is triggered when commits are pushed to a repository. ' \
|
||||
'If any secrets are detected, the push is blocked.'),
|
||||
help_path: Gitlab::Routing.url_helpers.help_page_path(
|
||||
'user/application_security/secret_detection/pre_receive/index'),
|
||||
|
|
|
|||
|
|
@ -12,15 +12,15 @@ module InitializerConnections
|
|||
return yield if Gitlab::Utils.to_boolean(ENV['SKIP_RAISE_ON_INITIALIZE_CONNECTIONS'])
|
||||
|
||||
previous_connection_counts =
|
||||
ActiveRecord::Base.connection_handler.connection_pool_list(ApplicationRecord.current_role).to_h do |pool|
|
||||
[pool.db_config.name, pool.connections.size]
|
||||
ActiveRecord::Base.connection_handler.connection_pool_list(ApplicationRecord.current_role).map do |pool|
|
||||
pool.connections.size
|
||||
end
|
||||
|
||||
yield
|
||||
|
||||
new_connection_counts =
|
||||
ActiveRecord::Base.connection_handler.connection_pool_list(ApplicationRecord.current_role).to_h do |pool|
|
||||
[pool.db_config.name, pool.connections.size]
|
||||
ActiveRecord::Base.connection_handler.connection_pool_list(ApplicationRecord.current_role).map do |pool|
|
||||
pool.connections.size
|
||||
end
|
||||
|
||||
raise_database_connection_made_error unless previous_connection_counts == new_connection_counts
|
||||
|
|
|
|||
|
|
@ -24,7 +24,7 @@ namespace :tw do
|
|||
CodeOwnerRule.new('AI Framework', '@sselhorn'),
|
||||
CodeOwnerRule.new('AI Model Validation', '@sselhorn'),
|
||||
# CodeOwnerRule.new('Analytics Instrumentation', ''),
|
||||
CodeOwnerRule.new('Anti-Abuse', '@phillipwells'),
|
||||
# CodeOwnerRule.new('Anti-Abuse', ''),
|
||||
CodeOwnerRule.new('Authentication', '@jglassman1'),
|
||||
CodeOwnerRule.new('Authorization', '@jglassman1'),
|
||||
# CodeOwnerRule.new('Billing and Subscription Management', ''),
|
||||
|
|
|
|||
|
|
@ -3902,9 +3902,6 @@ msgstr ""
|
|||
msgid "AdminSettings|Pause Elasticsearch indexing"
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminSettings|Pre-receive secret detection"
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminSettings|Prevent non-administrators from using the selected visibility levels for groups, projects and snippets."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -3938,6 +3935,9 @@ msgstr ""
|
|||
msgid "AdminSettings|Search with Elasticsearch enabled"
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminSettings|Secret Push Protection"
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminSettings|Select a group to use as a source of custom templates for new projects. %{link_start}Learn more%{link_end}."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -4328,6 +4328,9 @@ msgstr ""
|
|||
msgid "AdminUsers|Restore user access to the account, including web, Git and API."
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminUsers|Role Promotions"
|
||||
msgstr ""
|
||||
|
||||
msgid "AdminUsers|Search by name, email, or username"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -5195,21 +5198,21 @@ msgstr ""
|
|||
msgid "Allow possible spam"
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow pre-receive secret detection"
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow project maintainers to configure repository mirroring"
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow projects and subgroups to override the group setting"
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow projects to enable pre-receive detection. This does not enable pre-receive secret detection. When you enable this feature, you accept the %{link_start}GitLab Testing Agreement%{link_end}."
|
||||
msgid "Allow projects to enable secret push protection. This does not enable secret push protection. When you enable this feature, you accept the %{link_start}GitLab Testing Agreement%{link_end}."
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow public access to pipelines and job details, including output logs and artifacts."
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow secret push protection"
|
||||
msgstr ""
|
||||
|
||||
msgid "Allow this key to push to this repository"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -8594,7 +8597,7 @@ msgstr ""
|
|||
msgid "BlobViewer|View on %{environmentName}"
|
||||
msgstr ""
|
||||
|
||||
msgid "Block secrets such as keys and API tokens from being pushed to your repositories. Pre-receive secret detection is triggered when commits are pushed to a repository. If any secrets are detected, the push is blocked."
|
||||
msgid "Block secrets such as keys and API tokens from being pushed to your repositories. Secret push protection is triggered when commits are pushed to a repository. If any secrets are detected, the push is blocked."
|
||||
msgstr ""
|
||||
|
||||
msgid "Block user"
|
||||
|
|
@ -9593,6 +9596,9 @@ msgstr ""
|
|||
msgid "BulkImport|History"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|Import completed"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|Import failed. '%{path}' already exists. Change the destination and try again."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -9611,6 +9617,9 @@ msgstr ""
|
|||
msgid "BulkImport|Import is finished. Pick another name for re-import"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|Import of %{source_group} from %{hostname}"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|Import with projects"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -9707,6 +9716,9 @@ msgstr ""
|
|||
msgid "BulkImport|Template / File-based import / Direct transfer"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|The import of %{strong_open}%{source_group}%{strong_close} from %{strong_open}%{hostname}%{strong_close} to %{strong_color_open}%{destination_group}%{strong_color_close} is complete. You can view the results of the import."
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|This %{importable} was imported from another instance."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -9716,6 +9728,9 @@ msgstr ""
|
|||
msgid "BulkImport|Update of import statuses with realtime changes failed"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|View import results"
|
||||
msgstr ""
|
||||
|
||||
msgid "BulkImport|Your imported groups and projects will appear here."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -23378,9 +23393,6 @@ msgstr ""
|
|||
msgid "GitLab Duo could not connect to the AI provider."
|
||||
msgstr ""
|
||||
|
||||
msgid "GitLab Duo didn't respond. Try again? If it fails again, your request might be too large."
|
||||
msgstr ""
|
||||
|
||||
msgid "GitLab Enterprise Edition"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -26138,6 +26150,9 @@ msgstr ""
|
|||
msgid "I'm signing up for GitLab because:"
|
||||
msgstr ""
|
||||
|
||||
msgid "I'm sorry, I couldn't respond in time. Please try again."
|
||||
msgstr ""
|
||||
|
||||
msgid "I'm sorry, I was not able to find any documentation to answer your question."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -38884,12 +38899,6 @@ msgstr ""
|
|||
msgid "Pre-defined push rules"
|
||||
msgstr ""
|
||||
|
||||
msgid "Pre-receive Secret Detection"
|
||||
msgstr ""
|
||||
|
||||
msgid "Pre-receive secret detection skipped via"
|
||||
msgstr ""
|
||||
|
||||
msgid "PreScanVerification|(optional)"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -39310,6 +39319,9 @@ msgstr ""
|
|||
msgid "ProductAnalytics|All Sessions Compared"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|An analytics provider has been successfully created, but it has not received any events yet. To continue with the setup, instrument your application and start sending events."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|An error occurred while fetching data. Refresh the page to try again."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -39361,6 +39373,9 @@ msgstr ""
|
|||
msgid "ProductAnalytics|Contact our sales team"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|Continue set up"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|Creating your product analytics instance..."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -39553,6 +39568,9 @@ msgstr ""
|
|||
msgid "ProductAnalytics|The sender of tracking events"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|The system is creating your analytics provider. In the meantime, you can instrument your application."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProductAnalytics|Then, return to this page and continue with the setup."
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -40390,9 +40408,39 @@ msgstr ""
|
|||
msgid "ProjectMaintenance| To ensure that a full backup is available in case changes need to be restored, you should make an %{docs_link_start}export of the project%{docs_link_end}."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Blob IDs to remove"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Cancel"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Enter a list of object IDs to be removed to reduce repository size."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Enter multiple entries on separate lines."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Housekeeping will need to be triggered manually afterwards to remove old versions of the file."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|How do I get a list of object IDs?"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Manage repository storage and cleanup."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Provide a list of blob object IDs to be removed."
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Remove blobs"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Removing blobs by ID cannot be undone. Are you sure you want to continue?"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectMaintenance|Yes, remove blobs"
|
||||
msgstr ""
|
||||
|
||||
msgid "ProjectOverview|Create new fork"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -46305,6 +46353,12 @@ msgstr ""
|
|||
msgid "Secret Detection"
|
||||
msgstr ""
|
||||
|
||||
msgid "Secret push protection"
|
||||
msgstr ""
|
||||
|
||||
msgid "Secret push protection skipped via"
|
||||
msgstr ""
|
||||
|
||||
msgid "Secret token"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -46317,10 +46371,10 @@ msgstr ""
|
|||
msgid "SecretDetection|Only a project maintainer or owner can toggle this feature."
|
||||
msgstr ""
|
||||
|
||||
msgid "SecretDetection|Pre-receive Secret Detection is disabled"
|
||||
msgid "SecretDetection|Secret push protection is disabled"
|
||||
msgstr ""
|
||||
|
||||
msgid "SecretDetection|Pre-receive Secret Detection is enabled"
|
||||
msgid "SecretDetection|Secret push protection is enabled"
|
||||
msgstr ""
|
||||
|
||||
msgid "SecretDetection|This comment appears to have a token in it. Are you sure you want to add it?"
|
||||
|
|
@ -46638,7 +46692,7 @@ msgstr ""
|
|||
msgid "SecurityConfiguration|The status of the tools only applies to the default branch and is based on the %{linkStart}latest pipeline%{linkEnd}."
|
||||
msgstr ""
|
||||
|
||||
msgid "SecurityConfiguration|Toggle Pre-receive secret detection"
|
||||
msgid "SecurityConfiguration|Toggle secret push protection"
|
||||
msgstr ""
|
||||
|
||||
msgid "SecurityConfiguration|Upgrade or start a free trial"
|
||||
|
|
@ -51594,6 +51648,9 @@ msgstr ""
|
|||
msgid "Target branch: %{target_branch}"
|
||||
msgstr ""
|
||||
|
||||
msgid "Target branches"
|
||||
msgstr ""
|
||||
|
||||
msgid "Target project"
|
||||
msgstr ""
|
||||
|
||||
|
|
@ -56461,7 +56518,7 @@ msgstr ""
|
|||
msgid "User cap cannot be enabled. The group or one of its subgroups or projects is shared externally."
|
||||
msgstr ""
|
||||
|
||||
msgid "User caps is enabled for this group, visit the %{pending_members_link_start}pending members%{pending_members_link_end} page to manage them."
|
||||
msgid "User caps is enabled for this group. You can manage members on the %{pending_members_link_start}pending members%{pending_members_link_end} page."
|
||||
msgstr ""
|
||||
|
||||
msgid "User created at"
|
||||
|
|
@ -59897,7 +59954,10 @@ msgstr ""
|
|||
msgid "You cannot access the raw file. Please wait a minute."
|
||||
msgstr ""
|
||||
|
||||
msgid "You cannot add any more epics. This epic already has maximum number of child epics."
|
||||
msgid "You cannot add any more epics. This epic already has maximum number of child issues & epics."
|
||||
msgstr ""
|
||||
|
||||
msgid "You cannot add any more issues. This epic already has maximum number of child issues & epics."
|
||||
msgstr ""
|
||||
|
||||
msgid "You cannot approve your own deployment. This configuration can be adjusted in the protected environment settings."
|
||||
|
|
@ -61082,6 +61142,9 @@ msgstr ""
|
|||
msgid "cannot be enabled until identity verification is completed"
|
||||
msgstr ""
|
||||
|
||||
msgid "cannot be linked to the epic. This epic already has maximum number of child issues & epics."
|
||||
msgstr ""
|
||||
|
||||
msgid "cannot be used because it belongs to a compromised private key. Stop using this key and generate a new one."
|
||||
msgstr ""
|
||||
|
||||
|
|
|
|||
|
|
@ -63,7 +63,7 @@
|
|||
"@gitlab/favicon-overlay": "2.0.0",
|
||||
"@gitlab/fonts": "^1.3.0",
|
||||
"@gitlab/svgs": "3.99.0",
|
||||
"@gitlab/ui": "80.12.0",
|
||||
"@gitlab/ui": "80.13.1",
|
||||
"@gitlab/web-ide": "^0.0.1-dev-20240524043623",
|
||||
"@mattiasbuelens/web-streams-adapter": "^0.1.0",
|
||||
"@rails/actioncable": "7.0.8-1",
|
||||
|
|
|
|||
|
|
@ -32,8 +32,6 @@ module Gitlab
|
|||
span :project_containers_registry_size
|
||||
|
||||
# Pending members
|
||||
button :view_pending_approvals, text: /View pending approvals/
|
||||
div :pending_members_alert
|
||||
div :pending_members
|
||||
button :approve_member
|
||||
button :confirm_member_approval, text: /^OK$/
|
||||
|
|
|
|||
|
|
@ -26,5 +26,9 @@ FactoryBot.define do
|
|||
trait :timeout do
|
||||
status { 3 }
|
||||
end
|
||||
|
||||
trait :with_configuration do
|
||||
configuration { association(:bulk_import_configuration, bulk_import: instance) }
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
FactoryBot.define do
|
||||
factory :bulk_import_configuration, class: 'BulkImports::Configuration' do
|
||||
association :bulk_import, factory: :bulk_import
|
||||
bulk_import
|
||||
|
||||
url { 'https://gitlab.example' }
|
||||
access_token { 'token' }
|
||||
|
|
@ -89,17 +89,6 @@ RSpec.describe 'Admin updates settings', feature_category: :shared do
|
|||
expect(page).to have_content 'Application settings saved successfully'
|
||||
end
|
||||
|
||||
context 'when `export_audit_events` flag is disabled' do
|
||||
before do
|
||||
stub_feature_flags(export_audit_events: false)
|
||||
visit general_admin_application_settings_path
|
||||
end
|
||||
|
||||
it 'does not display the silent admin exports setting' do
|
||||
expect(page).not_to have_selector('[data-testid="silent-admin-exports"]')
|
||||
end
|
||||
end
|
||||
|
||||
it 'change Keys settings' do
|
||||
within_testid('admin-visibility-access-settings') do
|
||||
select 'Are forbidden', from: 'RSA SSH keys'
|
||||
|
|
|
|||
|
|
@ -40,6 +40,13 @@ RSpec.describe 'Projects > Settings > Repository settings', feature_category: :s
|
|||
end
|
||||
end
|
||||
|
||||
context 'Repository maintenance', :js do
|
||||
it 'does not render remove blobs section' do
|
||||
visit project_settings_repository_path(project)
|
||||
expect(page).not_to have_content('Remove blobs')
|
||||
end
|
||||
end
|
||||
|
||||
context 'Branch rules', :js do
|
||||
it 'renders branch rules settings' do
|
||||
visit project_settings_repository_path(project)
|
||||
|
|
@ -345,5 +352,13 @@ RSpec.describe 'Projects > Settings > Repository settings', feature_category: :s
|
|||
|
||||
include_examples 'shows mirror settings'
|
||||
end
|
||||
|
||||
context 'Repository maintenance', :enable_admin_mode do
|
||||
let(:mirror_available) { false }
|
||||
|
||||
it 'renders remove blobs section' do
|
||||
expect(page).to have_content('Remove blobs')
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -22,10 +22,13 @@ describe('IDE review mode', () => {
|
|||
store.state.currentProjectId = 'abcproject';
|
||||
store.state.currentBranchId = 'main';
|
||||
store.state.projects.abcproject = { ...projectData };
|
||||
Vue.set(store.state.trees, 'abcproject/main', {
|
||||
tree: [file('fileName')],
|
||||
loading: false,
|
||||
});
|
||||
store.state.trees = {
|
||||
...store.state.trees,
|
||||
'abcproject/main': {
|
||||
tree: [file('fileName')],
|
||||
loading: false,
|
||||
},
|
||||
};
|
||||
|
||||
dispatch = jest.spyOn(store, 'dispatch');
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,5 @@
|
|||
import { GlSkeletonLoader } from '@gitlab/ui';
|
||||
import { shallowMount } from '@vue/test-utils';
|
||||
import Vue from 'vue';
|
||||
import IdeTreeList from '~/ide/components/ide_tree_list.vue';
|
||||
import { createStore } from '~/ide/stores';
|
||||
import FileTree from '~/vue_shared/components/file_tree.vue';
|
||||
|
|
@ -15,7 +14,10 @@ describe('IdeTreeList component', () => {
|
|||
store.state.currentProjectId = 'abcproject';
|
||||
store.state.currentBranchId = 'main';
|
||||
store.state.projects.abcproject = { ...projectData };
|
||||
Vue.set(store.state.trees, 'abcproject/main', { tree, loading });
|
||||
store.state.trees = {
|
||||
...store.state.trees,
|
||||
'abcproject/main': { tree, loading },
|
||||
};
|
||||
|
||||
wrapper = shallowMount(IdeTreeList, {
|
||||
propsData: {
|
||||
|
|
|
|||
|
|
@ -0,0 +1,98 @@
|
|||
import { nextTick } from 'vue';
|
||||
import { GlDrawer, GlFormTextarea, GlModal } from '@gitlab/ui';
|
||||
import { shallowMountExtended } from 'helpers/vue_test_utils_helper';
|
||||
import { getContentWrapperHeight } from '~/lib/utils/dom_utils';
|
||||
import { DRAWER_Z_INDEX } from '~/lib/utils/constants';
|
||||
import RemoveBlobs from '~/projects/settings/repository/maintenance/remove_blobs.vue';
|
||||
|
||||
jest.mock('~/lib/utils/dom_utils');
|
||||
|
||||
const TEST_HEADER_HEIGHT = '123px';
|
||||
|
||||
describe('Remove blobs', () => {
|
||||
let wrapper;
|
||||
|
||||
const createComponent = () => {
|
||||
getContentWrapperHeight.mockReturnValue(TEST_HEADER_HEIGHT);
|
||||
wrapper = shallowMountExtended(RemoveBlobs);
|
||||
};
|
||||
|
||||
const findDrawerTrigger = () => wrapper.findByTestId('drawer-trigger');
|
||||
const findDrawer = () => wrapper.findComponent(GlDrawer);
|
||||
const findModal = () => wrapper.findComponent(GlModal);
|
||||
const removeBlobsButton = () => wrapper.findByTestId('remove-blobs');
|
||||
const findTextarea = () => wrapper.findComponent(GlFormTextarea);
|
||||
|
||||
beforeEach(() => createComponent());
|
||||
|
||||
describe('initial state', () => {
|
||||
it('renders a button to open the drawer', () => {
|
||||
expect(findDrawerTrigger().exists()).toBe(true);
|
||||
});
|
||||
|
||||
it('renders a drawer, closed by default', () => {
|
||||
expect(findDrawer().props()).toMatchObject({
|
||||
headerHeight: TEST_HEADER_HEIGHT,
|
||||
zIndex: DRAWER_Z_INDEX,
|
||||
open: false,
|
||||
});
|
||||
|
||||
expect(findDrawer().text()).toContain(
|
||||
'Enter a list of object IDs to be removed to reduce repository size.',
|
||||
);
|
||||
});
|
||||
|
||||
it('renders a modal, closed by default', () => {
|
||||
expect(findModal().props()).toMatchObject({
|
||||
visible: false,
|
||||
title: 'Remove blobs',
|
||||
modalId: 'remove-blobs-confirmation-modal',
|
||||
actionCancel: { text: 'Cancel' },
|
||||
actionPrimary: { text: 'Yes, remove blobs' },
|
||||
});
|
||||
|
||||
expect(findModal().text()).toBe(
|
||||
'Removing blobs by ID cannot be undone. Are you sure you want to continue?',
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('removing blobs', () => {
|
||||
beforeEach(() => findDrawerTrigger().vm.$emit('click'));
|
||||
|
||||
it('opens the drawer', () => {
|
||||
expect(findDrawer().props('open')).toBe(true);
|
||||
});
|
||||
|
||||
it('renders a text area without text', () => {
|
||||
expect(findTextarea().text('disabled')).toBe('');
|
||||
});
|
||||
|
||||
it('disables the primary action by default', () => {
|
||||
expect(removeBlobsButton().props('disabled')).toBe(true);
|
||||
});
|
||||
|
||||
describe('adding blob IDs', () => {
|
||||
beforeEach(() => findTextarea().vm.$emit('input', '1234'));
|
||||
|
||||
it('enables the primary action when blob IDs are added', () => {
|
||||
expect(removeBlobsButton().props('disabled')).toBe(false);
|
||||
});
|
||||
|
||||
describe('confirmation modal', () => {
|
||||
beforeEach(() => removeBlobsButton().vm.$emit('click'));
|
||||
|
||||
it('renders the confirmation modal when remove blobs button is clicked', () => {
|
||||
expect(findModal().props('visible')).toBe(true);
|
||||
});
|
||||
|
||||
it('closes the drawer when removal is confirmed', async () => {
|
||||
findModal().vm.$emit('primary');
|
||||
await nextTick();
|
||||
|
||||
expect(findDrawer().props('open')).toBe(false);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
|
|
@ -196,9 +196,9 @@ export const securityFeaturesMock = [
|
|||
];
|
||||
|
||||
export const preReceiveSecretDetectionMock = {
|
||||
name: 'Pre-receive Secret Detection',
|
||||
name: 'Secret push protection',
|
||||
description: `Block secrets such as keys and API tokens from being pushed to your repositories.
|
||||
'Pre-receive secret detection is triggered when commits are pushed to a repository. ' \
|
||||
'Secret push protection is triggered when commits are pushed to a repository. ' \
|
||||
'If any secrets are detected, the push is blocked.`,
|
||||
helpPath: SAST_HELP_PATH,
|
||||
configurationHelpPath: helpPagePath(
|
||||
|
|
|
|||
|
|
@ -47,12 +47,6 @@ RSpec.describe DiffHelper, feature_category: :code_review_workflow do
|
|||
end
|
||||
|
||||
describe 'diff_options' do
|
||||
let(:large_notebooks_enabled) { false }
|
||||
|
||||
before do
|
||||
stub_feature_flags(large_ipynb_diffs: large_notebooks_enabled)
|
||||
end
|
||||
|
||||
it 'returns no collapse false' do
|
||||
expect(diff_options).to include(expanded: false)
|
||||
end
|
||||
|
|
@ -90,18 +84,8 @@ RSpec.describe DiffHelper, feature_category: :code_review_workflow do
|
|||
allow(controller).to receive(:params) { { file_identifier: 'something.ipynb' } }
|
||||
end
|
||||
|
||||
context 'when large_ipynb_diffs is disabled' do
|
||||
it 'does not set max_patch_bytes_for_file_extension' do
|
||||
expect(diff_options[:max_patch_bytes_for_file_extension]).to be_nil
|
||||
end
|
||||
end
|
||||
|
||||
context 'when large_ipynb_diffs is enabled' do
|
||||
let(:large_notebooks_enabled) { true }
|
||||
|
||||
it 'sets max_patch_bytes_for_file_extension' do
|
||||
expect(diff_options[:max_patch_bytes_for_file_extension]).to eq({ '.ipynb' => 1.megabyte })
|
||||
end
|
||||
it 'sets max_patch_bytes_for_file_extension' do
|
||||
expect(diff_options[:max_patch_bytes_for_file_extension]).to eq({ '.ipynb' => 1.megabyte })
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -137,9 +137,9 @@ RSpec.describe ::Gitlab::Security::ScanConfiguration do
|
|||
help_path: "/help/user/application_security/container_scanning/index",
|
||||
configuration_help_path: "/help/user/application_security/container_scanning/index#configuration",
|
||||
type: "container_scanning" }
|
||||
:pre_receive_secret_detection | { name: _("Pre-receive Secret Detection"),
|
||||
:pre_receive_secret_detection | { name: _("Secret push protection"),
|
||||
description: "Block secrets such as keys and API tokens from being pushed to your repositories. " \
|
||||
"Pre-receive secret detection is triggered when commits are pushed to a repository. " \
|
||||
"Secret push protection is triggered when commits are pushed to a repository. " \
|
||||
"If any secrets are detected, the push is blocked.",
|
||||
help_path: Gitlab::Routing.url_helpers.help_page_path(
|
||||
"user/application_security/secret_detection/pre_receive/index"),
|
||||
|
|
|
|||
|
|
@ -37,14 +37,13 @@ RSpec.describe InitializerConnections do
|
|||
expect { block_with_database_call }.not_to raise_error
|
||||
end
|
||||
|
||||
it 'prevents any database connection if SKIP_RAISE_ON_INITIALIZE_CONNECTIONS is false',
|
||||
quarantine: 'https://gitlab.com/gitlab-org/gitlab/-/issues/444962' do
|
||||
it 'prevents any database connection if SKIP_RAISE_ON_INITIALIZE_CONNECTIONS is false' do
|
||||
stub_env('SKIP_RAISE_ON_INITIALIZE_CONNECTIONS', 'false')
|
||||
|
||||
expect { block_with_database_call }.to raise_error(/Database connection should not be called during initializer/)
|
||||
end
|
||||
|
||||
it 'restores original connection handler', quarantine: 'https://gitlab.com/gitlab-org/gitlab/-/issues/444963' do
|
||||
it 'restores original connection handler' do
|
||||
original_handler = ActiveRecord::Base.connection_handler
|
||||
|
||||
expect { block_with_database_call }.to raise_error(/Database connection should not be called during initializer/)
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue