Updating maturity of workflow endpoint

Related to #607860 (closed)

What does this MR do and why?

Marks the Trigger a flow endpoint (POST /api/v4/ai/duo_workflows/workflows) as generally available in GitLab 19.5, and tightens its contract before GA locks it in.

Changes

Lifecycle

  • Remove route_setting :lifecycle, :experiment from the create route in ee/lib/api/ai/duo_workflows/workflows.rb. This removes x-gitlab-lifecycle: experiment from the operation in the generated OpenAPI spec.
  • Docs: remove the Status details block from the Trigger a flow section (GA features do not have a status entry) and add a Generally available history entry.

Contract cleanup before GA

  • Success code: declare 201 Created instead of 200 in the endpoint desc block, matching what the endpoint returns and what the docs already said.
  • environment values: accept an explicit list (ide, web, chat_partial, chat, ambient) instead of every Workflow environment enum value. This drops external, which only the external agent sessions API sets and which this endpoint accepted by accident. New enum values no longer join the API contract automatically. ide and web stay accepted because the GitLab frontend and existing clients still send them.
  • Callback attributes: hide callback_hook_id and client_reference from the OpenAPI spec (documentation: { hidden: true }) and mark them as experiments in the docs attribute table. They are still accepted at runtime and still behind duo_flow_callback_hooks.
  • Runtime-neutral descriptions: start_workflow no longer promises a CI pipeline, and image and source_branch say they apply only when the flow runs in a CI pipeline. Not every flow runs in CI, and the endpoint is moving to ExecuteRunService in #629005.
  • Response docs:
    • workload.id is documented as integer, not string.
    • workload.id and workload.message are null when no workload was created, for example when start_workflow is not true.
    • status can gain new values.

What stays experimental

This MR changes only the create route. These are unchanged and remain experiments:

  • POST /ai/duo_workflows/workflows/:workflow_id/restart
  • GET /ai/duo_workflows/workflows/:workflow_id/trace.jsonl
  • POST /ai/duo_workflows/workflows/:workflow_id/execute
  • Resume, GET /ai/duo_workflows/ws, POST /ai/duo_workflows/direct_access, and GET /ai/duo_workflows/list_tools
  • POST /ai/duo_workflows/agent_workflows, the restricted endpoint that chat agents call with an ai_workflows-scoped token. It has its own copy of the parameters and handler, so this MR does not affect it.
  • The callback_hook_id and client_reference attributes of this endpoint.

What GA means for this endpoint

After this merges, the endpoint falls under the REST API breaking changes policy. Removing or renaming parameters, rejecting input that is valid today, removing enum values (source, environment, status), or removing response fields will require a deprecation. Until now, changes like these shipped without one because the endpoint was an experiment. For example, shallow_clone was removed in !250447 (merged).

The endpoint also backs the create_duo_workflow MCP tool, so its parameters are part of that tool's contract too.

Open before merge

Decided

  • incremental_checkpoints_enabled stays in the response for now. It can only be removed after the checkpoint data migration completes (#627332).
  • No GA read path yet. Reading a flow's result through GraphQL duoWorkflowWorkflows or webhook callbacks stays experimental. That will be matured searately
    • **Composite identity enforcement ** With enforce_composite_identity_for_api_started_workflows on, a request with start_workflow: true and no composite-identity service account returns 403. This will be an intended security tightening, closing a bug.

References

Screenshots or screen recordings

Not applicable. There are no UI changes.

How to set up and validate locally

  1. No noticeable behavior change when you test chat/flows while docs and spec call out the endpoint being GA.
Edited by Sebastian Rehm

Merge request reports

Loading
Loading