Skip to content

Bug: custom provider SecretRef marker leaks into Authorization header as Bearer secretref-managed #39823

@bailob

Description

@bailob

Summary

Agent-generated report, filed by an OpenClaw agent on behalf of the user after local debugging and user-assisted packet capture.

After upgrading to OpenClaw 2026.3.7, a custom OpenAI-compatible provider configured with an exec SecretRef for models.providers.*.apiKey can send the literal placeholder marker as the upstream bearer token instead of the resolved secret.

Observed request header sent upstream:

Authorization: Bearer secretref-managed

This causes upstream 401 responses such as invalid API key errors, even though:

  • the SecretRef resolves successfully,
  • the actual secret works with direct manual requests,
  • and the provider/model configuration itself is otherwise valid.

Privacy / secret handling note

This report intentionally excludes:

  • the real API key,
  • the full SecretRef payload,
  • raw credential material,
  • and any user-specific secret values.

Only the non-secret placeholder marker (secretref-managed) is described here.

Environment

  • OpenClaw: 2026.3.7
  • Platform: macOS
  • Provider type: custom OpenAI-compatible provider via models.providers
  • Credential source: apiKey configured as SecretRef with source: "exec"
  • Secret provider: user-defined exec SecretRef provider (1Password-backed resolver in this case, but the bug appears to be in OpenClaw marker/runtime handling rather than the external resolver itself)

Expected behavior

For SecretRef-managed custom providers:

  • generated agents/*/agent/models.json may persist a non-secret marker such as secretref-managed, but
  • runtime request/auth code must resolve the actual secret before building upstream HTTP auth headers,
  • and must never send the placeholder marker as the provider API key.

Actual behavior

OpenClaw emits upstream requests with:

Authorization: Bearer secretref-managed

The upstream provider correctly rejects this with 401.

What was verified

1) SecretRef resolution works

The configured exec SecretRef provider successfully resolves the real provider API key at runtime.

2) Direct upstream requests work

Using the resolved real API key directly against the same upstream base URL succeeds:

  • GET /models succeeds
  • minimal POST /chat/completions succeeds
  • tested with the same provider base URL and the same model ids used by OpenClaw

3) Generated models.json uses the marker

The affected generated agent models.json contains:

"apiKey": "secretref-managed"

for the affected provider.

4) Actual upstream request capture confirms marker leakage

A captured upstream request from OpenClaw showed:

Authorization: Bearer secretref-managed

So this is not just a speculative explanation; the marker is actually leaking into the outgoing auth header.

Suspected regression source

Most likely related to the 2026.3.7 SecretRef/models.json persistence hardening work, especially:

The new persistence behavior appears correct in principle (do not persist plaintext secrets), but a runtime auth path still seems to treat the marker as a usable API key for custom providers.

Why this appears to be an OpenClaw bug, not a user config issue

The current documented behavior says SecretRef-managed provider API keys should refresh from source markers rather than persist resolved secrets into models.json.

That implies this configuration remains supported.

The failure is that the marker is being used as a literal credential at request time instead of being resolved back to the real secret.

Potential root cause area

The likely failure mode is:

  1. SecretRef-managed provider apiKey is persisted into generated models.json as secretref-managed
  2. a runtime provider auth path reads models.json / merged provider config
  3. the marker is treated as a normal string API key
  4. runtime request construction emits Authorization: Bearer secretref-managed

Request

Please investigate the runtime/provider auth path for custom OpenAI-compatible providers using SecretRef-managed models.providers.*.apiKey, and ensure marker values such as secretref-managed are never emitted as actual upstream credentials.

It would also help to add a regression test that verifies:

  • SecretRef-managed custom providers can persist markers in generated models.json
  • but runtime requests always use the resolved secret, never the marker

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions