Add latest changes from gitlab-org/gitlab@master

This commit is contained in:
GitLab Bot 2025-05-29 18:11:00 +00:00
parent 815a08defc
commit a1b9a6464c
44 changed files with 172 additions and 567 deletions

View File

@ -87,6 +87,9 @@
.if-merge-request-targeting-stable-branch: &if-merge-request-targeting-stable-branch
if: '($CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_EVENT_TYPE != "merge_train") && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME =~ /^[\d-]+-stable(-ee|-jh)?$/'
.if-merge-request-targeting-stable-branch-is-tier-3: &if-merge-request-targeting-stable-branch-is-tier-3
if: '($CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_EVENT_TYPE != "merge_train") && $CI_MERGE_REQUEST_TARGET_BRANCH_NAME =~ /^[\d-]+-stable(-ee|-jh)?$/ && $CI_MERGE_REQUEST_LABELS =~ /pipeline::tier-3/'
.if-merge-request-labels-as-if-foss: &if-merge-request-labels-as-if-foss
if: '($CI_PIPELINE_SOURCE == "merge_request_event" && $CI_MERGE_REQUEST_EVENT_TYPE != "merge_train") && $CI_MERGE_REQUEST_LABELS =~ /pipeline:run-as-if-foss/'
@ -1941,7 +1944,7 @@
- !reference [".qa:rules:e2e-test-never-run", rules]
- <<: *if-merge-request-labels-run-all-e2e
# this rule needs to be synced with .notify:rules:notify-test-on-omnibus-failure to produce failure notification in stable branch merge requests
- <<: *if-merge-request-targeting-stable-branch
- <<: *if-merge-request-targeting-stable-branch-is-tier-3
changes: *setup-test-env-patterns
variables:
MR_STABLE_BRANCH_CODE_PATTERNS: "true"

View File

@ -9,10 +9,10 @@ import {
GlLink,
GlPopover,
} from '@gitlab/ui';
import ImmutableBadge from 'ee_component/packages_and_registries/container_registry/explorer/components/details_page/immutable_badge.vue';
import { localeDateFormat, newDate } from '~/lib/utils/datetime_utility';
import { numberToHumanSize } from '~/lib/utils/number_utils';
import { n__ } from '~/locale';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
import ClipboardButton from '~/vue_shared/components/clipboard_button.vue';
import DetailsRow from '~/vue_shared/components/registry/details_row.vue';
import ListItem from '~/vue_shared/components/registry/list_item.vue';
@ -51,11 +51,11 @@ export default {
DetailsRow,
SignatureDetailsModal,
GlPopover,
ImmutableBadge,
},
directives: {
GlTooltip: GlTooltipDirective,
},
mixins: [glFeatureFlagsMixin()],
props: {
tag: {
type: Object,
@ -168,9 +168,6 @@ export default {
this.tag.protection?.minimumAccessLevelForPush != null
);
},
isImmutable() {
return this.glFeatures.containerRegistryImmutableTags && this.tag.protection?.immutable;
},
tagRowId() {
return `${this.tag.name}_badge`;
},
@ -232,21 +229,7 @@ export default {
</gl-popover>
</template>
<template v-if="isImmutable">
<gl-badge
:id="tagRowId"
boundary="viewport"
class="gl-ml-4"
data-testid="immutable-badge"
>
{{ s__('ContainerRegistry|immutable') }}
</gl-badge>
<gl-popover :target="tagRowId" data-testid="immutable-popover">
{{
s__('ContainerRegistry|This container image tag cannot be overwritten or deleted.')
}}
</gl-popover>
</template>
<immutable-badge :tag="tag" :tag-row-id="tagRowId" />
<clipboard-button
v-if="tag.location"

View File

@ -5,7 +5,6 @@ import {
GlFormGroup,
GlForm,
GlFormInput,
GlFormRadio,
GlFormSelect,
GlLink,
GlSprintf,
@ -18,11 +17,6 @@ import {
} from '~/packages_and_registries/settings/project/constants';
import { __, s__ } from '~/locale';
import * as Sentry from '~/sentry/sentry_browser_wrapper';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
import glAbilitiesMixin from '~/vue_shared/mixins/gl_abilities_mixin';
const PROTECTED_RULE_TYPE = 'protected';
const IMMUTABLE_RULE_TYPE = 'immutable';
export default {
components: {
@ -34,9 +28,7 @@ export default {
GlFormSelect,
GlLink,
GlSprintf,
GlFormRadio,
},
mixins: [glFeatureFlagsMixin(), glAbilitiesMixin()],
inject: ['projectPath'],
props: {
rule: {
@ -44,6 +36,11 @@ export default {
required: false,
default: null,
},
isProtectedTagRuleType: {
type: Boolean,
required: false,
default: true,
},
},
data() {
return {
@ -55,7 +52,6 @@ export default {
minimumAccessLevelForDelete:
this.rule?.minimumAccessLevelForDelete ?? GRAPHQL_ACCESS_LEVEL_VALUE_MAINTAINER,
},
tagRuleType: PROTECTED_RULE_TYPE,
showValidation: false,
updateInProgress: false,
};
@ -73,21 +69,6 @@ export default {
tagNamePattern: this.protectionRuleFormData.tagNamePattern,
};
},
isFeatureFlagEnabled() {
return this.glFeatures.containerRegistryImmutableTags;
},
isProtectedTagRuleType() {
return this.tagRuleType === PROTECTED_RULE_TYPE;
},
canCreateImmutableTagRule() {
return (
this.isFeatureFlagEnabled &&
this.glAbilities.createContainerRegistryProtectionImmutableTagRule
);
},
showProtectionType() {
return this.canCreateImmutableTagRule && !this.rule;
},
isTagNamePatternValid() {
if (this.showValidation) {
return this.tagNamePattern.length > 0 && this.tagNamePattern.length < 100;
@ -190,8 +171,6 @@ export default {
}
},
},
PROTECTED_RULE_TYPE,
IMMUTABLE_RULE_TYPE,
minimumAccessLevelOptions: MinimumAccessLevelOptions,
};
</script>
@ -207,35 +186,7 @@ export default {
<div v-for="error in alertErrorMessages" :key="error">{{ error }}</div>
</gl-alert>
<template v-if="showProtectionType">
<gl-form-group :label="s__('ContainerRegistry|Protection type')">
<gl-form-radio
v-model="tagRuleType"
name="protection-type"
:value="$options.PROTECTED_RULE_TYPE"
autofocus
>
{{ s__('ContainerRegistry|Protected') }}
<template #help>
{{
s__(
'ContainerRegistry|Container image tags can be created, overwritten, or deleted by specific user roles.',
)
}}
</template>
</gl-form-radio>
<gl-form-radio
v-model="tagRuleType"
name="protection-type"
:value="$options.IMMUTABLE_RULE_TYPE"
>
{{ s__('ContainerRegistry|Immutable') }}
<template #help>
{{ s__('ContainerRegistry|Container image tags can never be overwritten or deleted.') }}
</template>
</gl-form-radio>
</gl-form-group>
</template>
<slot name="protection-type" :rule="rule"></slot>
<gl-form-group
:label="tagNamePatternLabel"
@ -247,7 +198,7 @@ export default {
id="input-tag-name-pattern"
v-model.trim="protectionRuleFormData.tagNamePattern"
type="text"
:autofocus="!showProtectionType"
:autofocus="!isProtectedTagRuleType"
required
trim
:state="isTagNamePatternValid"

View File

@ -13,12 +13,11 @@ import {
GlSkeletonLoader,
} from '@gitlab/ui';
import CrudComponent from '~/vue_shared/components/crud_component.vue';
import ContainerProtectionTagRuleForm from '~/packages_and_registries/settings/project/components/container_protection_tag_rule_form.vue';
import ContainerProtectionTagRuleForm from 'ee_else_ce/packages_and_registries/settings/project/components/container_protection_tag_rule_form.vue';
import getContainerProtectionTagRulesQuery from '~/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql';
import deleteContainerProtectionTagRuleMutation from '~/packages_and_registries/settings/project/graphql/mutations/delete_container_protection_tag_rule.mutation.graphql';
import { __, s__ } from '~/locale';
import { getAccessLevelLabel } from '~/packages_and_registries/settings/project/utils';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
import * as Sentry from '~/sentry/sentry_browser_wrapper';
@ -44,7 +43,6 @@ export default {
GlModal: GlModalDirective,
GlTooltip: GlTooltipDirective,
},
mixins: [glFeatureFlagsMixin()],
inject: ['projectPath'],
apollo: {
protectionRulesQueryPayload: {
@ -86,13 +84,9 @@ export default {
return this.tagProtectionRulesCount > 0;
},
description() {
return this.isFeatureFlagEnabled
? s__(
'ContainerRegistry|Set up rules to protect container image tags from unauthorized changes or make them permanently immutable. Protection rules are checked first, followed by immutable rules. You can add up to 5 protection rules per project.',
)
: s__(
'ContainerRegistry|When a container image tag is protected, only certain user roles can create, update, and delete the protected tag, which helps to prevent unauthorized changes. You can add up to 5 protection rules per project.',
);
return s__(
'ContainerRegistry|When a container image tag is protected, only certain user roles can create, update, and delete the protected tag, which helps to prevent unauthorized changes. You can add up to 5 protection rules per project.',
);
},
drawerTitle() {
return this.protectionRuleMutationItem
@ -102,9 +96,6 @@ export default {
isLoadingProtectionRules() {
return this.$apollo.queries.protectionRulesQueryPayload.loading;
},
isFeatureFlagEnabled() {
return this.glFeatures.containerRegistryImmutableTags;
},
protectionRulesQueryResult() {
return this.protectionRulesQueryPayload.nodes;
},
@ -180,9 +171,6 @@ export default {
this.closeDrawer();
this.refetchProtectionRules();
},
getBadgeText({ immutable }) {
return immutable ? s__('ContainerRegistry|immutable') : s__('ContainerRegistry|protected');
},
isEditable({ immutable }) {
return !immutable;
},
@ -264,6 +252,10 @@ export default {
data-testid="project-container-protection-tag-rules-settings"
@showForm="openNewFormDrawer"
>
<template #description>
<slot name="description"></slot>
</template>
<template v-if="containsTableItems" #count>
<gl-badge>
<gl-sprintf :message="s__('ContainerRegistry|%{count} of %{max}')">
@ -320,11 +312,7 @@ export default {
<span data-testid="tag-name-pattern" class="gl-break-all">
{{ item.tagNamePattern }}
</span>
<span v-if="isFeatureFlagEnabled">
<gl-badge data-testid="tag-rule-type-badge">
{{ getBadgeText(item) }}
</gl-badge>
</span>
<slot name="tag-badge" :item="item"></slot>
</span>
</template>

View File

@ -4,7 +4,7 @@ import { helpPagePath } from '~/helpers/help_page_helper';
import SettingsBlock from '~/vue_shared/components/settings/settings_block.vue';
import ContainerExpirationPolicy from '~/packages_and_registries/settings/project/components/container_expiration_policy.vue';
import ContainerProtectionRepositoryRules from '~/packages_and_registries/settings/project/components/container_protection_repository_rules.vue';
import ContainerProtectionTagRules from '~/packages_and_registries/settings/project/components/container_protection_tag_rules.vue';
import ContainerProtectionTagRules from 'ee_else_ce/packages_and_registries/settings/project/components/container_protection_tag_rules.vue';
export default {
components: {

View File

@ -1,4 +0,0 @@
- page_title _("New Application")
= render ::Layouts::PageHeadingComponent.new(_('New application'))
= render 'form', application: @application

View File

@ -1,16 +0,0 @@
= render ::Layouts::PageHeadingComponent.new(_("Your authorized applications"))
%main{ :role => "main" }
.table-holder
%table.table.table-striped
%thead
%tr
%th= _('Application')
%th= _('Created At')
%th
%th
%tbody
- @applications.each do |application|
%tr
%td= application.name
%td= application.created_at.strftime('%Y-%m-%d %H:%M:%S')
%td= render 'delete_form', application: application

View File

@ -5,4 +5,4 @@ feature_category: value_stream_management
introduced_by_url: https://gitlab.com/gitlab-org/gitlab/-/merge_requests/174502
milestone: '17.7'
queued_migration_version: 20241203074404
finalized_by: # version of the migration that finalized this BBM
finalized_by: '20250528232821'

View File

@ -0,0 +1,22 @@
# frozen_string_literal: true
class AddIndexToProjectComplianceViolationsNamespaceCreatedId < Gitlab::Database::Migration[2.3]
milestone '18.1'
disable_ddl_transaction!
INDEX_NAMESPACE_ID = 'idx_project_compliance_violations_on_namespace_id'
INDEX_NAMESPACE_CREATED_AT_ID_DESC = 'i_project_compliance_violations_on_namespace_id_created_at_id'
def up
add_concurrent_index :project_compliance_violations, [:namespace_id, :created_at, :id],
order: { created_at: :desc, id: :desc }, using: :btree, name: INDEX_NAMESPACE_CREATED_AT_ID_DESC
remove_concurrent_index_by_name :project_compliance_violations, INDEX_NAMESPACE_ID
end
def down
add_concurrent_index :project_compliance_violations, :namespace_id, name: INDEX_NAMESPACE_ID
remove_concurrent_index_by_name :project_compliance_violations, INDEX_NAMESPACE_CREATED_AT_ID_DESC
end
end

View File

@ -0,0 +1,21 @@
# frozen_string_literal: true
class FinalizeHkBackfillIssueMetricsNamespaceId < Gitlab::Database::Migration[2.3]
milestone '18.1'
disable_ddl_transaction!
restrict_gitlab_migration gitlab_schema: :gitlab_main_cell
def up
ensure_batched_background_migration_is_finished(
job_class_name: 'BackfillIssueMetricsNamespaceId',
table_name: :issue_metrics,
column_name: :id,
job_arguments: [:namespace_id, :issues, :namespace_id, :issue_id],
finalize: true
)
end
def down; end
end

View File

@ -0,0 +1 @@
cd712adf76694be2c439982836cfd66f49a04cdf1775ebc3a198d3fd8821ca79

View File

@ -0,0 +1 @@
cfb1b2b01820de3f7e413c7e7b0615e406063ea6970baf95e08a5427592cf34f

View File

@ -33259,6 +33259,8 @@ CREATE UNIQUE INDEX i_pm_package_versions_on_package_id_and_version ON pm_packag
CREATE UNIQUE INDEX i_pm_packages_purl_type_and_name ON pm_packages USING btree (purl_type, name);
CREATE INDEX i_project_compliance_violations_on_namespace_id_created_at_id ON project_compliance_violations USING btree (namespace_id, created_at DESC, id DESC);
CREATE INDEX i_project_requirement_statuses_on_namespace_id_framework_id ON project_requirement_compliance_statuses USING btree (namespace_id, compliance_framework_id, id);
CREATE INDEX i_project_requirement_statuses_on_namespace_id_project_id ON project_requirement_compliance_statuses USING btree (namespace_id, project_id, id);
@ -33599,8 +33601,6 @@ CREATE INDEX idx_project_audit_events_on_project_id_author_created_at_id ON ONLY
CREATE INDEX idx_project_compliance_violations_on_control_id ON project_compliance_violations USING btree (compliance_requirements_control_id);
CREATE INDEX idx_project_compliance_violations_on_namespace_id ON project_compliance_violations USING btree (namespace_id);
CREATE INDEX idx_project_compliance_violations_on_project_id ON project_compliance_violations USING btree (project_id);
CREATE INDEX idx_project_control_compliance_status_on_requirement_status_id ON project_control_compliance_statuses USING btree (requirement_status_id);

View File

@ -12,7 +12,7 @@ title: GitLab Docs
<h3>Visit <a href="https://docs.gitlab.com/ee/">docs.gitlab.com</a> for the latest version
of this help information with enhanced navigation, formatting, and search.</h3>
</div>
<!-- the div above will not display on the docs site but will display on /help -->
<!-- the div tag will not display on the docs site but will display on /help -->
<!-- markdownlint-enable MD044 -->

View File

@ -12,10 +12,10 @@ title: Job Artifacts API
{{< /details >}}
Use the job artifacts API to download or delete job artifacts.
Use this API to interact with [job artifacts](../ci/jobs/job_artifacts.md).
Authentication with a [CI/CD job token](../ci/jobs/job_artifacts.md#with-a-cicd-job-token)
available in the Premium and Ultimate tier.
is available in the Premium and Ultimate tier.
## Get job artifacts

View File

@ -12,6 +12,8 @@ title: Jobs API
{{< /details >}}
Use this API to interact with [CI/CD jobs](../ci/jobs/_index.md).
## List project jobs
{{< history >}}

View File

@ -12,18 +12,11 @@ title: Merge Trains API
{{< /details >}}
Every API call for [merge train](../ci/pipelines/merge_trains.md) must be authenticated with at least the Developer [role](../user/permissions.md).
Use this API to interact with [merge trains](../ci/pipelines/merge_trains.md).
If a user is not a member of a project and the project is private, a `GET` request on that project returns a `404` status code.
Prerequisites:
If Merge Trains is not available for the project, a `403` status code is returned.
## Merge Trains API pagination
By default, `GET` requests return 20 results at a time because the API results
are paginated.
For more information, see [pagination](rest/_index.md#pagination).
- You must have at least the Developer role.
## List Merge Trains for a project
@ -34,6 +27,9 @@ GET /projects/:id/merge_trains
GET /projects/:id/merge_trains?scope=complete
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|-----------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths). |
@ -44,6 +40,11 @@ GET /projects/:id/merge_trains?scope=complete
curl --header "PRIVATE-TOKEN: <your_access_token>" "https://gitlab.example.com/api/v4/projects/1/merge_trains"
```
Returns:
- `403: Forbidden` if Merge Trains are not available for the project
- `404: Not Found` if the user is not a member of a private project
Example response:
```json
@ -96,6 +97,9 @@ Get all merge requests added to a merge train for the requested target branch.
GET /projects/:id/merge_trains/:target_branch
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
Supported attributes:
| Attribute | Type | Required | Description |
@ -111,6 +115,11 @@ Example request:
curl --request GET --header "PRIVATE-TOKEN: <your_access_token>" "https://gitlab.example.com/api/v4/projects/597/merge_trains/main"
```
Returns:
- `403: Forbidden` if Merge Trains are not available for the project
- `404: Not Found` if the user is not a member of a private project
Example response:
```json
@ -166,6 +175,9 @@ Get merge train information for the requested merge request.
GET /projects/:id/merge_trains/merge_requests/:merge_request_iid
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
Supported attributes:
| Attribute | Type | Required | Description |
@ -179,6 +191,11 @@ Example request:
curl --request GET --header "PRIVATE-TOKEN: <your_access_token>" "https://gitlab.example.com/api/v4/projects/597/merge_trains/merge_requests/1"
```
Returns:
- `403: Forbidden` if Merge Trains are not available for the project
- `404: Not Found` if the user is not a member of a private project
Example response:
```json
@ -249,6 +266,10 @@ Example request:
curl --request POST --header "PRIVATE-TOKEN: <your_access_token>" "https://gitlab.example.com/api/v4/projects/597/merge_trains/merge_requests/1"
```
Returns:
- `403: Forbidden` if Merge Trains are not available for the project
Example response:
```json

View File

@ -12,7 +12,7 @@ title: Pipeline schedules API
{{< /details >}}
You can read more about [pipeline schedules](../ci/pipelines/schedules.md).
Use this API to interact with [pipeline schedules](../ci/pipelines/schedules.md).
## Get all pipeline schedules

View File

@ -12,7 +12,7 @@ title: Pipeline trigger tokens API
{{< /details >}}
You can read more about [triggering pipelines through the API](../ci/triggers/_index.md).
Use this API to [trigger pipelines](../ci/triggers/_index.md).
## List project trigger tokens

View File

@ -12,12 +12,7 @@ title: Pipelines API
{{< /details >}}
## Pipelines pagination
By default, `GET` requests return 20 results at a time because the API results
are paginated.
Read more on [pagination](rest/_index.md#pagination).
Use this API to interact with [CI/CD pipelines](../ci/pipelines/_index.md).
## List project pipelines
@ -41,6 +36,9 @@ are not included in the results. To return child pipelines, set `source` to `par
GET /projects/:id/pipelines
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|------------------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths) |
@ -114,6 +112,9 @@ You can also get a single [child pipeline](../ci/pipelines/downstream_pipelines.
GET /projects/:id/pipelines/:pipeline_id
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|---------------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths) |
@ -169,7 +170,7 @@ Example of response
}
```
### Get the latest pipeline
## Get the latest pipeline
{{< history >}}
@ -184,6 +185,9 @@ Get the latest pipeline for the most recent commit on a specific ref in a projec
GET /projects/:id/pipelines/latest
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|-----------|--------|----------|-------------|
| `ref` | string | No | The branch or tag to check for the latest pipeline. Defaults to the default branch when not specified. |
@ -238,7 +242,7 @@ Example of response
}
```
### Get variables of a pipeline
## Get variables for a pipeline
Get the variables of a pipeline. Does not include variables that come from a pipeline schedule.
For more information, see [issue 250850](https://gitlab.com/gitlab-org/gitlab/-/issues/250850).
@ -247,6 +251,9 @@ For more information, see [issue 250850](https://gitlab.com/gitlab-org/gitlab/-/
GET /projects/:id/pipelines/:pipeline_id/variables
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|---------------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths) |
@ -272,7 +279,7 @@ Example of response
]
```
### Get a pipeline's test report
## Get a test report for a pipeline
{{< alert type="note" >}}
@ -284,6 +291,9 @@ This API route is part of the [Unit test report](../ci/testing/unit_test_reports
GET /projects/:id/pipelines/:pipeline_id/test_report
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|---------------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths) |
@ -329,7 +339,7 @@ Sample response:
}
```
### Get a pipeline's test report summary
## Get a test report summary for a pipeline
{{< alert type="note" >}}
@ -341,6 +351,9 @@ This API route is part of the [Unit test report](../ci/testing/unit_test_reports
GET /projects/:id/pipelines/:pipeline_id/test_report_summary
```
Use the `page` and `per_page` [pagination](rest/_index.md#offset-based-pagination) parameters to
control the pagination of results.
| Attribute | Type | Required | Description |
|---------------|----------------|----------|-------------|
| `id` | integer/string | Yes | The ID or [URL-encoded path of the project](rest/_index.md#namespaced-paths) |
@ -509,7 +522,7 @@ Response:
}
```
## Cancel a pipeline's jobs
## Cancel all jobs for a pipeline
```plaintext
POST /projects/:id/pipelines/:pipeline_id/cancel

View File

@ -768,7 +768,7 @@ To determine the IP address of an instance runner:
1. Select **CI/CD > Runners**.
1. Find the runner in the table and view the **IP Address** column.
![Instance runner IP address](img/shared_runner_ip_address_v14_5.png)
![Screenshot showing the IP address column for an instance runner in the GitLab Admin area](img/shared_runner_ip_address_v14_5.png)
### Determine the IP address of a project runner
@ -779,7 +779,7 @@ project.
1. Go to the project's **Settings > CI/CD** and expand the **Runners** section.
1. Select the runner name and find the **IP Address** row.
![Project runner IP address](img/project_runner_ip_address_v17_6.png)
![Screenshot showing where to find the IP address for a project runner in the runner details](img/project_runner_ip_address_v17_6.png)
## Enable use of runner registration tokens in projects and groups

View File

@ -143,7 +143,7 @@ displays a list of test suites and cases reported from the XML file.
You can view all the known test suites and select each of these to see further
details, including the cases that make up the suite.
You can also retrieve the reports via the [GitLab API](../../api/pipelines.md#get-a-pipelines-test-report).
You can also retrieve the reports via the [GitLab API](../../api/pipelines.md#get-a-test-report-for-a-pipeline).
### Unit test reports parsing errors

View File

@ -2,7 +2,7 @@
stage: Verify
group: Pipeline Authoring
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://handbook.gitlab.com/handbook/product/ux/technical-writing/#assignments
title: Trigger pipelines by using the API
title: Trigger pipelines with the API
---
{{< details >}}

View File

@ -2052,10 +2052,6 @@ feedback: false
The default is to leave it there. If you want to omit it from a document, you
must check with a technical writer before doing so.
The click events in the feedback section are tracked with Google Tag Manager.
The conversions can be viewed on Google Analytics by navigating to
**Behavior > Events > Top events > docs**.
### GitLab restart
When a restart or reconfigure of GitLab is required, avoid duplication by linking

View File

@ -204,7 +204,7 @@ To override the default values in the `values.yaml` file in the
- Add a file with a different name or path to the repository. Set the
`HELM_UPGRADE_VALUES_FILE` [CI/CD variable](cicd_variables.md) with the path and name of the file.
Some values cannot be overridden with the options above, but [this issue](https://gitlab.com/gitlab-org/cluster-integration/auto-deploy-image/-/issues/31) proposes to change this behavior.
Some values cannot be overridden with the previous options, but [this issue](https://gitlab.com/gitlab-org/cluster-integration/auto-deploy-image/-/issues/31) proposes to change this behavior.
To override settings like `replicaCount`, use the `REPLICAS` [build and deployment](cicd_variables.md#build-and-deployment-variables) CI/CD variable.
### Customize `helm upgrade`

View File

@ -173,7 +173,7 @@ controller to external clients and, indirectly, to any application running insid
Bare-metal environments lack this commodity, requiring a slightly different setup to offer the
same kind of access to external consumers.
The docs linked above explain the issue and present possible solutions, for example:
The documentation linked previously explains the issue and provides possible solutions, for example:
- Through [MetalLB](https://github.com/metallb/metallb).
- Through [PorterLB](https://github.com/kubesphere/porterlb).

View File

@ -161,7 +161,7 @@ The supported buildpacks are:
- buildpack-nginx
```
If your application needs a buildpack that is not in the above list, you
If your application needs a buildpack that is not in the previous list, you
might want to use a [custom buildpack](customize.md#custom-buildpacks).
## Auto Code Quality
@ -190,7 +190,7 @@ out. The merge request widget also displays any
Static Application Security Testing (SAST) runs static
analysis on the current code, and checks for potential security issues. The
Auto SAST stage requires [GitLab Runner](https://docs.gitlab.com/runner/) 11.5 or above.
Auto SAST stage requires [GitLab Runner](https://docs.gitlab.com/runner/) 11.5 or later.
After creating the report, it's uploaded as an artifact which you can later
download and check out. The merge request widget also displays any security

View File

@ -183,7 +183,7 @@ that works for this problem. Follow these steps to use the tool in Auto DevOps:
- remote: https://gitlab.com/shinya.maeda/ci-templates/-/raw/master/map-deprecated-api.gitlab-ci.yml
variables:
HELM_VERSION_FOR_MAPKUBEAPIS: "v2" # If you're using auto-depoy-image v2 or above, please specify "v3".
HELM_VERSION_FOR_MAPKUBEAPIS: "v2" # If you're using auto-depoy-image v2 or later, please specify "v3".
```
1. Run the job `<environment-name>:map-deprecated-api`. Ensure that this job succeeds before moving

View File

@ -372,7 +372,7 @@ remove filtering:
- Its corresponding `pack-<SHA1>.idx` file.
- A `pack-<SHA1>.promisor` file.
1. Delete the `.promisor` file. The above step should have left only one
1. Delete the `.promisor` file. The previous step should have left only one
`pack-<SHA1>.promisor` file, which should be empty and should be deleted.
1. Remove partial clone configuration. The partial clone-related configuration

View File

@ -397,7 +397,7 @@ If license or advisory data is missing from the dependency list or MR pages, one
`package_metadata` synchronization is triggered by using cron jobs ([advisory sync](https://gitlab.com/gitlab-org/gitlab/-/blob/16-3-stable-ee/config/initializers/1_settings.rb#L864-866) and [license sync](https://gitlab.com/gitlab-org/gitlab/-/blob/16-3-stable-ee/config/initializers/1_settings.rb#L855-857)) and imports only the package registry types enabled in [admin settings](../../administration/settings/security_and_compliance.md#choose-package-registry-metadata-to-sync).
The file structure in `vendor/package_metadata` must coincide with the package registry type enabled above. For example, to sync `maven` license or advisory data, the package metadata directory under the Rails directory must have the following structure:
The file structure in `vendor/package_metadata` must coincide with the package registry type enabled previously. For example, to sync `maven` license or advisory data, the package metadata directory under the Rails directory must have the following structure:
- For licenses:`$GITLAB_RAILS_ROOT_DIR/vendor/package_metadata/licenses/v2/maven/**/*.ndjson`.
- For advisories:`$GITLAB_RAILS_ROOT_DIR/vendor/package_metadata/advisories/v2/maven/**/*.ndjson`.

View File

@ -155,13 +155,13 @@ Based on the metrics collected, for this job profile, you can limit the Kubernet
If you use a cluster with a node pool of three `e2-standard-4` nodes to run jobs, the `1 CPU` limit allows only **12 jobs** to run simultaneously (an `e2-standard-4` node has **4 vCPU** and **16 GB** of memory). Additional jobs wait for the running jobs to complete and free up the resources before starting.
The memory requested is critical because Kubernetes terminates any pod that uses more memory than the limit set or available on the cluster. However, the CPU limit is more flexible but impacts the job duration. A lower CPU limit set increases the time it takes for a job to complete. In the above example, setting the CPU limit to `250m` (or `0.25`) instead `1` increased the job duration by four times (from about two minutes to eight to ten minutes).
The memory requested is critical because Kubernetes terminates any pod that uses more memory than the limit set or available on the cluster. However, the CPU limit is more flexible but impacts the job duration. A lower CPU limit set increases the time it takes for a job to complete. In the previous example, setting the CPU limit to `250m` (or `0.25`) instead `1` increased the job duration by four times (from about two minutes to eight to ten minutes).
As the metrics collection method uses a polling mechanism, you should round up the maximum usage identified. For example, instead of `303 Mi` for the memory usage, round it to `400 Mi`.
Important considerations for the above example:
Important considerations for the previous example:
- The metrics above were collected on the local machine, which doesn't have the same CPU configuration than a Google Kubernetes Engine Cluster. However, these metrics were validated by monitoring them on a Kubernetes cluster with an `e2-standard-4` node.
- The metrics were collected on the local machine, which doesn't have the same CPU configuration than a Google Kubernetes Engine Cluster. However, these metrics were validated by monitoring them on a Kubernetes cluster with an `e2-standard-4` node.
- To get an accurate representation of those metrics, run the tests described in the [Assess phase](#assess-the-expected-cicd-workloads) on a Google Compute Engine VM.
## Plan the runner fleet configuration
@ -294,7 +294,7 @@ node_pools = {
}
```
In the configuration above:
In the previous configuration:
- The `runner-manager` block refers to the node pool where GitLab Runner is installed. In our example, a `e2-standard-2` is more than enough.
- The labels sections in the `runner-manager` block is useful when installing GitLab Runner on GitLab. A node selector is configured through the operator configuration to make sure that GitLab Runner is installed on a node of this node pool.
@ -351,7 +351,7 @@ EOT
]
```
In the configuration above:
In the previous configuration:
- The `pod_spec` parameter allows us to set a node selector for the pod running GitLab Runner. In the configuration, the node selector is set to `"app" = "gitlab-runner"` to ensure that GitLab Runner is installed on the runner-manager node pool.
- The `config_template` parameters provides a default limit for all jobs run by the GitLab Runner Manager. It also allows an overwrite of those limits as long as the value set is not greater than the default values.

View File

@ -2,6 +2,7 @@
stage: AI-powered
group: AI Framework
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://handbook.gitlab.com/handbook/product/ux/technical-writing/#assignments
description: Set up and manage GitLab Duo with Amazon Q on a Self-Managed instance using AWS integration.
title: Set up GitLab Duo with Amazon Q
---

View File

@ -3,6 +3,7 @@ stage: Software Supply Chain Security
group: Authentication
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://handbook.gitlab.com/handbook/product/ux/technical-writing/#assignments
gitlab_dedicated: yes
description: Two-factor authentication (2FA) adds an extra layer of security to your GitLab account by requiring a second form of verification in addition to your password.
title: Two-factor authentication
---

View File

@ -2,6 +2,7 @@
stage: Software Supply Chain Security
group: Authentication
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://handbook.gitlab.com/handbook/product/ux/technical-writing/#assignments
description: Use personal access tokens to authenticate with the GitLab API or Git over HTTPS. Includes creation, rotation, revocation, scopes, and expiration settings.
title: Personal access tokens
---

View File

@ -7885,9 +7885,6 @@ msgstr ""
msgid "AppleAppStore|Use GitLab to build and release an app in the Apple App Store."
msgstr ""
msgid "Application"
msgstr ""
msgid "Application ID"
msgstr ""
@ -18963,9 +18960,6 @@ msgstr ""
msgid "Created %{timestamp}"
msgstr ""
msgid "Created At"
msgstr ""
msgid "Created Date"
msgstr ""
@ -40374,9 +40368,6 @@ msgstr ""
msgid "New %{type} in %{project}"
msgstr ""
msgid "New Application"
msgstr ""
msgid "New File"
msgstr ""
@ -40404,9 +40395,6 @@ msgstr ""
msgid "New Security findings"
msgstr ""
msgid "New application"
msgstr ""
msgid "New branch"
msgstr ""
@ -71613,9 +71601,6 @@ msgstr ""
msgid "Your applications"
msgstr ""
msgid "Your authorized applications"
msgstr ""
msgid "Your browser doesn't support WebAuthn. Please use a supported browser, e.g. Chrome (67+) or Firefox (60+)."
msgstr ""

View File

@ -58,13 +58,8 @@ describe('tags list row', () => {
const getTooltipFor = (component) => getBinding(component.element, 'gl-tooltip');
const findProtectedBadge = () => wrapper.findByTestId('protected-badge');
const findProtectedPopover = () => wrapper.findByTestId('protected-popover');
const findImmutableBadge = () => wrapper.findByTestId('immutable-badge');
const findImmutablePopover = () => wrapper.findByTestId('immutable-popover');
const mountComponent = (
propsData = defaultProps,
{ immutableTagsFeatureFlagState = false } = {},
) => {
const mountComponent = (propsData = defaultProps) => {
wrapper = shallowMountExtended(TagsListRow, {
stubs: {
GlSprintf,
@ -75,11 +70,6 @@ describe('tags list row', () => {
},
propsData,
directives: { GlTooltip: createMockDirective('gl-tooltip') },
provide: {
glFeatures: {
containerRegistryImmutableTags: immutableTagsFeatureFlagState,
},
},
});
};
@ -224,56 +214,6 @@ describe('tags list row', () => {
});
});
describe('immutable tag', () => {
const immutableProtection = {
minimumAccessLevelForDelete: null,
minimumAccessLevelForPush: null,
immutable: true,
};
it('hidden if tag.protection does not exists', () => {
mountComponent(defaultProps, { immutableTagsFeatureFlagState: true });
expect(findImmutableBadge().exists()).toBe(false);
});
it('displays if tag.protection.immutable exists', () => {
mountComponent(
{
...defaultProps,
tag: {
...tag,
protection: {
...immutableProtection,
},
},
},
{ immutableTagsFeatureFlagState: true },
);
expect(findImmutableBadge().text()).toBe('immutable');
});
it('has the correct text for the popover', () => {
mountComponent(
{
...defaultProps,
tag: {
...tag,
protection: {
...immutableProtection,
},
},
},
{ immutableTagsFeatureFlagState: true },
);
const popoverText = findImmutablePopover().text();
expect(popoverText).toBe('This container image tag cannot be overwritten or deleted.');
});
});
describe('warning icon', () => {
it('is normally hidden', () => {
mountComponent();

View File

@ -20,18 +20,12 @@ import { containerProtectionTagRuleMutationInput } from '../mock_data';
Vue.use(VueApollo);
describe('container Protection Rule Form', () => {
describe('Container Protection Rule Form', () => {
let wrapper;
let fakeApollo;
const defaultProvidedValues = {
projectPath: 'path',
glFeatures: {
containerRegistryImmutableTags: true,
},
glAbilities: {
createContainerRegistryProtectionImmutableTagRule: true,
},
};
const rule =
@ -39,14 +33,8 @@ describe('container Protection Rule Form', () => {
.containerProtectionTagRule;
const findForm = () => wrapper.findComponent(GlForm);
const findProtectionTypeProtectedRadio = () =>
wrapper.findByRole('radio', { name: /protected/i });
const findProtectionTypeImmutableRadio = () =>
wrapper.findByRole('radio', { name: /immutable/i });
const findTagNamePatternInput = () =>
wrapper.findByRole('textbox', { name: /protect container tags matching/i });
const findImmutableTagNamePatternInput = () =>
wrapper.findByRole('textbox', { name: /apply immutability rule to tags matching/i });
const findMinimumAccessLevelForPushSelect = () =>
wrapper.findByRole('combobox', { name: /minimum role allowed to push/i });
const findMinimumAccessLevelForDeleteSelect = () =>
@ -89,24 +77,6 @@ describe('container Protection Rule Form', () => {
};
describe('form fields', () => {
describe('form field "protectionType"', () => {
beforeEach(() => {
mountComponent();
});
describe('form field "protectionType"', () => {
it('protected radio exists and is checked by default', () => {
expect(findProtectionTypeProtectedRadio().element.value).toBe('protected');
expect(findProtectionTypeProtectedRadio().element.checked).toBe(true);
});
it('immutable radio exists and default value', () => {
expect(findProtectionTypeImmutableRadio().element.value).toBe('immutable');
expect(findProtectionTypeImmutableRadio().element.checked).toBe(false);
});
});
});
describe('form field "tagNamePattern"', () => {
it('exists', () => {
mountComponent();
@ -194,65 +164,6 @@ describe('container Protection Rule Form', () => {
});
});
describe('when form field "protectionType"', () => {
beforeEach(() => {
mountComponent();
});
describe('is set to immutable', () => {
beforeEach(() => {
extendedWrapper(findProtectionTypeImmutableRadio()).setChecked();
});
it('form field "tagNamePattern" exists', () => {
expect(findImmutableTagNamePatternInput().exists()).toBe(true);
});
it('form field "minimumAccessLevelForPush" is hidden', () => {
expect(findMinimumAccessLevelForPushSelect().exists()).toBe(false);
});
it('form field "minimumAccessLevelForDelete" is hidden', () => {
expect(findMinimumAccessLevelForDeleteSelect().exists()).toBe(false);
});
});
describe('and form is submitted', () => {
const createMutationResolver = jest
.fn()
.mockResolvedValue(createContainerProtectionTagRuleMutationPayload);
const updateMutationResolver = jest
.fn()
.mockResolvedValue(updateContainerProtectionTagRuleMutationPayload);
const submitForm = () => {
findImmutableTagNamePatternInput().setValue(
containerProtectionTagRuleMutationInput.tagNamePattern,
);
findForm().trigger('submit');
return waitForPromises();
};
beforeEach(() => {
mountComponentWithApollo({ createMutationResolver, updateMutationResolver });
});
it('dispatches correct apollo mutation', async () => {
await extendedWrapper(findProtectionTypeImmutableRadio()).setChecked();
await submitForm();
expect(createMutationResolver).toHaveBeenCalledWith({
input: {
projectPath: 'path',
tagNamePattern: containerProtectionTagRuleMutationInput.tagNamePattern,
},
});
expect(updateMutationResolver).not.toHaveBeenCalled();
});
});
});
describe.each`
description | props | submitButtonText
${'when form has no prop "rule"'} | ${{}} | ${'Add rule'}
@ -443,39 +354,16 @@ describe('container Protection Rule Form', () => {
});
});
describe('when user does not have ability to create immutable tag rule', () => {
beforeEach(() => {
mountComponent({
provide: {
...defaultProvidedValues,
glAbilities: {
createContainerRegistryProtectionImmutableTagRule: false,
},
},
});
});
describe('when isProtectedTagRuleType prop is passed', () => {
it.each`
propValue | label | description
${true} | ${'Protect container tags matching'} | ${'Tags with names that match this regex pattern are protected. Must be less than 100 characters. What regex patterns are supported?'}
${false} | ${'Apply immutability rule to tags matching'} | ${'Tags with names that match this regex pattern are immutable. Must be less than 100 characters. What regex patterns are supported?'}
`('test', ({ propValue, label, description }) => {
mountComponent({ props: { isProtectedTagRuleType: propValue } });
it('form field "protectionType" does not exist', () => {
expect(findProtectionTypeProtectedRadio().exists()).toBe(false);
expect(findProtectionTypeImmutableRadio().exists()).toBe(false);
});
});
describe('when `containerRegistryImmutableTags` feature flag is turned off', () => {
beforeEach(() => {
mountComponent({
provide: {
...defaultProvidedValues,
glFeatures: {
containerRegistryImmutableTags: false,
},
},
});
});
it('form field "protectionType" does not exist', () => {
expect(findProtectionTypeProtectedRadio().exists()).toBe(false);
expect(findProtectionTypeImmutableRadio().exists()).toBe(false);
expect(wrapper.text()).toContain(label);
expect(wrapper.text()).toContain(description);
});
});
});

View File

@ -14,8 +14,6 @@ import containerProtectionTagRuleEmptyRulesQueryPayload from 'test_fixtures/grap
import containerProtectionTagRuleMaxRulesQueryPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql.max_rules.json';
import containerProtectionTagRuleNullProjectQueryPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql.null_project.json';
import containerProtectionTagRuleQueryPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql.json';
import containerProtectionImmutableTagRuleQueryPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql.immutable_rules.json';
import containerProtectionImmutableTagRuleMaintainerQueryPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/queries/get_container_protection_tag_rules.query.graphql.immutable_rules_maintainer.json';
import deleteContainerProtectionTagRuleMutationPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/mutations/delete_container_protection_tag_rule.mutation.graphql.json';
import deleteContainerProtectionTagRuleMutationErrorPayload from 'test_fixtures/graphql/packages_and_registries/settings/project/graphql/mutations/delete_container_protection_tag_rule.mutation.graphql.errors.json';
@ -56,9 +54,6 @@ describe('ContainerProtectionTagRules', () => {
const defaultProvidedValues = {
projectPath: 'path',
glFeatures: {
containerRegistryImmutableTags: true,
},
};
const { nodes: tagRules } =
@ -104,7 +99,7 @@ describe('ContainerProtectionTagRules', () => {
expect(findCrudComponent().props('title')).toBe('Protected container image tags');
expect(findCrudComponent().props('toggleText')).toBeNull();
expect(findCrudComponent().props('description')).toBe(
'Set up rules to protect container image tags from unauthorized changes or make them permanently immutable. Protection rules are checked first, followed by immutable rules. You can add up to 5 protection rules per project.',
'When a container image tag is protected, only certain user roles can create, update, and delete the protected tag, which helps to prevent unauthorized changes. You can add up to 5 protection rules per project.',
);
});
@ -212,14 +207,9 @@ describe('ContainerProtectionTagRules', () => {
await waitForPromises();
});
it('contains container protection tag rules and `protected` badge', () => {
it('contains container protection tag rules', () => {
tagRules.forEach((protectionRule, i) => {
expect(findTableRowCell(i, 0).findByTestId('tag-name-pattern').text()).toBe(
protectionRule.tagNamePattern,
);
expect(findTableRowCell(i, 0).findByTestId('tag-rule-type-badge').text()).toBe(
'protected',
);
expect(findTableRowCell(i, 0).text()).toBe(protectionRule.tagNamePattern);
expect(findTableRowCell(i, 1).text()).toBe(
MinimumAccessLevelText[protectionRule.minimumAccessLevelForPush],
);
@ -258,107 +248,6 @@ describe('ContainerProtectionTagRules', () => {
});
});
describe('table rows for immutable rules', () => {
beforeEach(async () => {
createComponent({
mountFn: mountExtended,
containerProtectionTagRuleQueryResolver: jest
.fn()
.mockResolvedValue(containerProtectionImmutableTagRuleQueryPayload),
});
await waitForPromises();
});
it('contains immutable container protection tag rules and `immutable` badge', () => {
tagRules.forEach((protectionRule, i) => {
expect(findTableRowCell(i, 0).findByTestId('tag-name-pattern').text()).toBe(
protectionRule.tagNamePattern,
);
expect(findTableRowCell(i, 0).findByTestId('tag-rule-type-badge').text()).toBe(
'immutable',
);
expect(findTableRowCell(i, 1).text()).toBe('');
expect(findTableRowCell(i, 2).text()).toBe('');
});
});
describe('column "rowActions"', () => {
it('does not show Edit button', () => {
expect(findTableRowButtonEdit(0).exists()).toBe(false);
});
describe('Delete button', () => {
it('exists in table', () => {
expect(findTableRowButtonDelete(0).exists()).toBe(true);
});
describe('when button is clicked', () => {
beforeEach(async () => {
await findTableRowButtonDelete(0).trigger('click');
});
it('renders the "delete container protection rule" confirmation modal', () => {
const modalId = getBinding(findTableRowButtonDelete(0).element, 'gl-modal');
expect(findModal().props('modal-id')).toBe(modalId);
expect(findModal().props('title')).toBe('Delete protection rule');
expect(findModal().text()).toBe(
'Are you sure you want to delete the protected container tags rule v.+?',
);
});
});
describe('when user does not have permission', () => {
beforeEach(async () => {
createComponent({
mountFn: mountExtended,
containerProtectionTagRuleQueryResolver: jest
.fn()
.mockResolvedValue(containerProtectionImmutableTagRuleMaintainerQueryPayload),
});
await waitForPromises();
});
it('does not exist in table', () => {
expect(findTableRowButtonDelete(0).exists()).toBe(false);
});
});
});
});
});
describe('when feature flag `containerRegistryImmutableTags` is disabled', () => {
describe('table rows', () => {
beforeEach(async () => {
createComponent({
mountFn: mountExtended,
provide: {
...defaultProvidedValues,
glFeatures: {
containerRegistryImmutableTags: false,
},
},
});
await waitForPromises();
});
it('contains container protection tag rules', () => {
tagRules.forEach((protectionRule, i) => {
expect(findTableRowCell(i, 0).text()).toBe(protectionRule.tagNamePattern);
expect(findTableRowCell(i, 1).text()).toBe(
MinimumAccessLevelText[protectionRule.minimumAccessLevelForPush],
);
expect(findTableRowCell(i, 2).text()).toBe(
MinimumAccessLevelText[protectionRule.minimumAccessLevelForDelete],
);
});
});
});
});
describe('modal "confirmation for delete action"', () => {
const createComponentAndClickButtonDeleteInTableRow = async ({
tableRowIndex = 0,
@ -637,25 +526,4 @@ describe('ContainerProtectionTagRules', () => {
expect(findAlert().text()).toBe('error');
});
});
describe('when feature flag `containerRegistryImmutableTags` is disabled', () => {
describe('layout', () => {
beforeEach(() => {
createComponent({
provide: {
...defaultProvidedValues,
glFeatures: {
containerRegistryImmutableTags: false,
},
},
});
});
it('renders card component with different description', () => {
expect(findCrudComponent().props('description')).toBe(
'When a container image tag is protected, only certain user roles can create, update, and delete the protected tag, which helps to prevent unauthorized changes. You can add up to 5 protection rules per project.',
);
});
});
});
});

View File

@ -5,7 +5,7 @@ import SettingsBlock from '~/vue_shared/components/settings/settings_block.vue';
import ContainerRegistrySection from '~/packages_and_registries/settings/project/components/container_registry_section.vue';
import ContainerExpirationPolicy from '~/packages_and_registries/settings/project/components/container_expiration_policy.vue';
import ContainerProtectionRepositoryRules from '~/packages_and_registries/settings/project/components/container_protection_repository_rules.vue';
import ContainerProtectionTagRules from '~/packages_and_registries/settings/project/components/container_protection_tag_rules.vue';
import ContainerProtectionTagRules from 'ee_else_ce/packages_and_registries/settings/project/components/container_protection_tag_rules.vue';
describe('Container registry project settings section', () => {
let wrapper;

View File

@ -44,7 +44,7 @@ GEM
google-protobuf (3.25.7)
googleapis-common-protos-types (1.20.0)
google-protobuf (>= 3.18, < 5.a)
grpc (1.71.0)
grpc (1.72.0)
google-protobuf (>= 3.25, < 5.0)
googleapis-common-protos-types (~> 1.0)
i18n (1.14.7)
@ -63,7 +63,7 @@ GEM
rouge
unparser
racc (1.8.1)
rack (3.1.13)
rack (3.1.14)
rainbow (3.1.1)
regexp_parser (2.10.0)
rouge (4.5.2)
@ -76,7 +76,7 @@ GEM
rspec-expectations (3.13.4)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.13.0)
rspec-mocks (3.13.3)
rspec-mocks (3.13.4)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.13.0)
rspec-parameterized (1.0.2)

View File

@ -1 +1 @@
81624de3633fa2fab3737bc438683966649e5568
20a0104c6e8d836906e15a68f35667856f2ceb68

View File

@ -4,5 +4,4 @@ require_relative "topology_service/version"
require "proto/claim_service_services_pb"
require "proto/classify_service_services_pb"
require "proto/health_service_services_pb"
require "proto/cell_service_services_pb"

View File

@ -1,30 +0,0 @@
# Generated by the protocol buffer compiler. DO NOT EDIT!
# source: proto/health_service.proto
require 'google/protobuf'
require 'google/api/annotations_pb'
Google::Protobuf::DescriptorPool.generated_pool.build do
add_file("proto/health_service.proto", :syntax => :proto3) do
add_message "gitlab.cells.topology_service.ReadinessProbeRequest" do
end
add_message "gitlab.cells.topology_service.ReadinessProbeResponse" do
end
add_message "gitlab.cells.topology_service.LivenessProbeRequest" do
end
add_message "gitlab.cells.topology_service.LivenessProbeResponse" do
end
end
end
module Gitlab
module Cells
module TopologyService
ReadinessProbeRequest = ::Google::Protobuf::DescriptorPool.generated_pool.lookup("gitlab.cells.topology_service.ReadinessProbeRequest").msgclass
ReadinessProbeResponse = ::Google::Protobuf::DescriptorPool.generated_pool.lookup("gitlab.cells.topology_service.ReadinessProbeResponse").msgclass
LivenessProbeRequest = ::Google::Protobuf::DescriptorPool.generated_pool.lookup("gitlab.cells.topology_service.LivenessProbeRequest").msgclass
LivenessProbeResponse = ::Google::Protobuf::DescriptorPool.generated_pool.lookup("gitlab.cells.topology_service.LivenessProbeResponse").msgclass
end
end
end

View File

@ -1,30 +0,0 @@
# Generated by the protocol buffer compiler. DO NOT EDIT!
# Source: proto/health_service.proto for package 'Gitlab.Cells.TopologyService'
require 'grpc'
require 'proto/health_service_pb'
module Gitlab
module Cells
module TopologyService
module HealthService
# Public read-only service
class Service
include ::GRPC::GenericService
self.marshal_class_method = :encode
self.unmarshal_class_method = :decode
self.service_name = 'gitlab.cells.topology_service.HealthService'
# (Lightweight) Used for checking if application is ready to accept requests
rpc :ReadinessProbe, ::Gitlab::Cells::TopologyService::ReadinessProbeRequest, ::Gitlab::Cells::TopologyService::ReadinessProbeResponse
# (Lightweight) Used for checking if application is alive, or whether it should be restarted
rpc :LivenessProbe, ::Gitlab::Cells::TopologyService::LivenessProbeRequest, ::Gitlab::Cells::TopologyService::LivenessProbeResponse
end
Stub = Service.rpc_stub_class
end
end
end
end