Back to Gitlabhq

Experiments API

doc/api/experiments.md

19.3.08.9 KB
Original Source

{{< details >}}

  • Tier: Free, Premium, Ultimate
  • Offering: GitLab.com

{{< /details >}}

Use this API to interact with A/B experiments. This API is for internal use only. It cannot be used with anonymous or unauthenticated users. For experiments involving anonymous users, use the glex_force query parameter instead.

Prerequisites:

List all experiments

{{< history >}}

{{< /history >}}

Lists all experiments on the GitLab instance. Each experiment has an enabled status that indicates whether the experiment is enabled globally, or only in specific contexts.

Each experiment also exposes a context array with the context keys the experiment declares: user, namespace, project, or actor. Pass these keys when you force, read, or clear a variant assignment. For an actor key, pass the context[user] parameter, because GitLab resolves the actor from the user. The array is empty for experiments that declare no context keys.

plaintext
GET /experiments
shell
curl --request GET \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments"

Example response:

json
[
  {
    "key": "code_quality_walkthrough",
    "context": ["user"],
    "definition": {
      "name": "code_quality_walkthrough",
      "introduced_by_url": "https://gitlab.com/gitlab-org/gitlab/-/merge_requests/58900",
      "rollout_issue_url": "https://gitlab.com/gitlab-org/gitlab/-/issues/327229",
      "milestone": "13.12",
      "type": "experiment",
      "group": "group::activation",
      "default_enabled": false
    },
    "current_status": {
      "state": "conditional",
      "gates": [
        {
          "key": "boolean",
          "value": false
        },
        {
          "key": "percentage_of_actors",
          "value": 25
        }
      ]
    }
  },
  {
    "key": "ci_runner_templates",
    "context": ["user", "namespace"],
    "definition": {
      "name": "ci_runner_templates",
      "introduced_by_url": "https://gitlab.com/gitlab-org/gitlab/-/merge_requests/58357",
      "rollout_issue_url": "https://gitlab.com/gitlab-org/gitlab/-/issues/326725",
      "milestone": "14.0",
      "type": "experiment",
      "group": "group::activation",
      "default_enabled": false
    },
    "current_status": {
      "state": "off",
      "gates": [
        {
          "key": "boolean",
          "value": false
        }
      ]
    }
  }
]

Delete cached assignments

Removes all cached variant assignments for an experiment from the cache store. Use this endpoint to clean up completed experiments whose code is removed from the codebase but whose cached assignments remain.

plaintext
DELETE /experiments/:name/cache

Supported attributes:

AttributeTypeRequiredDescription
namestringYesCache key of the experiment to clear.

If successful, returns 204 No Content.

The request returns 204 No Content even when no cached assignments exist for the given name. The request returns 400 Bad Request when the name references a cache key that is not an experiment. The request returns 401 Unauthorized when the request is not authenticated. The request returns 403 Forbidden when the user is not a GitLab team member.

[!warning] The name value is used directly as the cache key. This endpoint clears any matching cache entry, even one that does not belong to a currently defined experiment. This behavior supports cleaning up orphaned experiments whose code is removed. Verify the name before you call this endpoint.

Example request:

shell
curl --request DELETE \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/code_quality_walkthrough/cache"

Experiment assignments

Use these endpoints to force and read experiment variant assignments in the GLEX Redis cache. This is useful for backend-only experiments that run outside of a request/response cycle, where the glex_force query parameter is not available.

The experiment must declare context_keys in its experiment class in app/experiments. For more information, see Force variant assignment.

Force a variant assignment

Write a variant assignment to the experiment cache for a given context.

plaintext
POST /experiments/:experiment_name/assignments

Parameters:

AttributeTypeRequiredDescription
experiment_namestringYesName of the experiment.
variantstringYesVariant name to assign (for example, control, candidate).
context[user]stringNoUsername for context.
context[namespace]stringNoFull path of the namespace for context.
context[project]stringNoFull path of the project for context.

If you omit the context parameter, the API uses the authenticated user.

shell
curl --request POST \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/my_experiment/assignments" \
  --data "variant=candidate" \
  --data "context[user]=sidney-jones"

Example response:

json
{
  "experiment": "my_experiment",
  "variant": "candidate",
  "context_key": "my_experiment:a1b2c3d4e5f6"
}

Get the current assignment

Read the currently cached variant assignment for a given experiment and context.

plaintext
GET /experiments/:experiment_name/assignments

Parameters:

AttributeTypeRequiredDescription
experiment_namestringYesName of the experiment.
context[user]stringNoUsername for context.
context[namespace]stringNoFull path of the namespace for context.
context[project]stringNoFull path of the project for context.

If you omit the context[user] parameter, the API uses the authenticated user.

If the experiment declares actor in its context_keys, the actor is resolved from context[user]. There is no separate context[actor] parameter.

An experiment can declare multiple context keys, for example context_keys :user, :namespace. In that case, pass every declared key. Only the user and actor keys fall back to the authenticated user; namespace and project must always be passed explicitly.

Example request for an experiment with a user context:

shell
curl --request GET \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/my_experiment/assignments?context[user]=sidney-jones"

Example request for an experiment with a namespace context:

shell
curl --request GET \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/my_experiment/assignments?context[namespace]=my-group"

Example request for an experiment that declares context_keys :user, :namespace:

shell
curl --request GET \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/my_experiment/assignments?context[user]=sidney-jones&context[namespace]=my-group"

Example response:

json
{
  "experiment": "my_experiment",
  "variant": "candidate",
  "context_key": "my_experiment:a1b2c3d4e5f6",
  "cached": true
}

Clear a variant assignment

Remove a forced variant assignment from the experiment cache for a given context, returning the actor to normal rollout assignment.

plaintext
DELETE /experiments/:experiment_name/assignments

Parameters:

AttributeTypeRequiredDescription
experiment_namestringYesName of the experiment.
context[user]stringNoUsername for context.
context[namespace]stringNoFull path of the namespace for context.
context[project]stringNoFull path of the project for context.

Context resolution matches Get the current assignment: if you omit context[user], the API uses the authenticated user, and if the experiment declares actor, the actor is resolved from context[user].

If successful, returns 204 No Content.

The operation is idempotent: clearing a context that has no cached assignment also returns 204 No Content.

Example request:

shell
curl --request DELETE \
  --header "PRIVATE-TOKEN: <your_access_token>" \
  --url "https://gitlab.example.com/api/v4/experiments/my_experiment/assignments?context[user]=sidney-jones"