Skip to content

fix: resolve OPENROUTER_API_KEY before OPENAI_API_KEY in all code paths#295

Merged
teknium1 merged 1 commit into
NousResearch:mainfrom
0xbyt4:fix/openrouter-key-priority
Mar 3, 2026
Merged

fix: resolve OPENROUTER_API_KEY before OPENAI_API_KEY in all code paths#295
teknium1 merged 1 commit into
NousResearch:mainfrom
0xbyt4:fix/openrouter-key-priority

Conversation

@0xbyt4

@0xbyt4 0xbyt4 commented Mar 2, 2026

Copy link
Copy Markdown
Contributor

Summary

  • When both OPENROUTER_API_KEY and OPENAI_API_KEY are set (e.g. OPENAI_API_KEY exported in .bashrc), the wrong key was sent to OpenRouter causing authentication failures.
  • Fixed key resolution order in both cli.py and hermes_cli/runtime_provider.py to check OPENROUTER_API_KEY first.
  • Added 2 regression tests verifying correct priority and fallback behavior.

Fixes #289

Test plan

  • test_openrouter_key_takes_priority_over_openai_key -- both keys set, OpenRouter key wins
  • test_openai_key_used_when_no_openrouter_key -- fallback still works when only OPENAI_API_KEY is set
  • All existing provider resolution tests pass (7/7)

When both OPENROUTER_API_KEY and OPENAI_API_KEY are set (e.g. OPENAI_API_KEY
in .bashrc), the wrong key was sent to OpenRouter causing auth failures.

Fixed key resolution order in cli.py and runtime_provider.py.

Fixes NousResearch#289
@0xbyt4 0xbyt4 changed the title fix: prioritize OPENROUTER_API_KEY over OPENAI_API_KEY fix: resolve OPENROUTER_API_KEY before OPENAI_API_KEY in all code paths Mar 2, 2026
@teknium1 teknium1 merged commit 221e422 into NousResearch:main Mar 3, 2026
@teknium1

teknium1 commented Mar 3, 2026

Copy link
Copy Markdown
Contributor

Merged in 221e422. This was the right fix — covers both cli.py and runtime_provider.py (PR #290 only caught cli.py). Regression tests are a nice touch. Thanks for the contribution!

teknium1 added a commit that referenced this pull request Mar 7, 2026
…iority

Authored by manuelschipper. Adds GLM-4.7 and GLM-5 context lengths (202752)
to model_metadata.py. The key priority fix (prefer OPENAI_API_KEY for
non-OpenRouter endpoints) was already applied in PR #295; merged the Z.ai
mention into the comment.
angelburgosrosado pushed a commit to angelburgosrosado/hermes-agent that referenced this pull request Apr 27, 2026
…NAI_API_KEY in all code paths

Authored by 0xbyt4. Fixes NousResearch#289.
angelburgosrosado pushed a commit to angelburgosrosado/hermes-agent that referenced this pull request Apr 27, 2026
…g API key priority

Authored by manuelschipper. Adds GLM-4.7 and GLM-5 context lengths (202752)
to model_metadata.py. The key priority fix (prefer OPENAI_API_KEY for
non-OpenRouter endpoints) was already applied in PR NousResearch#295; merged the Z.ai
mention into the comment.
02356abc pushed a commit to 02356abc/hermes-agent that referenced this pull request May 14, 2026
…g API key priority

Authored by manuelschipper. Adds GLM-4.7 and GLM-5 context lengths (202752)
to model_metadata.py. The key priority fix (prefer OPENAI_API_KEY for
non-OpenRouter endpoints) was already applied in PR NousResearch#295; merged the Z.ai
mention into the comment.
olympus-terminal pushed a commit to olympus-terminal/hermes-agent that referenced this pull request May 16, 2026
…NAI_API_KEY in all code paths

Authored by 0xbyt4. Fixes NousResearch#289.
olympus-terminal pushed a commit to olympus-terminal/hermes-agent that referenced this pull request May 16, 2026
…g API key priority

Authored by manuelschipper. Adds GLM-4.7 and GLM-5 context lengths (202752)
to model_metadata.py. The key priority fix (prefer OPENAI_API_KEY for
non-OpenRouter endpoints) was already applied in PR NousResearch#295; merged the Z.ai
mention into the comment.
PowerCreek added a commit to TechDevGroup/hermes-agent that referenced this pull request May 26, 2026
…loses #99) (#108)

When the model emits a tool-call-specific finish reason
(``tool_calls`` / ``function_call``) but the normalized
``assistant_message.tool_calls`` reaches the response handler empty
(SDK normalization gap, upstream shape issue, etc.), the previous
behavior:

1. Line 3180 ``if assistant_message.tool_calls:`` evaluates falsy
2. Falls into the ``else: # No tool calls`` branch
3. ``final_response = ""`` (empty content)
4. ``_truly_empty`` becomes True; ``finish_reason="tool_calls"``
   is NOT ``"stop"`` so the #67 structural-empty recovery doesn't
   apply
5. ``_empty_content_retries`` burns 3 retries returning the same
   empty shape
6. Falls through to ``"(empty)"`` terminal

This produces the user-visible "returned no content" + retry loop
documented in hermes-agent#99. Devagentic-side workaround NousResearch#295
strips tools at the request boundary to avoid the model emitting
the problematic finish-reason — once that workaround lifts, this
branch catches any remaining edge cases.

## Fix

In the else branch at conversation_loop.py:3493, before the
empty-retry logic, check:

  _finish_wants_tools = finish_reason in {"tool_calls", "function_call"}
  _tool_calls_absent = not (assistant_message.tool_calls or [])

When both hold (and ``_finish_reason_tools_handled`` flag isn't
set — one-shot semantics like the #67 path), surface synthetic
recovery instead of the retry loop:

- Emit WARNING log with the diagnostic shape (finish_reason,
  model, provider, response_id) so operators see the structural
  mismatch
- Emit user-visible status (``⚠️ Model emitted
  finish_reason=tool_calls but no tool_calls parsed — surfacing
  recovery prompt``)
- Append synthetic assistant message + user-level recovery prompt
  that tells the model the shape was broken + how to retry

Composes with #67's structural-empty recovery (different
finish_reason gates them).

## Tests

- 9 new tests in
  ``tests/agent/test_finish_reason_tools_recovery.py``: positive
  for ``tool_calls`` + ``function_call`` finish reasons with None
  / empty-list tool_calls (3); negative for ``stop`` / ``length``
  / ``content_filter`` finish reasons (3); negative when
  tool_calls populated (1); already-handled one-shot (1);
  source-level patch-landed check (1).
- 28 total green across affected suites (new + #67 terminal +
  empty-response-diagnostic). No regression.

## Composition

Unblocks hermes-agent#100 (R12 worker tool surface for
``run_pipeline`` / ``propose_pipeline``) — that issue's
"Recommendation: Stay Backlog until hermes#99 lands" gate
clears with this PR.

Devagentic#295 (tools-strip at boundary) can be lifted once this
PR + a redeploy is in place; the client-side fix is now the
authoritative path.
Egavasyug pushed a commit to Egavasyug/hermes-agent that referenced this pull request Jun 10, 2026
…NAI_API_KEY in all code paths

Authored by 0xbyt4. Fixes NousResearch#289.
Egavasyug pushed a commit to Egavasyug/hermes-agent that referenced this pull request Jun 10, 2026
…g API key priority

Authored by manuelschipper. Adds GLM-4.7 and GLM-5 context lengths (202752)
to model_metadata.py. The key priority fix (prefer OPENAI_API_KEY for
non-OpenRouter endpoints) was already applied in PR NousResearch#295; merged the Z.ai
mention into the comment.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

hermes prioritizes OPENAI_API_KEY

2 participants