[BUG] forceLoginOrgUUID is incompatible with setup-token OAuth tokens — breaks all unattended/CI usage

Resolved 💬 4 comments Opened May 7, 2026 by chkp-roniz Closed Jun 4, 2026

Preflight Checklist

  • [x] I have searched existing issues and this hasn't been reported yet
  • [x] This is a single bug report (please file separate reports for different bugs)
  • [x] I am using the latest version of Claude Code

What's Wrong?

Summary

When forceLoginOrgUUID is set in managed-settings.json, any machine authenticated with a token from claude setup-token is hard-blocked at startup with no path to recovery. This makes the two features mutually exclusive in practice and breaks the documented CI/CD authentication flow whenever an enterprise wants to enforce org binding.

Impact

This is a real foot-gun for any enterprise rolling out Claude Code at scale:

  • Enterprises naturally want forceLoginOrgUUID enforced as a defence-in-depth control on engineer workstations.
  • The same managed-settings.json is typically distributed via configuration management (MDM, ansible, base images) to all hosts including CI runners.
  • The result is a production outage of every Claude-Code-powered workflow the moment the setting is published, with no warning and no migration path documented.
  • The error message points users at claude auth login, which is the wrong answer for CI — it ties workflows to a single human's OAuth credentials, which is a governance regression.

Root cause

  • claude setup-token requests only user:inference scope (intentional — narrow scope for unattended use).
  • forceLoginOrgUUID enforcement calls the profile endpoint, which requires user:profile.
  • Re-running setup-token cannot resolve this; the scope is fixed in the CLI's OAuth authorization URL. See #22450 for the related scope-narrowing issue.
  • The only way to obtain a user:profile-scoped token is claude auth login, which is interactive, tied to a human identity, and refresh-rotating — unusable in GitHub Actions, GitLab CI, Jenkins, or any other unattended runner.

What Should Happen?

Expected behaviour

One of the following:

  1. Preferred: forceLoginOrgUUID enforcement should be skipped or use an alternative verification path for tokens minted by setup-token. The org identity of a setup-token is already determinable server-side from the token itself — no user:profile round-trip should be required.
  2. Alternative: claude setup-token should optionally request user:profile scope (e.g. claude setup-token --scope user:profile or a separate setup-ci-token command) so enterprise admins can mint tokens that satisfy forceLoginOrgUUID.

Error Messages/Logs

Unable to verify organization for the current authentication token.
This machine requires organization <uuid> but the profile could not be fetched.
This may be a network error, or the token may lack the user:profile scope required for
verification (tokens from 'claude setup-token' do not include this scope).
Try again, or obtain a full-scope token via 'claude auth login'.

Steps to Reproduce

Steps to reproduce

  1. On any machine, deploy managed-settings.json containing:

``json
{ "forceLoginOrgUUID": "<your-org-uuid>" }
``

  1. Authenticate using claude setup-token (or set CLAUDE_CODE_OAUTH_TOKEN from a previously generated setup-token).
  2. Run any claude command, or trigger the anthropics/claude-code-action@v1 GitHub Action with claude_code_oauth_token as input.
  3. Observe the verification failure above. The CLI exits without performing the requested operation.

Claude Model

Not sure / Multiple models

Is this a regression?

I don't know

Last Working Version

_No response_

Claude Code Version

2.1.129 (Claude Code)

Platform

Other

Operating System

Ubuntu/Debian Linux

Terminal/Shell

Non-interactive/CI environment

Additional Information

  • #22450 — claude usage fails with same user:profile scope mismatch from setup-token
  • #23703 — setup-token scope narrowing breaks external use cases

View original on GitHub ↗

This issue has 4 comments on GitHub. Read the full discussion on GitHub ↗