Skip to content

Add Natural/Boundary retention (v1.1.11) and silent Hermes provider - #1

Merged
gabewillen merged 16 commits into
mainfrom
retention-natural-boundary-1.1.11
Jul 12, 2026
Merged

Add Natural/Boundary retention (v1.1.11) and silent Hermes provider#1
gabewillen merged 16 commits into
mainfrom
retention-natural-boundary-1.1.11

Conversation

@gabewillen

Copy link
Copy Markdown
Contributor

Summary

  • Expand Retention to Natural (default), Durable, Boundary, Ephemeral
    • Natural (omitted default): force_boundary=false, force_write=false — episode algorithms decide
    • Durable: force boundary + force write (unchanged chat-turn convenience)
    • Boundary: force turn edge only; write gate still applies
    • Ephemeral: never store; force retrieval boundary
  • Expose retention on C cortext_process_json_options and Python / JS / Go bindings
  • Patch version 1.1.11
  • Add silent augmem.hermes memory provider (no tools / no system-prompt branding) with cold-start live e2e
  • macOS flock fix for sqlite-objstore under _POSIX_C_SOURCE

Test plan

  • ./build/debug-test/tests/cortext_tests "[retention]" — 3 cases / 45 assertions
  • cd integrations/hermes && uv run pytest — 16 passed, 1 skipped
  • CI full suite on PR
  • Optional live: CORTEXT_HERMES_LIVE=1 OPENAI_API_KEY=... OPENAI_MODEL=gpt-5.4-mini uv run augmem-hermes live-e2e --force

Breaking note

Process* default retention is now Natural (not Durable force-turn). Callers that need the old “every message is a committed turn” behavior must pass Retention::Durable explicitly (CLI remember / Hermes stores already do).

Process* default is now Natural (force_boundary=false, force_write=false)
so episode algorithms decide; Durable keeps force turn + force write;
Boundary forces the edge only; Ephemeral stays no-store query. Expose
retention on C options and Python/JS/Go bindings (v1.1.11). Add
augmem.hermes silent memory provider with live cold-start e2e and a
macOS flock fix for sqlite-objstore.
Copilot AI review requested due to automatic review settings July 11, 2026 18:35

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands Cortext ingress retention semantics (defaulting Process* calls to Natural with no forced boundary/write), plumbs the new retention policy through the C API and language bindings, bumps the project to v1.1.11, and introduces a new Hermes Agent integration that provides an “invisible” (no tools / no system prompt branding) memory provider with optional live end-to-end verification.

Changes:

  • Add Retention::{Natural, Durable, Boundary, Ephemeral} behavior and update Process* defaults + C API options/bindings to pass retention explicitly.
  • Introduce integrations/hermes provider/plugin + CLI + tests, including optional cold-start live e2e verification.
  • Patch build/docs/versioning updates, plus a macOS feature-macro fix for sqlite-objstore flock() visibility.

Reviewed changes

Copilot reviewed 33 out of 35 changed files in this pull request and generated 7 comments.

Show a summary per file
File Description
third_party/sqlite-objstore/src/backend_file.c Adjust feature-test macros to avoid hiding flock() on macOS.
tests/cortext.test.cpp Add retention behavior tests for Natural/Durable/Boundary/Ephemeral.
src/operations/accumulator.cpp Change accumulator tracking to exclude only Ephemeral signals.
src/cortext.cpp Update force-boundary logic and default retention for cached ProcessText path.
src/capi.cpp Add retention parsing from cortext_process_json_options and thread through JSON APIs.
README.md Document v1.1.11 retention policies and updated Process* defaults.
integrations/hermes/uv.lock Add Hermes integration lockfile for reproducible Python env.
integrations/hermes/tests/test_provider.py Unit tests for Hermes provider behavior (invisibility, seams, provenance, media/tool ingest).
integrations/hermes/tests/test_live_e2e.py Optional live-model cold-start e2e test (skipped by default).
integrations/hermes/tests/test_cli.py Basic CLI tests for install/status helpers.
integrations/hermes/src/augmem/hermes/provider.py Implement silent Hermes MemoryProvider with 3 seam hooks + durable ingest and ephemeral prefetch.
integrations/hermes/src/augmem/hermes/plugin/plugin.yaml Define Hermes plugin metadata and hook registration.
integrations/hermes/src/augmem/hermes/plugin/init.py Plugin package entry exporting provider/register.
integrations/hermes/src/augmem/hermes/media.py Multimodal extraction + decoding and engine dispatch helpers.
integrations/hermes/src/augmem/hermes/live_e2e.py Live e2e harness exercising cold-start recall + control/treatment checks.
integrations/hermes/src/augmem/hermes/cli.py augmem-hermes CLI: install/status/live-e2e.
integrations/hermes/src/augmem/hermes/init.py Hermes integration package exports + version.
integrations/hermes/README.md Hermes integration documentation (seams, provenance, config, live e2e).
integrations/hermes/pyproject.toml Hermes integration packaging, deps, scripts, pytest config.
integrations/hermes/.gitignore Ignore venv/test/build artifacts for Hermes integration.
include/cortext/signal.hpp Change default Signal.retention to Natural and update comment.
include/cortext/retention.hpp Expand/describe retention policies and add Natural/Boundary.
include/cortext/internal/replay_ingress.hpp Update replay ingress default retention to Natural.
include/cortext/cortext.hpp Update public API docs + default retention arguments to Natural.
include/cortext/capi.h Add cortext_retention enum and cortext_process_json_options.retention.
docs/paper/sections/9_experimental.qmd Update experiment log narrative for retention expansion.
docs/paper/sections/8_interrupt_gate.qmd Update algorithm/pseudocode notes for retention policies.
CMakeLists.txt Bump project version to 1.1.11.
bindings/python/README.md Document new retention behavior and recommended usage.
bindings/python/pyproject.toml Bump Python binding version to 1.1.11.
bindings/python/augmem/cortext/init.py Add Python Retention enum and thread retention into process options.
bindings/javascript/src/addon.cpp Parse retention from JS options and pass to native C API.
bindings/javascript/package.json Bump JS package version to 1.1.11.
bindings/javascript/index.d.ts Add Retention type and ProcessOptions.retention.
bindings/go/cortext.go Add Go Retention type and thread it into native process options.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread include/cortext/retention.hpp Outdated
Comment thread src/operations/accumulator.cpp Outdated
Comment thread bindings/javascript/src/addon.cpp Outdated
Comment thread bindings/javascript/src/addon.cpp Outdated
Comment thread integrations/hermes/src/augmem/hermes/provider.py Outdated
Comment thread integrations/hermes/src/augmem/hermes/media.py
Comment thread tests/cortext.test.cpp Outdated
Pin Retention enum values, rename storable-signal tracking, harden JS
retention parsing, expose boundary_type for force diagnostics, queue
Hermes ingest without join stalls, and disable remote media fetch by
default.
@gabewillen

Copy link
Copy Markdown
Contributor Author

Addressed all Copilot review threads in f3815b5:

  1. Retention enum pins — explicit 0..3 values matching C ABI/cortext_retention.
  2. Accumulator flag nametrack_durable_signaltrack_storable_signal (Natural/Boundary/Durable).
  3. JS numeric retention — rejects NaN/Inf and non-integers (no silent truncation).
  4. JS string retention — case-insensitive (Durable/DURABLE work).
  5. Hermes non-blocking ingest — single worker + queue; hooks no longer join prior threads.
  6. Remote media fetch — off by default (fetch_remote_media: false); data URLs and local paths still work.
  7. Retention tests — assert boundary_type == "explicit_turn" for forced policies (exposed on Context/JSON).

Verified: cortext_tests "[retention]" (3 cases) and Hermes provider unit tests (13).

ubuntu-aist was failing because download_aist_model.py no longer accepts
--models-dir after the asset packaging cleanup.
Call sites that assert storage now pass Retention::Durable (or C API
CORTEXT_RETENTION_DURABLE) instead of relying on the old Durable default.
@gabewillen

Copy link
Copy Markdown
Contributor Author

@codex

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: be84033139

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/capi.cpp Outdated
Comment thread src/operations/accumulator.cpp Outdated
Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread integrations/hermes/src/augmem/hermes/media.py Outdated
Comment thread README.md
@gabewillen

Copy link
Copy Markdown
Contributor Author

@codex

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 66fe28f433

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/cortext.cpp
Comment thread bindings/javascript/src/addon.cpp Outdated
Comment thread bindings/javascript/src/addon.cpp Outdated
Comment thread src/capi.cpp Outdated
Comment thread integrations/hermes/src/augmem/hermes/media.py Outdated
Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread integrations/hermes/src/augmem/hermes/provider.py Outdated
Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread include/cortext/internal/replay_ingress.hpp Outdated

Copy link
Copy Markdown
Contributor Author

@codex review

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 64b057de05

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread src/operations/accumulator.cpp
Comment thread integrations/hermes/src/augmem/hermes/media.py
Comment thread integrations/hermes/src/augmem/hermes/provider.py Outdated
Comment thread include/cortext/cortext.hpp
Comment thread docs/paper/sections/9_experimental.qmd
@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@gabewillen

Copy link
Copy Markdown
Contributor Author

@codex Please review the latest fixes.

@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@gabewillen

Copy link
Copy Markdown
Contributor Author

@codex Please review the CI fix in the latest commit.

@chatgpt-codex-connector

Copy link
Copy Markdown

You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard.

@gabewillen gabewillen left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Summary

This PR introduces a four-value retention model (Natural/Durable/Boundary/Ephemeral), folds the old force_boundary/force_write flags into retention helpers, defers objstore payload puts until write acceptance, and adds a silent Hermes Agent memory provider. The core policy mapping looks intentional and is mostly well-covered for the happy paths (Durable force write, Ephemeral no-store, ABI-safe options expansion with reserved). Dominant risks are the public default flip from Durable→Natural (incomplete call-site migration and C simple-API surface), and flush-on-boundary interactions that can discard pending Natural units when Ephemeral/Boundary share a source_id.

Issue counts by severity

  • bugs: 2
  • suggestions: 5
  • nits: 3

Issues outside the diff

These findings reference lines that are not present in the diff and could not be posted as inline comments:

  • [nit] docs/paper/sections/9_experimental.qmd:138 -- The v1.1.11 retention expansion note still points smoke-eval output paths named release_1_1_10_smoke_..., which is confusing for release traceability.
    • Suggestion: Rename the logged run directory to a 1.1.11-tagged path (or note that the smoke reuses the 1.1.10 artifact id).

Comment thread include/cortext/cortext.hpp
Comment thread src/operations/boundary.cpp
Comment thread include/cortext/capi.h
Comment thread src/operations/accumulator.cpp
Comment thread tests/cortext.test.cpp
Comment thread integrations/hermes/tests/test_provider.py
Comment thread integrations/hermes/src/augmem/hermes/provider.py Outdated
Comment thread include/cortext/retention.hpp Outdated
Comment thread bindings/python/augmem/cortext/__init__.py
@gabewillen

Copy link
Copy Markdown
Contributor Author

@codex Please review the latest retention hardening fixes.

@gabewillen gabewillen left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Summary

Prior review items are largely addressed in head 0009fbfa: Natural cutover is intentional and documented; classic C process APIs hard-force Durable; Ephemeral no longer joins or resets open same-source units; Hermes fake engine, retention validation, docs, and prefetch worker reuse look fixed. One material correctness gap remains: same-source Ephemeral isolation stops at UpdateAccumulator / ResetAccumulatorAfterFlush, so later ops still contaminate open Natural accumulator scores (and related drift/pacing state). That residual path can skew later write-gate decisions and persisted signal scores; fix before merge if Natural+same-source recall is an expected production pattern.

Issue counts by severity

  • bugs: 1
  • suggestions: 1
  • nits: 1

Issues outside the diff

These findings reference lines that are not present in the diff and could not be posted as inline comments:

  • [bug] src/operations/accumulator_scores.cpp:28 -- Same-source Ephemeral isolation is incomplete. UpdateAccumulator correctly early-returns and ResetAccumulatorAfterFlush correctly skips reset, but UpdateAccumulatorScores still runs for an open Natural unit (n_signals > 0). It adds the probe composite score into acc.s_sum, may raise s_max / rewrite e_peak, and overwrites acc.signals.back().score with the query score. Because write-gate S_window is derived from s_sum/s_max, a same-source recall/probe can change whether a later Natural/Boundary close commits the pending unit, and can persist a corrupted last-signal score. The regression test only asserts n_signals == 3 and does not catch score contamination.
    • Suggestion: Skip score updates (and ideally all storable-unit mutations) when signal.retention == Retention::Ephemeral. Extend the same-source regression test to seed known s_sum/s_max/last signal score and assert they are unchanged after an Ephemeral probe through the full CoreStage path (or at least UpdateAccumulatorScores + reset).
  • [suggestion] src/operations/drift_accumulation.cpp:61 -- Related residual same-source interference: on Ephemeral probes, UpdateDriftAccumulation still mutates the open unit’s drift_accum/prev_x, and CheckStreamingPacing still mutates drift_acc_pacing/x_last_check (and may insert an empty accumulator for a brand-new source). This is weaker than score contamination but still violates the “observe without becoming part of the open Natural unit” intent established for Ephemeral.
    • Suggestion: Gate these ops (or their accumulator mutations) on non-Ephemeral retention, matching UpdateAccumulator. Prefer a single early “Ephemeral does not touch source accumulator state” policy so future ops cannot reintroduce the hole.

Comment thread integrations/hermes/README.md Outdated

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 0009fbfa67

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/operations/accumulator_reset.cpp
Comment thread src/capi.cpp
Comment thread include/cortext/capi.h
Comment thread src/operations/memory_storage.cpp
Comment thread integrations/hermes/src/augmem/hermes/media.py Outdated
Comment thread integrations/hermes/src/augmem/hermes/provider.py Outdated

@gabewillen gabewillen left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Summary

Head d16e141 keeps the core Ephemeral isolation fixes from the prior re-review (UpdateAccumulator early-return, Coherence skip, ResetAccumulatorAfterFlush skip, write-gate no-store, Hermes Durable/Ephemeral split docs). The previously open scores bug is still unfixed: UpdateAccumulatorScores still mutates open same-source Natural unit s_sum/s_max/last-signal score during Ephemeral probes, and that still feeds write-gate S_window and stored memory metrics. Drift/pacing open-unit mutation is also still present (UpdateDriftAccumulation, CheckStreamingPacing). Not merge-ready for same-source Natural+Ephemeral isolation until the scores path (at minimum) is gated and covered.

Issue counts by severity

  • bugs: 1
  • suggestions: 1
  • nits: 0

Comment thread src/operations/accumulator.cpp
Comment thread src/operations/accumulator.cpp

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: d16e141063

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/operations/accumulator.cpp
Comment thread src/capi.cpp
Comment thread integrations/hermes/src/augmem/hermes/provider.py

@gabewillen gabewillen left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Summary

Prior critical findings are fixed on head f0f2709: UpdateAccumulatorScores, UpdateDriftAccumulation, and CheckStreamingPacing all early-return for Retention::Ephemeral, and the same-source isolation test now asserts score fields (s_sum/s_max/last signal score) plus drift/pacing state, not only n_signals. CoreStage open-unit mutators (accumulate, scores, coherence, boundary explicit path, write gate, reset-after-flush) look isolated. One residual same-source hole remains in the interrupt gate, which can still advance open-unit refractory state when a probe allows an interrupt. Not a merge blocker relative to the fixed write-score pollution path, but worth closing for complete Ephemeral isolation.

Issue counts by severity

  • bugs: 0
  • suggestions: 1
  • nits: 0

Comment thread tests/operations_accumulator.test.cpp

@gabewillen gabewillen left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Summary

The critical residual from head e5b1f7cb is fixed: ComputeMniGateDecision no longer inserts a source accumulator for Ephemeral, uses a read-only fallback when no entry exists, and does not advance drift_at_last_interrupt or last_interrupt_tick when an interrupt is allowed. Prior CoreStage isolation (accumulate/scores/drift/pacing/reset/coherence) remains intact, and regression tests cover scores + drift/pacing + interrupt refractory. One remaining same-source lifecycle hole: forced Ephemeral boundary score still drives capacity finalize through CheckSpikeBypass without write or accumulator reset. Merge is close; that cascade should be gated before treating isolation as complete.

Issue counts by severity

  • bugs: 1
  • suggestions: 0
  • nits: 0

Comment thread src/operations/boundary.cpp
@gabewillen
gabewillen merged commit af61ad8 into main Jul 12, 2026
12 checks passed
@gabewillen
gabewillen deleted the retention-natural-boundary-1.1.11 branch July 12, 2026 01:40

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 69efa571f9

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread src/capi.cpp
Comment thread include/cortext/cortext.hpp
Comment thread integrations/hermes/src/augmem/hermes/provider.py
Comment thread include/cortext/retention.hpp
Comment thread integrations/hermes/src/augmem/hermes/media.py
Comment thread bindings/python/README.md
gabewillen added a commit that referenced this pull request Jul 24, 2026
Add Natural/Boundary retention (v1.1.11) and silent Hermes provider
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.

2 participants