Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2022-11-02 12:10:53 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2022-11-02 12:10:53 +0300
commit44837830832a41a6fe6360aca18e50826c723fd1 (patch)
tree47f83bfb5f90a4e598facb0b6688743f3a4173fe
parent03c509e17bfa71a124a69b6cf4897414d3bd1cb5 (diff)
Add latest changes from gitlab-org/gitlab@master
-rw-r--r--app/assets/javascripts/vue_merge_request_widget/components/extensions/container.js1
-rw-r--r--app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue3
-rw-r--r--config/open_api.yml15
-rw-r--r--doc/ci/review_apps/index.md68
-rw-r--r--doc/development/documentation/styleguide/word_list.md4
-rw-r--r--doc/development/testing_guide/review_apps.md68
-rw-r--r--doc/user/analytics/ci_cd_analytics.md18
-rw-r--r--doc/user/analytics/dora_metrics.md105
-rw-r--r--doc/user/analytics/index.md89
-rw-r--r--lib/api/api.rb9
-rw-r--r--lib/api/entities/personal_access_token.rb13
-rw-r--r--lib/api/entities/resource_access_token.rb7
-rw-r--r--lib/api/resource_access_tokens.rb33
-rw-r--r--lib/api/suggestions.rb6
-rw-r--r--qa/qa/specs/features/api/1_manage/import/import_github_repo_spec.rb369
-rw-r--r--qa/qa/specs/features/browser_ui/1_manage/project/import_github_repo_spec.rb132
-rw-r--r--qa/qa/specs/features/shared_contexts/github_import_shared_context.rb43
-rw-r--r--qa/qa/specs/spec_helper.rb6
-rw-r--r--spec/requests/api/suggestions_spec.rb15
19 files changed, 544 insertions, 460 deletions
diff --git a/app/assets/javascripts/vue_merge_request_widget/components/extensions/container.js b/app/assets/javascripts/vue_merge_request_widget/components/extensions/container.js
index a58d524b9ed..9887bda973c 100644
--- a/app/assets/javascripts/vue_merge_request_widget/components/extensions/container.js
+++ b/app/assets/javascripts/vue_merge_request_widget/components/extensions/container.js
@@ -17,6 +17,7 @@ export default {
'section',
{
attrs: {
+ class: 'mr-section-container mr-widget-workflow',
role: 'region',
'aria-label': __('Merge request reports'),
},
diff --git a/app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue b/app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue
index a3f70b551bf..62ad22c637b 100644
--- a/app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue
+++ b/app/assets/javascripts/vue_merge_request_widget/mr_widget_options.vue
@@ -563,6 +563,7 @@ export default {
:mr="mr"
:service="service"
/>
+ <extensions-container :mr="mr" />
<div class="mr-section-container mr-widget-workflow">
<div v-if="hasAlerts" class="gl-overflow-hidden mr-widget-alert-container">
<mr-widget-alert-message
@@ -589,8 +590,6 @@ export default {
</mr-widget-alert-message>
</div>
- <extensions-container :mr="mr" />
-
<widget-container v-if="mr" :mr="mr" />
<grouped-codequality-reports-app
diff --git a/config/open_api.yml b/config/open_api.yml
index f45691ea9f5..331a90a8710 100644
--- a/config/open_api.yml
+++ b/config/open_api.yml
@@ -14,12 +14,11 @@ metadata:
name: private_token
in: query
tags:
- - name: metadata
- description: Operations related to metadata of the GitLab instance
+ # Keep in alphabetical order
- name: access_requests
description: Operations related to access requests
- - name: merge_requests
- description: Operations related to merge requests
+ - name: cluster_agents
+ description: Operations related to the GitLab agent for Kubernetes
- name: deploy_keys
description: Operations related to deploy keys
- name: deploy_tokens
@@ -34,7 +33,11 @@ metadata:
description: Operations related to managing Flipper-based feature flags
- name: freeze_periods
description: Operations related to deploy freeze periods
+ - name: merge_requests
+ description: Operations related to merge requests
+ - name: metadata
+ description: Operations related to metadata of the GitLab instance
- name: release_links
description: Operations related to release assets (links)
- - name: cluster_agents
- description: Operations related to the GitLab agent for Kubernetes
+ - name: suggestions
+ description: Operations related to suggestions \ No newline at end of file
diff --git a/doc/ci/review_apps/index.md b/doc/ci/review_apps/index.md
index 2f23ebbfd9f..1650525d15b 100644
--- a/doc/ci/review_apps/index.md
+++ b/doc/ci/review_apps/index.md
@@ -4,96 +4,96 @@ group: Pipeline Insights
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://about.gitlab.com/handbook/product/ux/technical-writing/#assignments
---
-# Review Apps **(FREE)**
+# Review apps **(FREE)**
-Review Apps is a collaboration tool that assists with providing an environment to showcase product changes.
+Review apps are a collaboration tool that provide an environment to showcase product changes.
NOTE:
If you have a Kubernetes cluster, you can automate this feature in your applications
by using [Auto DevOps](../../topics/autodevops/index.md).
-Review Apps:
+Review apps:
- Provide an automatic live preview of changes made in a feature branch by spinning up a dynamic environment for your merge requests.
- Allow designers and product managers to see your changes without needing to check out your branch and run your changes in a sandbox environment.
- Are fully integrated with the [GitLab DevOps LifeCycle](../../index.md#the-entire-devops-lifecycle).
- Allow you to deploy your changes wherever you want.
-![Review Apps Workflow](img/continuous-delivery-review-apps.svg)
+![review apps workflow](img/continuous-delivery-review-apps.svg)
In the previous example:
-- A Review App is built every time a commit is pushed to `topic branch`.
+- A review app is built every time a commit is pushed to `topic branch`.
- The reviewer fails two reviews before passing the third review.
- After the review passes, `topic branch` is merged into the default branch, where it's deployed to staging.
- After its approval in staging, the changes that were merged into the default branch are deployed to production.
-## How Review Apps work
+## How review apps work
-A Review App is a mapping of a branch with an [environment](../environments/index.md).
-Access to the Review App is made available as a link on the [merge request](../../user/project/merge_requests/index.md) relevant to the branch.
+A review app is a mapping of a branch with an [environment](../environments/index.md).
+Access to the review app is made available as a link on the [merge request](../../user/project/merge_requests/index.md) relevant to the branch.
The following is an example of a merge request with an environment set dynamically.
-![Review App in merge request](img/review_apps_preview_in_mr.png)
+![review app in merge request](img/review_apps_preview_in_mr.png)
In this example, a branch was:
- Successfully built.
- Deployed under a dynamic environment that can be reached by selecting **View app**.
-After adding Review Apps to your workflow, you follow the branched Git flow. That is:
+After adding review apps to your workflow, you follow the branched Git flow. That is:
-1. Push a branch and let the runner deploy the Review App based on the `script` definition of the dynamic environment job.
+1. Push a branch and let the runner deploy the review app based on the `script` definition of the dynamic environment job.
1. Wait for the runner to build and deploy your web application.
1. To view the changes live, select the link in the merge request related to the branch.
-## Configuring Review Apps
+## Configuring review apps
-Review Apps are built on [dynamic environments](../environments/index.md#create-a-dynamic-environment), which allow you to dynamically create a new environment for each branch.
+Review apps are built on [dynamic environments](../environments/index.md#create-a-dynamic-environment), which allow you to dynamically create a new environment for each branch.
-The process of configuring Review Apps is as follows:
+The process of configuring review apps is as follows:
-1. Set up the infrastructure to host and deploy the Review Apps (check the [examples](#review-apps-examples) below).
+1. Set up the infrastructure to host and deploy the review apps (check the [examples](#review-apps-examples) below).
1. [Install](https://docs.gitlab.com/runner/install/) and [configure](https://docs.gitlab.com/runner/commands/) a runner to do deployment.
1. Set up a job in `.gitlab-ci.yml` that uses the [predefined CI/CD variable](../variables/index.md) `${CI_COMMIT_REF_SLUG}`
to create dynamic environments and restrict it to run only on branches.
- Alternatively, you can get a YAML template for this job by [enabling review apps](#enable-review-apps-button) for your project.
-1. Optionally, set a job that [manually stops](../environments/index.md#stop-an-environment) the Review Apps.
+ Alternatively, you can get a YAML template for this job by [enabling review apps](#enable-review-app-button) for your project.
+1. Optionally, set a job that [manually stops](../environments/index.md#stop-an-environment) the review apps.
-### Enable Review Apps button
+### Enable review app button
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/118844) in GitLab 12.8.
-When configuring Review Apps for a project, you add a new job to the `.gitlab-ci.yml` file,
+When configuring review apps for a project, you add a new job to the `.gitlab-ci.yml` file,
as mentioned above. To facilitate this, and if you are using Kubernetes, you can select
-**Enable Review Apps** and GitLab prompts you with a template code block that
+**Enable review app** and GitLab prompts you with a template code block that
you can copy and paste into `.gitlab-ci.yml` as a starting point.
Prerequisite:
- You need at least the Developer role for the project.
-To use the Review Apps template:
+To use the review apps template:
-1. On the top bar, select **Main menu > Projects** and find the project you want to create a Review App job for.
+1. On the top bar, select **Main menu > Projects** and find the project you want to create a review app job for.
1. On the left sidebar, select **Deployments > Environments**.
-1. Select **Enable Review Apps**.
+1. Select **Enable review app**.
1. Copy the provided code snippet and paste it into your
`.gitlab-ci.yml` file:
- ![Enable Review Apps modal](img/enable_review_app_v12_8.png)
+ ![enable review apps modal](img/enable_review_app_v12_8.png)
You can edit this template as needed.
-## Review Apps auto-stop
+## Review apps auto-stop
-See how to [configure Review Apps environments to expire and auto-stop](../environments/index.md#stop-an-environment-after-a-certain-time-period)
+See how to [configure review apps environments to expire and auto-stop](../environments/index.md#stop-an-environment-after-a-certain-time-period)
after a given period of time.
-## Review Apps examples
+## Review apps examples
-The following are example projects that demonstrate Review App configuration:
+The following are example projects that demonstrate review app configuration:
| Project | Configuration file |
|-------------------------------------------------------------------------|--------------------|
@@ -104,17 +104,17 @@ The following are example projects that demonstrate Review App configuration:
| [`https://about.gitlab.com/`](https://gitlab.com/gitlab-com/www-gitlab-com/) | [`.gitlab-ci.yml`](https://gitlab.com/gitlab-com/www-gitlab-com/-/blob/6ffcdc3cb9af2abed490cbe5b7417df3e83cd76c/.gitlab-ci.yml#L332) |
| [GitLab Insights](https://gitlab.com/gitlab-org/gitlab-insights/) | [`.gitlab-ci.yml`](https://gitlab.com/gitlab-org/gitlab-insights/-/blob/9e63f44ac2a5a4defc965d0d61d411a768e20546/.gitlab-ci.yml#L234) |
-Other examples of Review Apps:
+Other examples of review apps:
- <i class="fa fa-youtube-play youtube" aria-hidden="true"></i>
[Cloud Native Development with GitLab](https://www.youtube.com/watch?v=jfIyQEwrocw).
-- [Review Apps for Android](https://about.gitlab.com/blog/2020/05/06/how-to-create-review-apps-for-android-with-gitlab-fastlane-and-appetize-dot-io/).
+- [Review apps for Android](https://about.gitlab.com/blog/2020/05/06/how-to-create-review-apps-for-android-with-gitlab-fastlane-and-appetize-dot-io/).
## Route Maps
Route Maps allows you to go directly from source files
to public pages on the [environment](../environments/index.md) defined for
-Review Apps.
+review apps.
Once set up, the review app link in the merge request
widget can take you directly to the pages changed, making it easier
@@ -209,7 +209,7 @@ With Visual Reviews, members of any team (Product, Design, Quality, and so on) c
### Using Visual Reviews
After Visual Reviews has been [configured](#configure-review-apps-for-visual-reviews) for the
-Review App, the Visual Reviews feedback form is overlaid on the right side of every page.
+review app, the Visual Reviews feedback form is overlaid on the right side of every page.
![Visual review feedback form](img/toolbar_feedback_form_v13_5.png)
@@ -227,9 +227,9 @@ To use the feedback form to make a comment in the merge request:
<i class="fa fa-youtube-play youtube" aria-hidden="true"></i>
To see Visual reviews in action, see the [Visual Reviews Walk through](https://youtu.be/1_tvWTlPfM4).
-### Configure Review Apps for Visual Reviews
+### Configure review apps for Visual Reviews
-The feedback form is served through a script you add to pages in your Review App.
+The feedback form is served through a script you add to pages in your review app.
It should be added to the `<head>` of your application and
consists of some project and merge request specific values. Here's how it
looks for a project with code hosted in a project on GitLab.com:
diff --git a/doc/development/documentation/styleguide/word_list.md b/doc/development/documentation/styleguide/word_list.md
index 21981d858f3..3e32f0b020a 100644
--- a/doc/development/documentation/styleguide/word_list.md
+++ b/doc/development/documentation/styleguide/word_list.md
@@ -936,6 +936,10 @@ Instead of:
- Select **Create user** or **Save changes** if you created a new user or
edited an existing one respectively.
+## review app
+
+Use lowercase for **review app**.
+
## roles
Do not use **roles** and [**permissions**](#permissions) interchangeably. Each user is assigned a role. Each role includes a set of permissions.
diff --git a/doc/development/testing_guide/review_apps.md b/doc/development/testing_guide/review_apps.md
index d3e8642cfa0..5edf18725c0 100644
--- a/doc/development/testing_guide/review_apps.md
+++ b/doc/development/testing_guide/review_apps.md
@@ -4,9 +4,9 @@ group: unassigned
info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://about.gitlab.com/handbook/product/ux/technical-writing/#assignments
---
-# Review Apps
+# Using review apps in the development of GitLab
-Review Apps are deployed using the `start-review-app-pipeline` job which triggers a child pipeline containing a series of jobs to perform the various tasks needed to deploy a Review App.
+Review apps are deployed using the `start-review-app-pipeline` job which triggers a child pipeline containing a series of jobs to perform the various tasks needed to deploy a review app.
![start-review-app-pipeline job](img/review-app-parent-pipeline.png)
@@ -21,7 +21,7 @@ For any of the following scenarios, the `start-review-app-pipeline` job would be
- for scheduled pipelines
- the MR has the `pipeline:run-review-app` label set
-## QA runs on Review Apps
+## QA runs on review apps
On every [pipeline](https://gitlab.com/gitlab-org/gitlab/pipelines/125315730) in the `qa` stage (which comes after the
`review` stage), the `review-qa-smoke` and `review-qa-reliable` jobs are automatically started. The `review-qa-smoke` runs
@@ -34,7 +34,7 @@ You can also manually start the `review-qa-all`: it runs the full QA suite.
After the end-to-end test runs have finished, [Allure reports](https://github.com/allure-framework/allure2) are generated and published by
the `allure-report-qa-smoke`, `allure-report-qa-reliable`, and `allure-report-qa-all` jobs. A comment with links to the reports are added to the merge request.
-Errors can be found in the `gitlab-review-apps` Sentry project and [filterable by Review App URL](https://sentry.gitlab.net/gitlab/gitlab-review-apps/?query=url%3A%22https%3A%2F%2Fgitlab-review-require-ve-u92nn2.gitlab-review.app%2F%22) or [commit SHA](https://sentry.gitlab.net/gitlab/gitlab-review-apps/releases/6095b501da7/all-events/).
+Errors can be found in the `gitlab-review-apps` Sentry project and [filterable by review app URL](https://sentry.gitlab.net/gitlab/gitlab-review-apps/?query=url%3A%22https%3A%2F%2Fgitlab-review-require-ve-u92nn2.gitlab-review.app%2F%22) or [commit SHA](https://sentry.gitlab.net/gitlab/gitlab-review-apps/releases/6095b501da7/all-events/).
### Bypass failed review app deployment to merge a broken `master` fix
@@ -47,7 +47,7 @@ On every [pipeline](https://gitlab.com/gitlab-org/gitlab/pipelines/125315730) in
browser performance testing using a
[Sitespeed.io Container](../../ci/testing/browser_performance_testing.md).
-## Sample Data for Review Apps
+## Sample Data for review apps
Upon deployment of a review app, project data is created from the [`sample-gitlab-project`](https://gitlab.com/gitlab-org/sample-data-templates/sample-gitlab-project) template project. This aims to provide projects with prepopulated resources to facilitate manual and exploratory testing.
@@ -55,16 +55,16 @@ The sample projects will be created in the `root` user namespace and can be acce
## How to
-### Redeploy Review App from a clean slate
+### Redeploy review app from a clean slate
-To reset Review App and redeploy from a clean slate, do the following:
+To reset review app and redeploy from a clean slate, do the following:
1. Run `review-stop` job.
1. Re-deploy by running or retrying `review-deploy` job.
-Doing this will remove all existing data from a previously deployed Review App.
+Doing this will remove all existing data from a previously deployed review app.
-### Get access to the GCP Review Apps cluster
+### Get access to the GCP review apps cluster
You need to [open an access request (internal link)](https://gitlab.com/gitlab-com/access-requests/-/issues/new)
for the `gcp-review-apps-dev` GCP group and role.
@@ -74,7 +74,7 @@ This grants you the following permissions for:
- [Retrieving pod logs](#dig-into-a-pods-logs). Granted by [Viewer (`roles/viewer`)](https://cloud.google.com/iam/docs/understanding-roles#kubernetes-engine-roles).
- [Running a Rails console](#run-a-rails-console). Granted by [Kubernetes Engine Developer (`roles/container.pods.exec`)](https://cloud.google.com/iam/docs/understanding-roles#kubernetes-engine-roles).
-### Log into my Review App
+### Log into my review app
For GitLab Team Members only. If you want to sign in to the review app, review
the GitLab handbook information for the [shared 1Password account](https://about.gitlab.com/handbook/security/#1password-for-teams).
@@ -82,23 +82,23 @@ the GitLab handbook information for the [shared 1Password account](https://about
- The default username is `root`.
- The password can be found in the 1Password login item named `GitLab EE Review App`.
-### Enable a feature flag for my Review App
+### Enable a feature flag for my review app
-1. Open your Review App and sign in as documented above.
+1. Open your review app and sign in as documented above.
1. Create a personal access token.
1. Enable the feature flag using the [Feature flag API](../../api/features.md).
-### Find my Review App slug
+### Find my review app slug
1. Open the `review-deploy` job.
1. Look for `** Deploying review-*`.
1. For instance for `** Deploying review-1234-abc-defg... **`,
- your Review App slug would be `review-1234-abc-defg` in this case.
+ your review app slug would be `review-1234-abc-defg` in this case.
### Run a Rails console
1. Make sure you [have access to the cluster](#get-access-to-the-gcp-review-apps-cluster) and the `container.pods.exec` permission first.
-1. [Filter Workloads by your Review App slug](https://console.cloud.google.com/kubernetes/workload?project=gitlab-review-apps). For example, `review-qa-raise-e-12chm0`.
+1. [Filter Workloads by your review app slug](https://console.cloud.google.com/kubernetes/workload?project=gitlab-review-apps). For example, `review-qa-raise-e-12chm0`.
1. Find and open the `toolbox` Deployment. For example, `review-qa-raise-e-12chm0-toolbox`.
1. Select the Pod in the "Managed pods" section. For example, `review-qa-raise-e-12chm0-toolbox-d5455cc8-2lsvz`.
1. Select the `KUBECTL` dropdown list, then `Exec` -> `toolbox`.
@@ -111,7 +111,7 @@ the GitLab handbook information for the [shared 1Password account](https://about
### Dig into a Pod's logs
1. Make sure you [have access to the cluster](#get-access-to-the-gcp-review-apps-cluster) and the `container.pods.getLogs` permission first.
-1. [Filter Workloads by your Review App slug](https://console.cloud.google.com/kubernetes/workload?project=gitlab-review-apps). For example, `review-qa-raise-e-12chm0`.
+1. [Filter Workloads by your review app slug](https://console.cloud.google.com/kubernetes/workload?project=gitlab-review-apps). For example, `review-qa-raise-e-12chm0`.
1. Find and open the `migrations` Deployment. For example, `review-qa-raise-e-12chm0-migrations.1`.
1. Select the Pod in the "Managed pods" section. For example, `review-qa-raise-e-12chm0-migrations.1-nqwtx`.
1. Select `Container logs`.
@@ -149,11 +149,11 @@ subgraph "2. gitlab `review-prepare` stage"
end
subgraph "3. gitlab `review` stage"
- C["review-deploy<br><br>Helm deploys the Review App using the Cloud<br/>Native images built by the CNG-mirror pipeline.<br><br>Cloud Native images are deployed to the `review-apps`<br>Kubernetes (GKE) cluster, in the GCP `gitlab-review-apps` project."]
+ C["review-deploy<br><br>Helm deploys the review app using the Cloud<br/>Native images built by the CNG-mirror pipeline.<br><br>Cloud Native images are deployed to the `review-apps`<br>Kubernetes (GKE) cluster, in the GCP `gitlab-review-apps` project."]
end
subgraph "4. gitlab `qa` stage"
- E[review-qa-smoke, review-qa-reliable<br><br>gitlab-qa runs the smoke and reliable suites against the Review App.]
+ E[review-qa-smoke, review-qa-reliable<br><br>gitlab-qa runs the smoke and reliable suites against the review app.]
end
subgraph "CNG-mirror pipeline"
@@ -180,10 +180,10 @@ subgraph "CNG-mirror pipeline"
- We use the [`CNG-mirror`](https://gitlab.com/gitlab-org/build/CNG-mirror) project so that the `CNG`, (Cloud
Native GitLab), project's registry is not overloaded with a lot of transient Docker images.
1. Once `review-build-cng` is done, the [`review-deploy`](https://gitlab.com/gitlab-org/gitlab/-/jobs/467724810) job
- deploys the Review App using [the official GitLab Helm chart](https://gitlab.com/gitlab-org/charts/gitlab/) to
+ deploys the review app using [the official GitLab Helm chart](https://gitlab.com/gitlab-org/charts/gitlab/) to
the [`review-apps`](https://console.cloud.google.com/kubernetes/clusters/details/us-central1-b/review-apps?project=gitlab-review-apps)
Kubernetes cluster on GCP.
- - The actual scripts used to deploy the Review App can be found at
+ - The actual scripts used to deploy the review app can be found at
[`scripts/review_apps/review-apps.sh`](https://gitlab.com/gitlab-org/gitlab/-/blob/master/scripts/review_apps/review-apps.sh).
- These scripts are basically
[our official Auto DevOps scripts](https://gitlab.com/gitlab-org/gitlab/-/blob/master/lib/gitlab/ci/templates/Auto-DevOps.gitlab-ci.yml) where the
@@ -192,11 +192,11 @@ subgraph "CNG-mirror pipeline"
- Since we're using [the official GitLab Helm chart](https://gitlab.com/gitlab-org/charts/gitlab/), this means
you get a dedicated environment for your branch that's very close to what
it would look in production.
- - Each review app is deployed to its own Kubernetes namespace. The namespace is based on the Review App slug that is
+ - Each review app is deployed to its own Kubernetes namespace. The namespace is based on the review app slug that is
unique to each branch.
1. Once the [`review-deploy`](https://gitlab.com/gitlab-org/gitlab/-/jobs/467724810) job succeeds, you should be able to
- use your Review App thanks to the direct link to it from the MR widget. To log
- into the Review App, see "Log into my Review App?" below.
+ use your review app thanks to the direct link to it from the MR widget. To log
+ into the review app, see "Log into my review app?" below.
**Additional notes:**
@@ -213,23 +213,23 @@ subgraph "CNG-mirror pipeline"
`#quality` channel and/or create a ~Quality ~"type::bug" issue with a link to your
merge request.
- The manual `review-stop` can be used to
- stop a Review App manually, and is also started by GitLab once a merge
+ stop a review app manually, and is also started by GitLab once a merge
request's branch is deleted after being merged.
- The Kubernetes cluster is connected to the `gitlab` projects using the
[GitLab Kubernetes integration](../../user/infrastructure/clusters/index.md). This basically
- allows to have a link to the Review App directly from the merge request widget.
+ allows to have a link to the review app directly from the merge request widget.
-### Auto-stopping of Review Apps
+### Auto-stopping of review apps
-Review Apps are automatically stopped 2 days after the last deployment thanks to
+Review apps are automatically stopped 2 days after the last deployment thanks to
the [Environment auto-stop](../../ci/environments/index.md#stop-an-environment-after-a-certain-time-period) feature.
-If you need your Review App to stay up for a longer time, you can
+If you need your review app to stay up for a longer time, you can
[pin its environment](../../ci/environments/index.md#override-a-deployments-scheduled-stop-time) or retry the
`review-deploy` job to update the "latest deployed at" time.
The `review-cleanup` job that automatically runs in scheduled
-pipelines stops stale Review Apps after 5 days,
+pipelines stops stale review apps after 5 days,
deletes their environment after 6 days, and cleans up any dangling Helm releases
and Kubernetes resources after 7 days.
@@ -246,13 +246,13 @@ The Helm version used is defined in the
[`registry.gitlab.com/gitlab-org/gitlab-build-images:gitlab-helm3.5-kubectl1.17` image](https://gitlab.com/gitlab-org/gitlab-build-images/-/blob/master/Dockerfile.gitlab-helm3.5-kubectl1.17#L6)
used by the `review-deploy` and `review-stop` jobs.
-## Diagnosing unhealthy Review App releases
+## Diagnosing unhealthy review app releases
-If [Review App Stability](https://app.periscopedata.com/app/gitlab/496118/Engineering-Productivity-Sandbox?widget=6690556&udv=785399)
+If [review app stability](https://app.periscopedata.com/app/gitlab/496118/Engineering-Productivity-Sandbox?widget=6690556&udv=785399)
dips this may be a signal that the `review-apps` cluster is unhealthy.
-Leading indicators may be health check failures leading to restarts or majority failure for Review App deployments.
+Leading indicators may be health check failures leading to restarts or majority failure for review app deployments.
-The [Review Apps Overview dashboard](https://console.cloud.google.com/monitoring/classic/dashboards/6798952013815386466?project=gitlab-review-apps&timeDomain=1d)
+The [review apps Overview dashboard](https://console.cloud.google.com/monitoring/classic/dashboards/6798952013815386466?project=gitlab-review-apps&timeDomain=1d)
aids in identifying load spikes on the cluster, and if nodes are problematic or the entire cluster is trending towards unhealthy.
See the [review apps page of the Engineering Productivity Runbook](https://gitlab.com/gitlab-org/quality/engineering-productivity/team/-/blob/main/runbook/review-apps.md) for troubleshooting review app releases.
@@ -273,7 +273,7 @@ find a way to limit it to only us.**
## Other resources
-- [Review Apps integration for CE/EE (presentation)](https://docs.google.com/presentation/d/1QPLr6FO4LduROU8pQIPkX1yfGvD13GEJIBOenqoKxR8/edit?usp=sharing)
+- [Review apps integration for CE/EE (presentation)](https://docs.google.com/presentation/d/1QPLr6FO4LduROU8pQIPkX1yfGvD13GEJIBOenqoKxR8/edit?usp=sharing)
- [Stability issues](https://gitlab.com/gitlab-org/quality/team-tasks/-/issues/212)
### Helpful command line tools
diff --git a/doc/user/analytics/ci_cd_analytics.md b/doc/user/analytics/ci_cd_analytics.md
index de9275b8599..ef2d3a76990 100644
--- a/doc/user/analytics/ci_cd_analytics.md
+++ b/doc/user/analytics/ci_cd_analytics.md
@@ -6,7 +6,7 @@ info: To determine the technical writer assigned to the Stage/Group associated w
# CI/CD analytics **(FREE)**
-Use the CI/CD analytics page to view pipeline success rates and duration, and the history of [DORA metrics](index.md#devops-research-and-assessment-dora-key-metrics) over time.
+Use the CI/CD analytics page to view pipeline success rates and duration, and the history of DORA metrics over time.
## Pipeline success and duration charts
@@ -35,7 +35,7 @@ To view CI/CD analytics:
1. On the top bar, select **Main menu > Projects** and find your project.
1. On the left sidebar, select **Analytics > CI/CD Analytics**.
-## View deployment frequency chart **(ULTIMATE)**
+## View DORA deployment frequency chart **(ULTIMATE)**
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/275991) in GitLab 13.8.
@@ -44,7 +44,7 @@ frequency to the `production` environment. The environment must be part of the
[production deployment tier](../../ci/environments/index.md#deployment-tier-of-environments)
for its deployment information to appear on the graphs.
- Deployment frequency is one of the four [DORA metrics](index.md#devops-research-and-assessment-dora-key-metrics) that DevOps teams use for measuring excellence in software delivery.
+ Deployment frequency is one of the four DORA metrics that DevOps teams use for measuring excellence in software delivery.
The deployment frequency chart is available for groups and projects.
@@ -56,7 +56,7 @@ To view the deployment frequency chart:
![Deployment frequency](img/deployment_frequency_charts_v13_12.png)
-## View lead time for changes chart **(ULTIMATE)**
+## View DORA lead time for changes chart **(ULTIMATE)**
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/250329) in GitLab 13.11.
@@ -68,7 +68,7 @@ merge requests to be deployed to a production environment. This chart is availab
- For time periods in which no merge requests were deployed, the charts render a
red, dashed line.
- Lead time for changes is one of the four [DORA metrics](index.md#devops-research-and-assessment-dora-key-metrics) that DevOps teams use for measuring excellence in software delivery.
+ Lead time for changes is one of the four DORA metrics that DevOps teams use for measuring excellence in software delivery.
To view the lead time for changes chart:
@@ -78,13 +78,13 @@ To view the lead time for changes chart:
![Lead time](img/lead_time_chart_v13_11.png)
-## View time to restore service chart **(ULTIMATE)**
+## View DORA time to restore service chart **(ULTIMATE)**
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/356959) in GitLab 15.1
The time to restore service chart shows information about the median time an incident was open in a production environment. This chart is available for groups and projects.
-Time to restore service is one of the four [DORA metrics](index.md#devops-research-and-assessment-dora-key-metrics) that DevOps teams use for measuring excellence in software delivery.
+Time to restore service is one of the four DORA metrics that DevOps teams use for measuring excellence in software delivery.
To view the time to restore service chart:
@@ -94,13 +94,13 @@ To view the time to restore service chart:
![Lead time](img/time_to_restore_service_charts_v15_1.png)
-## View change failure rate chart **(ULTIMATE)**
+## View DORA change failure rate chart **(ULTIMATE)**
> [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/357072) in GitLab 15.2
The change failure rate chart shows information about the percentage of deployments that cause an incident in a production environment. This chart is available for groups and projects.
-Change failure rate is one of the four [DORA metrics](index.md#devops-research-and-assessment-dora-key-metrics) that DevOps teams use for measuring excellence in software delivery.
+Change failure rate is one of the four DORA metrics that DevOps teams use for measuring excellence in software delivery.
To view the change failure rate chart:
diff --git a/doc/user/analytics/dora_metrics.md b/doc/user/analytics/dora_metrics.md
new file mode 100644
index 00000000000..605985cd779
--- /dev/null
+++ b/doc/user/analytics/dora_metrics.md
@@ -0,0 +1,105 @@
+---
+stage: Plan
+group: Optimize
+info: To determine the technical writer assigned to the Stage/Group associated with this page, see https://about.gitlab.com/handbook/product/ux/technical-writing/#assignments
+---
+
+# DevOps Research and Assessment (DORA) metrics **(ULTIMATE)**
+
+> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/275991) in GitLab 13.7.
+> - [Added support](https://gitlab.com/gitlab-org/gitlab/-/issues/291746) for lead time for changes in GitLab 13.10.
+
+The [DevOps Research and Assessment (DORA)](https://cloud.google.com/blog/products/devops-sre/using-the-four-keys-to-measure-your-devops-performance)
+team has identified four metrics that measure DevOps performance.
+Using these metrics helps improve DevOps efficiency and communicate performance to business stakeholders, which can accelerate business results.
+
+DORA includes four key metrics, divided into two core areas of DevOps:
+
+- [Deployment Frequency](#deployment-frequency) and [Lead Time for Change](#lead-time-for-changes) measure team velocity.
+- [Change Failure Rate](#change-failure-rate) and [Time to Restore Service](#time-to-restore-service) measure stability.
+
+For software leaders, tracking velocity alongside quality metrics ensures they're not sacrificing quality for speed.
+
+## DORA Metrics dashboard in Value Stream Analytics
+
+The four DORA metrics are available out-of-the-box in the [Value Stream Analytics (VSA) overview dashboard](../group/value_stream_analytics/index.md#view-dora-metrics-and-key-metrics-for-a-group).
+This helps you visualize the engineering work in the context of end-to-end value delivery.
+
+The One DevOps Platform [Value Stream Management](https://gitlab.com/gitlab-org/gitlab/-/value_stream_analytics) provides end-to-end visibility to the entire software delivery lifecycle.
+This enables teams and managers to understand all aspects of productivity, quality, and delivery, without the ["toolchain tax"](https://about.gitlab.com/solutions/value-stream-management/).
+
+## Deployment frequency
+
+Deployment frequency is the frequency of successful deployments to production (hourly, daily, weekly, monthly, or yearly).
+This measures how often you deliver value to end users. A higher deployment frequency means you can
+get feedback sooner and iterate faster to deliver improvements and features. GitLab measures this as the number of
+deployments to a production environment in the given time period.
+
+Deployment frequency displays in several charts:
+
+- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
+- [Project-level value stream analytics](value_stream_analytics.md)
+- [CI/CD analytics](ci_cd_analytics.md)
+
+To retrieve metrics for deployment frequency, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
+
+## Lead time for changes
+
+Lead time for changes measures the time to deliver a feature once it has been developed,
+as described in [Measuring DevOps Performance](https://devops.com/measuring-devops-performance/).
+
+Lead time for changes displays in several charts:
+
+- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
+- [Project-level value stream analytics](value_stream_analytics.md)
+- [CI/CD analytics](ci_cd_analytics.md)
+
+To retrieve metrics for lead time for changes, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
+
+## Time to restore service
+
+Time to restore service measures how long it takes an organization to recover from a failure in production.
+GitLab measures this as the average time required to close the incidents
+in the given time period. This assumes:
+
+- All incidents are related to a production environment.
+- Incidents and deployments have a strictly one-to-one relationship. An incident is related to only
+one production deployment, and any production deployment is related to no more than one incident).
+
+Time to restore service displays in several charts:
+
+- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
+- [Project-level value stream analytics](value_stream_analytics.md)
+- [CI/CD analytics](ci_cd_analytics.md)
+
+To retrieve metrics for time to restore service, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
+
+## Change failure rate
+
+Change failure rate measures the percentage of deployments that cause a failure in production. GitLab measures this as the number
+of incidents divided by the number of deployments to a
+production environment in the given time period. This assumes:
+
+- All incidents are related to a production environment.
+- Incidents and deployments have a strictly one-to-one relationship. An incident is related to only
+one production deployment, and any production deployment is related to no
+more than one incident.
+
+To retrieve metrics for change failure rate, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
+
+### Insights: Custom DORA reporting
+
+Custom charts to visualize DORA data with Insights YAML-based reports.
+
+With this new visualization, software leaders can track metrics improvements, understand patterns in their metrics trends, and compare performance between groups and projects.
+
+### Supported DORA metrics in GitLab
+
+| Metric | Level | API | UI chart | Comments |
+|---------------------------|-------------------|-----------------------------------------------------|------------------------|----------|
+| `deployment_frequency` | Project | [GitLab 13.7 and later](../../api/dora/metrics.md) | GitLab 14.8 and later | The previous API endpoint was [deprecated](https://gitlab.com/gitlab-org/gitlab/-/issues/323713) in 13.10. |
+| `deployment_frequency` | Group | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 13.12 and later | |
+| `lead_time_for_changes` | Project | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 13.11 and later | Unit in seconds. Aggregation method is median. |
+| `lead_time_for_changes` | Group | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 14.0 and later | Unit in seconds. Aggregation method is median. |
+| `time_to_restore_service` | Project and group | [GitLab 14.9 and later](../../api/dora/metrics.md) | GitLab 15.1 and later | Unit in days. Aggregation method is median. |
+| `change_failure_rate` | Project and group | [GitLab 14.10 and later](../../api/dora/metrics.md) | GitLab 15.2 and later | Percentage of deployments. |
diff --git a/doc/user/analytics/index.md b/doc/user/analytics/index.md
index 56adbff9f59..01fe466755c 100644
--- a/doc/user/analytics/index.md
+++ b/doc/user/analytics/index.md
@@ -34,7 +34,7 @@ GitLab provides several analytics features at the group level. Some of these fea
You can use GitLab to review analytics at the project level. Some of these features require you to use a higher tier than GitLab Free.
- [Application Security](../application_security/security_dashboard/index.md)
-- [CI/CD](ci_cd_analytics.md)
+- [CI/CD & DORA](ci_cd_analytics.md)
- [Code Review](code_review_analytics.md)
- [Insights](../project/insights/index.md)
- [Issue](../group/issues_analytics/index.md)
@@ -51,93 +51,6 @@ The following analytics features are available for users to create personalized
Be sure to review the documentation page for this feature for GitLab tier requirements.
-## DevOps Research and Assessment (DORA) key metrics **(ULTIMATE)**
-
-> - [Introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/275991) in GitLab 13.7.
-> - [Added support](https://gitlab.com/gitlab-org/gitlab/-/issues/291746) for lead time for changes in GitLab 13.10.
-
-The [DevOps Research and Assessment (DORA)](https://cloud.google.com/blog/products/devops-sre/using-the-four-keys-to-measure-your-devops-performance)
-team developed several key metrics that you can use as performance indicators for software development
-teams.
-
-### Deployment frequency
-
-Deployment frequency is the frequency of successful deployments to production (hourly, daily, weekly, monthly, or yearly).
-This measures how often you deliver value to end users. A higher deployment frequency means you can
-get feedback sooner and iterate faster to deliver improvements and features. GitLab measures this as the number of
-deployments to a production environment in the given time period.
-
-Deployment frequency displays in several charts:
-
-- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
-- [Project-level value stream analytics](value_stream_analytics.md)
-- [CI/CD analytics](ci_cd_analytics.md)
-
-To retrieve metrics for deployment frequency, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
-
-### Lead time for changes
-
-DORA Lead time for changes measures the time to successfully deliver a feature into production.
-This metric reflects the efficiency of CI/CD pipelines.
-
-In GitLab, Lead time for changes calculates the median time it takes for a merge request to get merged into production.
-We measure "FROM code committed TO code successfully running in production" without adding the "coding_time" to the calculation.
-
-Over time, the lead time for changes should decrease, while your team's performance should increase.
-
-Lead time for changes displays in several charts:
-
-- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
-- [Project-level value stream analytics](value_stream_analytics.md)
-- [CI/CD analytics](ci_cd_analytics.md)
-
-To retrieve metrics for lead time for changes, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
-
-- The definition of lead time for change can vary widely, which often creates confusion within the industry.
-- "Lead time for changes" is not the same as "Lead time". In the value stream, "Lead time" measures the time it takes for work on issue to move from the moment it's requested (Issue created) to the time it's fulfilled and delivered (Issue closed).
-
-### Time to restore service
-
-Time to restore service measures how long it takes an organization to recover from a failure in production.
-GitLab measures this as the average time required to close the incidents
-in the given time period. This assumes:
-
-- All incidents are related to a production environment.
-- Incidents and deployments have a strictly one-to-one relationship. An incident is related to only
-one production deployment, and any production deployment is related to no more than one incident).
-
-Time to restore service displays in several charts:
-
-- [Group-level value stream analytics](../group/value_stream_analytics/index.md)
-- [Project-level value stream analytics](value_stream_analytics.md)
-- [CI/CD analytics](ci_cd_analytics.md)
-
-To retrieve metrics for time to restore service, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
-
-### Change failure rate
-
-Change failure rate measures the percentage of deployments that cause a failure in production. GitLab measures this as the number
-of incidents divided by the number of deployments to a
-production environment in the given time period. This assumes:
-
-- All incidents are related to a production environment.
-- Incidents and deployments have a strictly one-to-one relationship. An incident is related to only
-one production deployment, and any production deployment is related to no
-more than one incident.
-
-To retrieve metrics for change failure rate, use the [GraphQL](../../api/graphql/reference/index.md) or the [REST](../../api/dora/metrics.md) APIs.
-
-### Supported DORA metrics in GitLab
-
-| Metric | Level | API | UI chart | Comments |
-|---------------------------|-------------------|-----------------------------------------------------|------------------------|----------|
-| `deployment_frequency` | Project | [GitLab 13.7 and later](../../api/dora/metrics.md) | GitLab 14.8 and later | The previous API endpoint was [deprecated](https://gitlab.com/gitlab-org/gitlab/-/issues/323713) in 13.10. |
-| `deployment_frequency` | Group | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 13.12 and later | |
-| `lead_time_for_changes` | Project | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 13.11 and later | Unit in seconds. Aggregation method is median. |
-| `lead_time_for_changes` | Group | [GitLab 13.10 and later](../../api/dora/metrics.md) | GitLab 14.0 and later | Unit in seconds. Aggregation method is median. |
-| `time_to_restore_service` | Project and group | [GitLab 14.9 and later](../../api/dora/metrics.md) | GitLab 15.1 and later | Unit in days. Aggregation method is median. |
-| `change_failure_rate` | Project and group | [GitLab 14.10 and later](../../api/dora/metrics.md) | GitLab 15.2 and later | Percentage of deployments. |
-
## Definitions
We use the following terms to describe GitLab analytics:
diff --git a/lib/api/api.rb b/lib/api/api.rb
index 08269c81743..6f63d8998be 100644
--- a/lib/api/api.rb
+++ b/lib/api/api.rb
@@ -169,6 +169,7 @@ module API
# Mount endpoints to include in the OpenAPI V2 documentation here
namespace do
+ # Keep in alphabetical order
mount ::API::AccessRequests
mount ::API::Appearance
mount ::API::BulkImports
@@ -182,14 +183,16 @@ module API
mount ::API::FeatureFlagsUserLists
mount ::API::Features
mount ::API::FreezePeriods
- mount ::API::Metadata
mount ::API::MergeRequestDiffs
- mount ::API::UserCounts
+ mount ::API::Metadata
mount ::API::ProjectRepositoryStorageMoves
mount ::API::Release::Links
+ mount ::API::ResourceAccessTokens
mount ::API::SnippetRepositoryStorageMoves
mount ::API::Statistics
+ mount ::API::Suggestions
mount ::API::Tags
+ mount ::API::UserCounts
add_open_api_documentation!
end
@@ -299,7 +302,6 @@ module API
mount ::API::Releases
mount ::API::RemoteMirrors
mount ::API::Repositories
- mount ::API::ResourceAccessTokens
mount ::API::ResourceLabelEvents
mount ::API::ResourceMilestoneEvents
mount ::API::ResourceStateEvents
@@ -311,7 +313,6 @@ module API
mount ::API::Snippets
mount ::API::Submodules
mount ::API::Subscriptions
- mount ::API::Suggestions
mount ::API::SystemHooks
mount ::API::Tags
mount ::API::Templates
diff --git a/lib/api/entities/personal_access_token.rb b/lib/api/entities/personal_access_token.rb
index 55764daef9d..305412d3dcc 100644
--- a/lib/api/entities/personal_access_token.rb
+++ b/lib/api/entities/personal_access_token.rb
@@ -3,9 +3,16 @@
module API
module Entities
class PersonalAccessToken < Grape::Entity
- expose :id, :name, :revoked, :created_at, :scopes, :user_id, :last_used_at
- expose :active?, as: :active
- expose :expires_at do |personal_access_token|
+ expose :id, documentation: { type: 'string', example: 2 }
+ expose :name, documentation: { type: 'string', example: 'John Doe' }
+ expose :revoked, documentation: { type: 'boolean' }
+ expose :created_at, documentation: { type: 'dateTime' }
+ expose :scopes, documentation: { type: 'array', example: ['api'] }
+ expose :user_id, documentation: { type: 'string', example: 3 }
+ expose :last_used_at, documentation: { type: 'dateTime', example: '2020-08-31T15:53:00.073Z' }
+ expose :active?, as: :active, documentation: { type: 'boolean' }
+ expose :expires_at, documentation:
+ { type: 'dateTime', example: '2020-08-31T15:53:00.073Z' } do |personal_access_token|
personal_access_token.expires_at ? personal_access_token.expires_at.strftime("%Y-%m-%d") : nil
end
end
diff --git a/lib/api/entities/resource_access_token.rb b/lib/api/entities/resource_access_token.rb
index 569fd16f488..e4f140d3fc0 100644
--- a/lib/api/entities/resource_access_token.rb
+++ b/lib/api/entities/resource_access_token.rb
@@ -3,7 +3,12 @@
module API
module Entities
class ResourceAccessToken < Entities::PersonalAccessToken
- expose :access_level do |token, options|
+ expose :access_level,
+ documentation: { type: 'integer',
+ example: 40,
+ description: 'Access level. Valid values are 10 (Guest), 20 (Reporter), 30 (Developer) \
+ , 40 (Maintainer), and 50 (Owner). Defaults to 40.',
+ values: [10, 20, 30, 40, 50] } do |token, options|
options[:resource].member(token.user).access_level
end
end
diff --git a/lib/api/resource_access_tokens.rb b/lib/api/resource_access_tokens.rb
index 1735e63c566..754dfadb5fc 100644
--- a/lib/api/resource_access_tokens.rb
+++ b/lib/api/resource_access_tokens.rb
@@ -14,9 +14,12 @@ module API
resource source_type.pluralize, requirements: API::NAMESPACE_OR_PROJECT_REQUIREMENTS do
desc 'Get list of all access tokens for the specified resource' do
detail 'This feature was introduced in GitLab 13.9.'
+ is_array true
+ tags ["#{source_type}_access_tokens"]
+ success Entities::ResourceAccessToken
end
params do
- requires :id, type: String, desc: "The #{source_type} ID"
+ requires :id, types: [String, Integer], desc: "ID or URL-encoded path of the #{source_type}"
end
get ":id/access_tokens" do
resource = find_source(source_type, params[:id])
@@ -31,9 +34,11 @@ module API
desc 'Get an access token for the specified resource by ID' do
detail 'This feature was introduced in GitLab 14.10.'
+ tags ["#{source_type}_access_tokens"]
+ success Entities::ResourceAccessToken
end
params do
- requires :id, type: String, desc: "The #{source_type} ID"
+ requires :id, types: [String, Integer], desc: "ID or URL-encoded path of the #{source_type}"
requires :token_id, type: String, desc: "The ID of the token"
end
get ":id/access_tokens/:token_id" do
@@ -53,6 +58,12 @@ module API
desc 'Revoke a resource access token' do
detail 'This feature was introduced in GitLab 13.9.'
+ tags ["#{source_type}_access_tokens"]
+ success code: 204
+ failure [
+ { code: 400, message: 'Bad Request' },
+ { code: 404, message: 'Not found' }
+ ]
end
params do
requires :id, type: String, desc: "The #{source_type} ID"
@@ -77,13 +88,21 @@ module API
desc 'Create a resource access token' do
detail 'This feature was introduced in GitLab 13.9.'
+ tags ["#{source_type}_access_tokens"]
+ success Entities::ResourceAccessTokenWithToken
end
params do
- requires :id, type: String, desc: "The #{source_type} ID"
- requires :name, type: String, desc: "Resource access token name"
- requires :scopes, type: Array[String], values: ::Gitlab::Auth.resource_bot_scopes.map(&:to_s), desc: "The permissions of the token"
- optional :access_level, type: Integer, values: ALLOWED_RESOURCE_ACCESS_LEVELS.values, default: Gitlab::Access::MAINTAINER, desc: "The access level of the token in the #{source_type}"
- optional :expires_at, type: Date, desc: "The expiration date of the token"
+ requires :id, type: String, desc: "The #{source_type} ID", documentation: { example: 2 }
+ requires :name, type: String, desc: "Resource access token name", documentation: { example: 'test' }
+ requires :scopes, type: Array[String], values: ::Gitlab::Auth.resource_bot_scopes.map(&:to_s),
+ desc: "The permissions of the token",
+ documentation: { example: %w[api read_repository] }
+ optional :access_level, type: Integer,
+ values: ALLOWED_RESOURCE_ACCESS_LEVELS.values,
+ default: Gitlab::Access::MAINTAINER,
+ desc: "The access level of the token in the #{source_type}",
+ documentation: { example: 40 }
+ optional :expires_at, type: Date, desc: "The expiration date of the token", documentation: { example: '"2021-01-31' }
end
post ':id/access_tokens' do
resource = find_source(source_type, params[:id])
diff --git a/lib/api/suggestions.rb b/lib/api/suggestions.rb
index 0697169b49a..6260983087f 100644
--- a/lib/api/suggestions.rb
+++ b/lib/api/suggestions.rb
@@ -9,9 +9,10 @@ module API
resource :suggestions do
desc 'Apply suggestion patch in the Merge Request it was created' do
success Entities::Suggestion
+ tags %w[suggestions]
end
params do
- requires :id, type: String, desc: 'The suggestion ID'
+ requires :id, type: Integer, desc: 'The ID of the suggestion'
optional :commit_message, type: String, desc: "A custom commit message to use instead of the default generated message or the project's default message"
end
put ':id/apply', urgency: :low do
@@ -26,9 +27,10 @@ module API
desc 'Apply multiple suggestion patches in the Merge Request where they were created' do
success Entities::Suggestion
+ tags %w[suggestions]
end
params do
- requires :ids, type: Array[Integer], coerce_with: ::API::Validations::Types::CommaSeparatedToIntegerArray.coerce, desc: "An array of suggestion ID's"
+ requires :ids, type: Array[Integer], coerce_with: ::API::Validations::Types::CommaSeparatedToIntegerArray.coerce, desc: "An array of the suggestion IDs"
optional :commit_message, type: String, desc: "A custom commit message to use instead of the default generated message or the project's default message"
end
put 'batch_apply', urgency: :low do
diff --git a/qa/qa/specs/features/api/1_manage/import/import_github_repo_spec.rb b/qa/qa/specs/features/api/1_manage/import/import_github_repo_spec.rb
index 1abd75a7439..c59a4f468df 100644
--- a/qa/qa/specs/features/api/1_manage/import/import_github_repo_spec.rb
+++ b/qa/qa/specs/features/api/1_manage/import/import_github_repo_spec.rb
@@ -1,227 +1,194 @@
# frozen_string_literal: true
module QA
- # Spec uses real github.com, which means outage of github.com can actually block deployment
- # Keep spec in reliable bucket but don't run in blocking pipelines
- #
# https://github.com/gitlab-qa-github/import-test <- project under test
- RSpec.describe 'Manage', :github, :reliable, :skip_live_env, :requires_admin, product_group: :import do
- describe 'Project import', issue: 'https://gitlab.com/gitlab-org/gitlab/-/issues/353583' do
- let!(:api_client) { Runtime::API::Client.as_admin }
- let!(:group) { Resource::Group.fabricate_via_api! { |resource| resource.api_client = api_client } }
- let!(:user) do
- Resource::User.fabricate_via_api! do |resource|
- resource.api_client = api_client
- resource.hard_delete_on_api_removal = true
+ #
+ RSpec.describe 'Manage', product_group: :import do
+ describe 'GitHub import', :reliable do
+ include_context 'with github import'
+
+ context 'when imported via api' do
+ it 'imports project', testcase: 'https://gitlab.com/gitlab-org/gitlab/-/quality/test_cases/347670' do
+ imported_project.reload! # import the project
+
+ expect { imported_project.project_import_status[:import_status] }.to eventually_eq('finished')
+ .within(max_duration: 240, sleep_interval: 1)
+
+ aggregate_failures do
+ verify_status_data
+ verify_repository_import
+ verify_protected_branches_import
+ verify_commits_import
+ verify_labels_import
+ verify_issues_import
+ verify_milestones_import
+ verify_wikis_import
+ verify_merge_requests_import
+ verify_release_import
+ end
end
- end
- let!(:user_api_client) { Runtime::API::Client.new(user: user) }
-
- let(:imported_project) do
- Resource::ProjectImportedFromGithub.fabricate_via_api! do |project|
- project.name = 'imported-project'
- project.group = group
- project.github_personal_access_token = Runtime::Env.github_access_token
- project.github_repository_path = 'gitlab-qa-github/import-test'
- project.api_client = user_api_client
- project.issue_events_import = true
- project.full_notes_import = true
+ def verify_status_data
+ stats = imported_project.project_import_status.dig(:stats, :imported)
+ expect(stats).to include(
+ issue: 1,
+ label: 9,
+ milestone: 1,
+ note: 3,
+ pull_request: 1,
+ pull_request_review: 1,
+ diff_note: 1,
+ release: 1
+ )
end
- end
-
- before do
- group.add_member(user, Resource::Members::AccessLevel::MAINTAINER)
- end
-
- after do
- user.remove_via_api!
- end
- it 'imports Github repo via api', testcase: 'https://gitlab.com/gitlab-org/gitlab/-/quality/test_cases/347670' do
- imported_project.reload! # import the project
-
- expect { imported_project.project_import_status[:import_status] }.to eventually_eq('finished')
- .within(max_duration: 240, sleep_interval: 1)
-
- aggregate_failures do
- verify_status_data
- verify_repository_import
- verify_protected_branches_import
- verify_commits_import
- verify_labels_import
- verify_issues_import
- verify_milestones_import
- verify_wikis_import
- verify_merge_requests_import
- verify_release_import
+ def verify_repository_import
+ expect(imported_project.reload!.description).to eq('Project for github import test')
+ expect(imported_project.api_response[:import_error]).to be_nil
end
- end
- def verify_status_data
- stats = imported_project.project_import_status.dig(:stats, :imported)
- expect(stats).to include(
- issue: 1,
- label: 9,
- milestone: 1,
- note: 3,
- pull_request: 1,
- pull_request_review: 1,
- diff_note: 1,
- release: 1
- )
- end
+ def verify_protected_branches_import
+ branches = imported_project.protected_branches.map do |branch|
+ branch.slice(:name, :allow_force_push, :code_owner_approval_required)
+ end
+ expect(branches.first).to include(
+ {
+ name: 'main'
+ # TODO: Add validation once https://gitlab.com/groups/gitlab-org/-/epics/8585 is closed
+ # At the moment both options are always set to false regardless of state in github
+ # allow_force_push: true,
+ # code_owner_approval_required: true
+ }
+ )
+ end
- def verify_repository_import
- expect(imported_project.reload!.description).to eq('Project for github import test')
- expect(imported_project.api_response[:import_error]).to be_nil
- end
+ def verify_commits_import
+ expect(imported_project.commits.length).to eq(2)
+ end
- def verify_protected_branches_import
- branches = imported_project.protected_branches.map do |branch|
- branch.slice(:name, :allow_force_push, :code_owner_approval_required)
+ def verify_labels_import
+ labels = imported_project.labels.map { |label| label.slice(:name, :color) }
+
+ expect(labels).to include(
+ { name: 'bug', color: '#d73a4a' },
+ { name: 'documentation', color: '#0075ca' },
+ { name: 'duplicate', color: '#cfd3d7' },
+ { name: 'enhancement', color: '#a2eeef' },
+ { name: 'good first issue', color: '#7057ff' },
+ { name: 'help wanted', color: '#008672' },
+ { name: 'invalid', color: '#e4e669' },
+ { name: 'question', color: '#d876e3' },
+ { name: 'wontfix', color: '#ffffff' }
+ )
end
- expect(branches.first).to include(
- {
- name: 'main'
- # TODO: Add validation once https://gitlab.com/groups/gitlab-org/-/epics/8585 is closed
- # At the moment both options are always set to false regardless of state in github
- # allow_force_push: true,
- # code_owner_approval_required: true
- }
- )
-
- # GitHub branch protection rule "Require signed commits" is mapped to the
- # "Reject unsigned commits" push rule
- expect(imported_project.push_rules[:reject_unsigned_commits]).to be_truthy
- end
- def verify_commits_import
- expect(imported_project.commits.length).to eq(2)
- end
+ def verify_milestones_import
+ milestones = imported_project.milestones
- def verify_labels_import
- labels = imported_project.labels.map { |label| label.slice(:name, :color) }
-
- expect(labels).to include(
- { name: 'bug', color: '#d73a4a' },
- { name: 'documentation', color: '#0075ca' },
- { name: 'duplicate', color: '#cfd3d7' },
- { name: 'enhancement', color: '#a2eeef' },
- { name: 'good first issue', color: '#7057ff' },
- { name: 'help wanted', color: '#008672' },
- { name: 'invalid', color: '#e4e669' },
- { name: 'question', color: '#d876e3' },
- { name: 'wontfix', color: '#ffffff' }
- )
- end
+ expect(milestones.length).to eq(1)
+ expect(milestones.first).to include(title: '0.0.1', description: nil, state: 'active')
+ end
- def verify_milestones_import
- milestones = imported_project.milestones
+ def verify_wikis_import
+ wikis = imported_project.wikis
- expect(milestones.length).to eq(1)
- expect(milestones.first).to include(title: '0.0.1', description: nil, state: 'active')
- end
+ expect(wikis.length).to eq(1)
+ expect(wikis.first).to include(title: 'Home', format: 'markdown')
+ end
- def verify_wikis_import
- wikis = imported_project.wikis
+ def verify_issues_import
+ issues = imported_project.issues
+ issue = Resource::Issue.init do |resource|
+ resource.project = imported_project
+ resource.iid = issues.first[:iid]
+ resource.api_client = user_api_client
+ end.reload!
+ comments, events = fetch_events_and_comments(issue)
+
+ expect(issues.length).to eq(1)
+ expect(issue.api_resource).to include(
+ title: 'Test issue',
+ description: "*Created by: gitlab-qa-github*\n\nTest issue description",
+ labels: ['good first issue', 'help wanted', 'question']
+ )
+ expect(comments).to match_array(
+ [
+ "*Created by: gitlab-qa-github*\n\nSome test comment",
+ "*Created by: gitlab-qa-github*\n\nAnother test comment"
+ ]
+ )
+ expect(events).to match_array(
+ [
+ { name: "add_label", label: "question" },
+ { name: "add_label", label: "good first issue" },
+ { name: "add_label", label: "help wanted" },
+ { name: "add_milestone", label: "0.0.1" },
+ { name: "closed" },
+ { name: "reopened" }
+ ]
+ )
+ end
- expect(wikis.length).to eq(1)
- expect(wikis.first).to include(title: 'Home', format: 'markdown')
- end
+ def verify_merge_requests_import
+ merge_requests = imported_project.merge_requests
+ merge_request = Resource::MergeRequest.init do |mr|
+ mr.project = imported_project
+ mr.iid = merge_requests.first[:iid]
+ mr.api_client = user_api_client
+ end.reload!
+ comments, events = fetch_events_and_comments(merge_request)
+
+ expect(merge_requests.length).to eq(1)
+ expect(merge_request.api_resource).to include(
+ title: 'Test pull request',
+ state: 'opened',
+ target_branch: 'main',
+ source_branch: 'gitlab-qa-github-patch-1',
+ labels: %w[documentation],
+ description: "*Created by: gitlab-qa-github*\n\nTest pull request body"
+ )
+ expect(comments).to match_array(
+ [
+ "*Created by: gitlab-qa-github*\n\n**Review:** Commented\n\nGood but needs some improvement",
+ "*Created by: gitlab-qa-github*\n\n```suggestion:-0+0\nProject for GitHub import test to GitLab\r\n```",
+ "*Created by: gitlab-qa-github*\n\nSome test PR comment"
+ ]
+ )
+ expect(events).to match_array(
+ [
+ { name: "add_label", label: "documentation" },
+ { name: "add_milestone", label: "0.0.1" }
+ ]
+ )
+ end
- def verify_issues_import
- issues = imported_project.issues
- issue = Resource::Issue.init do |resource|
- resource.project = imported_project
- resource.iid = issues.first[:iid]
- resource.api_client = user_api_client
- end.reload!
- comments, events = fetch_events_and_comments(issue)
-
- expect(issues.length).to eq(1)
- expect(issue.api_resource).to include(
- title: 'Test issue',
- description: "*Created by: gitlab-qa-github*\n\nTest issue description",
- labels: ['good first issue', 'help wanted', 'question']
- )
- expect(comments).to match_array(
- [
- "*Created by: gitlab-qa-github*\n\nSome test comment",
- "*Created by: gitlab-qa-github*\n\nAnother test comment"
- ]
- )
- expect(events).to match_array(
- [
- { name: "add_label", label: "question" },
- { name: "add_label", label: "good first issue" },
- { name: "add_label", label: "help wanted" },
- { name: "add_milestone", label: "0.0.1" },
- { name: "closed" },
- { name: "reopened" }
- ]
- )
- end
+ def verify_release_import
+ releases = imported_project.releases
+
+ expect(releases.length).to eq(1)
+ expect(releases.first).to include(
+ tag_name: "0.0.1",
+ name: "0.0.1",
+ description: "Initial release",
+ created_at: "2022-03-07T07:59:22.000Z",
+ released_at: "2022-03-07T08:02:09.000Z"
+ )
+ end
- def verify_merge_requests_import
- merge_requests = imported_project.merge_requests
- merge_request = Resource::MergeRequest.init do |mr|
- mr.project = imported_project
- mr.iid = merge_requests.first[:iid]
- mr.api_client = user_api_client
- end.reload!
- comments, events = fetch_events_and_comments(merge_request)
-
- expect(merge_requests.length).to eq(1)
- expect(merge_request.api_resource).to include(
- title: 'Test pull request',
- state: 'opened',
- target_branch: 'main',
- source_branch: 'gitlab-qa-github-patch-1',
- labels: %w[documentation],
- description: "*Created by: gitlab-qa-github*\n\nTest pull request body"
- )
- expect(comments).to match_array(
- [
- "*Created by: gitlab-qa-github*\n\n**Review:** Commented\n\nGood but needs some improvement",
- "*Created by: gitlab-qa-github*\n\n```suggestion:-0+0\nProject for GitHub import test to GitLab\r\n```",
- "*Created by: gitlab-qa-github*\n\nSome test PR comment"
+ # Fetch events and comments from issue or mr
+ #
+ # @param [QA::Resource::Issuable] issuable
+ # @return [Array]
+ def fetch_events_and_comments(issuable)
+ comments = issuable.comments.map { |comment| comment[:body] }
+ events = [
+ *issuable.label_events.map { |e| { name: "#{e[:action]}_label", label: e.dig(:label, :name) } },
+ *issuable.state_events.map { |e| { name: e[:state] } },
+ *issuable.milestone_events.map { |e| { name: "#{e[:action]}_milestone", label: e.dig(:milestone, :title) } }
]
- )
- expect(events).to match_array(
- [
- { name: "add_label", label: "documentation" },
- { name: "add_milestone", label: "0.0.1" }
- ]
- )
- end
- def verify_release_import
- releases = imported_project.releases
-
- expect(releases.length).to eq(1)
- expect(releases.first).to include(
- tag_name: "0.0.1",
- name: "0.0.1",
- description: "Initial release",
- created_at: "2022-03-07T07:59:22.000Z",
- released_at: "2022-03-07T08:02:09.000Z"
- )
- end
-
- # Fetch events and comments from issue or mr
- #
- # @param [QA::Resource::Issuable] issuable
- # @return [Array]
- def fetch_events_and_comments(issuable)
- comments = issuable.comments.map { |comment| comment[:body] }
- events = [
- *issuable.label_events.map { |e| { name: "#{e[:action]}_label", label: e.dig(:label, :name) } },
- *issuable.state_events.map { |e| { name: e[:state] } },
- *issuable.milestone_events.map { |e| { name: "#{e[:action]}_milestone", label: e.dig(:milestone, :title) } }
- ]
-
- [comments, events]
+ [comments, events]
+ end
end
end
end
diff --git a/qa/qa/specs/features/browser_ui/1_manage/project/import_github_repo_spec.rb b/qa/qa/specs/features/browser_ui/1_manage/project/import_github_repo_spec.rb
index 4f0f54c1a15..15563e3aa2a 100644
--- a/qa/qa/specs/features/browser_ui/1_manage/project/import_github_repo_spec.rb
+++ b/qa/qa/specs/features/browser_ui/1_manage/project/import_github_repo_spec.rb
@@ -4,88 +4,90 @@ module QA
# Spec uses real github.com, which means outage of github can actually block deployment
# Keep spec in reliable bucket but don't run in blocking pipelines
RSpec.describe 'Manage', :github, :reliable, :skip_live_env, :requires_admin, product_group: :import do
- describe 'Project import' do
- let(:github_repo) { 'gitlab-qa-github/import-test' }
- let(:api_client) { Runtime::API::Client.as_admin }
- let(:group) { Resource::Group.fabricate_via_api! { |resource| resource.api_client = api_client } }
- let(:user) do
- Resource::User.fabricate_via_api! do |resource|
- resource.api_client = api_client
- resource.hard_delete_on_api_removal = true
+ describe 'GitHub import' do
+ context 'when imported via UI' do
+ let(:github_repo) { 'gitlab-qa-github/import-test' }
+ let(:api_client) { Runtime::API::Client.as_admin }
+ let(:group) { Resource::Group.fabricate_via_api! { |resource| resource.api_client = api_client } }
+ let(:user) do
+ Resource::User.fabricate_via_api! do |resource|
+ resource.api_client = api_client
+ resource.hard_delete_on_api_removal = true
+ end
end
- end
- let(:imported_project) do
- Resource::ProjectImportedFromGithub.init do |project|
- project.import = true
- project.group = group
- project.github_personal_access_token = Runtime::Env.github_access_token
- project.github_repository_path = github_repo
- project.api_client = api_client
+ let(:imported_project) do
+ Resource::ProjectImportedFromGithub.init do |project|
+ project.import = true
+ project.group = group
+ project.github_personal_access_token = Runtime::Env.github_access_token
+ project.github_repository_path = github_repo
+ project.api_client = api_client
+ end
end
- end
- let(:imported_issue) do
- Resource::Issue.init do |resource|
- resource.project = imported_project
- resource.iid = imported_project.issues.first[:iid]
- resource.api_client = api_client
- end.reload!
- end
+ let(:imported_issue) do
+ Resource::Issue.init do |resource|
+ resource.project = imported_project
+ resource.iid = imported_project.issues.first[:iid]
+ resource.api_client = api_client
+ end.reload!
+ end
- let(:imported_issue_events) do
- imported_issue.label_events.map { |e| { name: "#{e[:action]}_label", label: e.dig(:label, :name) } }
- end
+ let(:imported_issue_events) do
+ imported_issue.label_events.map { |e| { name: "#{e[:action]}_label", label: e.dig(:label, :name) } }
+ end
- before do
- group.add_member(user, Resource::Members::AccessLevel::MAINTAINER)
+ before do
+ group.add_member(user, Resource::Members::AccessLevel::MAINTAINER)
- Flow::Login.sign_in(as: user)
- Page::Main::Menu.perform(&:go_to_create_project)
- Page::Project::New.perform do |project_page|
- project_page.click_import_project
- project_page.click_github_link
+ Flow::Login.sign_in(as: user)
+ Page::Main::Menu.perform(&:go_to_create_project)
+ Page::Project::New.perform do |project_page|
+ project_page.click_import_project
+ project_page.click_github_link
+ end
end
- end
- after do
- user.remove_via_api!
- end
+ after do
+ user.remove_via_api!
+ end
- it 'imports a GitHub repo', testcase: 'https://gitlab.com/gitlab-org/gitlab/-/quality/test_cases/347877' do
- Page::Project::Import::Github.perform do |import_page|
- import_page.add_personal_access_token(Runtime::Env.github_access_token)
+ it 'imports a project', testcase: 'https://gitlab.com/gitlab-org/gitlab/-/quality/test_cases/347877' do
+ Page::Project::Import::Github.perform do |import_page|
+ import_page.add_personal_access_token(Runtime::Env.github_access_token)
- import_page.select_advanced_option(:single_endpoint_issue_events_import)
- import_page.select_advanced_option(:single_endpoint_notes_import)
- import_page.select_advanced_option(:attachments_import)
+ import_page.select_advanced_option(:single_endpoint_issue_events_import)
+ import_page.select_advanced_option(:single_endpoint_notes_import)
+ import_page.select_advanced_option(:attachments_import)
- import_page.import!(github_repo, group.full_path, imported_project.name)
+ import_page.import!(github_repo, group.full_path, imported_project.name)
- aggregate_failures do
- expect(import_page).to have_imported_project(github_repo, wait: 240)
- # validate button is present instead of navigating to avoid dealing with multiple tabs
- # which makes the test more complicated
- expect(import_page).to have_go_to_project_button(github_repo)
+ aggregate_failures do
+ expect(import_page).to have_imported_project(github_repo, wait: 240)
+ # validate button is present instead of navigating to avoid dealing with multiple tabs
+ # which makes the test more complicated
+ expect(import_page).to have_go_to_project_button(github_repo)
+ end
end
- end
- imported_project.reload!.visit!
- Page::Project::Show.perform do |project|
- aggregate_failures do
- expect(project).to have_content(imported_project.name)
- expect(project).to have_content('Project for github import test')
+ imported_project.reload!.visit!
+ Page::Project::Show.perform do |project|
+ aggregate_failures do
+ expect(project).to have_content(imported_project.name)
+ expect(project).to have_content('Project for github import test')
+ end
end
- end
- # Validate :single_endpoint_issue_events_import option was triggered correctly and imported the events
- expect(imported_issue_events).to match_array(
- [
- { name: "add_label", label: "question" },
- { name: "add_label", label: "good first issue" },
- { name: "add_label", label: "help wanted" }
- ]
- )
+ # Validate :single_endpoint_issue_events_import option was triggered correctly and imported the events
+ expect(imported_issue_events).to match_array(
+ [
+ { name: "add_label", label: "question" },
+ { name: "add_label", label: "good first issue" },
+ { name: "add_label", label: "help wanted" }
+ ]
+ )
+ end
end
end
end
diff --git a/qa/qa/specs/features/shared_contexts/github_import_shared_context.rb b/qa/qa/specs/features/shared_contexts/github_import_shared_context.rb
new file mode 100644
index 00000000000..c32f5d8bf4b
--- /dev/null
+++ b/qa/qa/specs/features/shared_contexts/github_import_shared_context.rb
@@ -0,0 +1,43 @@
+# frozen_string_literal: true
+
+module QA
+ RSpec.shared_context "with github import", :github, :skip_live_env, :requires_admin do
+ let!(:api_client) { Runtime::API::Client.as_admin }
+
+ let!(:group) do
+ Resource::Group.fabricate_via_api! do |resource|
+ resource.api_client = api_client
+ resource.path = "destination-group-for-import-#{SecureRandom.hex(4)}"
+ end
+ end
+
+ let!(:user) do
+ Resource::User.fabricate_via_api! do |resource|
+ resource.api_client = api_client
+ resource.hard_delete_on_api_removal = true
+ end
+ end
+
+ let!(:user_api_client) { Runtime::API::Client.new(user: user) }
+
+ let(:imported_project) do
+ Resource::ProjectImportedFromGithub.fabricate_via_api! do |project|
+ project.name = 'imported-project'
+ project.group = group
+ project.github_personal_access_token = Runtime::Env.github_access_token
+ project.github_repository_path = 'gitlab-qa-github/import-test'
+ project.api_client = user_api_client
+ project.issue_events_import = true
+ project.full_notes_import = true
+ end
+ end
+
+ before do
+ group.add_member(user, Resource::Members::AccessLevel::MAINTAINER)
+ end
+
+ after do
+ user.remove_via_api!
+ end
+ end
+end
diff --git a/qa/qa/specs/spec_helper.rb b/qa/qa/specs/spec_helper.rb
index 97901042883..97ac7d41311 100644
--- a/qa/qa/specs/spec_helper.rb
+++ b/qa/qa/specs/spec_helper.rb
@@ -14,9 +14,6 @@ QA::Runtime::Scenario.from_env(QA::Runtime::Env.runtime_scenario_attributes)
# Enable zero monkey patching mode before loading any other RSpec code.
RSpec.configure(&:disable_monkey_patching!)
-Dir[::File.join(__dir__, "features/shared_examples/*.rb")].sort.each { |f| require f }
-Dir[::File.join(__dir__, "features/shared_contexts/*.rb")].sort.each { |f| require f }
-
# For JH additionally process when `jh/` exists
require_relative('../../../jh/qa/qa/specs/spec_helper') if GitlabEdition.jh?
@@ -149,3 +146,6 @@ RSpec.configure do |config|
end
end
end
+
+Dir[::File.join(__dir__, "features/shared_examples/*.rb")].sort.each { |f| require f }
+Dir[::File.join(__dir__, "features/shared_contexts/*.rb")].sort.each { |f| require f }
diff --git a/spec/requests/api/suggestions_spec.rb b/spec/requests/api/suggestions_spec.rb
index 2393a268693..dfc5d169af6 100644
--- a/spec/requests/api/suggestions_spec.rb
+++ b/spec/requests/api/suggestions_spec.rb
@@ -91,7 +91,7 @@ RSpec.describe API::Suggestions do
end
context 'when suggestion is not found' do
- let(:url) { "/suggestions/foo-123/apply" }
+ let(:url) { "/suggestions/9999/apply" }
it 'renders a not found error and returns json content' do
project.add_maintainer(user)
@@ -103,6 +103,19 @@ RSpec.describe API::Suggestions do
end
end
+ context 'when suggestion ID is not valid' do
+ let(:url) { "/suggestions/foo-123/apply" }
+
+ it 'renders a not found error and returns json content' do
+ project.add_maintainer(user)
+
+ put api(url, user)
+
+ expect(response).to have_gitlab_http_status(:bad_request)
+ expect(json_response).to eq({ 'error' => 'id is invalid' })
+ end
+ end
+
context 'when unauthorized' do
it 'renders a forbidden error and returns json content' do
project.add_reporter(user)