Namespace model switching spoofable

Summary

The find_root_namespace helper method in the Duo Workflows API has two security vulnerabilities that allow unauthorized access to namespace-level AI model settings:

  1. Missing authorization check: Uses find_namespace instead of find_namespace!, allowing users to access any namespace without permission verification
  2. No context validation: Users can specify any namespace they have read access to, not just namespaces relevant to their current workflow context

Details

ee/lib/api/ai/duo_workflows/workflows.rb

def find_root_namespace
  # The IDE sends namespace data via the header, while the web agentic chat UI
  # sends it as a query param.
  # The IDE only sends the namespace_id of the project's
  # immediate group, so we have to find the root_ancestor separately.
  namespace_id = params[:root_namespace_id].presence || headers['X-Gitlab-Namespace-Id'].presence
  return unless namespace_id

  namespace = find_namespace(namespace_id)  # ⚠️ No authorization check
  namespace&.root_ancestor
end

Vulnerability 1: Missing Authorization Check

Issue: The code uses find_namespace(namespace_id) which, according to the helper documentation in lib/api/helpers.rb, explicitly states:

find_namespace returns the namespace regardless of user access level on the namespace

Impact: A malicious user can provide any root_namespace_id (via query parameter or X-Gitlab-Namespace-Id header) to access model selection settings for namespaces they don't have permission to read.

Vulnerability 2: No Context Validation

Issue: Even with authorization checks, users can specify any namespace they have read access to, regardless of whether that namespace is contextually relevant to their current workflow.

Impact: Users can exploit model settings from unrelated namespaces they happen to have access to, potentially:

  • Using premium AI models configured in other organizations
  • Bypassing their own organization's model restrictions
  • Accessing model configurations they shouldn't be using in the current context