Skip to content
This repository was archived by the owner on May 18, 2026. It is now read-only.

chore: prepare hermes-agent fork for v0.6.0 overlay handoff - #1

Merged
roadhero merged 2 commits into
mainfrom
fitb/phase3-restore-upstream
May 16, 2026
Merged

roadhero merged 2 commits into
mainfrom
fitb/phase3-restore-upstream

Conversation

@roadhero

@roadhero roadhero commented May 16, 2026 •

Copy link
Copy Markdown

Phase 3a of Fox in the Box's v0.6.0 upstream-separation migration (fox-in-the-box-ai/fox-in-the-box epic NousResearch#155, sub-issue NousResearch#170). Fork-side PR. Companion monorepo PR follows once this merges.

What this does

Hands off all hermes-agent Fox customizations from the fork to the sibling fox-overlay package via three coordinated changes plus a CI-attribution fix. Net effect once both PRs land: the fork is a virgin upstream tree (modulo the now-paused workflow), ready to be re-pointed at NousResearch/hermes-agent directly in Phase 8.

File changes

Reverted to upstream merge-base content (5 files, byte-perfect to e5dad4ac5):

File Fox edits removed
agent/auxiliary_client.py provider=auto fallback + auxiliary.default config fallback
cron/jobs.py rolling-5 failure_history field
cron/scheduler.py failure history + diagnostics + traceback recording
hermes_cli/runtime_provider.py target_model fix for Bedrock api_mode routing
tools/cronjob_tools.py surface failure_history + diagnostic fields to tool API

The 5 edits relocate to packages/fox-overlay/fox_overlay/agent_plugins/fox_overlay_plugin/monkey_patches/ in the monorepo PR (NousResearch#171), where each becomes a runtime monkey-patch with inspect.signature() self-check.

Deleted (3 files):

  • plugins/memory/mem0_oss/{__init__.py, README.md, plugin.yaml} — relocated to packages/fox-overlay/fox_overlay/agent_plugins/mem0_oss/ in monorepo PR. kind: backend manifest field added during relocation. Loaded via upstream's hermes_agent.plugins entry-point group.

Modified (2 files):

  • .github/workflows/notify-monorepo.yml — paused repository_dispatch push trigger. ⚠️ DELIBERATE DEVIATION from plan §Phase 3 line 416 ("Keep .github/workflows/notify-monorepo.yml as-is"). Justified: symmetric with the webui fork's already-paused workflow and with the monorepo's already-paused sync-submodules.yml. Without this, the merge push would dispatch a hermes-agent-updated event the monorepo silently drops — fighting itself. workflow_dispatch remains active — ⚠️ DO NOT manually trigger this workflow during the migration window; it will dispatch against a paused monorepo handler and waste a CI minute.
  • scripts/release.py — added "roadhero@gmail.com": "roadhero" to AUTHOR_MAP (commit 2). Resolves the contributor-check.yml CI red on this PR.

Revert mechanics

Reverts use git checkout e5dad4ac5 -- <path> where e5dad4ac5 = merge-base between fork main and upstream/main. This restores byte-perfect upstream content from the fork point. Pulls NO upstream evolution — Phase 8 (NousResearch#200) handles the full upstream-tag re-point separately. Verified bit-exact via shasum -a 256 parity across all 5 files.

Out of scope

5-hat process

Hat Result
Architect Brief approved by Dennis 2026-05-16
Engineer 2 commits (revert+delete+pause; AUTHOR_MAP fix)
Backend reviewer APPROVE (2 LOW, both cosmetic)
DevOps reviewer APPROVE-WITH-CHANGES (contributor-check red — fixed in commit 2)
Adversarial reviewer APPROVE-WITH-CHANGES (workflow-pause deviation must be flagged in PR body — done above)
QA PASS (diff bit-exact, zero ref-leakage, clean YAML, correct authorship)

Reviewer findings actioned

Finding Severity Resolution
contributor-check.yml red — roadhero@gmail.com not in AUTHOR_MAP BLOCKER (R2) Commit 2 adds entry to scripts/release.py
Workflow pause is a plan deviation; should be flagged in PR Rule 2 (R3) This PR body now explicitly flags it ⚠️ above
workflow_dispatch escape hatch warning LOW (R3) Warning added to workflow-pause section ⚠️ above
PR body line-count claim slightly off LOW (R1) Cosmetic; not corrected
auxiliary_client revert removes bug-fix-shaped edits LOW (R1) Flagged for monorepo PR review (where the monkey-patches land)
Commit granularity (3 purposes in 1 commit) LOW (R3) Accepted atomic-migration argument

Cross-repo cohesion

Per feedback_cross_repo_cohesion.md: this PR merges first; monorepo PR opens with the new submodule SHA. The fork between this merge and monorepo-PR merge runs with NO Fox customizations active on the agent side — that's expected; the monorepo's currently-pinned submodule SHA still points at 44a6808f (pre-merge fork main with Fox edits intact), so deployed :stable container is unaffected until the monorepo PR bumps the pin.

Authorship

Both commits authored by roadhero (Dennis Vorobyov) per Fox migration policy.

roadhero added 2 commits May 16, 2026 22:55
Phase 3a of Fox in the Box's v0.6.0 upstream-separation migration
(fox-in-the-box-ai/fox-in-the-box#155, sub-issue NousResearch#170). Fork-side PR.
Companion monorepo PR follows once this merges.

Three coordinated changes that together hand off all hermes-agent Fox
customizations to the sibling fox-overlay package:

1. Revert 5 modified files to upstream content (merge-base e5dad4a).
   The Fox edits relocate to fox_overlay/agent_plugins/fox_overlay_plugin/
   monkey_patches/ in the monorepo PR, where each becomes a runtime
   monkey-patch with inspect.signature() self-check.
   - agent/auxiliary_client.py        (-20 lines: provider=auto fallback)
   - cron/jobs.py                     (-11 lines: failure_history field)
   - cron/scheduler.py                (-58 lines: rolling-5 failure history)
   - hermes_cli/runtime_provider.py   (-1 line: target_model Bedrock fix)
   - tools/cronjob_tools.py           (-8 lines: diagnostics surfacing)

2. Remove plugins/memory/mem0_oss/ (-1218 lines, 3 files). Relocated to
   packages/fox-overlay/fox_overlay/agent_plugins/mem0_oss/ in the
   monorepo PR; loaded via upstream's hermes_agent.plugins entry-point
   group with the missing `kind: backend` manifest field added.

3. Pause .github/workflows/notify-monorepo.yml repository_dispatch.
   Symmetric with the webui fork's already-paused workflow (also from
   migration prep) and with the monorepo's already-paused
   sync-submodules.yml. Without this, the merge push would dispatch a
   `hermes-agent-updated` event the monorepo silently drops — fighting
   itself. workflow_dispatch remains for manual invocation.

Net effect on this fork once both PRs land: a virgin upstream tree
(modulo this still-active workflow file) ready to be re-pointed at
NousResearch/hermes-agent directly in Phase 8.

Out of scope:
  - Any monkey-patch implementation — that's the monorepo PR
  - Restoration of upstream tests (none touched in this fork)
  - Other workflows (release.yml, lint.yml etc.) — keep as-is

Per `feedback_cross_repo_cohesion.md`: this PR merges first; monorepo PR
opens with the new submodule SHA.
…ributions

Reviewer #2 (DevOps) on PR #1 flagged that `contributor-check.yml`
fails because `roadhero@gmail.com` (Fox in the Box maintainer) is
unmapped in scripts/release.py AUTHOR_MAP. The check walks
$MERGE_BASE..HEAD authors and rejects unknown emails.

This fork (fox-in-the-box-ai/hermes-agent) accepted direct pushes
from roadhero pre-PR-#1; the migration cohesion convention requires
PRs going forward, so the AUTHOR_MAP needs the entry.

Keeps the fork's first-ever PR all-green and avoids setting the
"red CI is OK here" cultural anchor on Phase 3.
@roadhero
roadhero merged commit ffb751c into main May 16, 2026
5 of 6 checks passed
roadhero added a commit to fox-in-the-box-ai/fox-in-the-box that referenced this pull request May 17, 2026
… (Phase 3b) (#221)

* feat(fox-overlay): agent plugin + monkey-patches + relocated mem0_oss

Phase 3b (monorepo side) of the v0.6.0 upstream-separation migration
(epic #155, sub-issue #171). Companion to merged fork PRs
fox-in-the-box-ai/hermes-agent#1 (revert Fox edits + remove mem0_oss
+ pause notify-monorepo) and #2 (bootstrap shim).

## What this does

Populates packages/fox-overlay/fox_overlay/agent_plugins/ with the
relocated Fox customizations so the gateway boots with Fox bug fixes
restored on top of virgin upstream:

  1. Three monkey-patches against upstream hermes-agent functions,
     applied via `inspect.getsource` + textual substitution at
     register-time (anchor-based; raises AssertionError at startup if
     upstream refactors the target — caught by Phase 9 nightly watch).

     - hermes_cli.runtime_provider.resolve_runtime_provider:
         target_model used for Bedrock api_mode routing
     - agent.auxiliary_client._resolve_task_provider_model:
         provider=auto resolves to explicit provider when cfg_model set
     - agent.auxiliary_client._get_auxiliary_task_config:
         auxiliary.default falls back when no task-specific config
     - cron.jobs.create_job + .mark_job_run: rolling failure_history
     - cron.scheduler.run_job: enriched FAILED output (diagnostics +
       traceback + session-log path)
     - cron.scheduler.tick: structured multi-line failure delivery
     - tools.cronjob_tools._format_job: surface last_error +
       failure_history + consecutive_failures when present

  2. mem0_oss memory provider relocated wholesale from
     forks/hermes-agent/plugins/memory/mem0_oss/ (byte-identical
     restored via git show; SHA256 verified). plugin.yaml gains
     `kind: backend` for upstream v0.13.0's plugin manifest validation.

  3. pyproject.toml entry-points wire fox_overlay + mem0_oss into
     upstream's hermes_agent.plugins group (discovery mechanism
     documented in plan §3 Agent 2).

  4. Dockerfile inserts `COPY packages/fox-overlay /app/fox-overlay` +
     `pip install -e /app/fox-overlay` between the upstream pip
     install (line 141) and the Phase 2 static-overlay ENV block
     (line 143). Layer-cache friendly: static-asset edits don't
     invalidate the (slow) upstream install layer.

  5. Submodule pin bumped to e301105ec (fork main after PR#1 + PR#2
     merged).

## Validation gates

  - Container rebuilds clean (FITB_VERSION=v0.6.0-p3-shim-qa, 1.45 GB)
  - Container starts, /health 200, supervisord all RUNNING
  - Gateway startup log (/data/data/hermes/logs/agent.log) shows all
    8 `[fox-overlay] patched ...` lines confirming each substitution
  - All 8 runtime sentinel attributes True after gateway boot
  - Zero AssertionError / Traceback / ERROR in any log

## Engineer-discovered gap (handled by fork PR #2)

Upstream's PluginManager.discover_and_load() is invoked only from
hermes_cli commands and tui_gateway, never from gateway/run.py. The
plan assumed entry-points auto-fire at gateway boot; they don't.
Resolved via the ~23-line bootstrap shim in fork PR #2 (plan
deviation flagged + Dennis-approved). Net agent patch surface goes
from plan's optimistic 0 files to 1 file / ~23 lines — still within
Phase 8's patch-series model.

## _helpers.py textual-substitution pattern

`substitute_function` reads upstream source via inspect.getsource,
applies (old, new) substitutions sequentially with EXACTLY-ONCE
anchor check, recompiles in a copy of the upstream module's globals,
and rebinds the attribute. Anchor drift → AssertionError at register
time. Idempotent via per-target sentinel.

Notably does NOT call textwrap.dedent — dedent normalizes
whitespace-only blank lines to bare \\n, breaking anchors that match
verbatim file content. Engineer-discovered during integration smoke
(cron.jobs.mark_job_run anchor with 16-space blank line failed
until dedent removed); fix documented in _helpers.py docstring.

## Out of scope (deferred per architect brief)

  - Bootstrap.py changes — Phase 4 owns those (webui-side shim)
  - Webui-side patches — Phase 4-7
  - Submodule re-point to virgin upstream — Phase 8 (extracts the
    fork-PR-#2 shim to packages/fox-overlay/patches/agent/001-*.patch
    at that time)

Closes #171.

* chore(fox-overlay): revert mem0_oss relocation (Phase 3 rollback)

Reverts the mem0_oss-relocation portion of this PR per Reviewer #2 and
Reviewer #3's HIGH finding during Phase 3b review. Architectural
mismatch: upstream's memory-provider discovery is a separate
directory-scan path (plugins/memory/__init__.py) with its own
FakePluginContext exposing register_memory_provider — incompatible
with the standard PluginContext that entry-point-discovered plugins
receive. Relocated mem0_oss could not register a MemoryProvider at
gateway runtime via either the upstream PluginManager OR the gateway
bootstrap shim.

## File changes

  - removed packages/fox-overlay/fox_overlay/agent_plugins/mem0_oss/
    (3 files, ~1218 lines)
  - reverted pyproject.toml: drop mem0ai + qdrant-client dependencies
    (mem0_oss is back as a bundled fork plugin; upstream's own
    discovery path installs its plugin.yaml deps if needed)
  - reverted pyproject.toml entry-points: drop mem0_oss entry; keep
    fox_overlay entry for the 3 monkey-patches
  - reverted agent_plugins/__init__.py: register() no longer imports
    or invokes mem0_oss; docstring updated with deferral rationale
  - reverted MANIFEST.toml: drop mem0_oss entry; add deferral comment
  - bumped hermes-agent submodule pin from e301105e to 0a278fc1 (fork
    main after PR #3 merge which restores plugins/memory/mem0_oss/
    byte-identical to pre-PR-#1 baseline)
  - added packages/fox-overlay/tests/test_agent_overlay.py — 9 pytest
    cases verifying each of the 8 monkey-patch sentinels + idempotency
    of register()

## Net Phase 3 scope (after this revert)

The 3 Fox monkey-patches (Bedrock target_model, auxiliary.default
fallback, cron failure diagnostics) ship as planned via the
fox-overlay entry-point + gateway bootstrap shim. mem0_oss continues
as a bundled fork plugin, working as it did in v0.5.4 — zero user-
visible regression.

## Future work (out of scope for v0.6.0)

A dedicated future phase handles proper memory-provider relocation,
requiring either:
  (a) An upstream PR to NousResearch/hermes-agent adding
      register_memory_provider to the standard PluginContext, OR
  (b) A Fox-side fake-context construction in the overlay that mirrors
      plugins/memory/__init__.py's discovery path.

Refs Reviewer #2 + Reviewer #3 findings on PR #221; rollback decision
by Dennis 2026-05-17 (Option A of three presented).
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant