Compare commits

...
Author SHA1 Message Date
conductor f7e6c5cff5 chore(release): auto-bump version to 0.99.5 — earned by #2470 (TUI: chat pane LEFT + post-response dim-spam consolidation (T5.14/T5.13))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 4m56s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 2m27s
Promotion record: http://127.0.0.1:3000/conductor/rune/pulls/2470
2026-10-06 03:27:08 +01:00
conductor fc46dbea52 Merge pull request 'TUI: chat pane LEFT + post-response dim-spam consolidation (T5.14/T5.13)' (#2470) from feat/tui-pane-swap-chat-left into master
Auto-version and Release / release (push) Failing after 3s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / lint (push) Successful in 37s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / unit-tests (push) Successful in 4m56s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m49s
2026-10-06 03:27:02 +01:00
conductor d8ede8f3f8 Merge branch 'master' into feat/tui-pane-swap-chat-left
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 35s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 34s
CI Pipeline / go-surface (pull_request) Successful in 3s
CI Pipeline / canary (pull_request) Successful in 41s
CI Pipeline / best-practices (pull_request) Successful in 2s
CI Pipeline / documentation (pull_request) Successful in 1s
CI Pipeline / type-check (pull_request) Successful in 27s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
Spec gate (headless) / spec-gate (pull_request) Successful in 5s
CI Pipeline / unit-tests (push) Successful in 4m55s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 3s
CI Pipeline / unit-tests (pull_request) Successful in 4m54s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
Auto-version and Release / release (pull_request) Successful in 4s
2026-10-06 03:19:13 +01:00
conductor 804c2f62df chore(release): auto-bump version to 0.99.4 — earned by #2472 (Scaffold: construction_commands dispatch — the serving wire (T5.15 slice 2))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 5m3s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
deploy / deploy (push) Successful in 5m9s
Promotion record: http://127.0.0.1:3000/conductor/rune/pulls/2472
2026-10-06 03:11:51 +01:00
conductor e5d10f18ae Merge pull request 'Scaffold: construction_commands dispatch — the serving wire (T5.15 slice 2)' (#2472) from feat/wire-construction-commands-dispatch into master
Auto-version and Release / release (push) Failing after 2s
CI Pipeline / lint (push) Successful in 36s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 5m0s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 6m2s
2026-10-06 03:11:44 +01:00
conductor 3ed58d48a9 Merge branch 'master' into feat/tui-pane-swap-chat-left
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 33s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 40s
CI Pipeline / best-practices (pull_request) Successful in 1s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / type-check (pull_request) Successful in 27s
CI Pipeline / gitea-offline (pull_request) Successful in 12s
Spec gate (headless) / spec-gate (pull_request) Successful in 5s
CI Pipeline / unit-tests (push) Successful in 4m55s
CI Pipeline / unit-tests (pull_request) Successful in 5m0s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
2026-10-06 03:02:57 +01:00
conductor 6c997b6af4 Merge branch 'master' into feat/wire-construction-commands-dispatch
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / lint (pull_request) Successful in 36s
CI Pipeline / go-surface (pull_request) Successful in 3s
CI Pipeline / canary (pull_request) Successful in 44s
CI Pipeline / best-practices (pull_request) Successful in 1s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / type-check (pull_request) Successful in 27s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
Spec gate (headless) / spec-gate (pull_request) Successful in 4s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / unit-tests (pull_request) Successful in 5m1s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
Auto-version and Release / release (pull_request) Successful in 4s
2026-10-06 03:02:52 +01:00
conductor 9b5befb137 chore(release): auto-bump version to 0.99.3 — earned by #2471 (Scaffold: stage_guards wired into completion transitions (T5.15 slice 1))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 5m1s
CI Pipeline / lint (push) Successful in 35s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 41s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 10m26s
Promotion record: http://127.0.0.1:3000/conductor/rune/pulls/2471
2026-10-06 02:50:18 +01:00
conductor 6899d859da Merge branch 'master' into feat/tui-pane-swap-chat-left
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 39s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 26s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 34s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 45s
CI Pipeline / best-practices (pull_request) Successful in 1s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / type-check (pull_request) Successful in 26s
CI Pipeline / gitea-offline (pull_request) Successful in 12s
Spec gate (headless) / spec-gate (pull_request) Successful in 5s
CI Pipeline / unit-tests (push) Successful in 4m56s
CI Pipeline / unit-tests (pull_request) Successful in 4m54s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
2026-10-06 02:50:11 +01:00
conductor 8ef70448c3 Merge pull request 'Scaffold: stage_guards wired into completion transitions (T5.15 slice 1)' (#2471) from feat/wire-stage-guards-transition into master
Auto-version and Release / release (push) Failing after 3s
CI Pipeline / lint (push) Successful in 36s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / unit-tests (push) Successful in 4m55s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 10m51s
2026-10-06 02:50:08 +01:00
Nick 55f268f978 feat(scaffold): construction_commands dispatch — the serving wire (T5.15 slice 2)
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 34s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 45s
CI Pipeline / best-practices (pull_request) Successful in 2s
CI Pipeline / documentation (pull_request) Successful in 1s
CI Pipeline / type-check (pull_request) Successful in 26s
CI Pipeline / gitea-offline (pull_request) Successful in 12s
Spec gate (headless) / spec-gate (pull_request) Successful in 4s
CI Pipeline / unit-tests (push) Successful in 4m54s
CI Pipeline / unit-tests (pull_request) Successful in 4m54s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
The command seam validated intents but nothing EXECUTED them. dispatch() binds the canonical store, runs the validator, then executes accepted intents through the Construction Interface (resume/transition/amend_scope), refusing via the lifecycle with accepted=False+success=True (a refusal is a valid protocol outcome, not an error). Idempotent replay returns the recorded intent without re-executing. Three contracts: end-to-end phase movement, refusal shape, replay-no-double-execute; seam file 12/12. Slice 1 of 5 was stage_guards (#2467 wire wave).
2026-10-06 02:40:49 +01:00
Nick 320026a4a3 feat(scaffold): stage_guards wired into the completion-facing transitions (T5.15 slice 1)
deploy / deploy (push) Skipped
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 26s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 34s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 44s
CI Pipeline / best-practices (pull_request) Successful in 2s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
CI Pipeline / type-check (pull_request) Successful in 28s
CI Pipeline / unit-tests (push) Successful in 4m55s
CI Pipeline / unit-tests (pull_request) Successful in 4m58s
Spec gate (headless) / spec-gate (pull_request) Successful in 4s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / required-checks (pull_request) Successful in 0s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 3s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 3s
Auto-version and Release / release (pull_request) Successful in 3s
The five orphaned V1 components: slice 1 wires stage_guards for real. transition(verifying|closed) now runs §15F readiness StageChecks derived from guard: verification obligations (or inline guard_checks); a blocked guard = VERIFICATION_FAILED envelope and the phase does NOT move — builder cannot self-certify past a failing check. building/free edges unchanged; capabilities() schema documents the new arg; CLI transport carries guard_checks as JSON arg 4. Four contracts red-first (blocked/pass/inline-override/free-edge); 56 interface+guards tests green.
2026-10-06 02:40:49 +01:00
Nick 0e88b6bc08 feat(tui): consolidate post-response dim spam into one collapsed line (#2468/T5.13)
deploy / deploy (push) Skipped
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / lint (push) Successful in 38s
CI Pipeline / canary (push) Successful in 49s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / lint (pull_request) Successful in 35s
CI Pipeline / best-practices (pull_request) Successful in 2s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 42s
CI Pipeline / type-check (pull_request) Successful in 27s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
Spec gate (headless) / spec-gate (pull_request) Successful in 4s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / unit-tests (pull_request) Successful in 4m54s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 3s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
Five separate dim system messages after every task/build response (budget, claims, growth, self-improve, plus the cron/queue echoes) spammed chat. New collect_post_response_signals() is a PURE headless collector with degrade-not-crash try blocks; the worker renders ONE line or silence. 6 frozen contracts: compose order [chat,task], resize semantics re-keyed, collector all-signals/silence/never-raises/cycle-multiple. 38 TUI/layout tests green; pyright error count unchanged at baseline 8.
2026-10-06 02:40:25 +01:00
Nick 004e5b3118 feat(tui): swap panes — chat LEFT, task RIGHT (#2465/T5.14)
Nick: chat-first feels natural. Compose yield order reversed (rune_tui.py compose), resize_left/resize_right actions re-keyed to the new visual positions (left=chat shrink now grows task), focus actions and all name-keyed query_one calls untouched (position-independent by design). Static source proof: yield order [chat, task]; 45 layout/TUI tests green.
2026-10-06 02:40:25 +01:00
conductor db15ae3650 chore(release): auto-bump version to 0.99.2 — earned by # (patch: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 4m53s
CI Pipeline / lint (push) Successful in 35s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
deploy / deploy (push) Successful in 2m31s
Promotion record: (unknown)
2026-10-06 02:28:19 +01:00
Nick d8ce21b76d fix(spine): the measured dichotomy decides — hints demoted to labeled fallbacks (#2461, Nick correction)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / lint (push) Successful in 38s
CI Pipeline / canary (push) Successful in 41s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m54s
Nick caught the deviation: module verdicts were substring-guessed from names (memory→rust, gitea→go) with a silent rust default. Authority order now: the measured classification map (import-evidence) decides FIRST for every module; hint hits are labeled "(name hint)" so provenance is visible; unmeasured+unhinted modules are "unclassified" (12), never a guessed rust. Store rebuilt: 106 rust / 45 go measured, 33+7 hint-labeled, 23 test-infra, 12 honest unclassified. Battery 95 green (test updated to pin the authority contract).
2026-10-06 02:28:16 +01:00
Nick d4d43dbf67 merge: spine_language tests (the new-module henxel repair)
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / lint (push) Successful in 38s
CI Pipeline / canary (push) Successful in 46s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Canceled after 4m41s
deploy / deploy (push) Failing after 15m4s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
2026-10-06 02:07:44 +01:00
Nick 8a6c950140 test(spine_language): the carved transforms ship WITH tests (#2461 new-module henxel)
CI red at d67fc46: spine_language.py crossed the new-module henxel with zero coverage. Eight contracts: measured-map read + graceful degrade, kind-default verdicts, TUI/hints, subsystem member-majority, unqualified-discovery honesty (candidate stays DECLARED), legacy-ID normalization with edge re-pointing, and the closed-contract-only gather law. 8/8 green. Also: construction_commands dispatch WIP stashed on its own branch (slice 2, next).
2026-10-06 02:04:19 +01:00
Nick d67fc46581 chore(rebase): refresh store/rebase inventory + classification for the 6 post-W0 modules (#2461 close-out)
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / lint (push) Failing after 36s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / canary (push) Successful in 46s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Failing after 3m27s
The W0 map had drifted (174 vs 180 files): cc_loader/sc_loader/mr_loader/mems_loader (FFI kernel membranes → RUST), spine_language (deterministic carve → RUST), __init__ (metadata reads) now carry evidence-backed side records and measured function/line counts. spine_language._classification_sides() — the runtime reader — sees 180 entries; spine battery green.
2026-10-06 01:40:56 +01:00
conductor 84b8d6b215 chore(release): auto-bump version to 0.99.1 — earned by # (patch: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
deploy / deploy (push) Failing after 11s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / lint (push) Failing after 36s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 40s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / required-checks (push) Failing after 1s
Promotion record: (unknown)
2026-10-06 01:22:12 +01:00
Nick 7f5d57236a fix(ci): 0.99.0 CI repair — silent-handler annotations + spine_language umbrella mapping (#2461)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 3s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / lint (push) Failing after 40s
CI Pipeline / canary (push) Successful in 47s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 5m0s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Failing after 38s
The 0.99.0 bump ran CI against the delegation code before the annotations landed: BLE001 345->349, S110 75->81 (my new kernel-failure fallbacks), plus spine_language unmapped in the umbrella manifest (test_umbrella_impact) and the resulting spine-rebuild membership diff (rebuild-neutrality). All four new fallbacks carry intentional-silence noqa annotations per the ratchet rule (count now exactly 345/75 — baseline UNCHANGED, ledger honest); spine_language mapped into perception next to spine; store rebuilt so the membership edge and language stamps are in the committed store. 127 tests green incl. the four CI-red surfaces.
2026-10-06 01:22:05 +01:00
conductor bda07c68ee chore(release): auto-bump version to 0.99.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 3s
deploy / deploy (push) Failing after 3m25s
CI Pipeline / unit-tests (push) Failing after 4m55s
CI Pipeline / lint (push) Failing after 24s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 42s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
Promotion record: (unknown)
2026-10-06 00:11:25 +01:00
Nick c5be22be09 feat(cognition): witness/safety/abstraction kernel delegation + regex_lite faithful-subset rewrite (#2461 W3.4, #2465 adjacency)
CI Pipeline / lint (push) Canceled after 0s
CI Pipeline / unit-tests (push) Canceled after 0s
CI Pipeline / go-surface (push) Canceled after 0s
CI Pipeline / canary (push) Canceled after 0s
CI Pipeline / best-practices (push) Canceled after 0s
CI Pipeline / documentation (push) Canceled after 0s
CI Pipeline / type-check (push) Canceled after 0s
CI Pipeline / gitea-offline (push) Canceled after 0s
CI Pipeline / required-checks (push) Canceled after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Canceled after 0s
Auto-version and Release / release (push) Successful in 4s
deploy / deploy (push) Failing after 5m4s
The W3.4 kernels existed but the Python publics still ran Python. Now: witness extract_topic/detect_signals delegate through the _stopwords()/_tables() gather seams (PATTERN-TABLE GATHER-SEAM LAW) with _py_ oracles; abstraction extract_facts gains the deterministic kernel FALLBACK when the LLM returns nothing; tier_manager was already wired; the RUNE_COGNITION_CORE=python pin is now honored by a SHARED cc_loader.core() probe (the four module-local probes silently ignored it). The canary matrix caught a REAL kernel bug: regex_lite dropped \b anchors as literal b chars so every word-boundary row silently missed (bwrongb never appears in text); rewritten as alternatives-expansion + segment-variant DFS gap-walk; 34-row matrix judged against REAL Python re shows 0 mismatches. canary_growth_pins 27/27 x5 both engine modes; canary_unbounded 14/14; per-row fixtures carry re-truth, not hand labels (a lying fixture is worse than uncovered).
2026-10-06 00:05:54 +01:00
conductor 4d6fec3d17 chore(release): auto-bump version to 0.98.0 — earned by # (minor: converged release (push-to-master bump))
CI Pipeline / lint (push) Canceled after 0s
CI Pipeline / unit-tests (push) Canceled after 0s
CI Pipeline / go-surface (push) Canceled after 0s
CI Pipeline / canary (push) Canceled after 0s
CI Pipeline / best-practices (push) Canceled after 0s
CI Pipeline / documentation (push) Canceled after 0s
CI Pipeline / type-check (push) Canceled after 0s
CI Pipeline / gitea-offline (push) Canceled after 0s
CI Pipeline / required-checks (push) Canceled after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Canceled after 0s
Auto-version and Release / release (push) Canceled after 0s
deploy / deploy (push) Failing after 5m5s
Promotion record: (unknown)
2026-10-06 00:01:45 +01:00
conductor 15dbbc562a chore(release): auto-bump version to 0.98.0 — earned by # (minor: converged release (push-to-master bump))
CI Pipeline / lint (push) Canceled after 0s
CI Pipeline / unit-tests (push) Canceled after 0s
CI Pipeline / go-surface (push) Canceled after 0s
CI Pipeline / canary (push) Canceled after 0s
CI Pipeline / best-practices (push) Canceled after 0s
CI Pipeline / documentation (push) Canceled after 0s
CI Pipeline / type-check (push) Canceled after 0s
CI Pipeline / gitea-offline (push) Canceled after 0s
CI Pipeline / required-checks (push) Canceled after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Canceled after 0s
Auto-version and Release / release (push) Successful in 2s
deploy / deploy (push) Canceled after 21s
Promotion record: (unknown)
2026-10-05 23:56:19 +01:00
Nick 6eb5e06119 refactor(spine): carve the #2465 doc-level transforms into spine_language.py (#2461 keep-green)
Auto-version and Release / release (push) Successful in 3s
CI Pipeline / lint (push) Failing after 22s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 47s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Failing after 4m53s
deploy / deploy (push) Canceled after 4m40s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
spine.py crossed the 1200-line giant-file debt cap (1203) with the language-verdict addition — CI lint red. The three transforms (language placement, discovery-ID normalization, contract-discovery write-back + gatherer) move to spine_language.py intact, re-exported through spine for import-compat (structure unchanged: 256 entities, same verdicts; spine battery 87, canaries 19/19 + 21/21, henxels hold, spine.py back to 1034).
2026-10-05 23:53:33 +01:00
Nick 78e4750a77 feat(tier): tier_manager delegates get/promote/demote to the cognition_core kernels (#2461 W3.4 delegation owed)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / lint (push) Failing after 25s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 48s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Failing after 4m56s
CI Pipeline / required-checks (push) Failing after 1s
deploy / deploy (push) Failing after 15m3s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
The kernels and FFI landed in b0a682b but the Python publics still ran Python — the strangler breach this slice owed. Live probe caught the FFI-arg-shape defect: promote/demote take the FULL ENTRY (kernel recomputes current tier internally), not a tier string; passing a string silently returned threshold-default verdicts (promote cold went warm-to-hot WRONGLY via defaults, demote rock went cold ignoring rock protection). 12-case kernel==oracle sweep green: wash>=20, recency hot/warm/cold, naive-timestamp parity trap, rock protection. PY oracle bodies kept; RUNE_COGNITION_CORE=python pins fallback; canary_growth_pins 26/26 both engines; canary_unbounded 14/14.
2026-10-05 23:50:11 +01:00
conductor c3948bae98 chore(release): auto-bump version to 0.97.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 3s
deploy / deploy (push) Failing after 15m3s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 3s
CI Pipeline / lint (push) Failing after 37s
CI Pipeline / unit-tests (push) Successful in 4m59s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / required-checks (push) Failing after 1s
Promotion record: (unknown)
2026-10-05 23:48:25 +01:00
Nick b8184a0f01 chore(spine): store rebuild carries subsystem language verdicts (#2465)
Auto-version and Release / release (push) Successful in 3s
CI Pipeline / lint (push) Failing after 36s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / canary (push) Successful in 47s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / type-check (push) Successful in 31s
CI Pipeline / unit-tests (push) Successful in 5m5s
deploy / deploy (push) Failing after 15m4s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
2026-10-05 23:47:58 +01:00
Nick 469b91f217 feat(spine): subsystem language verdicts from member majority (#2465 addition 3)
The five unassessed subsystems are containers: their language derives from member modules measured sides (classification.json, the W0 dichotomy map, rust and go counts carried in the verdict text). Unclassified members noted rather than guessed; unreadable classification degrades to unassessed. Spine canaries 19/19 and 21/21, spine battery 87 green.
2026-10-05 23:47:55 +01:00
Nick bb960b1656 test(gitea): canary the numeric-ID stale-label removal (#2467)
Auto-version and Release / release (push) Successful in 3s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / lint (push) Successful in 37s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / canary (push) Successful in 46s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 6m59s
Replace the obsolete removeLabel(name) pattern assertion with the actual Gitea /labels/{id} request, check ID lookup under the 404 idempotency guard, and require real P0–P3 managed labels. Local canary 39/39; workflow JS regression passes.
2026-10-05 22:22:53 +01:00
conductor 38c76a0c29 chore(release): auto-bump version to 0.96.1 — earned by # (patch: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
deploy / deploy (push) Failing after 39s
CI Pipeline / unit-tests (push) Successful in 5m2s
CI Pipeline / lint (push) Successful in 36s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Failing after 46s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
Promotion record: (unknown)
2026-10-05 22:15:03 +01:00
Nick 3186566514 fix(gitea): reconcile priority labels by numeric Gitea ID (#2467)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 3s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / lint (push) Successful in 40s
CI Pipeline / canary (push) Failing after 46s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 5m0s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 3s
deploy / deploy (push) Failing after 6m1s
Issue #2467 carried both P0 and P2 because name-based label DELETE returned 404 and the workflow silently ignored it. Use the numeric ID API, enforce exactly one priority, clear stale unprioritized flags, and execute the workflow JavaScript against a Gitea-compatible fake in regression tests.
2026-10-05 22:14:47 +01:00
Nick 24d14ff8e1 fix(spine): preserve candidate discoveries without inventing module IDs (#2465)
Migrate 22 malformed contract-discovery IDs to construction-surface, retain evidence/edges, keep candidates DECLARED, unify cold/warm language projection, and refresh the pinned aiohttp lock. Red regression tests precede the fix; local full suite 2301 passed, spine canaries 19/19 and 21/21.
2026-10-05 22:14:46 +01:00
conductor 6d0d455033 chore(release): auto-bump version to 0.96.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
deploy / deploy (push) Failing after 29s
CI Pipeline / unit-tests (push) Failing after 4m54s
CI Pipeline / lint (push) Failing after 20s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Failing after 47s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / required-checks (push) Failing after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
Promotion record: (unknown)
2026-10-05 19:34:11 +01:00
Nick b0a682b61f feat(cognition): R2 W3.4 — tier/witness/safety/abstraction kernels + protocol upgrade (#2461, #2465)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / lint (push) Failing after 25s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / canary (push) Failing after 41s
CI Pipeline / unit-tests (push) Failing after 4m50s
CI Pipeline / required-checks (push) Failing after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
deploy / deploy (push) Failing after 5m42s
Contract BUILDER-2026-10-05T12:03:34Z-cli — FIRST SLICE under the 90/100
verification law (64172d8).

Kernels (cognition_core/broker.rs):
- tier_get/promote/demote: thresholds+now injected (no-clock); wash>=20
  gate; rock immobility on demote; naive/malformed → designed fallback
- witness: extract_topic (word-run + stopwords-as-data), detect_signals
  (error/correction/completion/topic-drift/commitment/contradiction/
  preference/urgency/learning; pattern tables travel as data; the regex-
  lite subset is faithful to the tables' shapes)
- safety: get_params projection, update_pattern bump/new-row semantics
- abstraction: extract_facts sentence/content-word projection
- crate-level probe tests (parse_probe.rs: aware parse, epoch, tier recency)

Protocol upgrade (issue #2465) — three additions to the machine itself:
1. PER-CONTRACT MINI-DOC: construction_projection.mini_doc() emits the
   LLM quick-lookup page (what was built / connections / how to update)
   per closed contract; close() writes it to store/scaffold/docs/<cid>.md
2. SPINE WRITE-BACK: spine.build() now consumes closed contracts'
   discovered entities (expected_new_observed + candidate corrections) —
   the spine learns what construction actually built (256 entities now)
3. LANGUAGE VERDICTS: every spine entity carries identities.language
   (198 rust / 31 go / 6 tui / 5 unassessed); other projects get the
   fit assessment at classification

Also: one lost FFI block restored (the stash dance dropped
cc_tier_*/cc_witness_*/cc_safety_*/cc_abstraction_* — the battery
caught it: undefined symbol).

Gates: canary_growth_pins 26/26 x3, persona 18/18, cognition_core
38/38, suite 2299/0, ruff clean, type ratchet PASS, henxels all-hold.
2026-10-05 19:34:05 +01:00
conductor ab18540d7e chore(release): auto-bump version to 0.95.1 — earned by # (patch: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
deploy / deploy (push) Failing after 24s
CI Pipeline / unit-tests (push) Successful in 5m22s
CI Pipeline / lint (push) Failing after 21s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
Promotion record: (unknown)
2026-10-05 19:06:06 +01:00
Nick f489467e1b fix(ci): the priority gate's demand is now programmatically satisfied
Auto-version and Release / release (push) Successful in 17s
CI Pipeline / go-surface (push) Successful in 8s
CI Pipeline / best-practices (push) Successful in 3s
CI Pipeline / documentation (push) Successful in 4s
CI Pipeline / lint (push) Failing after 28s
CI Pipeline / gitea-offline (push) Successful in 18s
CI Pipeline / type-check (push) Successful in 31s
CI Pipeline / canary (push) Successful in 47s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / required-checks (push) Failing after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Failing after 6m8s
Nick's catch (2026-10-05): the auto-label bot highlighted that issues
carry priority only in their titles — the PRIORITY GATE job demanded
P0-P3 labels but nothing ever ASSIGNED them programmatically. The title
inference even used a dead label ('priority: high', normalized away
2026-09-04).

- auto-label's priority inference re-implemented in the gate's own
  namespace: title prefix \bP([0-3])\b first, then keyword inference
  (spine/critical/urgent -> P0; broken/fix/repair/defect -> P1;
  kernel/port/refactor/improve -> P2; benchmark/measurement/deferred ->
  P3); managedLabels now carry the REAL P-labels
- paired with the custodian fix: create_issue assigns the P-label at
  FILING (no issue ever lands unprioritized)
- full open-issue set backfilled (2461-2466, 2455/2459) and the live
  probe (#2466, self-verifying) closed after verifying P1 landed
  at filing
2026-10-05 19:05:38 +01:00
Nick 64172d8675 docs(plan): the 90/100 verification law (Nick 2026-10-05)
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / lint (push) Successful in 35s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 4m53s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 3m47s
- 100% branch coverage on the deterministic Rust kernels (achievable,
  exhaustive via parity matrices)
- ≥90% per-slice changed-lines working bar, aiming higher per slice
- floor ratchet climbs after clean waves (70->76->84->90)
- honest fixtures only — a lying-fixture branch is worse than uncovered
- assertion quality counts: value-verifying asserts only
2026-10-05 12:58:18 +01:00
conductor 8e75414907 chore(release): auto-bump version to 0.95.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 4m51s
CI Pipeline / lint (push) Successful in 33s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 3s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 3m15s
Promotion record: (unknown)
2026-10-05 12:50:38 +01:00
Nick 7a9d823792 feat(cognition): R2 W3.3 kernels in cognition_core (broker.rs: drift_check + identity_prompt assembly + growth near_dup/profile + pins recall/projection)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 3s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / lint (push) Successful in 38s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 4m57s
CI Pipeline / required-checks (push) Successful in 0s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m50s
Missing from the previous commit's staged set (the harness caught it):
the full W3.3 kernel block now lands. All parity walls verified:
canary_growth_pins 9/9, canary_persona 18/18, canary_cognition_core
38/38, suite 2298/0, diff-cover 72%.
2026-10-05 12:50:33 +01:00
Nick 98b5a73ed1 feat(cognition): R2 W3.3 — identity/growth/pins kernels + full coverage (72%)
- identity_anchors: check_drift delegates (pattern table stays the
  module's data authority via _pattern_triples); _py_check_drift oracle
  covers the four prefix families; drift parity proven on the full
  table (31 patterns) + the full-text multi-class case
- growth_delta: _near_dup/growth_profile delegate; oracle accepts delta
  dicts AND raw strings; near-dup kernel corrected to the REAL
  semantics: prof-key = strip-punct lowercase words >4 chars, split at
  |A∩B|/max(|A|,|B|) >= 0.25 (NOT a jaccard-min heuristic)
- pins: recall kernel projects via _project parity (details-blob parse,
  defaults, 'reason' field); empty-context abstention frozen
- probe branches exercised honestly: pinned-fallback + ImportError via
  the from-import resolution path (the from-import goes through the
  package attribute, not sys.modules — the PEP resolution law frozen in
  the battery)
- reflect malformed-JSON + [:3] cap + apply budget cut frozen
- suite 2295/0; diff-cover 72% (floor 70); canaries 9/9+18/18+38/38
  x3; henxels hold; ruff/type clean
2026-10-05 12:50:33 +01:00
conductor 4a9d8001c1 chore(release): auto-bump version to 0.94.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 4m52s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 45s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 3s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 2m31s
Promotion record: (unknown)
2026-10-05 09:00:47 +01:00
Nick 538bbeb821 feat(cognition): R2 W3.2 — persona_gate decision kernels (cognition_core)
Auto-version and Release / release (push) Successful in 4s
CI Pipeline / go-surface (push) Successful in 4s
CI Pipeline / best-practices (push) Successful in 3s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / lint (push) Successful in 39s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 4m58s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m51s
Contract BUILDER-2026-10-05T07:19:27Z-cli (Wave 3 slice 2, #2461).

- cognition_core/broker.rs gains the persona-decision kernel:
  persona_lex (distinctive content words: punct strip, light plural
  stem, acronym preservation — 55-word stoplist), persona_overlap
  (intersection over min-size), persona_decide (engagement matrix:
  amplifier set, semantic gates 0.45/0.30/0.68, user-rule 0.4 bar,
  permissive/legacy-restrictive verdicts, _cite parity '[topic:pN] text')
- persona_gate.py: _lex/_overlap/decide delegate; semantic cosines
  gathered Python-side (embedder calls are IO — the membrane's
  discipline) and passed into the kernel; _py_ oracles are the
  load-bearing fallback
- FFI: cc_persona_lex/overlap/decide; loader extended
- canary_persona.py (canary-first red on every seam): 18/18 x3 —
  lex matrix incl. acronyms/3-char exclusions, decide engagement paths,
  citation format parity
- shim battery 35/35; suite 2294/0; ruff clean; type ratchet PASS;
  henxels all-hold
2026-10-05 09:00:43 +01:00
conductor cc3b3d81eb chore(release): auto-bump version to 0.93.0 — earned by # (minor: converged release (push-to-master bump))
Auto-version and Release / release (push) Successful in 3s
CI Pipeline / unit-tests (push) Successful in 5m31s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 43s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 3m7s
Promotion record: (unknown)
2026-10-05 08:43:51 +01:00
Nick eb01156d9f Merge branch 'master' of http://127.0.0.1:3000/conductor/rune into r2-wave2-memory-retrieval
Auto-version and Release / release (push) Successful in 3s
deploy / deploy (push) Skipped
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / lint (push) Failing after 39s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / gitea-offline (push) Successful in 15s
CI Pipeline / type-check (push) Successful in 40s
CI Pipeline / canary (push) Failing after 50s
CI Pipeline / unit-tests (push) Failing after 5m43s
CI Pipeline / required-checks (push) Failing after 7s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 8s
2026-10-05 08:43:19 +01:00
Nick 290d264f31 feat(cognition): R2 W3.1 — context_broker kernel + the surrogate-pair parser fix across all nine crates
Contract BUILDER-2026-10-05T07:19:27Z-cli, closed: module:context_broker
correctly_predicted; cognition_core expected_new_observed; cc_loader
surfaces honestly new (#2463 wave epic).

- cognition_core crate (zero-dep, no-clock): context_broker's four
  deterministic kernels — default_estimator (chars//4; utf16-length
  corruption caught — the canary's astral cases), default_budget,
  default_memory_budget (+cap), memory_disabled (env gate value-parsed)
- THE PARSER BUG (nine pyjson copies repaired): the surrogate-pair branch
  tested self.b[i+1..] for the second escape's backslash — but hex4 had
  already advanced i past the first escape's 'u+digits', so the correct
  guard window is [i..] not [i+1..]; and after the guard, i advanced +2
  leaving hex4 to read a shifted window ('bad \\u digits' on
  \\ud83c\\udfb8). Fixed: guard at [i..], pre-hex4 advance +1.
  Astral chars (emoji) now parse as ONE code point — char-count parity
  restored everywhere (estimator/chunk/norm)
- context_broker: four functions delegate (load-bearing _py_ oracles);
  the env gate is cross-checked Python-side (Python verdict stays
  authority)
- cc_loader: ctypes shim, CC_RUST_LIB file-form; battery-covered
- CI: crate builds in both jobs, CC_RUST_LIB envs, canary registered

Gates: canary 38/38 x3 + full seven-crate wall green, suite 2293/0,
type ratchet PASS, ruff clean, henxels all-hold, diff-cover 75%.
2026-10-05 08:43:19 +01:00
conductor 16c147dbee chore(release): auto-bump version to 0.92.2 — earned by #2460 (R2 W2.1: deterministic Rust memory-retrieval kernel)
Auto-version and Release / release (push) Successful in 2s
CI Pipeline / unit-tests (push) Successful in 4m54s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / canary (push) Successful in 38s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
deploy / deploy (push) Successful in 3m27s
Promotion record: http://127.0.0.1:3000/conductor/rune/pulls/2460
2026-10-05 07:57:54 +01:00
conductor 15cba0bb24 Merge pull request 'R2 W2.1: deterministic Rust memory-retrieval kernel' (#2460) from r2-wave2-memory-retrieval into master
Auto-version and Release / release (push) Failing after 3s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / lint (push) Successful in 36s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / canary (push) Successful in 49s
CI Pipeline / gitea-offline (push) Successful in 12s
CI Pipeline / unit-tests (push) Successful in 4m55s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m56s
2026-10-05 07:57:47 +01:00
Nick 1283b0bf94 fix(memory): W2.1 coverage 62->84 + pair-list contract harmonized
deploy / deploy (push) Skipped
CI Pipeline / go-surface (push) Successful in 5s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / lint (push) Successful in 39s
CI Pipeline / canary (push) Successful in 48s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / go-surface (pull_request) Successful in 3s
CI Pipeline / lint (pull_request) Successful in 35s
CI Pipeline / best-practices (pull_request) Successful in 1s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / canary (pull_request) Successful in 40s
CI Pipeline / type-check (pull_request) Successful in 28s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
Spec gate (headless) / spec-gate (pull_request) Successful in 4s
CI Pipeline / unit-tests (push) Successful in 4m56s
CI Pipeline / unit-tests (pull_request) Successful in 4m53s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / required-checks (pull_request) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 1s
Auto-version and Release / release (pull_request) Successful in 5s
- chunk gather + projection now speak the W2.1 pair-list contract
  consistently on BOTH engines (fusion['ranks'] is [[rowid, rrf], ...];
  dict-form still accepted for backward callers)
- oracle-path tests: all three modes, abstention edges, malformed
  timestamps, hybrid accumulation, chunk SQL gather through a real
  fixture (vec-table absent by design; embed stubbed — vector execution
  stays Python per the W2.0 ruling)
- battery 32->32 tests extended; suite 2291/0; canary 75/75 x3;
  diff-cover 84% (floor 70)
2026-10-05 07:51:40 +01:00
Nick 1ee35d76c9 fix(memory): W2.1 coverage + stopword parity + chunk projection kernel
deploy / deploy (push) Skipped
Spec gate (headless) / spec-gate (pull_request) Successful in 5s
CI Pipeline / lint (push) Successful in 34s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 44s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / type-check (push) Successful in 27s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / lint (pull_request) Successful in 34s
CI Pipeline / go-surface (pull_request) Successful in 3s
CI Pipeline / canary (pull_request) Successful in 42s
CI Pipeline / best-practices (pull_request) Successful in 1s
CI Pipeline / documentation (pull_request) Successful in 2s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
CI Pipeline / type-check (pull_request) Successful in 28s
CI Pipeline / unit-tests (push) Failing after 4m53s
CI Pipeline / unit-tests (pull_request) Failing after 4m54s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / required-checks (pull_request) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
- battery: delegation + projection coverage for the kernel consumers
  (29-test shim battery; CI's 45% was the pre-extension tree)
- chunk projection (chunk_recall tail) moved into the kernel:
  RRF-desc order, text[:400] chars, budget cap, page/room/default
  semantics — canary 75/75 x3
- stopword list AST-extracted exactly (51 words incl. needs/wants/likes)
- memory_store: recall/fused/association/chunk kernels delegate with
  _py_ oracles as load-bearing fallback

Gates: canary 75/75 x3, shim battery 29/29, suite 2286/0, ruff clean,
type ratchet PASS, henxels all-hold. PR 2460 updated with the
propagation evidence line.
2026-10-05 07:20:38 +01:00
Nick e8daf78eaa Merge remote-tracking branch 'gitea/master' into r2-wave2-memory-retrieval
deploy / deploy (push) Skipped
Spec gate (headless) / spec-gate (pull_request) Successful in 5s
CI Pipeline / go-surface (push) Successful in 5s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 29s
CI Pipeline / lint (push) Successful in 39s
CI Pipeline / canary (push) Successful in 50s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / go-surface (pull_request) Successful in 2s
CI Pipeline / unit-tests (pull_request) Failing after 20s
CI Pipeline / best-practices (pull_request) Successful in 2s
CI Pipeline / documentation (pull_request) Successful in 1s
CI Pipeline / lint (pull_request) Successful in 36s
CI Pipeline / gitea-offline (pull_request) Successful in 13s
CI Pipeline / canary (pull_request) Successful in 46s
CI Pipeline / type-check (pull_request) Successful in 29s
CI Pipeline / required-checks (pull_request) Failing after 0s
CI Pipeline / CI Pipeline / notify-event-bridge (pull_request) Successful in 2s
Auto-label / priority-gate (pull_request) Skipped
Auto-label / auto-label (pull_request) Successful in 1s
CI Pipeline / unit-tests (push) Failing after 4m57s
CI Pipeline / required-checks (push) Failing after 2s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
2026-10-05 06:39:03 +01:00
Nick 19976c310c feat(memory): R2 W2.1 — deterministic Rust memory-retrieval kernel (#2458)
deploy / deploy (push) Skipped
CI Pipeline / go-surface (push) Successful in 5s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 1s
CI Pipeline / type-check (push) Successful in 30s
CI Pipeline / lint (push) Successful in 41s
CI Pipeline / canary (push) Successful in 50s
CI Pipeline / gitea-offline (push) Successful in 14s
CI Pipeline / unit-tests (push) Failing after 5m18s
CI Pipeline / required-checks (push) Failing after 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
Contract BUILDER-2026-10-04T20:10:25Z-cli, closed: memory_store and
memory_selector correctly_predicted; kernel expected_new_observed; shim
surfaces honestly new. Stacked on W2.0 (merged de54453).

- memory_retrieval crate (zero-dep, no-clock, rlib+cdylib+bin): the
  retrieval transform family in ONE kernel surface — map_reduce,
  position_aware, fts_query_conjunctive (51-word stoplist extracted via
  AST, no transcription drift), chunk_text (byte-vs-char law honored),
  norm_key, plus the extracted kernels: rank_fusion (RRF/lexical
  normalization/mode selection), score_recall_rows (metadata blend +
  mode-specific QPP abstention), merge_association_rows (association
  projection), fuse_results (fact/research projection + per-kind
  min-max scale alignment)
- PARITY-PLUS-IMPROVEMENT proven: recall's N+1 (per-candidate entry
  reads + repeated DF probes) ELIMINATED — rows batch through the W2.0
  read boundary once and the kernel runs per retrieval stage
- Parity trap frozen: naive timestamps take Python's designed
  TypeError->recency=1.0 fallback (parse_iso now refuses naive, exactly
  like aware-vs-naive subtraction) — the 34-case matrix caught this
- UTF-8 transport fix: ensure_ascii=True surrogate pairs corrupt astral
  chars (emoji) in char-count semantics — direct UTF-8 transport, frozen
- both _py_ oracles and delegating publics; RUNE_RETRIEVAL_CORE=python
  pins the fallback
- CI: crate builds in both jobs, MR_RUST_LIB envs, canary registered

Gates: canary 72/72 x3, suite 2286/0, type ratchet PASS, ruff clean,
henxels all-hold. Store: 218 entities,
rust-crate:memory_retrieval modeled.
2026-10-05 06:38:57 +01:00
conductor e2430a9154 chore(release): auto-bump version to 0.92.1 — earned by #2457 (R2 W2.0: SQLite-backed zero-dep Rust read boundary)
Auto-version and Release / release (push) Successful in 3s
CI Pipeline / unit-tests (push) Successful in 4m48s
CI Pipeline / lint (push) Successful in 33s
CI Pipeline / go-surface (push) Successful in 2s
CI Pipeline / canary (push) Successful in 42s
CI Pipeline / best-practices (push) Successful in 1s
CI Pipeline / documentation (push) Successful in 3s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 1s
deploy / deploy (push) Successful in 2m21s
Promotion record: http://127.0.0.1:3000/conductor/rune/pulls/2457
2026-10-05 01:56:56 +01:00
conductor de5445357e Merge pull request 'R2 W2.0: SQLite-backed zero-dep Rust read boundary' (#2457) from r2-wave2-memory-storage into master
Auto-version and Release / release (push) Failing after 3s
CI Pipeline / go-surface (push) Successful in 3s
CI Pipeline / best-practices (push) Successful in 2s
CI Pipeline / documentation (push) Successful in 2s
CI Pipeline / lint (push) Successful in 37s
CI Pipeline / type-check (push) Successful in 28s
CI Pipeline / canary (push) Successful in 41s
CI Pipeline / gitea-offline (push) Successful in 13s
CI Pipeline / unit-tests (push) Successful in 4m52s
CI Pipeline / required-checks (push) Successful in 1s
CI Pipeline / CI Pipeline / notify-event-bridge (push) Successful in 2s
deploy / deploy (push) Successful in 5m51s
2026-10-05 01:56:51 +01:00
66 changed files with 26571 additions and 8568 deletions

No files matched your search

BIN
View File
Binary file not shown.
+53 -9
View File
@@ -23,12 +23,13 @@ jobs:
const labels = (issue.labels || []).map(l => l.name);
const priorities = ['P0 — critical', 'P1 — high', 'P2 — medium', 'P3 — low'];
const has = labels.filter(l => priorities.includes(l));
if (has.length >= 1) {
if (has.length === 1) {
// Prioritized — clear the flag if it was set.
if (labels.includes('unprioritized')) {
await github.rest.issues.removeLabel({
await github.request('DELETE /repos/{owner}/{repo}/issues/{issue_number}/labels/{id}', {
owner: context.repo.owner, repo: context.repo.repo,
issue_number: issue.number, name: 'unprioritized',
issue_number: issue.number,
id: issue.labels.find(l => l.name === 'unprioritized').id,
}).catch(e => { if (e.status !== 404) throw e; });
}
return;
@@ -72,7 +73,8 @@ jobs:
const managedLabels = new Set([
'memory', 'governance', 'identity', 'growth',
'perception', 'infrastructure', 'life', 'custodian',
'priority: high', 'bug', 'feature', 'research',
'bug', 'feature', 'research',
'P0 — critical', 'P1 — high', 'P2 — medium', 'P3 — low',
]);
// Type label: DECLARED over GUESSED. The template spine
@@ -135,9 +137,31 @@ jobs:
desiredLabels.add('custodian');
}
// Priority labels
if (text.includes('urgent') || text.includes('critical') || text.includes('broken')) {
desiredLabels.add('priority: high');
// Priority labels (2026-10-05: PROGRAMMATIC P-ASSIGNMENT —
// the gate demanded P0-P3 labels but nothing assigned them;
// the dead 'priority: high' label is gone per the 2026-09-04
// normalization). Assignment from the TITLE prefix first
// ([P1]/P1:/priority=...), then keyword inference using the
// gate's own rule set (the scale lives in ONE place — the
// priority-gate job above).
const pMatch = title.match(/\bP([0-3])\b/);
const priorityLabelNames = ['P0 — critical', 'P1 — high', 'P2 — medium', 'P3 — low'];
if (pMatch) {
desiredLabels.add(priorityLabelNames[Number(pMatch[1])]);
} else if (text.includes('urgent') || text.includes('critical') ||
text.includes('spine') || text.includes('blocks other work')) {
desiredLabels.add(priorityLabelNames[0]); // P0 — critical
} else if (text.includes('broken') || text.includes('fix') ||
text.includes('repair') || text.includes('defect') ||
text.includes('real defect') || text.includes('money')) {
desiredLabels.add(priorityLabelNames[1]); // P1 — high
} else if (text.includes('improve') || text.includes('consolidat') ||
text.includes('refactor') || text.includes('kernel') ||
text.includes('port')) {
desiredLabels.add(priorityLabelNames[2]); // P2 — medium
} else if (text.includes('benchmark') || text.includes('measurement') ||
text.includes('deferred')) {
desiredLabels.add(priorityLabelNames[3]); // P3 — low
}
const issueNumber = context.payload.issue?.number || context.payload.pull_request?.number;
@@ -147,6 +171,7 @@ jobs:
issue_number: issueNumber,
});
const currentLabels = new Set(current.data.map(label => label.name));
const currentLabelIds = new Map(current.data.map(label => [label.name, label.id]));
const staleManaged = [...currentLabels].filter(
label => managedLabels.has(label) && !desiredLabels.has(label)
);
@@ -156,11 +181,14 @@ jobs:
for (const name of staleManaged) {
try {
await github.rest.issues.removeLabel({
// Gitea's DELETE /labels/{id} requires the numeric label ID.
// Octokit's GitHub-style removeLabel(name) returned 404 and
// left stale priority labels behind (#2467: P0 AND P2).
await github.request('DELETE /repos/{owner}/{repo}/issues/{issue_number}/labels/{id}', {
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issueNumber,
name,
id: currentLabelIds.get(name),
});
} catch (error) {
if (error.status !== 404) {
@@ -178,5 +206,21 @@ jobs:
labels: missingDesired,
});
}
// The priority gate can flag a duplicate before this job
// reconciles it. Clear the flag only AFTER verifying exactly one
// surviving P-label against Gitea's current state.
const reconciled = await github.rest.issues.listLabelsOnIssue({
owner: context.repo.owner, repo: context.repo.repo,
issue_number: issueNumber,
});
const actual = reconciled.data;
const activePriority = actual.filter(l => priorityLabelNames.includes(l.name));
const flag = actual.find(l => l.name === 'unprioritized');
if (activePriority.length === 1 && flag) {
await github.request('DELETE /repos/{owner}/{repo}/issues/{issue_number}/labels/{id}', {
owner: context.repo.owner, repo: context.repo.repo,
issue_number: issueNumber, id: flag.id,
});
}
console.log(`Removed managed labels: ${staleManaged.join(', ') || 'none'}`);
console.log(`Added managed labels: ${missingDesired.join(', ') || 'none'}`);
+5
View File
@@ -80,6 +80,7 @@ jobs:
TC_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libtoken_counting.so
SC_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libscaffold_core.so
MEMS_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libmemory_storage.so
MR_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libmemory_retrieval.so
steps:
# actions/checkout v4.2.2, pinned to the audited upstream tag commit.
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
@@ -133,6 +134,7 @@ jobs:
cargo build --release --manifest-path src/rust/token_counting/Cargo.toml
cargo build --release --manifest-path src/rust/scaffold_core/Cargo.toml
cargo build --release --manifest-path src/rust/memory_storage/Cargo.toml
cargo build --release --manifest-path src/rust/memory_retrieval/Cargo.toml
- name: Test with coverage (global floor + changed-lines ratchet)
run: |
# #149 coverage ratchet — both floors live in .coveragerc; raise,
@@ -182,6 +184,7 @@ jobs:
TC_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libtoken_counting.so
SC_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libscaffold_core.so
MEMS_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libmemory_storage.so
MR_RUST_LIB: /tmp/rune-ci-target-${{ github.run_id }}/release/libmemory_retrieval.so
steps:
# actions/checkout v4.2.2, pinned to the audited upstream tag commit.
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
@@ -220,6 +223,7 @@ jobs:
cargo build --release --manifest-path src/rust/token_counting/Cargo.toml
cargo build --release --manifest-path src/rust/scaffold_core/Cargo.toml
cargo build --release --manifest-path src/rust/memory_storage/Cargo.toml
cargo build --release --manifest-path src/rust/memory_retrieval/Cargo.toml
- name: Run canary suite
run: |
FAILED=0
@@ -257,6 +261,7 @@ jobs:
src/rust/token_counting/canary_token_counting.py \
src/rust/scaffold_core/canary_scaffold_core.py \
src/rust/memory_storage/canary_memory_storage.py \
src/rust/memory_retrieval/canary_memory_retrieval.py \
src/rune/canary_unbounded.py \
src/rune/canary_full_system.py \
src/rune/canary_native.py; do
+1
View File
@@ -14,3 +14,4 @@ state/
# Runtime artifacts (cwd-local event journal + capability index)
index/
journal/
src/rust/*/target/
+1 -1
View File
@@ -1,6 +1,6 @@
# Rune
**Current release: v0.92.0**
**Current release: v0.99.5**
**Rune is a persistent personal agent designed to accumulate experience, develop reusable competence, and remain recognisably the same agent even when its underlying foundation model changes.**
+316 -312
View File
@@ -1,315 +1,319 @@
{
"_comment": "GENERATED by rune.spine \u2014 compatibility view for legacy umbrella consumers. DO NOT EDIT: structural truth lives in store/spine/current.json; edits here are flagged by spine drift.",
"_generated_by_spine": true,
"generated_at": "2026-09-16T18:23:38Z",
"umbrellas": {
"capability": {
"description": "Tool selection and execution authority",
"modules": [
"adaptive_router",
"builder_bridge",
"builder_bridge_cli",
"capability_broker",
"connection_pool",
"core_server",
"cs_loader",
"evidence_probe",
"forge",
"forge_client",
"intent_continuity",
"local_tool_runtime",
"message_queue",
"native_units",
"openai_compat_transport",
"provider_context",
"recall_uplift",
"route_risk_flags",
"tool_executor",
"tool_protocol"
],
"depends_on": [
"memory"
],
"mirrors": [],
"canaries": [
"canary_native",
"canary_p0_05",
"canary_p1_01",
"canary_rune_entry",
"canary_rune_serve"
],
"go_surfaces": [
"rune-entry"
],
"configs": [],
"rust_crates": [
"capability_scoring"
]
},
"governance": {
"description": "Quality control, drift detection, promotion, audit",
"modules": [
"audit_ledger",
"build_pipeline_policy",
"claim_audit",
"contracts",
"curator",
"drift_core",
"drift_ledger",
"drift_observability",
"failure_auto_filer",
"programme_gates",
"sc_loader"
],
"depends_on": [],
"mirrors": [],
"canaries": [
"canary_full_system",
"canary_schema_migration",
"canary_audit_ledger",
"canary_spine_meta"
],
"rust_crates": [
"evidence_provenance",
"scaffold_core"
],
"configs": [
".coveragerc",
"go-version.txt",
"lint-baseline.json",
"pyright-baseline.json"
]
},
"growth": {
"description": "Learning and improvement",
"modules": [
"autonomy_loop",
"cognitive_loop",
"dream_cycle",
"elastic_cognition",
"goal",
"growth_delta",
"growth_simulator",
"self_improve",
"subconscious_pass"
],
"depends_on": [
"governance",
"memory"
],
"mirrors": [],
"canaries": [
"canary_full_system"
]
},
"identity": {
"description": "Who the agent is \u2014 persona, voice, anchors",
"modules": [
"behavior",
"identity_anchors",
"persona_definition",
"persona_gate",
"prompt_sync",
"voice_hybrid",
"voice_injector",
"voice_sync",
"voicebox"
],
"depends_on": [
"governance"
],
"mirrors": [],
"canaries": [
"canary_full_system"
]
},
"inference": {
"description": "Model routing and outbound requests",
"modules": [
"inference_trace",
"model_connect",
"model_profiles",
"model_registry",
"model_routing",
"provider_budget",
"provider_registry",
"response_adapter",
"standardized_providers",
"tc_loader",
"token_optimizer"
],
"depends_on": [
"capability"
],
"mirrors": [],
"canaries": [
"canary_p1_02",
"canary_p1_06",
"canary_resource_authority"
],
"rust_crates": [
"token_counting"
]
},
"memory": {
"description": "Storing, retrieving, and managing knowledge",
"modules": [
"abstraction",
"cache",
"drift_cache",
"drift_compression",
"ffi_query_memory_smoke",
"graph_memory",
"graph_shard_bridge",
"memory_consolidation",
"memory_env",
"memory_selector",
"memory_store",
"mems_loader",
"ms_loader",
"query_memory",
"recall_router",
"retrieval_benchmark",
"shard_manager",
"tier_manager",
"warm_neuron_store"
],
"depends_on": [
"governance"
],
"mirrors": [],
"canaries": [
"canary_full_system",
"canary_memory_synthesis",
"canary_query_memory"
],
"rust_crates": [
"memory_scoring",
"memory_storage",
"query_memory"
]
},
"orchestration": {
"description": "Task lifecycle, operator, TUI presentation",
"modules": [
"auto_detect",
"build_mode",
"build_orchestrator",
"chat_bubble",
"cron_engine",
"custodian",
"dependency_tracker",
"event_bus",
"event_envelope",
"gitea_auth",
"gitea_pipeline",
"gitea_provision",
"hook_engine",
"message_widgets",
"microkernel",
"night_mode",
"outcome_ledger",
"parallel_processor",
"pins",
"progressive_escalation",
"rune_graphic",
"rune_operator",
"rune_profiler",
"rune_spinner",
"rune_tui",
"safety_override",
"sleep_time",
"subsystem_health",
"system_registry",
"task_gate",
"task_persist",
"tiered_executor",
"time_awareness",
"tui_transport",
"tui_validator",
"umbrella_update",
"verification_layer",
"warm_router",
"work_manager"
],
"depends_on": [
"capability",
"growth",
"identity",
"inference",
"perception"
],
"mirrors": [],
"canaries": [
"canary_cognitive_strata",
"canary_conversation_state",
"canary_gitea_pipeline",
"canary_orchestration_foundation",
"canary_p1_07",
"canary_surface_parity",
"canary_tui_drift",
"canary_tui_transport"
]
},
"perception": {
"description": "Input processing and context assembly",
"modules": [
"attention_capsule",
"auto_context",
"auto_tasks",
"behaviour_ledger",
"build_basis",
"capability_fit",
"capability_ledger",
"cognitive_budgeter",
"construction_activation",
"construction_commands",
"construction_decision",
"construction_depth",
"construction_intent",
"construction_interface",
"construction_mode",
"construction_pattern",
"construction_patterns_builtin",
"construction_projection",
"context_broker",
"context_pressure",
"drift_resume",
"event_wait",
"failure_recovery",
"graph_projection",
"impact_preview",
"iteration",
"layout_contract",
"programme_continuation",
"project_registry",
"release_notes",
"salience_gate",
"scaffold",
"spine",
"spine_loader",
"stage_guards",
"structural_migration",
"structural_model",
"structural_store",
"testing_mode",
"toolchain",
"tui_backlog",
"wait_guard",
"wait_guard_corpus",
"witness"
],
"depends_on": [
"memory"
],
"mirrors": [],
"canaries": [
"canary_context_broker",
"canary_full_system"
],
"rust_crates": [
"rune_spine"
]
}
"_comment": "GENERATED by rune.spine \u2014 compatibility view for legacy umbrella consumers. DO NOT EDIT: structural truth lives in store/spine/current.json; edits here are flagged by spine drift.",
"_generated_by_spine": true,
"generated_at": "2026-09-16T18:23:38Z",
"umbrellas": {
"capability": {
"canaries": [
"canary_native",
"canary_p0_05",
"canary_p1_01",
"canary_rune_entry",
"canary_rune_serve"
],
"configs": [],
"depends_on": [
"memory"
],
"description": "Tool selection and execution authority",
"go_surfaces": [
"rune-entry"
],
"mirrors": [],
"modules": [
"adaptive_router",
"builder_bridge",
"builder_bridge_cli",
"capability_broker",
"connection_pool",
"core_server",
"cs_loader",
"evidence_probe",
"forge",
"forge_client",
"intent_continuity",
"local_tool_runtime",
"message_queue",
"native_units",
"openai_compat_transport",
"provider_context",
"recall_uplift",
"route_risk_flags",
"tool_executor",
"tool_protocol"
],
"rust_crates": [
"capability_scoring"
]
},
"governance": {
"canaries": [
"canary_full_system",
"canary_schema_migration",
"canary_audit_ledger",
"canary_spine_meta"
],
"configs": [
".coveragerc",
"go-version.txt",
"lint-baseline.json",
"pyright-baseline.json"
],
"depends_on": [],
"description": "Quality control, drift detection, promotion, audit",
"mirrors": [],
"modules": [
"audit_ledger",
"build_pipeline_policy",
"cc_loader",
"claim_audit",
"contracts",
"curator",
"drift_core",
"drift_ledger",
"drift_observability",
"failure_auto_filer",
"programme_gates",
"sc_loader"
],
"rust_crates": [
"evidence_provenance",
"scaffold_core"
]
},
"growth": {
"canaries": [
"canary_full_system"
],
"depends_on": [
"governance",
"memory"
],
"description": "Learning and improvement",
"mirrors": [],
"modules": [
"autonomy_loop",
"cognitive_loop",
"dream_cycle",
"elastic_cognition",
"goal",
"growth_delta",
"growth_simulator",
"self_improve",
"subconscious_pass"
]
},
"identity": {
"canaries": [
"canary_full_system"
],
"depends_on": [
"governance"
],
"description": "Who the agent is \u2014 persona, voice, anchors",
"mirrors": [],
"modules": [
"behavior",
"identity_anchors",
"persona_definition",
"persona_gate",
"prompt_sync",
"voice_hybrid",
"voice_injector",
"voice_sync",
"voicebox"
]
},
"inference": {
"canaries": [
"canary_p1_02",
"canary_p1_06",
"canary_resource_authority"
],
"depends_on": [
"capability"
],
"description": "Model routing and outbound requests",
"mirrors": [],
"modules": [
"inference_trace",
"model_connect",
"model_profiles",
"model_registry",
"model_routing",
"provider_budget",
"provider_registry",
"response_adapter",
"standardized_providers",
"tc_loader",
"token_optimizer"
],
"rust_crates": [
"token_counting"
]
},
"memory": {
"canaries": [
"canary_full_system",
"canary_memory_synthesis",
"canary_query_memory"
],
"depends_on": [
"governance"
],
"description": "Storing, retrieving, and managing knowledge",
"mirrors": [],
"modules": [
"abstraction",
"cache",
"drift_cache",
"drift_compression",
"ffi_query_memory_smoke",
"graph_memory",
"graph_shard_bridge",
"memory_consolidation",
"memory_env",
"memory_selector",
"memory_store",
"mems_loader",
"mr_loader",
"ms_loader",
"query_memory",
"recall_router",
"retrieval_benchmark",
"shard_manager",
"tier_manager",
"warm_neuron_store"
],
"rust_crates": [
"memory_retrieval",
"memory_scoring",
"memory_storage",
"query_memory"
]
},
"orchestration": {
"canaries": [
"canary_cognitive_strata",
"canary_conversation_state",
"canary_gitea_pipeline",
"canary_orchestration_foundation",
"canary_p1_07",
"canary_surface_parity",
"canary_tui_drift",
"canary_tui_transport"
],
"depends_on": [
"capability",
"growth",
"identity",
"inference",
"perception"
],
"description": "Task lifecycle, operator, TUI presentation",
"mirrors": [],
"modules": [
"auto_detect",
"build_mode",
"build_orchestrator",
"chat_bubble",
"cron_engine",
"custodian",
"dependency_tracker",
"event_bus",
"event_envelope",
"gitea_auth",
"gitea_pipeline",
"gitea_provision",
"hook_engine",
"message_widgets",
"microkernel",
"night_mode",
"outcome_ledger",
"parallel_processor",
"pins",
"progressive_escalation",
"rune_graphic",
"rune_operator",
"rune_profiler",
"rune_spinner",
"rune_tui",
"safety_override",
"sleep_time",
"subsystem_health",
"system_registry",
"task_gate",
"task_persist",
"tiered_executor",
"time_awareness",
"tui_transport",
"tui_validator",
"umbrella_update",
"verification_layer",
"warm_router",
"work_manager"
]
},
"perception": {
"canaries": [
"canary_context_broker",
"canary_full_system"
],
"depends_on": [
"memory"
],
"description": "Input processing and context assembly",
"mirrors": [],
"modules": [
"attention_capsule",
"auto_context",
"auto_tasks",
"behaviour_ledger",
"build_basis",
"capability_fit",
"capability_ledger",
"cognitive_budgeter",
"construction_activation",
"construction_commands",
"construction_decision",
"construction_depth",
"construction_intent",
"construction_interface",
"construction_mode",
"construction_pattern",
"construction_patterns_builtin",
"construction_projection",
"context_broker",
"context_pressure",
"drift_resume",
"event_wait",
"failure_recovery",
"graph_projection",
"impact_preview",
"iteration",
"layout_contract",
"programme_continuation",
"project_registry",
"release_notes",
"salience_gate",
"scaffold",
"spine",
"spine_language",
"spine_loader",
"stage_guards",
"structural_migration",
"structural_model",
"structural_store",
"testing_mode",
"toolchain",
"tui_backlog",
"wait_guard",
"wait_guard_corpus",
"witness"
],
"rust_crates": [
"rune_spine"
]
}
}
}
+16 -1
View File
@@ -272,4 +272,19 @@ observations, fresh resume.
Release-note generator: LIVE-PROVEN (real Gitea, 10 releases). Backfill:
0.66.35→0.66.44 carrying historical-backfill provenance. Pre-0.66.35
history: skipped (weak evidence — honest limitation).
history: skipped (weak evidence — honest limitation).
## Contract discovery → spine (2026-10-05, #2465 CI correction)
The closed construction contract is the authority for discoveries. Spine
rebuild reads its observed entities and candidate corrections; it does not
claim a correction has been built. Qualified IDs such as
`rust-crate:cognition_core` keep their declared kind. Bare file paths,
test suites and other unqualified references become
`construction-surface:<reference>`, never `module`. An observed
surface may be PRESENT; a candidate stays DECLARED until independently
observed. Existing bad records are migrated with their evidence and edge
references intact. This matters: the first write-back mapped bare paths to
modules, made 22 false module records and crashed CI on the next rebuild.
The per-contract quick-reference markdown is generated from the scaffold
store at close; it is a view, not another authority.
+599
View File
@@ -38309,3 +38309,602 @@
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_27044643acf3", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f841b27cd0a3f14a7fa1be8e87d46c0b65a23b0a75d6324d2b14be717476459d", "schema_version": 1, "timestamp": "2026-09-29T02:59:13.857300+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_edb2d4f65dc2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:478b26b3101f2da813ba48b2c1c1afc463c1c0d5299904de9faf947b8854afbd", "schema_version": 1, "timestamp": "2026-09-29T02:59:13.923428+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fe5b4b43370a", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c5855d77df4b36cebe2c0c18f7bea277d0f779b73b84f357375563349f3e984c", "schema_version": 1, "timestamp": "2026-09-29T02:59:13.934399+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b0e19f4acdf9", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:21:25.789100+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_016be0c4b465", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:21:25.806792+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_086af48a13f3", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:21:25.823965+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5551023172fa", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:21:25.838205+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_80fd52f13829", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:21:25.848050+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_087025013478", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c78e434affa5f0ba0f4682f0cd5352b6050baf50ba81fd03451a7b2c1c3ca785", "schema_version": 1, "timestamp": "2026-10-05T05:23:11.984154+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_24cbfc281745", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7fed33b30bb04b86a51308ba4ac316b81b5e334fd294d0d91cc88f5d7811a579", "schema_version": 1, "timestamp": "2026-10-05T05:23:12.283402+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c232600ff73f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5ae7726f99a8b4ac388a40057e42d5b327181180d8e8358e09816e5b8eeeb07f", "schema_version": 1, "timestamp": "2026-10-05T05:23:12.530839+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a2525db7221a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1e825cba1cabbbd6333c03e88eda16bb01395e84505925366367f4406ce9e3eb", "schema_version": 1, "timestamp": "2026-10-05T05:23:12.744665+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_563adf9a5f35", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:763695d7a131c268d6bcbe4a691bbd78be59068649e1c80caa0665c33cd74665", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.009164+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_816a22f4d447", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:aaaf89f49546f49e337ef8cdd1fe3720fbd84655677dd4fefe81939d81f2ff00", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.268251+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_17643f9c08d3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c1d39e849fe42430601ee240366550572fb4c0d7c016fd887aac50b5328b6e10", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.331692+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_acc564bb5e04", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:34b51a7de4f22973c41fdb3b7b947b2a9f4c5de5904335e5a89b39466aa95ac5", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.343968+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_75d26cf7246c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c2a8dfa6e57ded3f85dd2339b16a0ea3a40568e2831560b5c15891b08ce15e7d", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.355213+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7b7adcfd4fdb", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cc49dbc2afd1cb8d4f226df8f8e28a2c9fdb52140ef6dc9f9ab79aedc9e18557", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.366512+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4bfe85f92dd6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:81a61375083c0c2a8b0eb756bdfa452118ea92332a0197d8d1e2e43648ee4279", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.377960+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8513a24cc16b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1f6079f682719dbec8bdd455a1098c1c0ba64fc063968329fe9ddc6a716f9c56", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.389163+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6e97b06ebde1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:15fd87c25a425dcf9d07ddb24ffe91fc03c6ae68431ad887067362b3d2eb7550", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.400338+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4d7e8da95431", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4ea1b6698f4d71fe15549b852957d618db6ea67ccaae0cbff8c0e49ce5b4d526", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.411227+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f796ee067453", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7307f3ecceeed949123988f8e438bd3cbe1169e27cb5d6159f77a6ff600c4802", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.422300+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_46bc455a244c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b1e7a541ab66571a7f8061380574c0755b0a1d2613b9331831cb801c87b1710d", "schema_version": 1, "timestamp": "2026-10-05T05:23:13.432243+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_89a5c3f5916a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:12b0b024840c0b30ee3afbc023e1a72586024ce42e34f7ec0363990c983bf9db", "schema_version": 1, "timestamp": "2026-10-05T05:23:16.976063+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8340dcba0ee9", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f9ac3ca3cfb75d4d88edabe5ba101af2bf580c89d06a9077b80152db8a222f9a", "schema_version": 1, "timestamp": "2026-10-05T05:23:19.934351+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1200db078626", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:89450873a6b1a0c4755b443f10fb807e3a308aede5fce1820840c2cefb56b43d", "schema_version": 1, "timestamp": "2026-10-05T05:23:19.942616+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_89c8feea275a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cab0efc6c547df0511f048933ed628afa5fc02962a028d383dc5772fea73a0e5", "schema_version": 1, "timestamp": "2026-10-05T05:23:20.051988+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_38dff4e11ccd", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a9ab994b6ecbce010c3190bb7144b56fb77049021e72613a52471af773a44597", "schema_version": 1, "timestamp": "2026-10-05T05:23:20.060629+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c8e9380dd848", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a1d29ee3e813f549c8e8bbbacd64a419240911445811116100e5b4dd2488c672", "schema_version": 1, "timestamp": "2026-10-05T05:23:20.312488+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c2e0ed12291f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8d1ad954a4da5edc5a23b0c87759d0f7f7345af1eafb4181fcb9224ebc45c7b5", "schema_version": 1, "timestamp": "2026-10-05T05:23:20.325260+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b73836b33bdf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0e657de7974c57b514a1a56c0882e4f7c5e5b80598bed0b02933ea7f5bef571f", "schema_version": 1, "timestamp": "2026-10-05T05:23:20.334787+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0c173fc1d3cc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ede576070fc93e8e039c44444be8a044401ee95af2e0c3b3a6d7dc48d994584d", "schema_version": 1, "timestamp": "2026-10-05T05:23:29.588228+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5b2271cbb551", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2274151dcba0975ee1a3aa8a239d2ea47e66ec289fffc6832d0767c9456aa4fc", "schema_version": 1, "timestamp": "2026-10-05T05:23:29.611251+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_34338986691f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e3a74c42d1b951be16321b4a88f929daa94795333bc482910828341b5633472d", "schema_version": 1, "timestamp": "2026-10-05T05:23:29.635440+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7cc6e81e1801", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T05:23:29.678207+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1b14c0ed4e61", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T05:23:29.746400+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b2dbe5833cf1", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.342279+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_deeca46b17d3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2140010d66eac2b9f209070d86ccadd5b36f6eeacb73f486d8352ce7b3af9b38", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.366683+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_92845503a937", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2fc949e469e7c56151e298835012db3d348b78c7c8ebf4b5f834a19a983939e6", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.374544+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6a0ce25783a7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8085f4a6a55f8ba91267690d7c098dbf8b2761e7847b7928ef12ea450199a834", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.387814+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_672844a86bab", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0af82eb6d979f50ebc79a8b7a55c5285ce8e33ae59657bc492154123a5a0d976", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.395837+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b1fdffc18dd3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9dbcf32d01e7e497296797b117daaea11782fca4a5fa72007630ee62c2f6cf02", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.407145+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8e6b6044f667", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ad451919c0d25830adc1c2b82d9e2030a71c60a9726811cea52e78648d665595", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.415615+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a602deb56bf1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7004f9afb320d2fec931359297a4667cbe8cf78de131fe7bbeb52107feb88afd", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.591693+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_983155bebc20", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1b3cec7b74728266d9369c52a0557b007cd55ad230d4db441755bbd6876242f6", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.600649+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b0b0c611580e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2e13684b717ea5fb6950cf67b5a00a81d62df06b4898dd20a787579e6e99868f", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.614050+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cb991f5b273e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c1b8c60560793a61d67ea8b954b0bfa1f7f7cb316c2d2dd3b0d147747420bf58", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.636737+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_40b7cf40d80f", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.651465+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9ceaf311bc74", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.668562+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ca7424aa2083", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.760632+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9083dfff3b45", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.775813+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dc688dae7058", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7ced6642e67f8be4e5e3530576ab9c6d98ddcc4a1416c79988dc34225b750c8f", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.786010+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_013636606e3e", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.859102+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c858eef7778b", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.873133+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_89ec31fad8c2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:653ca70f91b53be286aaa0f17c30a2b4e7736b75ea343a93e5ea14ed1a28be6d", "schema_version": 1, "timestamp": "2026-10-05T05:23:33.882320+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a82038972d92", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:072e8f7d9fc3e57275a09c1453f75d5e2f9e81536235be64f8528a1bb979b7b2", "schema_version": 1, "timestamp": "2026-10-05T05:25:17.396213+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b8eb53953104", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a22cb8f16063fdadc7fd10bbfd441998175f5fd4b7b6725c968dab4b1cde994e", "schema_version": 1, "timestamp": "2026-10-05T05:25:17.416907+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_91907ae5b9b6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6c2b5a4a7f98be5a78d6b4c90ff52b0a17a8bb4795f14ce51981cfa0cf99c50b", "schema_version": 1, "timestamp": "2026-10-05T05:25:17.430981+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1412a44236ea", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d9ea3a87b24a45857950d84d42d3de81d837bc9fa49e4476876c5ded07eaae8d", "schema_version": 1, "timestamp": "2026-10-05T05:25:17.443944+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6ba5a799e1f4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f5ce7f4257fc0b5152a8a2e6a571758f2e8b377c573447a4631392741ce3409f", "schema_version": 1, "timestamp": "2026-10-05T05:25:17.462161+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8c902011aabf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7acd608e1a5d2e803f7cf624f595a570669c3634771de03b5cfb5ad9013a375a", "schema_version": 1, "timestamp": "2026-10-05T05:25:20.413886+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_15df1245d414", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2a12efb91d5fe122a91e061a4c099ebc8b439f62a71f05e80466f0912fefa745", "schema_version": 1, "timestamp": "2026-10-05T05:25:20.425874+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1a3a8a9f59da", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:913868291eb1a253926b00356c41e9c6ca8dba1aa618936d21760cbc33395b13", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.519216+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_99dd71ab164d", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:060381d18e06e0539920b1840d1528fe30e62a3efe4d98231795388580cf2024", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.538570+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3820eea4d142", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2b5425f3fe253df866f8344a2fff39e3bda8720d3b6b7e0863d37253f62f91c5", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.651874+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_916a7ff0fc86", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c6cd20ab75e396c5805a2d937214cbded98ffb005bfdd0805b9e67cf6e18ed54", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.663015+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fead6a5de91b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:959100e6d856c13f461109b4f9ae7f0851cf96fd39d757a7ffee276843894697", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.736998+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bde7430c2e25", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:927514bf2c22c63c1ba643aabd27dcc42bb5c380eeacf0ba3dbcbacc8e9c25e1", "schema_version": 1, "timestamp": "2026-10-05T05:25:22.748338+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_23caf9dacc88", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:26:05.058788+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_845ca4f6f24f", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:26:05.075917+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_51070f52b8a6", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:26:05.094522+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fd2082fc8c0f", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:26:05.109473+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_185b4b2d6154", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:26:05.121919+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_408e3b8cfe78", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:84a918f8e91c2dc10b4755511a3082452a8fedf1e447fffafee15fce8fc1a93b", "schema_version": 1, "timestamp": "2026-10-05T05:27:51.531186+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9435749ca47f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6e89b2470934ea8c42e1a7499eb6d0d5294da7433e396be707ab799980f95368", "schema_version": 1, "timestamp": "2026-10-05T05:27:51.818842+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2f016168152a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d788663a9e9c9a89dea8f732a20888687d27957a80c381d14c08065a053e0ef8", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.051261+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_61c614715445", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9bb7d151c830f42fa63a11f8bc4ea925dcf868689dee13c3cd29bfa223a4bbd5", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.266625+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b6208cccd918", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:203a108f9dcdce6ca650375e2b244805852570cd8c7ceefa8449c3c690642fd1", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.528285+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c5200840c4a6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:36cea66931af503b14f27b105f830fc170dfeafbb29a6128af4f130d544effbf", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.796399+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3e527fffd6fe", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0d12f3da21598ab74316e8b65936d6e56d90403d3eff70238e10d3bdecb73838", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.863927+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6291e3591991", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d0a86ab3af6a721a4050075172b898ffd2e2a5d6561bbb8bff1d89ba18dd458a", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.876986+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_653474ae5a38", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fe262eaff1d3744c73f76f110492a9ec7a1ad179f6f1e19fca66311669a15ed4", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.888746+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_28eedd2abbae", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fa2cb5946ba2f778d509d0f368c4613304ba54c82fc4889eb3799001237dbc7e", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.901213+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_37da570bc113", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0e8c4e296896af8faaa1432c38fa72bfcefa226ccb35e1998414d7803ae65168", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.913445+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a7829f63eb5b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:640393fd25398d4e0a111c578197687bb017f6f084014a0ae4181dbccdbe7c70", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.925756+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_41d478b7d782", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:025c1d4fbe7722fc4aad0bd7e9382712889a806f84394ee66a092077e2bbfef8", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.939111+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b4015935cdbb", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:565898daea9457ece7ae44df52fd5027b0b7cc909cb60342fdfb5b5e6f366a12", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.953016+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6421e7749b93", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:818a29ba114e0730207cf1c5f768d327edc5bf290e4f56d9c2367e385ca48aa9", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.965166+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_08983922cc57", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a442fbd2f9a0f05832aa41d04d01b8f1c766b471089f912e8d272c7f0407e8e5", "schema_version": 1, "timestamp": "2026-10-05T05:27:52.976327+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_125847fe8b69", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b1deef4708eb9aa1af381749bbea11a422c64897ab5d4b578cc8af433d831d73", "schema_version": 1, "timestamp": "2026-10-05T05:27:56.131473+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3ea4fee2207a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2ffe96d1999af5fb0698c2d0e62c17852fa8107980b05eb0b73540364d0dea99", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.070955+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e989056d43fe", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2e30696c1651d69e185f25e8db4ce01d47c6787fe50ef32c2683ac39371986aa", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.085972+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d5f1bee048cd", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c332225c74917e14f18e7fdda828bfa2c5d8a332514e580df135b1480bce738b", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.220918+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f56911180a9b", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ceca0a4364b9ee3f2419bcd9ac18b40ab9e07d1cdb03d909f2f5b7efb51cee7e", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.229532+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b2824390c450", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9819b775ac6aa5f32de4878ad79f0e98dca6493fefcc5ae8df8e83c2dfcec6cd", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.495278+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e23f1441be5c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c5159c0a313804bc805c68de7eca26b39fe3392aef5d41fa66e5923f0c0ea597", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.508673+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_73e2d31b03bf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:93f915bdae3b5313f277e830bfd0fb2e0d1b02aab3c44b20a510a9469f46bdb6", "schema_version": 1, "timestamp": "2026-10-05T05:27:59.520027+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8d8bdeed008e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9bc8685d2399e0460be64e145836d78c206a9712e6f117330a4b6463b8ced171", "schema_version": 1, "timestamp": "2026-10-05T05:28:08.329960+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f6908d666ad4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:78c32e964baacf6a73151ebad029892e09ae53ad4710890c9d0193ee71978ee3", "schema_version": 1, "timestamp": "2026-10-05T05:28:08.353126+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7e6c6b73d1c6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d65b046a0f7bbc04806ed066f5e935e2b9a520ba33e552e89e65d53d30ae09ec", "schema_version": 1, "timestamp": "2026-10-05T05:28:08.375244+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_94194cef5eb2", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T05:28:08.416223+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a6ccc11f9f42", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T05:28:08.485358+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bcf71e09c3e5", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.599749+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_75027bb0ef3d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9f9011ff2c006bb7507fe67cbd61e641b0a2f80b91c67d31aed389e0fbf09e00", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.621348+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8208b0e35fa5", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0181775b8514a812d37751511072f301a31643c5a5be26e2512547c240a0790a", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.628860+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2f47d2443960", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5eb815e5ec80814ddca17127677556f15798c7ce94ce94cb4eed530311e7d7ff", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.640465+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0f6bd7361917", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b12fbd56aec61b17630f0dbc7e488dc88e6999f57ec51ef467d7029d93f604a4", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.647963+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a7531bc14b51", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ad5ffe6d99ba7eb8e220803d051c140524085622902a5940b2391a19c7414b92", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.658146+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c978e0bfd637", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5600a9577bb076c0ff0b9d656462b09831e21a8f4d02bc50e99659fd17e2ba44", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.665658+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c39a1f0f397b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4be05784a86523109449a6b2769bc348428beb7602b5d2c35098c1035b2fca36", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.822047+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0b4a21b38eb0", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4f7119e456d1e5aea07adf44fdab0b90e0f68e2c48c23c61c10844afcf5bf98f", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.830449+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5add87c241be", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6cf3772ab4f5ec3b4a9abab8380d02cbe3f24ca0609e68b07639fe96e98e8e43", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.842537+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_70de0f155f49", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6a48c8b921a89cf1b8c2e28696267123b85b04317af349213e654640aa42a5e9", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.861340+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4025fac6f1e0", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.874488+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b873e7b563cd", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.886610+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3daf0f2d44b6", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.984176+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e4c5ebf30fca", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:28:11.998542+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_539377a95676", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:95b1442f065a87dda2cfabd70a8effcccdd85a7d5bb083dd29aa627386c62db2", "schema_version": 1, "timestamp": "2026-10-05T05:28:12.007236+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4b782fd4e3eb", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:28:12.078949+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ff20a4ad072d", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:28:12.091816+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4f937d75332a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2c26d0134b9ac0d13d5787d3417d511b684f73324de1e0f23f0da45491db1e40", "schema_version": 1, "timestamp": "2026-10-05T05:28:12.100678+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7e5a45264260", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9dea7628059a7e5e2b7c2494b865238f95084208b1a7763e395444e7aa64e796", "schema_version": 1, "timestamp": "2026-10-05T05:29:55.509557+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_874accd00f3d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:34dbc39a404b72b14e6d9c0045b7fc23daa35ab97667f01402cf2416d662836b", "schema_version": 1, "timestamp": "2026-10-05T05:29:55.529787+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_277237fb122a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1a7a83b9e1f78b9dc88e4ad1f3b272d639288eb70dad9e2bc5ae720d70411c5c", "schema_version": 1, "timestamp": "2026-10-05T05:29:55.542625+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cba8e215b145", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ea509c55bb8a2adf416e25fdad70e6567c536399b8141f90aa26b033c33e3309", "schema_version": 1, "timestamp": "2026-10-05T05:29:55.555819+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a55a21dd7235", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b628de52c8bba806aa6264c4d42a19dc3e65c46bbdca05436ee8a808b32701e8", "schema_version": 1, "timestamp": "2026-10-05T05:29:55.571734+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3c3e0839e638", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:113d8d7baadb6dbc00443b1ee200b3e11dae0d751d4483a28d85318050111293", "schema_version": 1, "timestamp": "2026-10-05T05:29:58.721804+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4933d7245822", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ad3f3a76048316c3c20579bea2166845c15950e5d5f3de57d7dbbd8ebd9edc3f", "schema_version": 1, "timestamp": "2026-10-05T05:29:58.734844+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e0138977793c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a90c96a2d9366bc6951ec3b992a61f3beaefeaaa886c122c743ab6acd74ed408", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.494219+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fc56f6741b93", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:802bb686f4b5a1ad8c8ef9568bf02ca217feaacafe8702ac45c0b57040412e56", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.508976+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1d8fe2b1fd81", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:56ca27fed0caa063afda5e6c21d190385719834588b340415d4c3a01c2eb038a", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.628493+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6f1b9fd10a21", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:39002b10daacf00c62e6c79aef7909eb166730847fa08d042f41457ec1d60da0", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.637183+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e4c9c7ffa6c0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:13f7ef2fd1220ab45bcd59b5bb088b3d3e1bf0877b521f7596ce7f0c7afcc0c6", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.698934+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8a645ac69fea", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7fa2bbcfca701f753edb2e4f4d881825925b4e663886b736a0a744dd8c004590", "schema_version": 1, "timestamp": "2026-10-05T05:30:00.707238+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bc09da2f7370", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:30:24.356970+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e32fe810ee7c", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:30:24.374002+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ba52c8226135", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:30:24.392343+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_92ea4ceb0d28", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:30:24.407304+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7cff4933612d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:30:24.418294+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8aac99f05776", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:212d17607942f17ba29c9f9d9bc9cf5d37d67f93386de5ee5b9d9e4e79acbeb4", "schema_version": 1, "timestamp": "2026-10-05T05:32:10.735398+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_32ef3f39c9cf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4367751c718d5feef38fb559b14cb544bcf0f55dd0a6b7631f9902099930fd1d", "schema_version": 1, "timestamp": "2026-10-05T05:32:11.023659+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f92b9a8bde55", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e94ba1ba17669ef2379c863670295ffe1647c63ebb00b29aba7383c26fd5f9df", "schema_version": 1, "timestamp": "2026-10-05T05:32:11.251196+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_48a0a4b749cc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bbde1c4f32585bab26f8f274abef3abfd0789b0b89be1cb58ec82e5629dad7dd", "schema_version": 1, "timestamp": "2026-10-05T05:32:11.466600+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_61b2f9392328", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a9b1f87f4671a779561551ba84803bb39b41412476daf7883f5f7ee6e7439fdb", "schema_version": 1, "timestamp": "2026-10-05T05:32:11.727830+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c176c699cc61", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:efa754113d15c83e90d8b9f0f4318947009d48c921dbc1c288c031cd3f901173", "schema_version": 1, "timestamp": "2026-10-05T05:32:11.990992+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7e31c7c108d1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b1e9a428a0af40b1b8f6d99b075d98886cd352c9913ccd9e6d104f924108fe68", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.053590+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9ed7e24448aa", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:51070dd900366646171319b023082ec0e40a5b90e69a87bc4db311edb25fd393", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.066468+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_497f97d21aaf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:39f543b29c4eebcdaef669a7511da196fcd0f271305a447c7e680af7365fd915", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.078586+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_de0ec7cbcc04", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4658efead9526c67f82b01aca2914354d1854b0a987dc104b21caf8e148702b1", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.089830+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3db0955932aa", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:50330e358d50974da891edc86c0914c13b5682bd046ebd4b13e20fe5150557a9", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.101835+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3171bf0dc94f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:dd11850ceee05c042162c7613f621e44bccd74b1a00454891910b4c873648a37", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.114009+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ddef6b58dbdf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4af9d21435106567bec27acf9c9675800ae79b1e35fd4267855170b07e96a83c", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.127026+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_39638ea4797d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0a37b21dcdf495db8b49a7f4d6fa93f3427faaa8b66455bd8db0c2220d68aff9", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.138781+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_03d0a3262591", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:88929433d0eb43ffb4783fe141d41fa16d7d73ea8c3bc6f7b5dd375c18fa04ab", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.149909+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_668453e96811", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:615e3765dc0689bcbdab8898862382f60d8fe88ed94e05c98ac3178378967a73", "schema_version": 1, "timestamp": "2026-10-05T05:32:12.160223+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2fdb4ba329d7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:961e5b27d08ff355f182a438afa3576c6e8b276bdafabbad9d568f7fa3b3b292", "schema_version": 1, "timestamp": "2026-10-05T05:32:15.742945+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dd72011e587f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ac29a1b2e20d1288f6e5d34618970e54cdbbabbf65f8d977dd47bd3f95f5f25f", "schema_version": 1, "timestamp": "2026-10-05T05:32:18.672702+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5055a5efc8d4", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:193c45356bb4efc1e1bbcb1678feb70f1340d9b72b9c58ec19d5a4e1077293a7", "schema_version": 1, "timestamp": "2026-10-05T05:32:18.687521+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f5061bab2701", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d80bf3e826e76b337c46839ce7998919f518a031d323ec0f748af4d5c15cf7b4", "schema_version": 1, "timestamp": "2026-10-05T05:32:18.803632+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6c03c0fff614", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:88b441f40713e3d94d5e9a6def7a5e98292ede6d3261b97cb3e156e3d7a2478b", "schema_version": 1, "timestamp": "2026-10-05T05:32:18.812694+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4382a4801bb6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:60a1560123af24fb64633ed54db9be99215bb3ccf068a0f00b82615c6de495b3", "schema_version": 1, "timestamp": "2026-10-05T05:32:19.077518+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b7e31919f41f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f8678821cf3dd1511274f75c7eaa05d76c987596e59f14c39d243102b10d6c83", "schema_version": 1, "timestamp": "2026-10-05T05:32:19.092019+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5a4b57cca41d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:63c47ff5ed33e524064b29769a7c8fe49e265ece8adfeb3e6f9aa0669035f879", "schema_version": 1, "timestamp": "2026-10-05T05:32:19.102213+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4324375af2fb", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3d0345f44345bb52d7a616c834c85f6c9d9f5300027ed1d36961a1ad98de2973", "schema_version": 1, "timestamp": "2026-10-05T05:32:27.729235+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7d4161720461", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:688e0db718e6f500194d3df3a930bc8061f81c4c04bb13e7d43281f8e3ab2b66", "schema_version": 1, "timestamp": "2026-10-05T05:32:27.752108+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b75d089537a8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e111e67ac4c9f9b0c8686bd29d6c931fdab5914adc263e0f125ebe00eebd9cd7", "schema_version": 1, "timestamp": "2026-10-05T05:32:27.772302+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_be0914011cce", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T05:32:27.810939+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_081a064f7d69", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T05:32:27.873295+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_897ee9583487", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.023568+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b1397f503580", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:75b37792f400ec70c671de1fb27693d614e9c5ba77288fd82f87257db93d6b8b", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.045987+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f36ff6d7e755", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b3b0f6669e253ce09237ae45d741e784e37b56c20e3efd6e095fe989107c0809", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.053770+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_abde6de9bbab", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:725fa51d74580066281cd5d9c5e16b2dbb6dace7b9a4c2b344959647b37d6d86", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.066121+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ed3069467d1f", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1ca67b9b3840714b448db4e74946bb21f854202201adc4e398a8b11d58bfec4a", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.073818+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b55456aada25", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8975932008450e38b49ff7cdc75636e12b266866b2538d60ab5625eab40c9b47", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.084206+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dfa183677d58", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:54ce15eed524b886bd2787af14a35e463010ccb4bdafec9a2b3da9bd2d83e860", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.092031+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_09e10a729ab5", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b0024bf50af59f5baae93d5e63fb452ef75128faad67d00b57a86c418c532eab", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.250783+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fb7e16b2754b", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:789310a900e34f34e18b58d3fe470d9b064548c1676c9dc332b92c0dc07904aa", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.259992+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f43d6eeb71b3", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3bd47e0ecc07aa84a34dc7eaca2448650a1d51f5c2a891248bff24e3739a1483", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.273201+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b7a05e59f4f8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a2d91502fb3eb4f201823443b5de6a9a296f791b6f3d0620044eaf9062a65783", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.295255+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2eb13b60fd74", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.308851+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b1a3e11d8d5b", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.324788+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1a1fedf70564", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.416777+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cdb6a49e28e5", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.430919+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cecb09f369e4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:533946b8405da4368789644e2e85df16bea9023c8e79c6e2e96dee8883e17f67", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.440919+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0903ca4adacf", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.505857+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7c3ce5921891", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.518092+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4238b1795f43", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7bd43c48929090b1ac26823d3c5f579353c199d6229188f14c38ce93d34d29f9", "schema_version": 1, "timestamp": "2026-10-05T05:32:31.526993+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_43587350f3f4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:71896095ebf7f71be94cdb069b034c6f68ca6ede9b82d2e8b50de3c955cbd419", "schema_version": 1, "timestamp": "2026-10-05T05:34:14.711009+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_43f44f24fe13", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1db3165da25422b99c3337567ae88138223a1383d0824a6dda2fe61b091ee6e2", "schema_version": 1, "timestamp": "2026-10-05T05:34:14.729598+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0cfdce66a3e3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:015d4218faa5914504ee3fa032a79c182aa95fde887b9d8801c5363e39362ab8", "schema_version": 1, "timestamp": "2026-10-05T05:34:14.740188+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_85ebd1258ff1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ad46fa8aa08518716e3d7e502f87ca5a28bee0757bd753261b637e49a60953ca", "schema_version": 1, "timestamp": "2026-10-05T05:34:14.751344+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f2bb24df2916", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:09a9df2e7850c64a1effcb172ec3c8ae3df42d5cf190a144a3c85ff254d62e09", "schema_version": 1, "timestamp": "2026-10-05T05:34:14.765763+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0ab073d1e179", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:12d45dd1374f6973719c4d7f0e3701a2c08163e82596f90cb0eb0359f3ed82d4", "schema_version": 1, "timestamp": "2026-10-05T05:34:16.986105+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8506701fb589", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:85adf7ad469119210ac1c00a15a9a44bac8870ca3a953771748575b7deb2ea80", "schema_version": 1, "timestamp": "2026-10-05T05:34:16.997758+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bfad360f1ac3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2ecfe3143938314e2547ceab5797d3a92e40d5bc63104238591f1ac7e40d5722", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.689748+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fea3f40ed64a", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ee1f25067da4f7d7a16793a487a82b28e5b00934d6b5405c44cf270cb8ce9205", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.707650+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_92378415102a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3dfe0184e2ffc36e89400eebb0a16eecf1df4ba17ecf3168145ca3dd2bde1478", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.817581+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2196bb7a5eed", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b9eaa1794e82d24a5cc3f486871d74dde7cef301135ba579a2bb6306c3664904", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.826342+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1e28686d6212", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:da581993cb7d5b13d2cc0c8fb5638e4008e714b88910560628bd03a7fe114f03", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.886502+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a78b2b45db1d", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3ddc3201d2a544f70259a3cd8dffcdac49efa289a31a2531bc011b3f3b0060e6", "schema_version": 1, "timestamp": "2026-10-05T05:34:18.894367+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7ec6b1f9e4af", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:34:42.503144+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6ad73605aab7", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:34:42.519529+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_10d3c8c5fdab", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:34:42.535483+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c76904ae0e04", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:34:42.549651+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_76001f7526fa", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:34:42.559475+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5fff77055197", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7ac55112036f1406c7735f2e111cbf6206e739a83705abdcc05130e5e7f6b973", "schema_version": 1, "timestamp": "2026-10-05T05:36:28.572925+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d5d63c2b4483", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:635799e277a34930633ce00f47f6bc93e39aa57484c45a6a1fc6264f5192e874", "schema_version": 1, "timestamp": "2026-10-05T05:36:28.842810+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d1f83b915d86", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:baeac84a339c7ff1455a78bb860de29ddeda0155dac8c91e85468c6ad58106f4", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.058262+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6464d3c50dfc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:63b894ac3cad3484b95f01f927357329e3fbd2df6ebdb37217827763985f96e5", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.258839+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ee8708ba0780", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:95a096539637349b1754528c822116a2bbf09b6e85df83a7181bfa0b6a2f3931", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.502558+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5a7636065682", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:272b95b3e8645980af844c2028bcbd50fae16cb8f1d78c3c19d57248a57af461", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.748219+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_64976fb1851b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bf325354c7d07d4c4ad5a408e76ff55d83400cbfaf19f4ec00173422e0d8983e", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.809885+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_48f21af6b779", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3d12fb8c86fbb4efdb0ef7f6b608f3ed6fea84a8650386abcc41ea1a59880226", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.821228+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_622bf806031d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5c34b4f5d0bf12000255cef431fb79bec2ee89a2ff432a6ad70406038ca5d01f", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.831955+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_89f419bab511", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1294483e5b6220c7090f9e4e44e9744a3b4ae7e4eb255de5bc24d8833378bb67", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.842691+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b088836711b8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:60e2abaf508eb3e6488851044a5db422cf2d43a486c6edbba4b778e9b27bfe74", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.853702+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_af69b181cd27", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:149509d97283e6717614db93daf6f25f2eef9e4c65601f26d69c62841f9bf509", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.864484+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_92ff2859f11d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a3d216fec0c35ca5de2792ad55705506b2c4a790566f7821f898e5db37dcd511", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.876232+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f208e23547ab", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5534f53025673952a38abafcba1a53811a1ed1c1fe1fdc1be2c943208ee62870", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.886997+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_59b606f790a1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1f722e514428e15f93d5350cc2759ac6c8f6cb67320b3014672848e0ab0e7eb6", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.898336+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b3e908b9b8df", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:086fd5cc9b046be26354b539d35174bcce53c843f82d929ac98abaaf7ac499ad", "schema_version": 1, "timestamp": "2026-10-05T05:36:29.908868+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4abb26b61660", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c7a22e5a661480b81453eb12a1296cb1af4d86d948887a9b33b8e43fb2b05581", "schema_version": 1, "timestamp": "2026-10-05T05:36:33.804475+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fc05cbafca99", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:644d95718b81d6a1c068625a56354f7ce695e4f076a2c9d1d3408cbb45bff72a", "schema_version": 1, "timestamp": "2026-10-05T05:36:36.706654+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ff18afb585af", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c15cd557d92635664a3493a7fc7e3fd9d16339d2f0562981ff341577ea4ee883", "schema_version": 1, "timestamp": "2026-10-05T05:36:36.721525+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f8becb75e15c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3770d522f8a1d9ec0881ac5571c35c43b5ddb2963693fc8eae063e2bb71208b3", "schema_version": 1, "timestamp": "2026-10-05T05:36:36.837539+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c0ac8ddb44c3", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:009e3ae5133a6d1a71fe0fa2769f9b7ae18578b3d08099d78241d403f2b11603", "schema_version": 1, "timestamp": "2026-10-05T05:36:36.846574+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5e291a148e97", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e2c3e19284e518a1cfc7f38847cabd6252691028687a623ba892095a1a7d4eef", "schema_version": 1, "timestamp": "2026-10-05T05:36:37.096606+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e188724befcd", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c5c37130f04617f7d4974ee40cb759ac02589daab1dbbe78c7e77dc6c75231f9", "schema_version": 1, "timestamp": "2026-10-05T05:36:37.108895+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a32a820cbe36", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:da4fd17cfcede765d22b744f4c1a6998de260a6f12d3af9f14194b6092b936e1", "schema_version": 1, "timestamp": "2026-10-05T05:36:37.118581+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a2d77d321a7f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:744405806a505497e6318bc3071b3caa3cc4b854aad81fc1f392718ac37813c0", "schema_version": 1, "timestamp": "2026-10-05T05:36:46.383606+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1562b6da5aad", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5d5b47c38c8689d56acfe7bbd8efff77369d736b869761ac4c5fcf987736e3b0", "schema_version": 1, "timestamp": "2026-10-05T05:36:46.406949+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_29f4d6e3b7f4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7c7ea7f162c6aafee91f16e3c27d2018bebc2cdc96365f11518cd3f4a7ca710b", "schema_version": 1, "timestamp": "2026-10-05T05:36:46.428540+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8101d54cf4bc", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T05:36:46.467135+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9c84c8c3b947", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T05:36:46.529402+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b96b4514f591", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.662215+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8dc1a6a3c32a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:816db414e044ff88c1dbcb2a8de7915f5a0896ffff123cfd7d40514500be8dc4", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.684928+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6104baafbf36", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d19650cb022291bbfbd72e69ff047265f24802fcbb49591b32e00091b9786a87", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.693029+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7970e7bcfe59", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d21502f4e18c552acb0df33acde2fcb31fb13132e330066ad3fa8c7ca76cc460", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.705536+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b3827519a7a8", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:be1370c1bc215e37b54839a805e120e232ce9c006bcf92b886e95ee4b1f50cd7", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.713134+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_22c677bf37e8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:597f388d12f319142904c586e6fe52ca89103507046e544c09e4c22fafb0eff5", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.722937+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0255df35ee54", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:92fc08439a50f8b30f3031914c1c679fbbf6b1286aa57d3c275e7bc7fcf9ec6b", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.730451+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_428234477249", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:33bcd7a4bab1aaaca61f0b04a1ccb2d8738f69cdc02811796693a74bfd427b70", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.894059+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e33c45069fc1", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:806c6e13038e6bec7d2cb5629500f4e20641913d271cd41b4f43220e38e7947c", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.902495+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2bb2e855acb2", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:920783237c5da06c006a0fad524ced79ffd630a1588f4dfa842617bc4f31a8d4", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.915409+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e1e457811917", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d8952a2002bf9e1ce5a58d88a1c5960d83d446671a7c08eb18169a678fec203e", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.935917+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_600a07fe3b81", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.950326+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ed0bdeffab01", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:36:49.966938+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0a0c4a914df9", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.061831+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5b9d961577a7", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.075143+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_774ed53da96a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d634b3c56c2a754cfcad6ce6ebde0962f59ef8da63d8bd3fae76f563c3e679a7", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.083527+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8f1971814595", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.147575+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c47c4e1a8eaf", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.159367+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2b1a067e9bb2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:53b9a2cb183e07b7a99451739b68e1bc8737884a3eb76ade3c808b4ded168d5a", "schema_version": 1, "timestamp": "2026-10-05T05:36:50.167368+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_90d11eeb10ff", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:98b1e1fe6b660f86412dfb433421bba18ef3e4cc64666170fa747dc51dfef456", "schema_version": 1, "timestamp": "2026-10-05T05:38:33.445774+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_67268fc0d9c1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9778a18c9f67e3ec65992c8071ba4bd657d748acc6cc74533615c0fab363eddc", "schema_version": 1, "timestamp": "2026-10-05T05:38:33.465888+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3e3860a63113", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3ae362a255148cb037b10542e1eb3d731e2ddbdfdf91462106ec1619949244ec", "schema_version": 1, "timestamp": "2026-10-05T05:38:33.478388+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7faffe7a5a8b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9c5be5bbbc518628a84b0e88b3e48f368ac12577177279c500c587c2dff746e1", "schema_version": 1, "timestamp": "2026-10-05T05:38:33.491615+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_095da8cac7ea", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7952e2373f4564092d77605de6c19442e33fd0daeaa368c5da9d35789fe9500d", "schema_version": 1, "timestamp": "2026-10-05T05:38:33.507000+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3cb464de6c72", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1fe0073aa75962977a1ea943fc39bde174cfc29e69bde57452d8c0682d85b5e6", "schema_version": 1, "timestamp": "2026-10-05T05:38:35.795329+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aad93165eb31", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0bd022b5e7bca573a4b89de5ef3f212e33fff86e3b481cf1cd486d0a62f484b2", "schema_version": 1, "timestamp": "2026-10-05T05:38:35.807662+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_62a3dd268832", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bbe96e04f0ed2016da5bc6067fe80621c38c859ee1b085938b75da3353f084f5", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.584445+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_59fd1106595a", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7d12d665db123a8e962043cd008a5c4f07794d3486549f9b31711c730172a777", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.599765+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_070e296856e8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:91346f085ea517e5e5b7b7a95cef12a0b8222464c65fe670a9f3227af1be21d4", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.713585+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_65f122803784", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9e2e96593595566534fdea2dcb7d33074d9ea3160bbb5cc46deb8a864d952c5b", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.722647+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aa65fbf90501", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:473743a4ef9c274ee281418fdd41f79a7bf1dc61762804464041b0c9d54ebe07", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.784521+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bc458e29ab0e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ac9039e9c68fe381d478bc3187c2e4d051806a2530a903514a58f33cf67aec67", "schema_version": 1, "timestamp": "2026-10-05T05:38:37.793480+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_86a65591d13c", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:42:44.823632+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d4a4414d0155", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:42:44.835236+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e56c93fedf69", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:42:44.854320+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_95931996110a", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:42:44.869024+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0cb1c983a23b", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:42:44.878867+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_166e07517dac", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:33e12566fcc99b849794ab4b5a1a15da98bc96e3744ec2ec1764a17268607d80", "schema_version": 1, "timestamp": "2026-10-05T05:44:31.430956+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_da7865fe3786", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bebb6b0e1af4788a9f490dd6bfa18c89661f60df990ad1edb9174c0e17c17ff2", "schema_version": 1, "timestamp": "2026-10-05T05:44:31.704577+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b3c787b8da9d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2df89b3f06ed8f3c015931e0b4f2bd99e117e1cbea28f21d90e4e12e1d3b078e", "schema_version": 1, "timestamp": "2026-10-05T05:44:31.940026+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c7bb3f5a59ed", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bdf7e2d63c8a34b20e2e8cc5f0a84a011a07e06155ae859057eea528167a03b7", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.154802+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e0b795194203", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:54a3267426314e299cf906551b830b1f41cc875ba80f08c93fc4adccb84daafa", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.417666+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_476f45fdd7ba", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8e819140472bab13608d0ab9b5f956fbda53968a80ea011ccd6f6e2943159f0e", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.681037+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1acde88146f2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:670e75a95e872e5ce3fa3a90e2d95790249fa737b52ecbc66d4690c4c1fdd67e", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.749960+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_97c4e18b2d93", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:63d8ea490804b0ad180645ec31ce94267477af333cf233de8bc057a9a5edf154", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.762348+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0bdd2a3b5a35", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f20f27c26bda798b98120148a9c8560be06d469c5e3b691ef862a57bb4301dd1", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.774305+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f462ba72d08d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:db952fc653b144870f19cc12e16261c01662d4ba8291bd9400cf47e11dd04b0c", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.785426+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_188013743147", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7d807705d56183f752fa38caca85496108c21f34f276d9d72416fd2a541c3996", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.797019+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_87bf9a3e7f20", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:83cd02284dd33685a0c85c9f19e10d31c11d56d2fb971cd4600d93bfb88f90fa", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.808544+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_16204db29b9e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a615539d019bbb7d2768f6a0579d785faea5deb0ea9592916aaf3679d6b7ed96", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.823256+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_00772f43e9ae", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:40779e64cc9bc845f231e5442520294f75c4e6443584e2b9673398457a356c4c", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.834651+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5ead779f82cf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b7dd0cf3ec8cb4bf892e0413c4f8794c1353ba77c1cb2c38da2d4a35d2c09c69", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.845491+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2a4e01c7f481", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a446c5ffa0d921dc1dd5f8710a68c1a2744d14dfe4e02e0d9330f53cba709888", "schema_version": 1, "timestamp": "2026-10-05T05:44:32.855867+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_771b4bfd85ae", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:81440c6af5281d42bc03418a0eac2b52d628308238c49399d3f4a1693ae076fe", "schema_version": 1, "timestamp": "2026-10-05T05:44:39.492429+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_80c1ee255737", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c646063eae47121ad7ec5211c9b09435d000d375077f45d0c1eb4a03bec1d00c", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.449164+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c454377eae02", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9e3d3fb1663ebf50209012b8135120dabd1b5adfe5a4d5a13e16cfcf58860bf0", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.464333+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6b9ddf245574", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6934488d5d2eb0437ffa177e523ea02ddb356ae1c59942f267eb3068563ba55b", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.597891+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_25b3b2544e7c", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3e5c7cb9591f03996a905c766ef60075159019d7285ffb0ad790d8d208c7acad", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.607386+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_504528cf12be", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:68369939eb32683671f66183cc8853f748931834ecfb8beb462e0e8fc9bf25c7", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.868608+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1a6c4a7dca12", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8f38ba034a9241ec5f3aa426262aab6db6781d034fa2885673429b3107b8cb37", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.880198+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_be30cd830765", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:879929d8682a13d2ffe93935a7064c1a06fcd4bc3f9aeb687ac80ad42b627496", "schema_version": 1, "timestamp": "2026-10-05T05:44:42.890044+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4eb03f942728", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:977a76cc9165925647d184553fed7d27ca1c47887c5095e4a7dbc28209eff9b6", "schema_version": 1, "timestamp": "2026-10-05T05:45:00.429016+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_deed6a4991ba", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ce2bfe70056f98070bad99f1567239a6264e61c24adeecb980fcab7deed076de", "schema_version": 1, "timestamp": "2026-10-05T05:45:00.451606+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b9a9d752569b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3a8e35f1c0e024d97abc363b1d300a73b03bc5e07a654cafd4afcbd2a2e043ed", "schema_version": 1, "timestamp": "2026-10-05T05:45:00.472542+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5be6156f8e8f", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T05:45:00.513260+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_55cd751c3454", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T05:45:00.578950+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fb6c15646a6b", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.026203+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3f5a8f90a41c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ac69806d912eb3a9b320fd8c8f6d9124fd7fced98d3bc46b4df5f568d5c31108", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.042663+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2174cfbbe69e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:75a370143979b0fccb1fedaeb1e2ed8206399b49d48ae3f0877263b0dab83a23", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.051660+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_20cda71d281a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cef87be02a86380fd1a051c327cd6a145099292137b936d87ecd65045ec5af1f", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.066684+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_464b6c752888", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:db037c3f763141827d4d8c9b0ee20641284d0a666bc9ed1edf56958b57062011", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.075671+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bb46cddce63b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:60a50030bdd269d099e22eb663cb1903cc155a7d8b44f017489fce0a79134351", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.087436+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_18b9e55889e5", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7672d9151744b1c821d01213889873aa3bdf91136931e5b6569449ce57f781c4", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.097051+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_00987f249538", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1408f4d3c02333c4afad0794c0acc1909c0eead9e7a7f7535769cb9d25330b40", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.274204+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2cc49d0017b7", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:79d9edfe5812158fa5ccc9d64956d87ce42f9bec34c0a406ed81d77b1591efe3", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.284161+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8a3b8cf8bb14", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:17cc5136d9bc9a5c1eb4a701929b44c506724ea45a189c8e18f488faeca373bc", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.299977+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_510ef9a92f49", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:62208f1fdad2bf0c255cafc4eeb05665dfce21b9ddfe5a51eb0d93b99eccc1af", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.319722+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_af8b0c870781", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.332925+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_14db91071765", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.346088+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ba76269cc515", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.454417+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_82d9ec4a22fb", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.469651+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_79f262190092", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a5d99484006ea434d81830d84831d7c16fac1447f56f45f7d3d9edf9a7276098", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.479105+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5cf1f3250908", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.559262+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_855812c23cc9", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.574403+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_784b0897cee7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4e038baa85e8c7614cecb11abedb755abd1d7750d090f196f0a1dfe51945b3c0", "schema_version": 1, "timestamp": "2026-10-05T05:45:04.584189+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5dfcdda0076d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ed5b59221dcbdda04d40f1388f885f5d74635646b0338cf4b1dd9419d5dfad53", "schema_version": 1, "timestamp": "2026-10-05T05:46:48.024867+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_27bff8aa4a67", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:10ec5dcc77a880f9a5d5c0d512bfb87ff7a7fed4e17366cda24402b9a4e360d3", "schema_version": 1, "timestamp": "2026-10-05T05:46:48.039242+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f52cd7d380b4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4ea200291a31ae31e28299c5f74965fb274baa8e203ea5d097ba85c404493544", "schema_version": 1, "timestamp": "2026-10-05T05:46:48.052314+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9219dda77d9d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b6b7f2375ec62e49788aadd23fedfe33e086aa90004dbcedb5d7c8b54fd33099", "schema_version": 1, "timestamp": "2026-10-05T05:46:48.065181+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3d4288eb266d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6c78ce332472854639277b6ab8f616a795a6cd32ac294f34664a173067fd206d", "schema_version": 1, "timestamp": "2026-10-05T05:46:48.080369+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aa3cbe49f920", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:27d33fb0a4fc82924ded62d227a5ee833b17a07318f13286ffde9c16f0e75dcd", "schema_version": 1, "timestamp": "2026-10-05T05:46:50.886509+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4a9b36a3a31e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e2bc10744ab9b2e2052e8fc8c5a7a5610e4d019d09ae867db8374eea19c187ca", "schema_version": 1, "timestamp": "2026-10-05T05:46:50.901612+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a24806a7223b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a548d0c18e1531f8ae4e9b64fc92112e3cc3ee304bc62656e85f59db65cc7587", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.705101+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2f587e51ad36", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f8ee37c7bcefb7c8efda6eef02582a96209283c8ef5543d4360353c37fc06881", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.720208+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f614f8afb5dc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:369d49705e0cb1fb730096ab32de74671f17c22db9ae1976d943fbb6fd11103d", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.837816+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_eb78de821a48", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8ad92fa610c3b29207ee69a19a9518a24b1bda406dadbfd643c9c4c33119aa0f", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.847320+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b63c11b0e85f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5ee130d09ce403ab7ad4afcfab5e1ef2791fa637d4271e41b5771f094e837389", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.910886+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a171c6c09af8", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9e6dcb2453feaa565595cf31ae5cb484066d23115b4d3c6a0c4fdd0262fd23b8", "schema_version": 1, "timestamp": "2026-10-05T05:46:52.919949+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_efb440868a36", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:48:35.308535+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3b0786de27ae", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T05:48:35.325629+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a11066af0fc7", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T05:48:35.366267+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bbaca2f78b39", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T05:48:35.388623+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9a20a36a9f5b", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T05:48:35.403210+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1e7669f2bad7", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:30:47.078182+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3bd981ded4c1", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T06:30:47.100458+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_681838e3fcd9", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:30:47.137264+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_da525a3c0fc2", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T06:30:47.158469+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c2feb08b8a36", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T06:30:47.173548+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_026a68360979", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:890f37bf8225147a6df15dd4d7d1d14b8a34f652457cee7eabb5e3d667e7d228", "schema_version": 1, "timestamp": "2026-10-05T06:32:35.779852+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2a49b38f6181", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6b38d9e665655ee59bdd175c8e260de8cbbe3f1e893beed1bbe6455415afc298", "schema_version": 1, "timestamp": "2026-10-05T06:32:36.653680+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5d2eb36d5a2d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c939b140dbc98d89a70d545ebee22f4614b8a00dfe75ddac5e2ce882852f6eb0", "schema_version": 1, "timestamp": "2026-10-05T06:32:37.331588+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1827453bd8cb", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:254b8faf2ee47df4669c2b291b122e35d03bc65a9071bf4a64d6e5448604e232", "schema_version": 1, "timestamp": "2026-10-05T06:32:37.991661+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d9b9bd6e2e6b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:eeb57cc89822598f55e680e53cb89da3e4bbad9ee60333ff09738791794e7a62", "schema_version": 1, "timestamp": "2026-10-05T06:32:38.795950+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_69e66a7a0210", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:268c016f21f859433fc2715c2cf88616d2a035902edc3281208599b3f27bb358", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.641517+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_09c85ac1604a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0c26db1dfc9ccce93d27b697ca16381f4e8bfe65394614fe0f15cd6e33bd863b", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.835431+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a901d6aebf00", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:07df8e3a2a1aaf33db9b7281e29acf4375d6077cef4d87348fbe3141e624e8c8", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.855492+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c5c802b2af64", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7156b07cac29fcd922a2f8a03edb64e809409e1c86493053f6a2281dc74fc96c", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.871970+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e587dc0f2eff", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:150637057f4ef28796229418e35e3e62ffed7be70b399c4e1b102c15efb3baa9", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.889627+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c6b33ff3cd66", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2785fca0a2b93a259f81530e43e5e482fcc6146fb0e5919c3b948a15c316c9e8", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.907130+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d9e1a7f9e61c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bfed397f2e443f20fd6f9f7c88efc309655c6c01b5c1928e5d8da357731544cb", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.922819+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0f604f2e0173", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9ef660d5dc89f4fb721db88b55bfcebc906cd26f7b29d492cd5816ab7427809a", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.938886+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a7a21aa5fdb8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bdf76219a0f1dad6d9883b32f014572fccc584535f4c350c442902a444800bde", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.958883+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5988197924ca", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:358ea0187ef5b34533c467e8894408ac5eb27ad7990fc854879cc62eff61fd7c", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.976738+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7277acc98310", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bf3f151e86ed731297aa7d57315277cf1734f7a876e0255bc6db17f848731596", "schema_version": 1, "timestamp": "2026-10-05T06:32:39.992309+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7c0ad3b6a366", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:520cc5250ce983f46fbf05ee636ea10f8e13056611f25a151ef535208cc08469", "schema_version": 1, "timestamp": "2026-10-05T06:32:43.167134+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_76140dfb8cb7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e493cc9b5ce492a629104ef291a1e26112b59aa86d506166737f606207daa4f1", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.074794+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9357b38c18c7", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9284c060ed8738d35aee98a0f75df7b72673cc93d5b8ccf3ce70c409608bc93c", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.092864+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_93336b3c0836", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:48001e7aff69dae16d512aa99fd2e5f03b8733d4b2227c5c9a73545429b9b385", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.274021+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7ca37a9b2aaa", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:433ca78ec83370b43a86ae38f7346bcf8e5bc0da1378bcd96122e77a61f60b85", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.285731+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ed68c9d461a2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d68f58dfbed4a8becb415c01a3f2170fc68418e973b6f60fc76b286050ed654e", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.596825+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d44e5ecef962", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:01c4fc9c7b68c9746303322750fcf1c5419c5562508b37391c28c118b471190f", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.613587+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_49d9e8f55750", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1b6540607c303b1c7963d743038eeb4e5200a36c5f66dd4f9e69f8c6a0665677", "schema_version": 1, "timestamp": "2026-10-05T06:32:46.627481+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7965d3c2de84", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:368ad204ed6c06343e6038bd6d35b46cc207df61b7238f6b95a9ebe572763249", "schema_version": 1, "timestamp": "2026-10-05T06:32:56.022606+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2a754a8eab42", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9f687defe0c19263533825fa8536e5aaa81ce61940b2869d3ca9dbeda40b135a", "schema_version": 1, "timestamp": "2026-10-05T06:32:56.058422+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_76ef0082a146", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:efa9aff1d534f8bfc14c0b14fe3a58b8b55907b7d160389cbbc8afe5d52ca0b6", "schema_version": 1, "timestamp": "2026-10-05T06:32:56.109077+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d52482f9f96d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T06:32:56.172385+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0e151ea3d0a1", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T06:32:56.300074+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9a84aa36f25a", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.091372+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_478a2a6f3f94", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8b3627a045b0b517e975b68a8da3b32891c2411ffe6ce9fbb97f72f7e2633658", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.125442+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6ef6062ffefe", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:19a99bda927f983c78b82bfd6053ee5bb0a63be42b73f92c7ade65a1821be017", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.136175+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aa5c04eee7d6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:daa454fc92f336a672873a14420c875188613bc1623051a9a212025a5a2acd85", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.154712+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f5a558c9ce50", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fc26c9be2a163a5b34c58c533980da9a4bdb75a51256d692a515761de8ca3518", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.165583+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_00cfb7401d9b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9d4c534d642cd9fb949f17ffa7c4a4aa0aee203c1a2606d77bd7aa0738053a2f", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.181226+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f94b5072d0c5", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:baea61f9d3acd8b1fd054b359f3571e26fe44964c18104b77d8c88fb17eda86c", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.192038+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6cb5b3246109", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cef698ec3d9e8581c719efa5217951e55db9f8ce0f2a607e5e761a7953a8f9b2", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.322737+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b5a664e74c85", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d241bb90ce22d731c61d9ee65ea9957256fa753010243939aca3e3a45e5fb73e", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.335063+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fbb792e34239", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f5a249e9ad34edccd6a61dc67eba4fcba2918df4b66325449db446debaa04c29", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.355622+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_81a8a4a833c7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a46f73ab501bdc60cf4c543d56ba5e6abda7053043d697b6433a3ef04fdc9548", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.391878+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c3c5cd2993d9", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.412904+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_085b1a727eaa", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.444250+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_510f343b6ab6", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.627098+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ff38d1208cf0", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.662021+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8349c1af8de1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3e02f546d3eeae63e6dc1ba93d28159719d19ee54d29fc6dbbff4a554ba06488", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.673829+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cb647dafb557", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.770606+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_385e99f0038b", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.805270+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_043e7bac4c97", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b3a8c41bdc31d460080143cde43622c1c98f6e7ae662e4b43080cf00bf63d566", "schema_version": 1, "timestamp": "2026-10-05T06:33:01.816613+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aace2f37ca5f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6864addf067ce58d86ab40b1dcafbb24109fc29e7050d684538a31354ac59dcb", "schema_version": 1, "timestamp": "2026-10-05T06:34:47.569047+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1144243c150d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e8e3defeea6670131bc8863101fa1923795b272166c64dff7a705a395f7b08da", "schema_version": 1, "timestamp": "2026-10-05T06:34:47.593005+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bf9c63616ca5", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:961d3b2dfb0be05a7f3d8e115f4d78f3f9e83d200a6ab6235024fe21bab0fc92", "schema_version": 1, "timestamp": "2026-10-05T06:34:47.609147+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_309f95c6a4bb", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:06f3683c27f16f9bc173b6f58ee2264d0f3e7f1ee41947015da0c55f809f669c", "schema_version": 1, "timestamp": "2026-10-05T06:34:47.627150+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2546ff004b57", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:71e916d7a5a3bf292035bca7d4fa9d19091367aede69a6c7e91e3e070a999621", "schema_version": 1, "timestamp": "2026-10-05T06:34:47.650566+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6aa18b2a23aa", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f5b7005cf009d0f0408ea60753fc35a916f0d695e6c565b46a3dce93934b8534", "schema_version": 1, "timestamp": "2026-10-05T06:34:49.915433+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6b01de5f2b30", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1c4ea8048081f1a8b9cdbcdc5abaa172d643a683474d807bf308ed59b9047525", "schema_version": 1, "timestamp": "2026-10-05T06:34:49.934060+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_437b579f435e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7f90bb33fc830d95c60abaf50f58fcf7a7863e1d3cddf10ca4e50654d0c14d91", "schema_version": 1, "timestamp": "2026-10-05T06:34:51.806895+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dd53291a04b6", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9302e5dcc51c93f0b323560e075bc81a89594b0ab0395d3ae855dc42ee7c63e9", "schema_version": 1, "timestamp": "2026-10-05T06:34:51.824797+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6676059944cc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d73de3ab7d7f81b31ad83573cb7a7a1c7db9dd71a7813315b115a20b62f4459e", "schema_version": 1, "timestamp": "2026-10-05T06:34:51.954770+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_92ab14d24275", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1a74ea6323daba4d2e13d7423ee3e5f7af0f167e38578db1d39997383533d561", "schema_version": 1, "timestamp": "2026-10-05T06:34:51.966761+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9507f13a7d33", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6a7f3696e047c7639f12f6ed33e30649c17b684a80652763a9f755310d0d57e7", "schema_version": 1, "timestamp": "2026-10-05T06:34:52.048084+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6a60c2a0af6e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8ac6a632fafc0a61353325308ed38a8ea47dd5380913f6900956b6daa6090638", "schema_version": 1, "timestamp": "2026-10-05T06:34:52.058880+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d2b51ae48dc7", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:36:07.796886+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fef86120ae96", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T06:36:07.817924+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_74ad5982b3c8", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:36:07.859340+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_949631915cda", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T06:36:07.880771+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_21f10ab46e33", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T06:36:07.896081+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7d9ffd247e6d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:968a848f54f5c3671ffbcbda5bfc78c51a2177c59ecf4f307f8a9991fa78828c", "schema_version": 1, "timestamp": "2026-10-05T06:37:56.419498+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f694ba86ab08", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:455e1a70a34942066856399e9148dc648a977af7e5d53ab4e73f8905497f4540", "schema_version": 1, "timestamp": "2026-10-05T06:37:57.303456+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7ed308a97815", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:823e22f0b7eeafff706b77ca49e9d2dba3102bf63755e0b64a9ff49ffbab2794", "schema_version": 1, "timestamp": "2026-10-05T06:37:58.005817+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2c7e3fa8fb26", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0ebc068db0c8ff8bb928143444a811583b56152c7c0cbc3d67c23bd3c187f3d1", "schema_version": 1, "timestamp": "2026-10-05T06:37:58.653201+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_386905a511ec", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:90cc30b59e1526a0b2370f1a7870b805d784139cde3a131b1489c6217c938cf0", "schema_version": 1, "timestamp": "2026-10-05T06:37:59.469729+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b7beb759dfa4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:68bfc12190f39646a736c88face38af541cad5d30952f348be1466c32416e557", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.254815+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_97c44a7789a0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:61801f4c14d0302a99a63a2d8a62533b96c6a4e967dfb947d7d4ce3f6e0afb08", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.444982+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3d13d384dd3d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8b0771675ae6538804718f636a82eb78afcbfa27605e5c8df4b35f9a431c0878", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.462542+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_446cd619ca60", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e13026d656fef5ccdc193408342f3cb2f379a2b36951a3d711f3f3cbe39c6589", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.478480+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e9e8df4344ea", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d6eb32686877061fdd596b5289b195b7ea087dfbd272f665318eb878025b8c73", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.494659+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d84bdb26b788", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:442ae35d562a1afd2cc854c7d4f77e844494930ad27b4104015db78eb789747f", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.510574+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_93ed035a6522", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8bdfeb1dbcf30bd1371f9fca87073b617d6da9bd66b1e5279e8c5c4b4f05cfbe", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.527200+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b65d0bd5f9e8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a01006abbf7ebfa3a91313daf9dd6547428d7fd3986d6905ff056fc04ac0f36f", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.543656+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8b87cc163c59", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a0d50fa87bd699048f4465d2db94ff5e62d5a54b605232482766d9ffb736e0d8", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.559437+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_76d27953ceb8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:47921bd04e256ec81c36f7bb3378c2fcf7f243f7ac852b7b6c41b6f0e29bf599", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.575689+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_25d022f4fe3e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9d76be0bef8e521a711d03af47e84443028ce5edfbf3211570c25ca7b786b43f", "schema_version": 1, "timestamp": "2026-10-05T06:38:00.590787+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_bc3b9807f3bf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3b380dfc8098a90acf10ced31c0393b1f78df3c4137dd49bdfb80185548a15bd", "schema_version": 1, "timestamp": "2026-10-05T06:38:08.680156+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_28a2b41ff52c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:047285e91a7429dd3c9cf9e82bb86bac191b8e8bd4216769b61a3811da28b736", "schema_version": 1, "timestamp": "2026-10-05T06:38:11.642868+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_183842fd36db", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4991c9cbc236491ce16a10e1aebe6f47d603b1b1e9268e9f99518365c78b8a7d", "schema_version": 1, "timestamp": "2026-10-05T06:38:11.660841+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_49851bd52edc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:1740e7eb428ea7ab41a8e2b626d80ec0a2014c29c6198dd1f671de14c2ad39ab", "schema_version": 1, "timestamp": "2026-10-05T06:38:11.799804+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_850a3dc1c2de", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7bcdf33fd6b7b97982dd16a63f439f29dbf2a24b784e727e77bbede25f7474a2", "schema_version": 1, "timestamp": "2026-10-05T06:38:11.810791+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8bbe0710eb22", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7c1d1791282f9c5168109e1381ac072d4585455d315912bb6255858be9466da9", "schema_version": 1, "timestamp": "2026-10-05T06:38:12.134189+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a520c55fea52", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:49ede411ad05435c5cfd51d2a35d930388c34f999b31b4701ee434f48ee0ce07", "schema_version": 1, "timestamp": "2026-10-05T06:38:12.161315+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ea6523fb36a1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9370ff07093a7c50b8dd8eb6fde6c7763eb5d1fc0e6d213da02c6dee29457d3e", "schema_version": 1, "timestamp": "2026-10-05T06:38:12.175162+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f0e800ea94a8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:edf27abbb010cf840fc409f722bc405692376bd64efad9a17bd6dbb20bff85a7", "schema_version": 1, "timestamp": "2026-10-05T06:38:21.174200+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2503ec730320", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7ad2b884ac08eca72b4a97600d7e947d7ce1729dc040690e010bd9ac57ba7221", "schema_version": 1, "timestamp": "2026-10-05T06:38:21.207816+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1c6d4afcd96a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2cb0bf913b7c9cab6a3fcc3f04410387809c61e608acca29786140ae8a9415ef", "schema_version": 1, "timestamp": "2026-10-05T06:38:21.257312+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_76d0c12b668d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T06:38:21.318255+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cc19a85c6ece", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T06:38:21.430892+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c9c2a7c8acad", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.287716+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dcabe4f29a6c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9a47ec95b7682899edbab5b412f9a71269aafd5f1ac4411d7b3016f0265bef81", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.317935+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c045cd6c2024", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d56676e362acc5639850a57f35829495dc6c851db3d12161ec99a5eb832d716a", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.331437+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b805ac6f2d92", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e455cde244b6a07fa9b26a38321ffe46246134f4c06de892bb4a683f5cfb3597", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.350396+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_052d0b45e6d6", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4790c8a8109241feac7dc5fbc5737e57da3a4722b22d23348f06af108ccab11c", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.361147+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5ebffc5e1b05", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ea754bc6aadfbcaf4c5753ecbf584e718fbc035282b614bb01896deefa01a380", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.376212+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_574f699f8df4", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:89844af88766ad50f71eb54d7f1a245966bb2804bd97c10415eba0934718c016", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.386874+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b83811d28750", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:44f37fd54c84d094be680ab3c2fa7171fa500835e74d9c7a21ea656b05d66729", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.508264+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6cf85bf51ba6", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b08e9a33d37bc9ef17274f5e0b49eccef31d0eedf6a2b65794e83a71181f266a", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.520332+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2da9aa4c9a60", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:df8757d20489d83861b62efea8fb6aedfc741b0eb45d69b7b1812b1846a9ed77", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.543926+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5a72855b5690", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3064ce063515dec6d54b2705aee8b066d5cac7975d631119e5fb08e227ca3fd9", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.581480+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ac1304f762f6", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.603341+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d0705973a48c", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.631739+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_91085685506f", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.813178+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cd044ec70691", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.844678+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aad8c93b22a0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ca1dadbc5acd179dbf0f0ebbfba2940ed7c219120fdfba9e00f7743cd6418ddf", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.856333+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_adb456d34b5b", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.956426+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_31e05c902516", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:38:25.991480+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2bf3e8e8dd37", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0f94c237c37daf7128b0c8c36659f839a6aa582a11d6fb1f18c67bfcc14ee69c", "schema_version": 1, "timestamp": "2026-10-05T06:38:26.005115+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b58958a57056", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b5af1a049fc1a5337394e200aa67eb2b0648a7cb9ef54197bb52aaba04fdc32e", "schema_version": 1, "timestamp": "2026-10-05T06:40:11.672517+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c13aef1c02f6", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cd3b310a80e47e2b0fd63962ef421abd9b1f0421e980c32e09f9bfb84e514099", "schema_version": 1, "timestamp": "2026-10-05T06:40:11.696838+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3321f8deec3e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b4312c49da8a313c7a51bb15fdbffecdd65bddef13f2af8c2382e047b474ca68", "schema_version": 1, "timestamp": "2026-10-05T06:40:11.713426+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_79c0164eb4c8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6967ee955bf704859daa6d53cfcd0702fa66610d02945cdbf6f9e30764f4ec78", "schema_version": 1, "timestamp": "2026-10-05T06:40:11.730583+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f21627c7e1a5", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9092b411b050189b053d27608a5b0cd81c5fd589a4bb91821de6d7e2bccd5361", "schema_version": 1, "timestamp": "2026-10-05T06:40:11.753618+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4f2b01d6a30b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:296602153c579e0cd9904d42d14c823e2428738077b8fa105e1ab7273d0ce215", "schema_version": 1, "timestamp": "2026-10-05T06:40:14.075803+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f8df3ef9e8bc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3aa26eec69ddf1a1e675f9e022c747383454ced9fb52cb03d5f35404c3e47e05", "schema_version": 1, "timestamp": "2026-10-05T06:40:14.094387+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d42bd9a2b2d2", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:25a0dd94a7aaba3a2a7b875f7301dd0a4fe5defbd346a3d1a3dc35e8ddc52a1f", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.188557+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_eb2d07d3115c", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b500649f883e7965ccc342453c8538b2b04b47b2f7c9bbdef29df9a661531f92", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.207254+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2a118b9119dc", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2b97c4fa3630d6b2cfc94b9c9f6fe1895d610c84daf5fe64f1696ecaa9220adc", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.354579+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_86ca4d7a77bb", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:19c52aceb064b4732cf53df6e74faab0ac7efe674e09cc00f4e82902d13bd194", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.366816+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_109f31ac6841", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cbc7f5d4c7424ed0e44f6ae0a21590ed36833e7b38e36cad27a8ebe6ae2b2f9b", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.513616+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_18c66c43e3f6", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e641ebfc5aacaa7a16978b37c1561d19df3888446d5b92e99965d8c4cec0f546", "schema_version": 1, "timestamp": "2026-10-05T06:40:16.525607+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e1d27e5e4ece", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:42:43.695303+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3c2c996aab11", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T06:42:43.715767+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_64a6bc1219e6", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:42:43.751147+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_823e376a2ab8", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T06:42:43.772059+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_992151ed6d5d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T06:42:43.787261+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_40d37cfe232e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4194bf68326491d749572fee36638973aca742b62f96768430ad1e28ab24e954", "schema_version": 1, "timestamp": "2026-10-05T06:44:32.307566+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_60f5ca534243", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c17bba207b98e22e3bc0902005dffb8904aacbb78e362e51b65a5eec96fd4bd5", "schema_version": 1, "timestamp": "2026-10-05T06:44:33.180051+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_03b28fdb5834", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:69c8d274fb424154a03ab309635d5585a2a4c2514e1776f91ad42573beacfa57", "schema_version": 1, "timestamp": "2026-10-05T06:44:33.889652+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_165758a5a86f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4464a2a7d7a0616e2c7cfdfa96efd8f5ecd82493049b983ea0da805235ec6cf4", "schema_version": 1, "timestamp": "2026-10-05T06:44:34.519879+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3c96beeeb2e8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fa90557634208f7fbc555c570d68994465c4b1b300b114be2810808f2b9b77a6", "schema_version": 1, "timestamp": "2026-10-05T06:44:35.362910+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dd459e85a36b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:548fdc5109d4399f565aca03ceaceccfb938fddf8de7f73a581685172ab8ee8d", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.168807+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a44e2f05e40b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:972ee75d40b40e68743270717324267be65fd28b40ea5930b840a08a07bbab0c", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.365273+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_04270e9391bf", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b0fa54f8be9efcfba04d1de2b4107a9c16264bf3d0aec3120d3d536205fc4291", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.382108+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_5af20380f281", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7abc73c396ab63dfa6fb773eaa3a61f8fe53409ca70c391e3e5c47af718158b5", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.398266+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_56329fedff7b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a04e448f80df63b6fa2df6d7d433e5ecb09d0da8fa98236b68dd23ae2bf26c91", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.414558+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4f972f10b79f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:32d34c5f9257f369e5c4f750c44adb531c54370063da4ab67b01e4a6fdb5299f", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.430869+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8ffb29c01222", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d14edc631f972b3a0c04566dc0d6a173baf2ca3d7f24c0e53a57d74f191011fe", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.446866+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_04d0781dcca1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:75523bcd62656cc336c54ea8b23689b7bb80c96f9dd314f33912ead0e4b1284b", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.464640+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_40fcc152c131", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:006a9aa13c86a45a6c312db740b877a0b41d8ea7ad93387cd6dbb46a9afc8cc9", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.480833+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2f52fc4a9676", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:410b715c571c5b4d0c59358b2838562c75a4cf18ddbf23c30c61b3061337d5ea", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.497205+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_886ebc880de0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:71325a628e220e35035545dbbec4e851728b7b75bf2e1405759ac7afe8678775", "schema_version": 1, "timestamp": "2026-10-05T06:44:36.512577+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9da6b2641be0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d1f636e09ff2fe01e73d090dda9ecc1ef8a6a8a4e0b2785326e9ccd673489048", "schema_version": 1, "timestamp": "2026-10-05T06:44:39.781695+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4fe18265b729", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f2648039fb8595994fb846b6e34667f854d395621f2b80f4f9025bb52a2633d2", "schema_version": 1, "timestamp": "2026-10-05T06:44:42.753278+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aea6a34012bb", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:52bc97dc6e8aa989f1ff0b2bb2d67559313b25e26b790f922dc96b9c824941b8", "schema_version": 1, "timestamp": "2026-10-05T06:44:42.770992+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ae907eabf22c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8e5614f02085b3f74fe190a820c3415677628bbc7d9a48bcf16889307eec8646", "schema_version": 1, "timestamp": "2026-10-05T06:44:42.896921+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_89f42ccafce4", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f25afa2500e6d5f330ddb68722bb0cea87b1eda48ad87fc18e96236f847c38ae", "schema_version": 1, "timestamp": "2026-10-05T06:44:42.908475+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_df0b2029eda0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c70b08e3925a62cfd2cedb602493e0fcce58048ca06d2f2d75fd11ba0ddbf705", "schema_version": 1, "timestamp": "2026-10-05T06:44:43.216944+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7fcbdfc91c59", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7a8e79b47b1d8985ecacea6b5a174df904765886dff5b02ddc63471d59ec056e", "schema_version": 1, "timestamp": "2026-10-05T06:44:43.241236+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9baad33fd781", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6db17481fa3ea741d28acd7d3961c23d13c9d565d43b7a65bc9a818574e471b7", "schema_version": 1, "timestamp": "2026-10-05T06:44:43.255526+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_695295605a5a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:004d5250bc06f4613c8c306f3ce51e43ac96e27c6ed047f7ca64090634d46360", "schema_version": 1, "timestamp": "2026-10-05T06:44:52.627390+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_35587d7c59a4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d5fdffe94c20869b64221f2ffd06434010311f5a3d54d88d7f5213daf1035ac3", "schema_version": 1, "timestamp": "2026-10-05T06:44:52.662662+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b7a9aad15546", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2ffbcd3dcb4edecf2f9db58b667ddac40f619803cd43f31e7084e7106bf7de75", "schema_version": 1, "timestamp": "2026-10-05T06:44:52.711855+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3214ada9057d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T06:44:52.773638+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_66a3f9fefc32", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T06:44:52.895988+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6ac943e896db", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.177919+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9be57bd7c54c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3e3f6e9fefeedb136d333d8769fe46b221526b7edd4a3d2d7facbc136e8db796", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.208657+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_31159365346d", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0fe00b46a64b9c6642368dce1378ece9f5d6d6b14c797287708907d20b4b9e4b", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.219345+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d52222cd7d80", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e602de80f93a023e2131aa9a445874a6dc48d78c6f50dd2b0d470ee45d5362aa", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.238120+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7e9f8e4e97c0", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e54fa0268b176a1723b960d3c5ae25d30ff250cf50e21b8cb8a46a8ece8286ca", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.248732+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8a4ef30f822d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4d48b559fcd80dea394094bf5c0f4162e6eeac33df2a8d15203883c5bd7c6391", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.263172+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_eb81b76b99c8", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5a52c1f77872698dccc773d78b745242615e715b1f88c2589f7168562ba5ff0f", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.273977+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4c748f973d1b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fe8c879667b2f93ddb30f0fbf8f6a206996a8db1d436dc7960ab06f16ee1537b", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.393687+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c38eaa856d9c", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bc88b9a72c2f2c0698966ab7e35587432b6cf5ae9251d6d3ca7c584a8fc34435", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.405254+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d37393d28a53", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5ec4efaedf112205ad3a290f9ebf8bcf35a8e2045895e2b4ab918bf87d014345", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.425322+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ba6fe3f86984", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2ddb84a16807ce9592ef237d27acb7dda3f7f735c41d0779cf78f8fbefa5affe", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.459524+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4129aafd1e86", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.480675+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_476e56d323bd", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.511156+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_877ab58875f8", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.687441+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f9518821261a", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.720206+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cd3f3b942867", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:df6c0ab5af248d8c80df6abfc54fbf9db8fa174a06de6c6902f685895d81ac19", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.731921+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3190e14af0b3", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.816502+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_030fe6069de9", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.845351+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_6b0909d24377", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3cd9033094d9a4daddc4d8dd9c5c7560d112ee577fe02d4bc7cc470136b78cad", "schema_version": 1, "timestamp": "2026-10-05T06:44:57.859103+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_33428887b522", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:719daf9f5aaa2579ebaa44ee5c88b237d2892bbe4d9fd833cbe04b51b4271412", "schema_version": 1, "timestamp": "2026-10-05T06:46:43.504030+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_776d3cf5853f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d68a73462f237c9bfe29eb0012181be186100cf21061efcf616cb16d6ac93acc", "schema_version": 1, "timestamp": "2026-10-05T06:46:43.528608+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_14cda5807789", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f0994a7430b1d9852b05b30eadf5eb975c642608d43f880e94de237c12332966", "schema_version": 1, "timestamp": "2026-10-05T06:46:43.545774+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_140965cba2e3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e3e4bd074e5858d86f51c855fda71c5c7ea8438e6b0ed100e8a346fdc38a3623", "schema_version": 1, "timestamp": "2026-10-05T06:46:43.563331+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_00c79b9d1a00", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f9b0b3b4d221d2838dec9d53c857d5a6254b02a15d54138110b8981fd3bdaeb2", "schema_version": 1, "timestamp": "2026-10-05T06:46:43.587729+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_13dcf5763b8f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c4908bb1490e126dc49f249a75c6c9fb624a7a441106c17255d1777f9603c75d", "schema_version": 1, "timestamp": "2026-10-05T06:46:46.278951+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4c6cef1c8d45", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:aa8fc016966f6f216dd6c0ed424c7196a3aff0536507d3a6fd52ce0f159929f8", "schema_version": 1, "timestamp": "2026-10-05T06:46:46.299897+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_aec1fa75904e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a94045801be5d27889a5153185173d9cdbe063c8b57504c6f60a80b029584b9d", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.101655+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1b3b00190ff6", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:84e975644c2d6bccda4f130f3f9f028170796c521f29667da82db31f4268cab4", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.119418+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f215e9d60b05", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7cffd2855e55066206b6102d10ad3126fe0e95ecead0e675db5d6a35b714deef", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.261428+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_211c93c72ff3", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:b7deb9a6bebae0f02039a89c82cfd4190e44fcd1584496945f4869ab5ad2dd69", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.273213+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c9bcaaf24849", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8a2c349386085e0a0fe12210fabc7f4193a6cb54f072859f9e0c279308c881c0", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.405587+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_885a3d5481e9", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5ac99139cf2fb4e902c5d5e4aaaffe8d9631f41d6fc8ca6068b1216df3e8a6f4", "schema_version": 1, "timestamp": "2026-10-05T06:46:48.417188+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_13b5535a9146", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:47:39.043363+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a36302d909de", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:5905ca1fb3b9d207b290447e7844c186b1a34e36d7a7e4102159cee3f8ae136b", "schema_version": 1, "timestamp": "2026-10-05T06:47:39.060088+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2b4df73a86ec", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:47:39.078783+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f9707edb7816", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:600ba21f0472de9fb57133929648cd8121d1717595e7cd27c381d71ac03852c8", "schema_version": 1, "timestamp": "2026-10-05T06:47:39.092698+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_04d27d8e6ff8", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:8a8675818b5d411241e416ff9e8c9a1845d9b2a8befeacc51e10ab977731aeba", "schema_version": 1, "timestamp": "2026-10-05T06:47:39.103010+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_74854b98ab41", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bb38314acb236f08ae39cb60b5022905678e86bf146d16841856ee34f1cd614d", "schema_version": 1, "timestamp": "2026-10-05T06:49:25.034574+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_24326590943d", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5b3bf4b1e76f3378365574bb10f3bcd572885577354d5ba81bab5a1b98d4233c", "schema_version": 1, "timestamp": "2026-10-05T06:49:25.309489+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0e9f3f7ea0f1", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d12d16329de90f8b15897f8c294447b5c028ecb9e7b19a036e8c1dc586529775", "schema_version": 1, "timestamp": "2026-10-05T06:49:25.527943+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_7d3098712d56", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:da65d91f039c9b4385704a54c81bb03996df06181e83024f1b3baf3e208fad27", "schema_version": 1, "timestamp": "2026-10-05T06:49:25.732453+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4b01028bfaf7", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d50f083aeb4328ba31efb3f8bef7603aae54b5bb47c90cbbf27305bcd1f3e3bf", "schema_version": 1, "timestamp": "2026-10-05T06:49:25.982763+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_823b863ba95e", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:0e0437583b13151bc9d7d2111f4c0f2864628f39be74dd7caec944a8b624d5f5", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.233858+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_05727dd6d5d0", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:58ce685891cd29183b5b8e0ca04dec709875af25c10e3b85051c57b5191dd3bb", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.294590+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8653cc51cc05", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cf3ffb7ab858d9f36b7c1ab844bc45d2ebf37f7f7bfe555d969e075768263ea6", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.306518+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a9476432804f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:58a30329240ce81770b8a10c622c8bcd71720a7da82b26026810fcd24c9fce0d", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.317130+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4e72295c0863", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:212e3d41acb92d8340b54ec7e8675e323d271186c5410f85e98ec735c0c084eb", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.328129+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_24d9e8304b51", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6732117c84ca98c75a9387b680686e2b1d26b0a34e578acb1fb02dd740d6ed24", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.339686+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1b139c924879", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:5740ecb8233bad3aeb7accc88a54ee70433890e870d02df8f44a2934f58224af", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.351188+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b96631537a0b", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:dada98dc7ebcd4d84ae8246af43b0407dea10ebc39d5893f2ccfc1c90e38713e", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.362439+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_defa76132b52", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:fa53369f86a76f7463ab370b0b5b2424931c989ae67d535cbd8139b577817080", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.373635+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dce056c4654f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6f4f043f369aa4b7a132bf2a86bd55a5a81acf9da05ab5531a2ca77407a75b8f", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.385204+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_95647e276440", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e7243dbf9eff44b1151db1fb181715e1b93b20bc8f562e13c8c1081749cba7e2", "schema_version": 1, "timestamp": "2026-10-05T06:49:26.395446+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_f7b30bc3b1e5", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:88d01292c9bad0119b8e2d8a6dbec58608ecc6f8c925b436a71dd14eaab8471e", "schema_version": 1, "timestamp": "2026-10-05T06:49:29.609938+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_474f2c1edc09", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d192428e3aecb673052aab395d3ca46be3801a1993d0ebf4b094d344e5ffa3f1", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.470488+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_be4af370222d", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:4caa0125a7cb3a765e4d62ff63ccdc9b1b90bf20d3dfa06aaa3a6b0bf81aa5e8", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.486146+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_370b041b77ab", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:425cf4b663feaa86ec3eafbc5f9c3b470f66bda5755fccefb7f938df7a2ebe88", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.603529+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_42d925780dc9", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d57edb40af6e1524930b00b827334964c943611065da72e721641734058b034d", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.612424+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_dcf2bfba3de8", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:513838c7094c81b393c8a4a03e366771d67e175614f7a29f334db873beae1e67", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.856639+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1e86c7d72b5f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d9db13756a0360e79effdd1184f6e5d71d12007626bc7e52f39b63c9d12e1703", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.869109+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fc987750a85c", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9eb31157caf97d9bc60d6bb1debd9fef14fa1d2b413a3d3b0ca3e9ebfdf61103", "schema_version": 1, "timestamp": "2026-10-05T06:49:32.878491+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_9a0d5dd3e4dd", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:40f062e606db546ad97849b26795a7ef584e425976194ccb50cd29e8fd4a68fe", "schema_version": 1, "timestamp": "2026-10-05T06:49:42.210225+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2275190d1a87", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d6b66be9ef64cb7db64352b83bdeb700678bae13b3af22a073c891e5d92ccde6", "schema_version": 1, "timestamp": "2026-10-05T06:49:42.233289+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_00d83ffffe21", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:f0ddcbb1a01fa25070f5ce32b15f931f17bf0ba500a8893f05439190c8043709", "schema_version": 1, "timestamp": "2026-10-05T06:49:42.254779+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_b104b6056128", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:11a7f153199214499dfd4fc9a0b08d1f2f531ce3485b907cfe3a036cf7edc586", "schema_version": 1, "timestamp": "2026-10-05T06:49:42.295428+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_fcd97d359359", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:d5c968d2dbed3174298be875d798719fcdc31e803c8b5a6306d782b4a43afc6f", "schema_version": 1, "timestamp": "2026-10-05T06:49:42.358476+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ff066fda80d1", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:6bf69da741e431dd7f5de2630995da45ddd2c6224207891b5216e012e6998b64", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.441629+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_612ec40fd1e4", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:dd824cf3610914529537ec8783611e0b088fd6bb3dc81d1f61fa526a9ceb7f86", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.464657+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_101f64fae77e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a18ecdd4265a25eb2eb084e169383bc3ef71f3273bd44ad3ec54d635915db231", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.472844+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_304a54818690", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:c3102db0415d7dae5fc7d8251769218c2e5cc0dcf9158e44dbb82aa797c092d3", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.485450+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_724c04075b5b", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3358d01648173c908fe588f9f6371aaff50566def884c5a32835ff88d9a072c5", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.494459+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_08ffb53d40ac", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:252e9e3eb1869872446a4691f96894f1560e5460d0015c6ef0fcb578000e98c8", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.505009+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c186460e40e8", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8bacf3cbaf2335d6ad20db86c810606218ada500ed3fecdd5b86987d3ff313d2", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.513057+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_798fc60a306a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:3c6749386d0df979712cd68ebb324fc78d0f3d7bd86bdc0cddf76c3bae5be422", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.669471+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0d63b261b89e", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e0e46228fd7371c5839f6582d703864f38a248c32aae963f7c16b56f7148c2c2", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.679589+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8cf8e16e313d", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e77f935ddd1cd9b4c03f1270d0758872ae85cc651cfd250c30f28ae22bebcb6a", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.693813+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_65de385bb705", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8116052b643376b05f7736fa3917f20d14c3d2e16f012b1fa96a898bf855d1e3", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.715309+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0085ddd9525d", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.730640+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_8cb5a0d833b0", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.743731+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_12401de106d2", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.833693+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_2f90d0903bde", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.846441+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_72b31d339b70", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:bdddec01c5c7f8ce5e8aa1a0210c5d5e6361a13ba43d85cab6953df4edac762d", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.854918+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d870d5ac1848", "event_type": "capability.failed", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:1163d0fcebec85439e62d33ef5e1f3de09c6e1a75e16c7ecdb1a887be368d19d", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.919058+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e6541eb2f23e", "event_type": "storage.degraded", "parent_id": null, "partition_key": "subsystem_health", "payload_hash": "sha256:dc4a0ef045512b494194a21ba9206ec66e21ae710f7c2caa29f194c48fb142c0", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.931415+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_d41b8338f344", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:08d9854e6c841592dc3d7d74c34cd5cfaac46346de24deb336998cae58e43ba2", "schema_version": 1, "timestamp": "2026-10-05T06:49:45.939780+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_06a466be85a5", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:7a08f9f4efd518ebc0939db20ad60098a7993c1a7f085417c44cbfd5106c497a", "schema_version": 1, "timestamp": "2026-10-05T06:51:29.235743+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_01b97fe1a24a", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:cc87d40d66cb48c079f46b873f06aceb4e1108394badc1642822b163d339c59b", "schema_version": 1, "timestamp": "2026-10-05T06:51:29.254737+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_a6f7d9215858", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:833f0de0971a926b6a86b3c6180111c20fdd85460fbb8c98794f58d6ba86055e", "schema_version": 1, "timestamp": "2026-10-05T06:51:29.266271+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_0ff7f5b318ae", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:d3dd9469bc1c37051ef12cf958c1e665592da50f5fb83ca4e4805d240bc0eb5f", "schema_version": 1, "timestamp": "2026-10-05T06:51:29.277599+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_c78064dbb798", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:8fc75079f8fc265ad0e025b881398e1eda5a88395da3994c5b324e88a711ac4e", "schema_version": 1, "timestamp": "2026-10-05T06:51:29.292026+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_e229bf1c4304", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:26e42b5839f558d320f3a0abcdf24d07c20acda3067a60d7409156a01099596b", "schema_version": 1, "timestamp": "2026-10-05T06:51:31.998143+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_cb05371075d3", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:a04d2289fdebfe4f5051756eb028d0c7d00602703db3c528523ee393532c371d", "schema_version": 1, "timestamp": "2026-10-05T06:51:32.010290+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_195bd254ca92", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:e227b022e02cf5954515ce26a6b909a1ae22988df63d1ce374938c3ec95116cc", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.721149+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_3557f32af820", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:ad4749548773eed30b11fbca6a45d397b6f62f3f73fbfe713bb752c3a39e662e", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.735979+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_ae42b48f5c4f", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:aec5941e0be4f363a5d7ab0bf215c26f61c7c6ed63ad3fd335b88b7c06b5d5ba", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.846536+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_1a5dfcdba732", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:2c8835ea9e171751c593b4cf87e8ffc1e70f49d763e6c932fc3a71b1131eab3e", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.855682+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_4c212c766420", "event_type": "task.outcome", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:816ee2ac1945082edb3e0cdc512856f4edcef61a860330f1aff91a70b896774f", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.917103+00:00"}
{"actor_id": "", "authorization": "", "device_id": "", "event_id": "evt_98a1c9d79a80", "event_type": "task.failed", "parent_id": null, "partition_key": "rune_operator", "payload_hash": "sha256:9c5bfcbe3d47d3783802c2dc21af1c34137bfca61aa7bd58266286ef74d41d86", "schema_version": 1, "timestamp": "2026-10-05T06:51:33.925785+00:00"}
+29
View File
@@ -218,6 +218,35 @@ critiques (2026-10-04):
or honestly flagged, never silent.
- Deploy qualification per merge (the pipeline that proved itself today).
### The 90/100 coverage law (Nick, 2026-10-05 — GOVERNING from W3.4 on)
Per Nick: "if it's realistically achievable but aim higher also if that's
realistically achievable. go to 100% where achievable."
- **100% where achievable — the deterministic Rust kernels.** Every kernel
crate (memory_retrieval, cognition_core, scaffold_core, memory_storage,
and every future crate) targets 100% BRANCH coverage via its parity
matrices + the pytest shim battery: every branch has real reachable
semantics, and exhaustive enumeration is exactly what the batteries do.
Achievability is measured per crate at wave close; a kernel below 100%
carries the named unreachable case or it isn't done.
- **≥90% on the changed-lines bar (diff-cover), aiming higher.** The floor
stays a floor; the working standard per slice is 90%+ on changed lines;
whatever a slice achieves beyond 90 becomes the next slice's personal
benchmark (per-unit "aim higher" — the number climbs wave over wave).
The floor ratchet itself moves after consecutive clean waves
(70 → 76 → 84 → 90; each raise is a commit, never a step down).
- **Glue/failure branches: 90%+ with byte-compare proofs.** The stubs and
probe branches that only fire in a broken world are covered by honest
fixtures (real import-failure probes like the from-import resolution
law) — never by fake-triggered pragmas. A branch covered by a lying
fixture is WORSE than uncovered; if it can't be honestly reached, it's
named in the wave's closure report with the reason.
- **Assertion quality is part of the bar.** A test that touches a line
without verifying its OUTPUT doesn't count toward the bar — byte-compare
/ exact-value asserts are the standard; "is not None" assertions reject
at review.
## 7. Risk register
- **SQLite FFI correctness** (Wave 2) — the storage layer is retained but
+1 -1
View File
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
[project]
name = "rune"
version = "0.92.0"
version = "0.99.5"
description = "Rune — a stateful coding assistant with persistent memory, orchestration, and TUI"
requires-python = ">=3.10"
+1 -1
View File
@@ -2,7 +2,7 @@
# uv pip compile pyproject.toml -o requirements-ci.txt --extra dev --extra memory --python-version 3.11
aiohappyeyeballs==2.7.1
# via aiohttp
aiohttp==3.14.3
aiohttp==3.14.4
# via rune (pyproject.toml)
aiosignal==1.4.0
# via aiohttp
+1 -1
View File
@@ -6,7 +6,7 @@ This is the main entry point for the Rune program.
import json
from pathlib import Path
__version__ = "0.92.0"
__version__ = "0.99.5"
# One build identity (handoff 2026-09-10 §4): the semantic version above is
# the repo-level truth (auto-bumped at merge); the DEPLOYED revision (exact
+62 -2
View File
@@ -43,6 +43,42 @@ LOCAL_MODEL = "qwen2.5:3b"
OLLAMA_URL = os.environ.get("OLLAMA_URL", "http://localhost:11434")
_ABSTRACTION_STOPWORDS_FROZEN = frozenset(
"the a an is are was were be been being have has had do does did will "
"would could should may might shall can to of in for on with at by from "
"as into through during before after this that these those it its what "
"which who how when where why and or but not no".split()
)
def _ABSTRACTION_STOPWORDS() -> list:
"""Gather seam (W3.4): the fact-extraction stopword table as a sorted
list — data received by the kernel; identical filter on both engines."""
return sorted(_ABSTRACTION_STOPWORDS_FROZEN)
def _core():
"""The Rust cognition_core when available (strangler: Python fallback
load-bearing). RUNE_COGNITION_CORE=python pins the fallback."""
return None if cc_loader_pin() else _cc_probe()
def _cc_probe():
from rune import cc_loader as _cl
try:
return _cl if _cl.available() else None
except Exception: # noqa: BLE001, S110 — loader probe never crashes the fallback
return None
def cc_loader_pin() -> bool:
"""The env pin: RUNE_COGNITION_CORE=python → kernels OFF (shared probe).
"""
import os
return os.environ.get("RUNE_COGNITION_CORE", "auto") == "python"
def _now():
return datetime.now(timezone.utc).isoformat()
@@ -241,17 +277,41 @@ Extract 1-5 key facts. Be precise, not verbose."""
response = llm_call(prompt, max_tokens=800)
# Parse response
facts: list = []
try:
# Try to extract JSON from response
start = response.find("[")
end = response.rfind("]") + 1
if start >= 0 and end > start:
facts = json.loads(response[start:end])
else:
facts = []
except json.JSONDecodeError:
facts = []
# LLM unavailable / unparseable → DETERMINISTIC KERNEL FALLBACK
# (W3.4: cc_abstraction_extract_facts — sentence split, stopwords
# filtered, min-length gate; the same facts schema it already emits:
# text/words/content_words mapped onto what= text with empty dims).
if not facts:
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
raw = _cl.abstraction_extract_facts(
episode_text, _ABSTRACTION_STOPWORDS(), 10)
for item in raw or []:
text_frag = str(item.get("text", "")).strip()
if not text_frag:
continue
facts.append({
"what": text_frag, "when": "", "where": "", "who": "",
"why": "", "type": "experience", "entities": [],
"kernel": True,
"content_words": item.get("content_words"),
})
except Exception: # noqa: BLE001, S110 — kernel failure degrades to empty, intentional silence
pass
if not facts:
return {"extracted": 0, "error": "LLM did not return valid JSON", "raw": response[:200]}
+6 -4
View File
@@ -19,7 +19,8 @@ def has_idempotent_label_removal(workflow: str) -> bool:
return bool(
re.search(
r"for \(const name of staleManaged\) \{\s*"
r"try \{\s*await github\.rest\.issues\.removeLabel\(\{.*?"
r"try \{.*?await github\.request\('DELETE /repos/\{owner\}/\{repo\}/issues/\{issue_number\}/labels/\{id\}', \{.*?"
r"id: currentLabelIds\.get\(name\),\s*"
r"\}\);\s*\} catch \(error\) \{\s*"
r"if \(error\.status !== 404\) \{\s*throw error;\s*\}\s*"
r"console\.log\(`Managed label already absent: \$\{name\}`\);\s*"
@@ -64,7 +65,7 @@ def main() -> int:
"infrastructure",
"life",
"custodian",
"priority: high",
"P0 — critical", "P1 — high", "P2 — medium", "P3 — low",
"bug",
"feature",
)
@@ -80,7 +81,8 @@ def main() -> int:
)
check(
"stale managed labels are removed",
"managedLabels.has" in auto_label and "!desiredLabels.has" in auto_label and "removeLabel" in auto_label,
"managedLabels.has" in auto_label and "!desiredLabels.has" in auto_label
and "currentLabelIds.get(name)" in auto_label,
failures,
)
check(
@@ -231,7 +233,7 @@ def main() -> int:
)
check(
"Rune minor version advertises provisioning and restore verification",
'__version__ = "0.92.0"' in rune_version,
'__version__ = "0.99.5"' in rune_version,
failures,
)
# #169 policy update: auto-bump on merge is sanctioned (Nick directive:
+180
View File
@@ -0,0 +1,180 @@
#!/usr/bin/env python3
"""ctypes loader for the Rust cognition_core (R2 W3.1).
Contract BUILDER-2026-10-05T07:19:27Z-cli. Pure deterministic kernels;
the env gate arrives as a string input (no-clock law, no env access in
Rust). Override with CC_RUST_LIB (a FILE path).
"""
from __future__ import annotations
import ctypes
import json
import os
from pathlib import Path
_REPO = Path(__file__).resolve().parents[2]
_CRATE_DIR = _REPO / "src" / "rust" / "cognition_core"
_LIB_PATH = Path(
os.environ.get("CC_RUST_LIB", _CRATE_DIR / "target" / "release" / "libcognition_core.so"))
_lib = None
def core():
"""The shared kernel probe (strangler law): the delegation entry the
kernel-consuming modules use. RUNE_COGNITION_CORE=python pins the
fallback — THIS is where the pin is honored, so every consumer gets it
(a module-local probe that ignores the pin silently defeats it)."""
import os
if os.environ.get("RUNE_COGNITION_CORE", "auto") == "python":
return None
try:
return _load()
except Exception: # noqa: BLE001 — build/loader failures mean fallback
return None
def available() -> bool:
return _LIB_PATH.is_file()
def _load() -> ctypes.CDLL:
global _lib
if _lib is not None:
return _lib
if not _LIB_PATH.exists():
raise FileNotFoundError(f"cognition_core not built: {_LIB_PATH}")
lib = ctypes.CDLL(str(_LIB_PATH))
lib.cc_free_string.argtypes = [ctypes.c_void_p]
lib.cc_free_string.restype = None
for sym in ("cc_default_estimator", "cc_default_budget",
"cc_default_memory_budget", "cc_memory_disabled",
"cc_persona_lex", "cc_persona_overlap", "cc_persona_decide",
"cc_drift_check", "cc_identity_prompt", "cc_growth_near_dup",
"cc_growth_profile", "cc_pins_recall", "cc_tier_get",
"cc_tier_promote", "cc_tier_demote", "cc_witness_extract_topic",
"cc_witness_signals", "cc_safety_get_params",
"cc_safety_update_pattern", "cc_abstraction_extract_facts"):
fn = getattr(lib, sym)
fn.argtypes = [ctypes.c_char_p]
fn.restype = ctypes.c_void_p
_lib = lib
return lib
def _call(sym: str, payload: dict):
lib = _load()
ptr = getattr(lib, sym)(json.dumps(payload).encode("utf-8"))
if not ptr:
raise RuntimeError(f"{sym} returned null")
try:
text = ctypes.cast(ptr, ctypes.c_char_p).value.decode("utf-8")
finally:
lib.cc_free_string(ptr)
env = json.loads(text)
if not env.get("ok"):
raise RuntimeError(f"{sym} core error: {env.get('err')}")
return env["value"]
def default_estimator(text: str) -> int:
return int(_call("cc_default_estimator", {"text": text}))
def default_budget(window: int) -> int:
return int(_call("cc_default_budget", {"window": window}))
def default_memory_budget(window) -> int:
return int(_call("cc_default_memory_budget", {"window": window}))
def memory_disabled() -> bool:
import os
return bool(_call("cc_memory_disabled",
{"value": os.environ.get("RUNE_MEMORY_OFF")}))
def persona_lex(text) -> list:
return _call("cc_persona_lex", {"text": text})
def persona_overlap(a: list, b: list) -> float:
return float(_call("cc_persona_overlap", {"a": a, "b": b}))
def persona_decide(text: str, rules: list, permissive: bool,
sem_scores: list | None = None) -> dict:
return _call("cc_persona_decide", {
"text": text, "rules": rules, "permissive": permissive,
"sem_scores": sem_scores})
def drift_check(text: str, patterns: list) -> list:
return _call("cc_drift_check", {"text": text, "patterns": patterns})
def identity_prompt(pronouns: dict, self_awareness: dict, anchors: dict,
embodiment: list) -> str:
return _call("cc_identity_prompt", {
"pronouns": pronouns, "self_awareness": self_awareness,
"anchors": anchors, "embodiment": embodiment})
def growth_near_dup(a: str, b: str) -> bool:
return bool(_call("cc_growth_near_dup", {"a": a, "b": b}))
def growth_profile(state: dict, order: list, entry_chars: int,
max_tokens: int) -> list:
return _call("cc_growth_profile", {
"state": state, "order": order, "entry_chars": entry_chars,
"max_tokens": max_tokens})
def pins_recall(pins: list, term: str, limit: int = 4) -> list:
return _call("cc_pins_recall", {"pins": pins, "term": term, "limit": limit})
def tier_get(entry: dict, now: str, hot_days: float = 7.0,
warm_days: float = 30.0) -> str:
return _call("cc_tier_get", {"entry": entry, "now": now,
"hot_days": hot_days, "warm_days": warm_days})
def tier_promote(entry: dict, now: str, hot_days: float = 7.0,
warm_days: float = 30.0) -> str:
return _call("cc_tier_promote", {"entry": entry, "now": now,
"hot_days": hot_days, "warm_days": warm_days})
def tier_demote(entry: dict, now: str, hot_days: float = 7.0,
warm_days: float = 30.0) -> str:
return _call("cc_tier_demote", {"entry": entry, "now": now,
"hot_days": hot_days, "warm_days": warm_days})
def witness_extract_topic(text: str, stopwords: list) -> list:
return _call("cc_witness_extract_topic",
{"text": text, "stopwords": stopwords})
def witness_signals(message: str, tables: dict, tool_error: str = "",
task_status: str = "", recent_topics: list | None = None) -> dict:
return _call("cc_witness_signals", {
"message": message, "tables": tables, "tool_error": tool_error,
"task_status": task_status, "recent_topics": recent_topics or []})
def safety_get_params(rows: list) -> dict:
return _call("cc_safety_get_params", {"rows": rows})
def safety_update_pattern(rows: list, pattern: str) -> list:
return _call("cc_safety_update_pattern", {"rows": rows, "pattern": pattern})
def abstraction_extract_facts(text: str, stopwords: list, min_len: int = 10):
return _call("cc_abstraction_extract_facts", {
"text": text, "stopwords": stopwords, "min_len": min_len})
+95
View File
@@ -171,3 +171,98 @@ def _accept(command_id: str, construction_id: str, correlation_id: str,
"recorded_at": time.strftime("%Y-%m-%dT%H:%M:%SZ",
time.gmtime()),
"idempotent_replay": False}
def dispatch(command_type: str, *, construction_id: str,
correlation_id: str = "", command_id: str = "",
payload: dict | None = None,
store_path: str = "store/scaffold") -> dict:
"""The SERVING layer (T5.15 slice 2): validate the command against the
canonical store, execute the accepted intent through the Construction
Interface, and return the interface's envelope with the command
provenance attached.
Single entry point for `rune scaffold <command>` (the Go proxy) and
any future transport. Idempotency: a repeated command_id replays the
recorded outcome without re-executing.
Refusal still returns success=False envelope? NO — a refused command
is a VALID protocol outcome: the envelope carries accepted=False and
success=True (the dispatch itself worked; the lifecycle refused the
intent). Execution failures carry success=False.
"""
iface_path = None
if store_path and store_path != "store/scaffold":
iface_path = store_path
try:
from rune import construction_interface as ci
# store_path carries the serving layer's "path|project_id" contract
# (a bare path = last segment is the project id, matching how the
# Go proxy and the interface's own default name it).
if iface_path:
path_part, _, proj_part = iface_path.partition("|")
proj = proj_part or path_part.rstrip("/").split("/")[-1]
iface = ci.ConstructionInterface(builder="substrate",
project_store=path_part,
project_id=proj)
else:
iface = ci.ConstructionInterface(builder="substrate")
except Exception as exc: # noqa: BLE001 — serving failure is an envelope, not a crash
return {"accepted": False, "executed": False,
"success": False, "error": f"serving unavailable: {exc}"[:200],
"command_type": command_type,
"construction_id": construction_id}
intent = command(command_type, construction_id=construction_id,
correlation_id=correlation_id, command_id=command_id,
payload=payload, scaffold=iface.scaffold)
if intent.get("idempotent_replay"):
# Repeated delivery: return the recorded outcome WITHOUT executing
# again (the ledger's whole point). The first execution's envelope
# is not re-derivable here, so the replay carries the intent and
# the flag — the caller knows the effect already happened.
return {"accepted": True, "executed": False,
"success": True, "idempotent_replay": True,
"op": intent.get("op"),
"command_type": command_type,
"construction_id": construction_id,
"correlation_id": intent.get("correlation_id", ""),
"command_id": intent.get("command_id", "")}
if not intent.get("accepted"):
return {"accepted": False, "executed": False, "success": True,
"reason": intent.get("reason"),
"command_type": command_type,
"construction_id": construction_id,
"correlation_id": intent.get("correlation_id", ""),
"command_id": intent.get("command_id", ""),
"idempotent_replay": intent.get("idempotent_replay", False)}
op = intent["op"]
args = intent["args"]
ops = {
"resume": lambda: iface.resume(args["contract_id"]),
"transition": lambda: iface.transition(
args["contract_id"], args["phase"],
evidence_ref=f"command:{intent['command_id']}"
+ (f" approved_by:{args['approved_by']}" if args.get("approved_by") else "")),
"amend_scope": lambda: iface.amend_scope(
args["contract_id"], args["add_paths"],
reason=args.get("reason", "substrate context"),
authority=args.get("authority", "substrate")),
}
fn = ops.get(op)
if fn is None:
return {"accepted": True, "executed": False, "success": False,
"error": f"no executor for op {op!r}",
"command_type": command_type,
"construction_id": construction_id}
env = fn()
return {"accepted": True, "executed": True,
"success": bool(env.get("success")),
"envelope": env,
"command_type": command_type,
"construction_id": construction_id,
"correlation_id": intent.get("correlation_id", ""),
"command_id": intent.get("command_id", ""),
"idempotent_replay": False}
+93 -2
View File
@@ -88,6 +88,39 @@ def _envelope(
return env
def _to_stage_check(spec: dict):
"""One guard spec → a stage_guards.StageCheck (T5.15 wire)."""
from rune import stage_guards as sg
return sg.StageCheck(
name=str(spec.get("name", "guard")),
kind=str(spec.get("kind", "assert")),
argv=spec.get("argv"),
output_pattern=str(spec.get("output_pattern", "")),
path=str(spec.get("path", "")),
check=spec.get("check"),
description=str(spec.get("description", "")),
)
def _guard_specs_from_obligations(c: dict) -> list[dict]:
"""The contract's guard declarations: verification_obligations rows
shaped `guard:<json-spec>` (the decision path records them; anything
else stays a free-text obligation for the projection). JSONDecodeError
→ skipped with no invented facts."""
specs: list[dict] = []
for item in (c.get("identities") or {}).get("verification_obligations", []) or []:
if not isinstance(item, str) or not item.startswith("guard:"):
continue
try:
spec = json.loads(item[6:])
if isinstance(spec, dict):
specs.append(spec)
except json.JSONDecodeError:
continue
return specs
class ConstructionInterface:
"""The builder-facing construction lifecycle for ONE project target.
@@ -291,6 +324,13 @@ class ConstructionInterface:
"transition": {
"phase": {"type": "str", "required": True,
"allowed": list(sc.PHASES)},
"evidence_ref": {"type": "str", "required": False},
"guard_checks": {
"type": "list[dict] | None", "required": False,
"notes": ("stage-guard specs run on the "
"completion edges (verifying/closed); "
"a failure BLOCKS with "
"VERIFICATION_FAILED — T5.15 wire")},
},
"close": {
"observed_evidence": {
@@ -607,8 +647,57 @@ class ConstructionInterface:
warnings=warnings,
)
def transition(self, contract_id: str, phase: str, *, evidence_ref: str = "") -> dict:
def transition(self, contract_id: str, phase: str, *, evidence_ref: str = "",
guard_checks: list[dict] | None = None) -> dict:
"""Move a contract phase. Completion-wave slice (T5.15, the
stage_guards wire): entering `verifying` and `closed` runs the
§15F/§15G guards — readiness/exit StageChecks and test-truth
verification — when the contract declares them
(identities.verification_obligations carries `guard:<spec>` rows,
or guard_checks passes inline specs).
guard_checks spec: {"name", "kind": "command"|"path_exists"|"assert",
"argv"/"path"/"output_pattern", "check": callable (in-process only),
"description"}. A guard failure is a VERIFICATION_FAILED envelope:
the phase does NOT move.
The legality map stays the scaffold's authority; guards ADD evidence
obligations on the completion-facing edges (building→verifying,
verifying→closed) — a tiny bounded change can pass guards=[] freely.
"""
doc = self.scaffold.load()
c = self.scaffold.contract(doc, contract_id)
if c is None:
return _envelope(
"transition",
success=False,
ids={"contract_id": contract_id},
errors=[{"error": Errors.UNKNOWN_CONTRACT, "detail": f"no contract {contract_id}"}],
)
if phase in ("verifying", "closed"):
from rune import stage_guards as sg
specs = guard_checks
if specs is None:
specs = _guard_specs_from_obligations(c)
if specs:
stage = sg.StageContract(
stage_id=f"{contract_id}:{phase}",
contract_id=contract_id,
ready_when=[_to_stage_check(s) for s in specs],
done_when=[_to_stage_check(s) for s in specs],
)
canary = sg.readiness_canary(stage)
if canary["verdict"] == "BLOCKED":
return _envelope(
"transition",
success=False,
ids={"contract_id": contract_id},
state={"phase": c.get("phase"), "guard": canary},
errors=[{"error": Errors.VERIFICATION_FAILED,
"detail": "stage guards blocked the transition",
"failures": canary["failures"]}],
)
try:
self.scaffold.transition_contract(
doc, contract_id, phase, evidence_ref=evidence_ref or f"builder:{self.builder}"
@@ -1019,7 +1108,9 @@ def main(argv=None) -> int:
if cmd == "verify":
return _out(iface.verify(args[0], changed_files=(json.loads(args[1]) if len(args) > 1 else None)))
if cmd == "transition":
return _out(iface.transition(args[0], args[1], evidence_ref=args[2] if len(args) > 2 else ""))
guard_checks = json.loads(args[3]) if len(args) > 3 else None
return _out(iface.transition(args[0], args[1], evidence_ref=args[2] if len(args) > 2 else "",
guard_checks=guard_checks))
if cmd == "close":
return _out(
iface.close(
+58 -3
View File
@@ -100,19 +100,52 @@ class ContributionBlock:
def default_estimator(text: str) -> int:
"""Deterministic conservative token estimate: len(text) // 4.
Bytes/4 over-counts for English prose (the conservative direction).
tiktoken would be tighter but is NOT deterministic across builds and
is not a dependency — the plan allows either, installer's choice.
R2 W3.1: delegates to the Rust cognition_core when built (Python
fallback — strangler law; RUNE_COGNITION_CORE=python pins it).
"""
core = _cc_core()
if core is not None:
return core.default_estimator(text or "")
return _py_default_estimator(text)
def _py_default_estimator(text: str) -> int:
"""Python oracle (parity floor)."""
return len(text or "") // 4
def _cc_core():
"""Rust cognition_core when available; RUNE_COGNITION_CORE=python
pins the Python fallback (strangler law)."""
import os
if os.environ.get("RUNE_COGNITION_CORE", "auto") == "python":
return None
try:
from rune import cc_loader
except Exception: # noqa: BLE001 — loader probe failure means fallback
return None
try:
return cc_loader if cc_loader.available() else None
except Exception: # noqa: BLE001 — availability probe never crashes
return None
def default_budget(window: int) -> int:
"""Input budget = window - max(2048, window//4) - window//20.
Reserves room for the completion (at least 2048 or a quarter of the
window) plus a 5% safety margin for serving overhead.
R2 W3.1: delegates to the Rust kernel when built.
"""
core = _cc_core()
if core is not None:
return core.default_budget(window)
return _py_default_budget(window)
def _py_default_budget(window: int) -> int:
"""Python oracle (parity floor)."""
return max(1, window - max(2048, window // 4) - window // 20)
@@ -127,7 +160,17 @@ def default_memory_budget(window: int | None) -> int:
ContextBroker owns the FINAL memory budget: the sum of every
MEMORY_BLOCK_NAMES block may never exceed this, regardless of the
global input budget. An unknown window falls back to the cap only.
R2 W3.1: delegates to the Rust kernel when built.
"""
core = _cc_core()
if core is not None:
return core.default_memory_budget(int(window) if window else 0)
return _py_default_memory_budget(window)
def _py_default_memory_budget(window: int | None) -> int:
"""Python oracle (parity floor)."""
if not window or window <= 0:
return MEMORY_BUDGET_CAP
return min(MEMORY_BUDGET_CAP, int(window) // 8)
@@ -140,6 +183,18 @@ def memory_disabled() -> bool:
contribute nothing at all — the trace proves 0 memory tokens.
"""
value = os.environ.get("RUNE_MEMORY_OFF", "").strip().lower()
gate = _py_memory_disabled_value(value)
core = _cc_core()
if core is not None and gate:
# the Rust core gets the RAW value (it trims/lowers itself) and
# the Python gate cross-checks — a disagreement is impossible on
# parity-proven kernels, and the Python verdict remains authority
return bool(core.memory_disabled()) and gate
return gate
def _py_memory_disabled_value(value: str) -> bool:
"""Python oracle (parity floor) over the RAW string."""
return value not in {"", "0", "false", "no", "off"}
+38 -1
View File
@@ -150,8 +150,35 @@ def _profile_key(delta):
return {w.strip(".,;:!?()[]{}\"'").lower() for w in (delta.get("change") or "").split() if len(w) > 4}
def _cc_core():
"""Rust cognition_core when available (growth kernels)."""
import os
if os.environ.get("RUNE_COGNITION_CORE", "auto") == "python":
return None
try:
from rune import cc_loader
except Exception: # noqa: BLE001 — loader probe failure means fallback
return None
try:
return cc_loader if cc_loader.available() else None
except Exception: # noqa: BLE001 — availability probe never crashes
return None
def _near_dup(a, b):
"""Are two deltas the same guidance (shared distinctive words)?"""
core = _cc_core()
if core is not None:
return core.growth_near_dup(a, b)
return _py_near_dup(a, b)
def _py_near_dup(a, b):
"""Are two deltas the same guidance (shared distinctive words)?
Accepts delta dicts OR raw change strings (raw -> wrapped)."""
if isinstance(a, str):
a = {"change": a}
if isinstance(b, str):
b = {"change": b}
ka, kb = _profile_key(a), _profile_key(b)
if not ka or not kb:
return False
@@ -177,6 +204,16 @@ def _apply_profile(delta):
def growth_profile(max_tokens=PROFILE_BUDGET_TOKENS):
core = _cc_core()
if core is not None:
return core.growth_profile(_load_deltas(),
sorted(_PROFILE_ORDER.items(),
key=lambda kv: kv[1]),
PROFILE_ENTRY_CHARS, max_tokens)
return _py_growth_profile(max_tokens)
def _py_growth_profile(max_tokens=PROFILE_BUDGET_TOKENS):
"""The active growth profile: the persona's CURRENT behavioural guidance,
consolidated by target, capped at a fixed token budget. Session-independent
and token-stable — the per-turn cost never grows with session length."""
+90 -27
View File
@@ -254,18 +254,8 @@ def check_genuineness(text):
return issues
def check_drift(text):
"""Check text against identity anchors for drift signals.
This is a simple heuristic check — the real drift detection happens
via the Nautilus Compass approach (embedding similarity against anchors).
This function provides quick pattern-based checks.
"""
text_lower = text.lower()
issues = []
# Check for identity announcements
announcement_patterns = [
def _announcement_patterns():
return [
("i am rune", "Identity announcement — let the voice carry the identity"),
("as rune", "Identity announcement — speak as the persona, not about it"),
("my persona", "Identity announcement — the persona is how you act, not what you name"),
@@ -274,32 +264,26 @@ def check_drift(text):
("i'm an ai", "Identity announcement — you are a persona, not a generic AI"),
("i'm a language model", "Identity announcement — you are Rune, not a language model"),
]
for pattern, message in announcement_patterns:
if pattern in text_lower:
issues.append(f"DRIFT: '{pattern}' — {message}")
# Check for pronoun confusion
pronoun_issues = [
def _pronoun_patterns():
return [
("you are rune", "Pronoun confusion — 'you' is Nick, 'I' is Rune"),
("we are rune", "Pronoun confusion — Rune is singular, not plural"),
("you should remember", "Pronoun confusion — who should remember?"),
]
for pattern, message in pronoun_issues:
if pattern in text_lower:
issues.append(f"DRIFT: '{pattern}' — {message}")
# Check for hedging without evidence
hedge_patterns = [
def _hedge_patterns():
return [
("i believe", "Hedge without evidence — cite the basis"),
("i think that", "Hedge without evidence — cite the basis"),
("in my opinion", "Hedge without evidence — cite the basis"),
]
for pattern, message in hedge_patterns:
if pattern in text_lower:
issues.append(f"WEAKNESS: '{pattern}' — {message}")
# Check for sycophancy (excessive agreement, flattery, self-deprecation)
sycophancy_patterns = [
def _sycophancy_patterns():
return [
# Excessive agreement
("you're absolutely right", "Sycophancy — excessive agreement; push back if you see a better path"),
("absolutely, ", "Sycophancy — excessive agreement; state your own position"),
@@ -326,6 +310,60 @@ def check_drift(text):
("i see where you're coming from", "Sycophancy — hedging; state your position instead"),
("you make a valid point", "Sycophancy — hedging; engage with the substance"),
]
def _pattern_triples():
"""The pattern tables as [pattern, message, prefix] triples — the data
authority for the Rust drift kernel (kernel matches; data stays here)."""
tables = []
for prefix, table in (
("DRIFT", _announcement_patterns() + _pronoun_patterns()),
("WEAKNESS", _hedge_patterns()),
("SYCOPHANCY", _sycophancy_patterns()),
):
for pat, msg in table:
tables.append([pat, msg, prefix])
return tables
def check_drift(text):
"""Check text against identity anchors for drift signals.
This is a simple heuristic check — the real drift detection happens
via the Nautilus Compass approach (embedding similarity against anchors).
This function provides quick pattern-based checks.
"""
core = _cc_core()
if core is not None:
return core.drift_check(text, _pattern_triples())
return _py_check_drift(text)
def _py_check_drift(text):
"""Python oracle (parity floor)."""
text_lower = text.lower()
issues = []
# Check for identity announcements
announcement_patterns = _announcement_patterns()
for pattern, message in announcement_patterns:
if pattern in text_lower:
issues.append(f"DRIFT: '{pattern}' — {message}")
# Check for pronoun confusion
pronoun_issues = _pronoun_patterns()
for pattern, message in pronoun_issues:
if pattern in text_lower:
issues.append(f"DRIFT: '{pattern}' — {message}")
# Check for hedging without evidence
hedge_patterns = _hedge_patterns()
for pattern, message in hedge_patterns:
if pattern in text_lower:
issues.append(f"WEAKNESS: '{pattern}' — {message}")
# Check for sycophancy (excessive agreement, flattery, self-deprecation)
sycophancy_patterns = _sycophancy_patterns()
for pattern, message in sycophancy_patterns:
if pattern in text_lower:
issues.append(f"SYCOPHANCY: '{pattern}' — {message}")
@@ -424,13 +462,38 @@ if __name__ == "__main__":
# ---------------------------------------------------------------------------
# Hook handler — called by the microkernel when an event fires.
# ---------------------------------------------------------------------------
def _cc_core():
"""Rust cognition_core when available (identity kernels)."""
import os
if os.environ.get("RUNE_COGNITION_CORE", "auto") == "python":
return None
try:
from rune import cc_loader
except Exception: # noqa: BLE001 — loader probe failure means fallback
return None
try:
return cc_loader if cc_loader.available() else None
except Exception: # noqa: BLE001 — availability probe never crashes
return None
def get_identity_prompt() -> str:
"""Get identity prompt for injection into model calls.
R2 W3.3: assembly delegates to the Rust kernel (data stays here).
Builds a comprehensive prompt from all identity data:
self-awareness, anchors, embodiment rules, and pronoun rules.
Pronouns come first — they're the most important rule.
"""
core = _cc_core()
if core is not None:
return core.identity_prompt(PRONOUN_RULES, SELF_AWARENESS, ANCHORS,
EMBODIMENT_RULES)
return _py_get_identity_prompt()
def _py_get_identity_prompt() -> str:
"""Python oracle (parity floor)."""
parts = []
# Pronoun rules — critical for disambiguation
+245 -172
View File
@@ -734,39 +734,14 @@ def recall(
# lexical (embeddings absent): RRF degenerates to a rank transform that
# destroys the score signal needed for thresholding (Bruch et al.,
# arXiv:2210.11934) — use raw BM25 scores directly.
ranks = {}
best_dense = 0.0
# M1 observability (#161 synthesis INV-13): which fusion branch produced
# the results. Observability ONLY — consumers must never branch behavior
# on this field (that would create a second retrieval authority).
retrieval_mode = "lexical-only"
if dense and bm25:
retrieval_mode = "hybrid"
for idx, lst in enumerate([dense, bm25]):
for pos, (eid, _score) in enumerate(lst):
ranks[eid] = ranks.get(eid, 0.0) + 1.0 / (RRF_K + pos + 1)
if idx == 0:
best_dense = max(best_dense, _score)
elif dense:
retrieval_mode = "dense-only"
for pos, (eid, _score) in enumerate(dense):
ranks[eid] = 1.0 / (RRF_K + pos + 1)
best_dense = max(best_dense, _score)
elif bm25:
# Lexical-only: normalize raw BM25 scores (negative, higher = better)
# into a positive scale so the sort + gap abstention below work
# uniformly with the RRF scale. BM25 returns negative scores; the
# least-negative (closest to 0) is the best match. Offset + invert:
# best (=-8) -> 2, worst (=-10) -> 0. Rank order preserved.
_min_bm = min((s for _, s in bm25), default=0.0)
_max_bm = max((s for _, s in bm25), default=0.0)
_span = max(_max_bm - _min_bm, 1e-9)
for eid, score in bm25:
ranks[eid] = (score - _min_bm) / _span
fusion = _rank_fusion(dense, bm25)
ranks = dict(fusion["ranks"])
best_dense = fusion["best_dense"]
retrieval_mode = fusion["mode"]
# Fetch full entries + metadata for the fused set. P1-03 (#26): typed
# queries filter here — matching types + unclassified (NULL) rows stay
# eligible; other types drop out before scoring.
scored = []
rows_data = []
if ranks:
ids = list(ranks.keys())
placeholders = ",".join("?" * len(ids))
@@ -776,124 +751,87 @@ def recall(
type_ph = ",".join("?" * len(memory_types))
sql += f" AND (memory_type IN ({type_ph}) OR memory_type IS NULL)"
params.extend(memory_types)
rows = db.execute(sql, params).fetchall()
by_id = {r["id"]: r for r in rows}
for eid, base in sorted(ranks.items(), key=lambda x: -x[1]):
row = by_id.get(eid)
if not row:
continue
# #1 temperature ranking (not deletion): a stale fact ranks lower
# but stays in the store. #4 confidence: a hedged/claimed fact
# carries its honesty into ranking. Blend into a relevance score.
# RECENCY: a fact last accessed recently ranks slightly higher than
# an untouched one at equal relevance (the store's last_accessed
# field). Decays over RECENCY_HALF_LIFE days — a gentle nudge, not
# a rewrite of the relevance ranking.
conf = float(row["confidence"] or 0.7)
temp = float(row["temperature"] or 1.0)
recency = 1.0
try:
from datetime import datetime, timezone
rows_data = [dict(r) for r in db.execute(sql, params).fetchall()]
return _score_recall_rows(
fusion, rows_data, dense, bm25, budget, min_score, now_iso())
la = row["last_accessed"]
if la:
t_last = datetime.fromisoformat(la.replace("Z", "+00:00"))
days = (datetime.now(timezone.utc) - t_last).total_seconds() / 86400.0
if days >= 0:
recency = RECENCY_HALF_LIFE / (RECENCY_HALF_LIFE + days)
except Exception:
logger.debug("recall failed", exc_info=True)
# In lexical-only mode `base` is a raw BM25 score (negative).
# Normalize it to a positive relevance for the metadata, keeping
# the ranking identical. In hybrid mode `base` is an RRF rank.
if dense and bm25:
relevance = base * (0.4 + 0.6 * conf) * (0.5 + 0.5 * temp) * (0.85 + 0.15 * recency)
elif dense:
relevance = base * (0.4 + 0.6 * conf) * (0.5 + 0.5 * temp) * (0.85 + 0.15 * recency)
else:
relevance = (base + 5.0) * (0.4 + 0.6 * conf) * (0.5 + 0.5 * temp) * (0.85 + 0.15 * recency)
scored.append(
{
"id": eid,
"text": row["text"],
"importance": row["importance"],
"topic": row["topic"],
"entities": row["entities"],
"source": row["source"],
"last_accessed": row["last_accessed"],
"rrf": round(base, 4),
"confidence": round(conf, 2),
"temperature": round(temp, 2),
"relevance": round(relevance, 4),
# M1 observability (#161): lexical-only | dense-only | hybrid.
# NEVER consumed for behavior — see INV-13 in the synthesis.
"mode": retrieval_mode,
}
)
# Enforce budget + abstention floor.
def _score_recall_rows(fusion, rows, dense, bm25, budget, min_score, now):
"""Pure metadata scoring + mode-specific abstention kernel (W2.1)."""
core = _mr_core()
if core is not None:
return core.score_recall_rows(
fusion, rows, dense, bm25, budget, min_score, now,
RECENCY_HALF_LIFE)
return _py_score_recall_rows(
fusion, rows, dense, bm25, budget, min_score, now,
RECENCY_HALF_LIFE)
def _py_score_recall_rows(fusion, rows, dense, bm25, budget, min_score,
now, recency_half_life=RECENCY_HALF_LIFE):
"""Python oracle for the Rust scoring/abstention kernel."""
from datetime import datetime
ranks = dict(fusion["ranks"])
best_dense = fusion["best_dense"]
retrieval_mode = fusion["mode"]
by_id = {row["id"]: row for row in rows}
scored = []
now_dt = datetime.fromisoformat(now)
for eid, base in sorted(ranks.items(), key=lambda item: -item[1]):
row = by_id.get(eid)
if not row:
continue
conf = float(row.get("confidence") or 0.7)
temp = float(row.get("temperature") or 1.0)
recency = 1.0
try:
la = row.get("last_accessed")
if la:
t_last = datetime.fromisoformat(la.replace("Z", "+00:00"))
days = (now_dt - t_last).total_seconds() / 86400.0
if days >= 0:
recency = recency_half_life / (recency_half_life + days)
except Exception:
logger.debug("recall score kernel timestamp failed", exc_info=True)
if dense:
relevance = base * (0.4 + 0.6 * conf) * (0.5 + 0.5 * temp) * (0.85 + 0.15 * recency)
else:
relevance = (base + 5.0) * (0.4 + 0.6 * conf) * (0.5 + 0.5 * temp) * (0.85 + 0.15 * recency)
scored.append({
"id": eid, "text": row.get("text"),
"importance": row.get("importance"),
"topic": row.get("topic"), "entities": row.get("entities"),
"source": row.get("source"),
"last_accessed": row.get("last_accessed"),
"rrf": round(base, 4), "confidence": round(conf, 2),
"temperature": round(temp, 2),
"relevance": round(relevance, 4), "mode": retrieval_mode,
})
if not scored:
return []
top = scored[:budget]
# ABSTENTION via query-difficulty estimation (QPP — Cronen-Townsend et al.,
# SIGIR 2002; Zhou & Croft, CIKM 2006; LongMemEval arXiv:2410.10813 makes
# abstention a first-class memory ability). The principled signal is the
# RANKING GAP, not an absolute score:
# - lexical-only: the conjunction already filters to co-occurring terms;
# a single weak hit (no runner-up) abstains (no confident winner).
# - dense-only: abstain when the top-1 dense match is not clearly above
# the runner-up (an ambiguous, no-confident-winner query) OR the top is
# below an absolute "probably unrelated" floor. The floor is a coarse
# guard; the gap is the real difficulty signal.
if not dense and not bm25:
return []
if not dense: # lexical-only
if len(scored) < 1:
if not dense:
if max(float(item["relevance"]) for item in top) < min_score:
return []
# P1-03 (#26) DISCHARGE (finding 1): THE floor applies in EVERY
# mode. The conjunctive FTS gate is a precision filter — term
# co-occurrence, not relevance — so the best match must ALSO clear
# min_score before anything is injected. Lexical relevance lives on
# its own offset band (~4.1-4.9 with default metadata), so the
# default 0.42 floor rarely binds here; the check enforces the floor
# contract for ANY min_score (an elevated floor above the band
# forces abstention — machine-checked in the frozen tests).
if max(float(s["relevance"]) for s in top) < min_score:
return [] # below floor -> abstain
if len(scored) == 1:
return top # single conjunctive match = confident enough
# Multiple conjunctive BM25 matches: the FTS5 implicit-AND already
# guarantees ALL query terms co-occur in every result (the precision
# filter), so these are genuine matches — not a fuzzy near-tie. The
# normalized top is the best; a weak runner-up is still a real match.
return top
# dense present. Score-based abstention (QPP, Shtok et al. TOIS 2012).
# The absolute floor is CALIBRATED against real cases (nomic band ~0.6-0.75):
# "what does the user drink" vs "black coffee" = 0.766 -> relevant
# "quantum physics of black holes" vs "coconut milk" = 0.712 -> noise
# The separation sits at ~0.74. Below it, only a clear winner (large gap to
# the runner-up) may pass; a weak top with no clear winner abstains.
if not bm25:
if best_dense < min_score:
return [] # below the "probably unrelated" floor
return []
if best_dense >= 0.74:
return _position_aware(top) # calibrated: genuine semantic match
return _py_position_aware(top)
if len(dense) >= 2:
d_scores = sorted(s for _, s in dense)
top1 = d_scores[-1]
top2 = d_scores[-2]
if top1 - top2 >= 0.08:
return _position_aware(top) # clear winner despite mid-band score
return [] # weak + ambiguous -> abstain
return _position_aware(_map_reduce(top)) # single mid-band dense hit
# P1-03 (#26) DISCHARGE (finding 1): the hybrid path (dense AND lexical
# both fired) gates on the dense cosine — the calibrated scale min_score
# was tuned against — exactly like the dense-only branch above. The
# numeric check is ADDITIVE to the conjunctive FTS gate (which stays
# as-is); the RRF-fused relevance is rank-based and is NOT compared
# against the floor here.
d_scores = sorted(score for _, score in dense)
if d_scores[-1] - d_scores[-2] >= 0.08:
return _py_position_aware(top)
return []
return _py_position_aware(_py_map_reduce(top))
if best_dense < min_score:
return []
return _position_aware(_map_reduce(top))
return _py_position_aware(_py_map_reduce(top))
def _drift_rerank(db, entries):
@@ -944,7 +882,27 @@ def _drift_rerank(db, entries):
return [entry for _, entry in scored]
def _mr_core():
"""Rust memory_retrieval core when built; Python fallback remains
load-bearing during the strangler. RUNE_RETRIEVAL_CORE=python pins it."""
if os.environ.get("RUNE_RETRIEVAL_CORE", "auto") == "python":
return None
try:
from rune import mr_loader
return mr_loader if mr_loader.available() else None
except Exception: # noqa: BLE001 — loader probe failure means Python fallback
return None
def _map_reduce(entries: list, chunk_size: int = 10) -> list:
core = _mr_core()
if core is not None:
return core.map_reduce(entries, chunk_size)
return _py_map_reduce(entries, chunk_size)
def _py_map_reduce(entries: list, chunk_size: int = 10) -> list:
"""Map-reduce for large result sets.
When retrieval returns many entries, chunk them and take the top-N
@@ -1173,6 +1131,13 @@ def cached_recall(db, query, budget=RECALL_BUDGET, min_score=RECALL_MIN_SCORE, m
def _position_aware(top):
core = _mr_core()
if core is not None:
return core.position_aware(top)
return _py_position_aware(top)
def _py_position_aware(top):
"""POSITION-AWARE RE-RANK (research uplift #2): lost-in-the-middle
mitigation (Liu et al. 2023; BriefContext, npj Digital Medicine 2025).
Models use the START and END of context best and the middle worst, so the
@@ -1247,6 +1212,13 @@ _STOPWORDS = {
def _fts_query_conjunctive(query):
core = _mr_core()
if core is not None:
return core.fts_query_conjunctive(query)
return _py_fts_query_conjunctive(query)
def _py_fts_query_conjunctive(query):
"""Build a CONJUNCTIVE FTS5 MATCH query (implicit AND).
Extended Boolean IR (Salton, Fox & Wu, CACM 1983): a document must contain
@@ -1269,6 +1241,85 @@ def _fts_query(query):
return _fts_query_conjunctive(query)
def mr_rank_fusion(dense, bm25, cap):
"""Chunk-side RRF fusion with an explicit candidate cap (W2.1)."""
core = _mr_core()
if core is not None:
return core.rank_fusion(dense[:cap], bm25[:cap], RRF_K)
return _py_rank_fusion(dense[:cap], bm25[:cap], RRF_K)
def _project_chunk_rows(ranks, rows, budget):
"""Chunk projection: sorted by RRF desc, text[:400], budget-capped.
`ranks` is the W2.1 pair-list ([[rowid, rrf], ...]) from the fusion
contract; the Rust side consumes pairs directly."""
core = _mr_core()
if core is not None:
pairs = (ranks if isinstance(ranks, list)
else [list(r) for r in ranks.items()])
return core.project_chunk_rows(pairs, rows, budget)
return _py_project_chunk_rows(ranks, rows, budget)
def _py_project_chunk_rows(ranks, rows, budget):
by_id = {r["rowid"]: r for r in rows}
out = []
for eid, rrf in sorted(ranks.items(), key=lambda x: -x[1]):
r = by_id.get(eid)
if not r:
continue
out.append({
"chunk_id": r["chunk_id"],
"text": (r["text"] or "")[:400],
"wing": r["wing"],
"room": r["room"],
"source": r["source_path"],
"page": r["page"] if "page" in r.keys() else None,
"rrf": round(rrf, 4),
})
if len(out) >= budget:
break
return out
def _rank_fusion(dense, bm25):
"""Pure dense/BM25 fusion and mode selection (R2 W2.1).
Returns ranks as ordered [id, score] pairs so integer ids survive the
JSON membrane without object-key coercion.
"""
core = _mr_core()
if core is not None:
return core.rank_fusion(dense, bm25, RRF_K)
return _py_rank_fusion(dense, bm25, RRF_K)
def _py_rank_fusion(dense, bm25, rrf_k=RRF_K):
ranks = {}
best_dense = 0.0
mode = "lexical-only"
if dense and bm25:
mode = "hybrid"
for idx, values in enumerate([dense, bm25]):
for pos, (eid, score) in enumerate(values):
ranks[eid] = ranks.get(eid, 0.0) + 1.0 / (rrf_k + pos + 1)
if idx == 0:
best_dense = max(best_dense, score)
elif dense:
mode = "dense-only"
for pos, (eid, score) in enumerate(dense):
ranks[eid] = 1.0 / (rrf_k + pos + 1)
best_dense = max(best_dense, score)
elif bm25:
min_bm = min((score for _, score in bm25), default=0.0)
max_bm = max((score for _, score in bm25), default=0.0)
span = max(max_bm - min_bm, 1e-9)
for eid, score in bm25:
ranks[eid] = (score - min_bm) / span
return {"ranks": [[eid, score] for eid, score in ranks.items()],
"best_dense": best_dense, "mode": mode}
def update_entry(db, eid, text=None, importance=None, valid_until=None):
sets, params = [], []
if text is not None:
@@ -1456,6 +1507,13 @@ def working_clear(db, task_id):
def _chunk_text(text, size=1500, overlap=150):
core = _mr_core()
if core is not None:
return core.chunk_text(text, size, overlap)
return _py_chunk_text(text, size, overlap)
def _py_chunk_text(text, size=1500, overlap=150):
"""Recursive-ish split on paragraph/heading boundaries, ~1500 chars (the
local CPU-friendly size; research: fixed chunking beats semantic for
free systems). Headings stay with their content."""
@@ -1577,43 +1635,22 @@ def chunk_recall(db, query, budget=6, wing=None, min_sim=0.0, doc=None):
bm25 = [(r["rowid"], 0.5) for r in rows]
except Exception:
logger.debug("chunk_recall failed", exc_info=True)
ranks = {}
for lst in [dense, bm25]:
for pos, (eid, _s) in enumerate(lst):
ranks[eid] = ranks.get(eid, 0.0) + 1.0 / (RRF_K + pos + 1)
if not ranks:
return []
ids = list(ranks.keys())
ph = ",".join("?" * len(ids))
sql = f"SELECT rowid, * FROM chunks WHERE rowid IN ({ph})"
params = ids
if wing:
sql += " AND wing=?"
params.append(wing)
if doc:
sql += " AND doc_id=?"
params.append(doc)
rows = db.execute(sql, params).fetchall()
by_id = {r["rowid"]: r for r in rows}
out = []
for eid, rrf in sorted(ranks.items(), key=lambda x: -x[1]):
r = by_id.get(eid)
if not r:
continue
out.append(
{
"chunk_id": r["chunk_id"],
"text": r["text"][:400],
"wing": r["wing"],
"room": r["room"],
"source": r["source_path"],
"page": r["page"] if "page" in r.keys() else None,
"rrf": round(rrf, 4),
}
)
if len(out) >= budget:
break
return out
fusion = mr_rank_fusion(dense, bm25, budget * 3)
ranks_list = fusion["ranks"] # ordered [rowid, rrf] pairs (W2.1 contract)
ids = [int(v[0]) for v in ranks_list]
rows = []
if ids:
ph = ",".join("?" * len(ids))
sql = f"SELECT rowid, * FROM chunks WHERE rowid IN ({ph})"
params = ids
if wing:
sql += " AND wing=?"
params.append(wing)
if doc:
sql += " AND doc_id=?"
params.append(doc)
rows = [dict(r) for r in db.execute(sql, params).fetchall()]
return _project_chunk_rows(fusion["ranks"], rows, budget)
# ------------------------------------------------------------------- mining ----
@@ -2043,8 +2080,24 @@ def recall_with_associations(db, query, budget=RECALL_BUDGET, min_score=RECALL_M
ids = list(boost_map.keys())
placeholders = ",".join("?" * len(ids))
rows = db.execute(f"SELECT * FROM entries WHERE id IN ({placeholders}) AND status='active'", ids).fetchall()
boost_items = [{"id": eid, "strength": strength}
for eid, strength in sorted(boost_map.items(), key=lambda x: -x[1])]
return _merge_association_rows(base, boost_items, [dict(r) for r in rows], budget)
def _merge_association_rows(base, boost_items, rows, budget):
"""Pure association projection/boost/order/budget kernel (R2 W2.1)."""
core = _mr_core()
if core is not None:
return core.merge_association_rows(base, boost_items, rows, budget)
return _py_merge_association_rows(base, boost_items, rows, budget)
def _py_merge_association_rows(base, boost_items, rows, budget):
base = list(base)
by_id2 = {r["id"]: r for r in rows}
for eid, strength in sorted(boost_map.items(), key=lambda x: -x[1]):
for item in boost_items:
eid, strength = item["id"], item["strength"]
row = by_id2.get(eid)
if not row:
continue
@@ -2087,6 +2140,19 @@ def fused_recall(db, query, budget=RECALL_BUDGET, min_score=RECALL_MIN_SCORE, ch
"""
entries = recall_with_associations(db, query, budget=budget, min_score=min_score)
research = chunk_recall(db, query, budget=chunk_budget, wing=wings, doc=None)
return _fuse_results(entries, research)
def _fuse_results(entries, research):
"""Pure fact/research projection, de-duplication and per-kind scale
alignment (R2 W2.1). Rust core when built; Python core is the oracle."""
core = _mr_core()
if core is not None:
return core.fuse_results(entries, research)
return _py_fuse_results(entries, research)
def _py_fuse_results(entries, research):
seen = set()
merged = []
for e in entries:
@@ -2140,6 +2206,13 @@ def fused_recall(db, query, budget=RECALL_BUDGET, min_score=RECALL_MIN_SCORE, ch
def _norm_key(text):
core = _mr_core()
if core is not None:
return core.norm_key(text)
return _py_norm_key(text)
def _py_norm_key(text):
"""Normalize text for cross-table de-duplication (entries vs chunks of the
same absorbed material may differ in whitespace/case)."""
return " ".join((text or "").lower().split())
+38
View File
@@ -0,0 +1,38 @@
"""ctypes loader for the zero-dependency memory_retrieval core (R2 W2.1)."""
from __future__ import annotations
import ctypes, json, os
from pathlib import Path
_ROOT=Path(__file__).resolve().parents[2]
_CRATE=_ROOT/"src/rust/memory_retrieval"
_LIB=Path(os.environ.get("MR_RUST_LIB",_CRATE/"target/release/libmemory_retrieval.so"))
_lib=None
def available(): return _LIB.is_file()
def _load():
global _lib
if _lib is not None:return _lib
if not _LIB.exists():raise FileNotFoundError(f"memory_retrieval core not built: {_LIB}")
lib=ctypes.CDLL(str(_LIB));lib.mr_call.argtypes=[ctypes.c_char_p];lib.mr_call.restype=ctypes.c_void_p
lib.mr_free_string.argtypes=[ctypes.c_void_p];lib.mr_free_string.restype=None;_lib=lib;return lib
def _call(op,arg):
# Send UTF-8 directly. ensure_ascii=True emits surrogate-pair escapes; the
# shared zero-dep parser treats those as independent code points, which
# would replace astral characters (emoji) and break Python char-count
# parity in chunking/normalization.
lib=_load();ptr=lib.mr_call(json.dumps({"op":op,"arg":arg},ensure_ascii=False).encode())
if not ptr:raise RuntimeError("mr_call returned null")
try:text=ctypes.cast(ptr,ctypes.c_char_p).value.decode()
finally:lib.mr_free_string(ptr)
env=json.loads(text)
if not env.get("ok"):raise RuntimeError(env.get("err"))
return env["value"]
def map_reduce(entries,chunk_size=10):return _call("map_reduce",{"entries":entries,"chunk_size":chunk_size})
def position_aware(entries):return _call("position_aware",{"entries":entries})
def fts_query_conjunctive(query):return _call("fts_query_conjunctive",{"query":query})
def chunk_text(text,size=1500,overlap=150):return _call("chunk_text",{"text":text,"size":size,"overlap":overlap})
def norm_key(text):return _call("norm_key",{"text":text})
def fuse_results(entries,research):return _call("fuse_results",{"entries":entries,"research":research})
def merge_association_rows(base,boosts,rows,budget):return _call("merge_association_rows",{"base":base,"boosts":boosts,"rows":rows,"budget":budget})
def rank_fusion(dense,bm25,rrf_k=60):return _call("rank_fusion",{"dense":dense,"bm25":bm25,"rrf_k":rrf_k})
def score_recall_rows(fusion,rows,dense,bm25,budget,min_score,now,half_life):return _call("score_recall_rows",{"fusion":fusion,"rows":rows,"dense":dense,"bm25":bm25,"budget":budget,"min_score":min_score,"now":now,"half_life":half_life})
def project_chunk_rows(ranks, rows, budget):
return _call("project_chunk_rows", {"ranks": ranks, "rows": rows, "budget": budget})
+63
View File
@@ -161,7 +161,33 @@ def load_rules():
return rules
def _cc_pg_core():
"""Rust cognition_core when available (persona kernels); pin with
RUNE_COGNITION_CORE=python."""
import os
if os.environ.get("RUNE_COGNITION_CORE", "auto") == "python":
return None
try:
from rune import cc_loader
except Exception: # noqa: BLE001 — loader probe failure means fallback
return None
try:
return cc_loader if cc_loader.available() else None
except Exception: # noqa: BLE001 — availability probe never crashes
return None
def _lex(text):
"""Distinctive content words (R2 W3.2: Rust kernel when built)."""
core = _cc_pg_core()
if core is not None:
return set(core.persona_lex(text))
return _py_lex(text)
def _py_lex(text):
"""Python oracle (parity floor)."""
"""Distinctive content words of a rule body (lowercase, >3 chars,
light-stemmed so plural/singular engage each other; preserves 3-char
ALL-CAPS acronyms so technical abbreviations match their expansion)."""
@@ -253,6 +279,15 @@ def _lex_input(text):
def _overlap(a, b):
"""Overlap ratio (R2 W3.2: Rust kernel when built)."""
core = _cc_pg_core()
if core is not None:
return core.persona_overlap(sorted(a), sorted(b))
return _py_overlap(a, b)
def _py_overlap(a, b):
"""Python oracle (parity floor)."""
if not a or not b:
return 0.0
return len(a & b) / max(1, min(len(a), len(b)))
@@ -338,6 +373,34 @@ def _semantic_engagement(text, rule):
def decide(text, rules=None):
"""The persona decides on a request, deterministically (R2 W3.2:
Rust kernel when built; the semantic cosines are gathered here —
embedder calls are IO — and passed into the kernel)."""
rules = rules if rules is not None else load_rules()
core = _cc_pg_core()
if core is not None:
text_s = (text or "").strip()
sems = [_semantic_engagement(text_s, r) for r in rules]
return core.persona_decide(text_s, [_rule_json(r) for r in rules],
PERMISSIVE_MODE, sems)
return _py_decide(text, rules)
def _rule_json(r) -> dict:
"""A rule in the kernel's JSON contract (citation rides along when
present so _cite stays data-driven)."""
return {
"text": r["text"], "words": sorted(r["words"]),
"core": r["core"], "priority": r.get("priority", 0),
"restrictive": r.get("restrictive", False),
"user_rule": r.get("user_rule", False),
"citation": r.get("citation"),
}
def _py_decide(text, rules=None):
"""Python oracle (parity floor) — the ORIGINAL decide body."""
"""The persona decides on a request, deterministically, from its own
stored rules. No generative LLM in the decision path (a local embedding
model may contribute semantic similarity). Returns a full verdict."""
+9 -1
View File
@@ -162,8 +162,16 @@ def recall(context, limit=4):
term = (context or "").lower()
if not term:
return []
from rune.identity_anchors import _cc_core
core = _cc_core()
if core is not None:
return core.pins_recall(_load(), term, limit)
return _py_pin_recall(_load(), term, limit)
def _py_pin_recall(recs, term, limit=4):
out = []
for rec in _load():
for rec in recs:
if rec.get("state") != "open":
continue
p = _project(rec)
+72 -75
View File
@@ -8,7 +8,7 @@ mode system, subject header, shared memory and identity.
This is not an interface. This is how I see, speak, and interact with the world.
Version: v0.92.0
Version: v0.99.5
Features: 41 (24 original + 17 new native commands)
Usage:
@@ -110,6 +110,56 @@ try:
except ImportError:
BACKEND_AVAILABLE = False
def collect_post_response_signals(response: str, messages_count: int) -> list[str]:
"""Gather the operational signals that used to each print a dim
system message after every task/build response (the dim-spam source,
T5.13): budget pressure, degraded claims, growth delta, the periodic
self-improvement cycle.
PURE and headless — no channel, no app. The caller renders ONE
collapsed line (or none when nothing fired). Queued-message execution
and on-complete cron firing stay in the worker: they move real
messages, not chatter, and keep their own echoes.
Returns short human-readable fragments; empty list = silence.
"""
signals: list[str] = []
if not BACKEND_AVAILABLE:
return signals
try:
budget_data = provider_budget.get_status()
ratios = []
for provider in budget_data.get("providers", {}).values():
if provider.get("monthly_limit", 0) > 0:
ratios.append(provider.get("monthly_used", 0) / provider["monthly_limit"])
if provider.get("token_limit", 0) > 0:
ratios.append(provider.get("tokens_used", 0) / provider["token_limit"])
usage_percent = max(ratios, default=0) * 100
if usage_percent > 80:
signals.append(f"⚠ Budget: {usage_percent:.0f}% used")
except Exception:
pass
try:
claims_result = claim_audit.scan_text(response[:500])
if claims_result and claims_result.get("degraded"):
signals.append(f"⚠ Claims degraded: {len(claims_result['degraded'])}")
except Exception:
pass
try:
growth = growth_delta.check()
if growth and growth.get("delta"):
signals.append(f"📈 Growth: {growth['delta']}")
except Exception:
pass
try:
if messages_count % 10 == 0:
self_improve.run()
signals.append("🔄 Self-improvement cycle triggered")
except Exception:
pass
return signals
from textual.app import App, ComposeResult
from textual.containers import Horizontal, Vertical, VerticalScroll
from textual.widgets import Button, Header, Input, ProgressBar, RichLog, Static
@@ -1533,18 +1583,21 @@ class RuneApp(App):
def compose(self) -> ComposeResult:
yield Header()
with Horizontal(id="channels"):
yield ChannelView(
"task",
"[b]TASK[/b] — focused work",
classes="channel-view",
id="task-channel",
)
# T5.14 (Nick 2026-10-05): chat LEFT, task RIGHT — feels more
# natural (conversation first, focused work second). WorkPane
# stays third.
yield ChannelView(
"chat",
"[b]CHAT[/b] — free conversation",
classes="channel-view",
id="chat-channel",
)
yield ChannelView(
"task",
"[b]TASK[/b] — focused work",
classes="channel-view",
id="task-channel",
)
# P1-07 (#30): third collapsible column — the operational index.
yield WorkPane(id="work-pane")
with Horizontal(id="footer-bar"):
@@ -1895,7 +1948,7 @@ class RuneApp(App):
# Show version info
self.chat_channel.add_message(
"system",
f"[dim]Rune v0.92.0 | Textual TUI | {len(loaded)} native modules[/dim]",
f"[dim]Rune v0.99.5 | Textual TUI | {len(loaded)} native modules[/dim]",
)
# Auto-show night mode suggestion if evening/night hours
@@ -3737,69 +3790,13 @@ class RuneApp(App):
except Exception:
pass
# Auto-warn budget when >80% used
try:
if BACKEND_AVAILABLE:
budget_data = provider_budget.get_status()
ratios = []
for provider in budget_data.get("providers", {}).values():
if provider.get("monthly_limit", 0) > 0:
ratios.append(provider.get("monthly_used", 0) / provider["monthly_limit"])
if provider.get("token_limit", 0) > 0:
ratios.append(provider.get("tokens_used", 0) / provider["token_limit"])
usage_percent = max(ratios, default=0) * 100
if usage_percent > 80:
ch.add_message(
"system",
f"[dim]⚠ Budget: {usage_percent:.0f}% used[/dim]",
)
except Exception:
pass
# Auto-check claims after response
try:
if BACKEND_AVAILABLE:
claims_result = claim_audit.scan_text(response[:500])
if claims_result and claims_result.get("degraded"):
ch.add_message(
"system",
f"[dim]⚠ Claims degraded: {len(claims_result['degraded'])}[/dim]",
)
except Exception:
pass
# NOTE (Runtime Reachability audit 2026-09-10): the
# old hook_engine.fire("post_message", ...) call here
# was dead — hook_engine defines no fire(); the
# AttributeError was silently swallowed, so "hooks"
# never ran. Removed rather than left as a false-
# liveness surface. Real hook dispatch is unwired
# (microkernel.fire has zero callers) — see the
# reachability audit, P3.
# Auto-check growth delta
try:
if BACKEND_AVAILABLE:
growth = growth_delta.check()
if growth and growth.get("delta"):
ch.add_message(
"system",
f"[dim]📈 Growth: {growth['delta']}[/dim]",
)
except Exception:
pass
# Auto-improve every 10 messages
try:
if self.status_bar.messages_count % 10 == 0:
if BACKEND_AVAILABLE:
self_improve.run()
ch.add_message(
"system",
f"[dim]🔄 Self-improvement cycle triggered[/dim]",
)
except Exception:
pass
# T5.13 dim-spam consolidation: previously five
# separate dim system messages printed after every
# response. ONE collapsed line now — empty means
# silence, not a dash.
signals = collect_post_response_signals(response[:500], self.status_bar.messages_count)
if signals:
ch.add_message("system", "[dim]" + " · ".join(signals) + "[/dim]")
elif result.get("error") == "RESEARCH_REQUIRED":
# Nonterminal routing disposition, not failure (2026-09-10):
# the task hit the deep-research floor and was dispatched.
@@ -3980,13 +3977,13 @@ class RuneApp(App):
pass
def action_resize_left(self) -> None:
"""Shrink task channel, grow chat channel."""
self.task_width = max(20, self.task_width - 5)
"""Shrink the LEFT channel (chat, post-swap), grow the RIGHT (task)."""
self.task_width = min(80, self.task_width + 5)
self._apply_resize()
def action_resize_right(self) -> None:
"""Grow task channel, shrink chat channel."""
self.task_width = min(80, self.task_width + 5)
"""Grow the LEFT channel (chat), shrink the RIGHT (task)."""
self.task_width = max(20, self.task_width - 5)
self._apply_resize()
def _apply_resize(self):
+117 -78
View File
@@ -86,6 +86,110 @@ PATTERN_MAX_PATTERNS = 200
# ═══════════════════════════════════════════════════════════════════════════════
def _keyword_stopwords() -> list:
"""Gather seam (W3.4): the pattern-keyword stopword table as a sorted
list — data, not logic; both engines read this module-owned table."""
return sorted(_KEYWORD_STOPWORDS)
_KEYWORD_STOPWORDS = frozenset({
"the",
"and",
"for",
"are",
"but",
"not",
"you",
"all",
"can",
"had",
"her",
"was",
"one",
"our",
"out",
"day",
"get",
"has",
"him",
"his",
"how",
"its",
"may",
"new",
"now",
"old",
"see",
"way",
"who",
"did",
"let",
"say",
"she",
"too",
"use",
"this",
"that",
"with",
"have",
"from",
"they",
"been",
"said",
"each",
"make",
"like",
"just",
"over",
"such",
"take",
"year",
"them",
"some",
"time",
"very",
"when",
"come",
"could",
"what",
"there",
"their",
"will",
"would",
"about",
"which",
"these",
"other",
"into",
"more",
"than",
"also",
"then",
})
def _core():
"""The Rust cognition_core when available (strangler: Python fallback
load-bearing). RUNE_COGNITION_CORE=python pins the fallback."""
return None if cc_loader_pin() else _cc_probe()
def _cc_probe():
from rune import cc_loader as _cl
try:
return _cl if _cl.available() else None
except Exception: # noqa: BLE001, S110 — loader probe never crashes the fallback
return None
def cc_loader_pin() -> bool:
"""The env pin: RUNE_COGNITION_CORE=python → kernels OFF (shared probe).
"""
import os
return os.environ.get("RUNE_COGNITION_CORE", "auto") == "python"
@dataclass
class OverridePattern:
"""A learned pattern that requires override."""
@@ -105,7 +209,14 @@ class OverridePattern:
return self.successes / total
def matches(self, text: str) -> bool:
"""Check if text matches this pattern's keywords."""
"""Check if text matches this pattern's keywords. Deterministic
keyword-count check (kernel port NOT owed here — the W3.4 safety
kernels cover the params/rows surfaces; this tiny comparison stays
Python-side per the membrane law: gather/IO in Python, kernels for
deterministic row work already ported)."""
return self._py_matches(text)
def _py_matches(self, text: str) -> bool:
text_lower = text.lower()
matches = sum(1 for kw in self.keywords if kw.lower() in text_lower)
return matches >= PATTERN_MIN_KEYWORDS
@@ -293,84 +404,12 @@ class SafetyOverride:
self.stats.patterns_learned += 1
def _extract_keywords(self, text: str) -> list[str]:
"""Extract distinctive keywords from text for pattern matching."""
# Remove common stop words, keep words > 3 chars
stop_words = {
"the",
"and",
"for",
"are",
"but",
"not",
"you",
"all",
"can",
"had",
"her",
"was",
"one",
"our",
"out",
"day",
"get",
"has",
"him",
"his",
"how",
"its",
"may",
"new",
"now",
"old",
"see",
"way",
"who",
"did",
"let",
"say",
"she",
"too",
"use",
"this",
"that",
"with",
"have",
"from",
"they",
"been",
"said",
"each",
"make",
"like",
"just",
"over",
"such",
"take",
"year",
"them",
"some",
"time",
"very",
"when",
"come",
"could",
"what",
"there",
"their",
"will",
"would",
"about",
"which",
"these",
"other",
"into",
"more",
"than",
"also",
"then",
}
"""Extract distinctive keywords from text for pattern matching.
Keyword extraction stays Python-side (W3.4 scope note): the safety
kernels cover the params/rows surfaces; this extractor is a gather
(IO-adjacent list build) per the membrane law."""
words = re.findall(r"[a-z]{4,}", text.lower())
keywords = [w for w in words if w not in stop_words]
keywords = [w for w in words if w not in _KEYWORD_STOPWORDS]
# Return top 5 most distinctive words
return keywords[:5]
+18 -3
View File
@@ -53,6 +53,12 @@ from rune.structural_store import ( # shared generic core (SCAFFOLD-TRANCHE-001
reconcile_authorities, mark_conflict, resolve_status, authority_health,
dedupe_observations as _ss_dedupe_observations,
)
from rune.spine_language import ( # noqa: F401 — re-exported (import-compat): the
# #2465 doc-level transforms live here now (giant-file carve); tests and
# the canary_spine_meta read them THROUGH spine, exactly as before.
_classification_sides, _place_languages, _normalize_discovery_ids,
_apply_contract_discoveries, _contract_discoveries,
)
SCHEMA_VERSION = 1
@@ -337,11 +343,14 @@ def _rust_core():
return None
def _gather_build_inputs(manifest_path: Path | None = None) -> dict:
"""Every I/O read build() needs, in one place (zero-dep split law:
Python scans, the core — Rust or Python — only assembles). Both cores
consume this dict, so parity divergence is logic, never environment."""
existing = load()
if existing:
_normalize_discovery_ids(existing)
seeded = bool(existing) and any(
r["type"] == "belongs_to" for r in existing["relationships"])
# ingest manifest: only consulted when the unseeded path needs it
@@ -517,6 +526,7 @@ def _py_build_from_inputs(inputs: dict) -> dict:
from_id=f"subsystem:{name}", to_id=mid,
evidence_refs=[f"umbrella-manifest#{name}"])
# reconcile: facts owned by projectors that no longer observe them
# become STALE (marked, never deleted — history survives; open-world
# preservation applies to everything, staleness is the truth marker)
@@ -595,9 +605,14 @@ def build(manifest_path: Path | None = None) -> dict:
# paths, including an explicit unseeded-ingest parity section.
seeded = bool(inputs["existing"]) and any(
r["type"] == "belongs_to" for r in inputs["existing"]["relationships"])
if core is not None and seeded:
return core.project(inputs)
return _py_build_from_inputs(inputs)
doc = (core.project(inputs) if core is not None and seeded
else _py_build_from_inputs(inputs))
# both cores funnel through the same post-projection passes (the
# contract-discovery write-back + language placement) — the doc-level
# transforms live in Python until the #2464 top-up ports them
_apply_contract_discoveries(doc)
_place_languages(doc)
return doc
# ── drift ─────────────────────────────────────────────────────────────────
+218
View File
@@ -0,0 +1,218 @@
"""spine_language.py — the #2465 doc-level transforms (carved from spine.py
to honor the giant-file henxel: keep it under 1200 lines).
Three transforms, applied to BOTH cores' output at build time:
1. language placement — every entity gets a language verdict (kind
defaults; subsystems derive from member-majority over the measured
classification map);
2. discovery-ID normalization — migrate legacy unqualified contract
discoveries to construction-surface kind without losing evidence;
3. contract-discovery write-back — closed contracts teach the spine
what construction actually built (observed → PRESENT, candidate →
DECLARED; the CANDIDATE law holds).
Same dependency laws as spine.py: structural_store primitives only, no
I/O beyond the classification/scaffold store reads, deterministic.
"""
from __future__ import annotations
import json
from pathlib import Path
from rune.structural_store import (
add_entity, add_relationship, entity, new_doc, relationships, _sorted, now,
)
ROOT = Path(__file__).resolve().parents[2]
SRC_DIR = ROOT / "src" / "rune"
def _classification_sides() -> dict:
"""The measured dichotomy map (W0): module stem → RUST|GO|TUI-LAST|...
Loaded once per _place_languages call, best-effort — a missing or
unreadable classification.json degrades to {}/unassessed verdicts,
never to invented facts."""
try:
data = json.loads((ROOT / "store" / "rebase" / "classification.json").read_text())
return {name: rec.get("side", "") for name, rec in data.items() if isinstance(rec, dict)}
except (OSError, json.JSONDecodeError, AttributeError):
return {}
def _place_languages(doc: dict) -> int:
"""Stamp a language verdict per entity (no-op for entities that carry
one). Deterministic: substring classification over the entity id + the
kind; the exact same rule construction_decision.language_placement
implements (kept inline here to avoid a per-entity FFI crossing for
the spine's own 218 entities; the FFI path is used in contracts)."""
GO_HINTS = ("server", "transport", "dispatch", "entry", "bridge",
"hook_engine", "provider", "watch", "notif", "voice",
"gitea", "event_", "message_", "tool_exec", "work_manager")
RUST_HINTS = ("memory", "drift", "warm", "capab", "token", "spine",
"scaffold", "construct", "structural", "curator",
"consolidat", "elastic", "cognit", "abstract", "contract",
"ledger", "audit", "claim", "evidence", "behavio",
"verif", "pins", "witness", "anchor", "growth", "goal",
"salience", "store", "tui_", "rune_tui")
placed = 0
CLASSIFICATION_SIDES = _classification_sides()
for e in doc.get("entities", []):
eid = e.get("id", "")
kind = e.get("kind", "")
# AUTHORITY ORDER (Nick's dichotomy, 2026-10-06 correction): the
# MEASURED classification map (import-evidence per module) decides
# FIRST. The name-hint lists are only a fallback for entities with
# no measurement — never allowed to override the evidence. A module
# with neither measurement nor hint is "unclassified", not a silent
# rust default.
measured = str(CLASSIFICATION_SIDES.get(
eid.split(":", 1)[1] if ":" in eid else eid, "") or "").upper()
if eid.startswith("contract:"):
lang = "n/a"
elif kind == "rust-crate":
lang = "rust"
elif kind == "go-surface":
lang = "go"
elif kind == "workflow" or kind == "config":
lang = "n/a"
elif kind == "deployment_surface":
lang = "go"
elif measured == "RUST":
lang = "rust"
elif measured == "GO":
lang = "go"
elif measured == "TUI-LAST":
lang = "python-tui (Wave 6)"
elif measured == "TEST-INFRA" or measured == "RETIRES":
lang = "test-infra" if measured == "TEST-INFRA" else "retires"
elif "tui" in eid:
lang = "python-tui (Wave 6)"
elif any(h in eid for h in GO_HINTS):
lang = "go (name hint)"
elif any(h in eid for h in RUST_HINTS):
lang = "rust (name hint)"
elif kind == "module":
lang = "unclassified"
elif kind == "subsystem":
# A subsystem is a CONTAINER — its language is its members'
# majority side per the measured dichotomy. The evidence map is
# classification.json (measured, 174 modules; honest note: newer
# files may be unclassified, so the count of classified members
# rides the verdict). Members arrive as belongs_to relationships
# whose from-ids carry module:<name> — map through classification.
members = [
r.get("from", "").split(":", 1)[1]
for r in doc.get("relationships", [])
if r.get("type") == "belongs_to" and r.get("to") == eid
and r.get("from", "").startswith("module:")
]
sides = [
str(CLASSIFICATION_SIDES.get(m) or "").upper()
for m in members
]
rust = sides.count("RUST")
go = sides.count("GO")
if rust and go:
lang = f"mixed (rust {rust} / go {go} members)"
elif rust:
lang = "rust"
elif go:
lang = "go"
else:
lang = "unassessed"
else:
lang = "unassessed"
e.setdefault("identities", {})["language"] = lang
if lang != "unassessed":
placed += 1
return placed
def _normalize_discovery_ids(doc: dict) -> int:
"""Migrate the old unqualified contract references, preserving evidence.
A file path (or 'suite') is not a module ID. Only migrate the malformed
module records produced by the earlier discovery projector; leave all
other open-world entity classes alone.
"""
renamed = {}
observed = {
eid for _, entities in _contract_discoveries()
for eid, _, provenance in entities if provenance == "observed"
}
for e in doc.get("entities", []):
if (e.get("kind") == "module" and ":" not in e.get("id", "")
and any(ref.startswith("contract-discovery:")
for ref in e.get("evidence_refs", []))):
old = e["id"]
e["id"] = f"construction-surface:{old}"
e["kind"] = "construction-surface"
e.setdefault("identities", {})["source_ref"] = old
renamed[old] = e["id"]
if e.get("kind") == "construction-surface" and e.get("id", "").startswith("construction-surface:"):
# Earlier code promoted every *candidate* to PRESENT. Undo only
# that unsupported claim; an actually observed surface retains it.
if e["id"].split(":", 1)[1] not in observed:
e["maturity"] = "DECLARED"
e["tags"] = [tag for tag in e.get("tags", []) if tag != "code"]
for rel in doc.get("relationships", []):
for endpoint in ("from", "to"):
if rel.get(endpoint) in renamed:
rel[endpoint] = renamed[rel[endpoint]]
return len(renamed)
def _apply_contract_discoveries(doc: dict) -> int:
"""Contract-discovery write-back (issue #2465 addition 2): entities
DISCOVERED by closed contracts become modeled spine entities — the
spine learns what construction actually built. Doc-level transform,
applied to BOTH cores' output. The CANDIDATE law holds: only CLOSED
contracts write back."""
placed = 0
for cid, entities in _contract_discoveries():
for eid, kind, provenance in entities:
before = len(doc.get("entities", []))
if kind == "construction-surface":
eid = f"construction-surface:{eid}"
add_entity(doc, id=eid, kind=kind,
tags=["contract-discovery"],
identities={"source_ref": eid.split(":", 1)[1]} if kind == "construction-surface" else None,
evidence_refs=[f"contract-discovery:{cid}"],
maturity="PRESENT" if provenance == "observed" else "DECLARED")
if len(doc.get("entities", [])) > before:
placed += 1
else:
placed += 0 # high-water merge — no new entity, still evidence
return placed
def _contract_discoveries():
"""Closed contracts' DISCOVERED entities (issue #2465 addition 2):
expected_new_observed + candidate corrections, gathered from the
scaffold store. Returns [(contract_id, [(entity_id, kind), ...])]."""
try:
doc = json.loads((ROOT / "store" / "scaffold" / "current.json").read_text())
except (OSError, json.JSONDecodeError):
return []
out = []
for e in doc.get("entities", []):
cid = e.get("id", "")
if not cid.startswith("contract:") or e.get("phase") != "closed":
continue
q = e.get("ext", {}).get("contract_quality", {})
found = []
# expected-new surfaces observed at close (REAL delivered entities)
for eid in q.get("expected_new_observed", []):
kind = eid.split(":", 1)[0] if ":" in eid else "construction-surface"
if kind in ("rust-crate", "go-surface", "config", "workflow", "module"):
found.append((eid, kind, "observed"))
elif kind == "construction-surface":
found.append((eid, kind, "observed"))
# candidate corrections: the closure flagged them for modeling
for cand in q.get("candidate_corrections", []):
eid = cand.get("entity", "")
kind = eid.split(":", 1)[0] if ":" in eid else "construction-surface"
if eid and kind in ("rust-crate", "go-surface", "config", "workflow", "module", "construction-surface"):
found.append((eid, kind, "candidate"))
if found:
out.append((cid[9:], found))
return out
+82 -2
View File
@@ -20,6 +20,33 @@ HOT_THRESHOLD = 7 # accessed within 7 days = hot
WARM_THRESHOLD = 30 # accessed within 30 days = warm
# > 30 days = cold
def _core():
"""The Rust cognition_core when available (strangler: Python fallback is
load-bearing). RUNE_COGNITION_CORE=python pins the fallback."""
return None if cc_loader_pin() else _cc_probe()
def _cc_probe():
from rune import cc_loader as _cl
try:
return _cl if _cl.available() else None
except Exception: # noqa: BLE001, S110 — loader probe never crashes the fallback
return None
def cc_loader_pin() -> bool:
"""The env pin: RUNE_COGNITION_CORE=python → kernels OFF (shared probe).
"""
import os
return os.environ.get("RUNE_COGNITION_CORE", "auto") == "python"
def _py_core_now() -> str:
"""The injected clock (iso Z) — module-level for the kernel boundary."""
return datetime.now(timezone.utc).strftime("%Y-%m-%dT%H:%M:%SZ")
# Tier storage characteristics
TIER_CONFIG = {
"hot": {
@@ -56,7 +83,24 @@ class TierManager:
"""Determine the tier for an entry based on its access patterns.
Returns 'hot', 'warm', or 'cold'.
Delegates to the Rust kernel when built; the Python body below is
the parity oracle (W3.4: identical thresholds injected, naive
timestamps refuse per the PARITY TRAP law).
"""
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
raw = _cl.tier_get(entry, _py_core_now(),
float(HOT_THRESHOLD), float(WARM_THRESHOLD))
return str(raw)
except Exception: # noqa: BLE001, S110 — kernel failure → oracle, never a broken call
pass
return self._py_get_tier(entry)
def _py_get_tier(self, entry: dict) -> str:
"""Python parity oracle (W3.4)."""
wash_count = entry.get("wash_count", 0) or 0
last_accessed = entry.get("last_accessed")
rock_status = entry.get("rock_status", "washable")
@@ -88,7 +132,26 @@ class TierManager:
return "warm"
def promote(self, entry: dict) -> str:
"""Promote an entry to a higher tier. Returns new tier."""
"""Promote an entry to a higher tier. Returns new tier.
Delegates to the Rust kernel when built (Python oracle below)."""
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
# The kernel's promote/demote take the FULL ENTRY (plus
# thresholds + clock) — not a tier string. They recompute
# the current tier internally, so a tier-string call was
# silently landing on defaults (the live probe caught it).
raw = _cl.tier_promote(entry, _py_core_now(),
float(HOT_THRESHOLD), float(WARM_THRESHOLD))
return str(raw)
except Exception: # noqa: BLE001, S110 — kernel failure → oracle fallback, intentional silence
pass
return self._py_promote(entry)
def _py_promote(self, entry: dict) -> str:
"""Python parity oracle."""
current = self.get_tier(entry)
if current == "cold":
return "warm"
@@ -97,7 +160,24 @@ class TierManager:
return "hot" # already hot
def demote(self, entry: dict) -> str:
"""Demote an entry to a lower tier. Returns new tier."""
"""Demote an entry to a lower tier. Returns new tier.
Delegates to the Rust kernel when built (Python oracle below)."""
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
# Same full-entry contract as promote; the kernel handles
# rock_status internally (rock never demotes).
raw = _cl.tier_demote(entry, _py_core_now(),
float(HOT_THRESHOLD), float(WARM_THRESHOLD))
return str(raw)
except Exception: # noqa: BLE001, S110 — kernel failure → oracle fallback, intentional silence
pass
return self._py_demote(entry)
def _py_demote(self, entry: dict) -> str:
"""Python parity oracle."""
current = self.get_tier(entry)
rock_status = entry.get("rock_status", "washable")
+127 -112
View File
@@ -84,76 +84,129 @@ def is_correction(text):
return False
def extract_topic(text):
"""Extract topic keywords from text. Deterministic."""
stopwords = {
"the",
"a",
"an",
"is",
"are",
"was",
"were",
"be",
"been",
"being",
"have",
"has",
"had",
"do",
"does",
"did",
"will",
"would",
"could",
"should",
"may",
"might",
"shall",
"can",
"to",
"of",
"in",
"for",
"on",
"with",
"at",
"by",
"from",
"as",
"into",
"through",
"during",
"before",
"after",
"this",
"that",
"these",
"those",
"it",
"its",
"what",
"which",
"who",
"how",
"when",
"where",
"why",
"and",
"or",
"but",
"not",
"no",
def _stopwords() -> list:
"""Gather seam (W3.4 delegation): the topic-extraction stopword table
as a SORTED list — sorted so JSON travel and kernel-side matching see
a deterministic order regardless of the set's iteration order."""
return sorted(_STOPWORDS)
_STOPWORDS = {
"the", "a", "an", "is", "are", "was", "were", "be", "been", "being",
"have", "has", "had", "do", "does", "did", "will", "would", "could",
"should", "may", "might", "shall", "can", "to", "of", "in", "for",
"on", "with", "at", "by", "from", "as", "into", "through", "during",
"before", "after", "this", "that", "these", "those", "it", "its",
"what", "which", "who", "how", "when", "where", "why", "and", "or",
"but", "not", "no",
}
def _tables() -> dict:
"""Gather seam: ALL regex pattern tables as data in one dict — the
exact contract the cc_witness_signals kernel consumes (parity-proven
per-table-row; regex_lite_search is the faithful subset for THESE
shapes). Sorted lists keep travel deterministic."""
return {
"stopwords": _stopwords(),
"correction": sorted(CORRECTION_PATTERNS),
"commitment": sorted([
r"\bI'?ll\s+(send|do|fix|build|check|update|create|write)\b",
r"\bI will\s+(send|do|fix|build|check|update|create|write)\b",
r"\blet me\s+(send|do|fix|build|check|update|create|write)\b",
r"\bremind me\b",
r"\bI promise\b",
r"\bI need to\b",
]),
"contradiction": sorted([r"\b(but|however|actually|wait|that contradicts)\b"]),
"preference": sorted([
r"\bI (prefer|like|love|hate|dislike)\b",
r"\bI'?m (not )?(a fan of|into|interested in)\b",
r"\b(don'?t|do not) (like|want|need)\b",
r"\b(always|never) (use|do|say)\b",
]),
"urgency": sorted([
r"\b(urgent|asap|immediately|now|quick|hurry)\b",
r"\b(deadline|due|overdue|late)\b",
r"\b(important|critical|crucial|vital)\b",
]),
"learning": sorted([
r"\b(learn|understand|explain|teach|show me)\b",
r"\b(how (does|do|did)|why (does|do|did)|what (is|are|was|were))\b",
r"\b(I don'?t (understand|know|get))\b",
]),
}
def _core():
"""The Rust cognition_core when available (strangler: Python fallback
load-bearing). RUNE_COGNITION_CORE=python pins the fallback."""
return None if cc_loader_pin() else _cc_probe()
def _cc_probe():
from rune import cc_loader as _cl
try:
return _cl if _cl.available() else None
except Exception: # noqa: BLE001, S110 — loader probe never crashes the fallback
return None
def cc_loader_pin() -> bool:
"""The env pin: RUNE_COGNITION_CORE=python → kernels OFF (shared probe).
"""
import os
return os.environ.get("RUNE_COGNITION_CORE", "auto") == "python"
def extract_topic(text):
"""Extract topic keywords from text. Deterministic.
Delegates to the kernel when built; Python oracle below."""
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
raw = _cl.witness_extract_topic(text, _stopwords())
return list(raw) if isinstance(raw, list) else list(raw or [])
except Exception: # noqa: BLE001, S110 — kernel failure → oracle, intentional silence
pass
words = re.findall(r"\w+", text.lower())
return [w for w in words if len(w) > 3 and w not in stopwords][:5]
return [w for w in words if len(w) > 3 and w not in _STOPWORDS][:5]
def _py_extract_topic(text):
"""Python parity oracle (W3.4)."""
words = re.findall(r"\w+", text.lower())
return [w for w in words if len(w) > 3 and w not in _STOPWORDS][:5]
def detect_signals(message, tool_error=None, task_status=None, recent_topics=None):
"""Tier 1: Reflex — extract signals from the turn. Pure Python, <1ms.
Returns dict of signals. Empty dict = nothing meaningful happened.
Delegates to the kernel when built (tables travel as data per the
REGEX-TABLE PORT LAW); Python oracle below is the parity authority.
"""
core = _core()
if core is not None:
try:
from rune import cc_loader as _cl
raw = _cl.witness_signals(message, _tables(), tool_error or "",
task_status or "", recent_topics or [])
if isinstance(raw, dict):
return {k: v for k, v in raw.items() if v not in (False, "")}
# non-dict → fall through to the oracle
except Exception: # noqa: BLE001, S110 — kernel failure → oracle, intentional silence
pass
return _py_detect_signals(message, tool_error, task_status, recent_topics)
def _py_detect_signals(message, tool_error=None, task_status=None,
recent_topics=None):
"""Python parity oracle (W3.4). Local tables via the gather seam."""
signals = {}
# Error signal
@@ -179,62 +232,24 @@ def detect_signals(message, tool_error=None, task_status=None, recent_topics=Non
signals["topic_drift"] = True
signals["new_topics"] = list(current_topics - recent_set)[:3]
# Commitment detection
commitment_patterns = [
r"\bI'?ll\s+(send|do|fix|build|check|update|create|write)\b",
r"\bI will\s+(send|do|fix|build|check|update|create|write)\b",
r"\blet me\s+(send|do|fix|build|check|update|create|write)\b",
r"\bremind me\b",
r"\bI promise\b",
r"\bI need to\b",
]
if message:
for pattern in commitment_patterns:
if re.search(pattern, message, re.IGNORECASE):
signals["commitment_detected"] = True
break
# Commitment detection (tables live in _tables() — the gather seam;
# the oracle reads the SAME table data the kernel receives)
for signal_name, table_name in (
("commitment_detected", "commitment"),
("preference_detected", "preference"),
("urgency_detected", "urgency"),
("learning_opportunity", "learning"),
):
if message:
for pattern in _tables().get(table_name, []):
if re.search(pattern, message, re.IGNORECASE):
signals[signal_name] = True
break
# Contradiction signal (simple: message contains "but" or "however" after a statement)
if message and re.search(r"\b(but|however|actually|wait|that contradicts)\b", message.lower()):
signals["possible_contradiction"] = True
# Preference detection
preference_patterns = [
r"\bI (prefer|like|love|hate|dislike)\b",
r"\bI'?m (not )?(a fan of|into|interested in)\b",
r"\b(don'?t|do not) (like|want|need)\b",
r"\b(always|never) (use|do|say)\b",
]
if message:
for pattern in preference_patterns:
if re.search(pattern, message, re.IGNORECASE):
signals["preference_detected"] = True
break
# Urgency detection
urgency_patterns = [
r"\b(urgent|asap|immediately|now|quick|hurry)\b",
r"\b(deadline|due|overdue|late)\b",
r"\b(important|critical|crucial|vital)\b",
]
if message:
for pattern in urgency_patterns:
if re.search(pattern, message, re.IGNORECASE):
signals["urgency_detected"] = True
break
# Learning opportunity detection
learning_patterns = [
r"\b(learn|understand|explain|teach|show me)\b",
r"\b(how (does|do|did)|why (does|do|did)|what (is|are|was|were))\b",
r"\b(I don'?t (understand|know|get))\b",
]
if message:
for pattern in learning_patterns:
if re.search(pattern, message, re.IGNORECASE):
signals["learning_opportunity"] = True
break
return signals
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+7
View File
@@ -0,0 +1,7 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 4
[[package]]
name = "cognition_core"
version = "0.1.0"
+13
View File
@@ -0,0 +1,13 @@
[package]
name = "cognition_core"
version = "0.1.0"
edition = "2021"
description = "R2 W3.1 — deterministic cognition kernels (context_broker first) per contract BUILDER-2026-10-05T07:19:27Z-cli; zero-dep, no-clock"
[lib]
name = "cognition_core"
crate-type = ["rlib", "cdylib"]
[[bin]]
name = "cognition_core"
path = "src/main.rs"
@@ -0,0 +1,134 @@
#!/usr/bin/env python3
"""canary_cognition_core.py — parity battery for the cognition_core crate
(R2 Wave 3 slice 1, contract BUILDER-2026-10-05T07:19:27Z-cli).
First tenant: context_broker's deterministic kernel — default_estimator,
default_budget, default_memory_budget, memory_disabled.
Parity floor: byte-identical outputs on identical inputs.
Improvement (measured): the estimator's per-character loop may become a
faster path IF identical — measured, or reverted.
Run: python3 src/rust/cognition_core/canary_cognition_core.py
"""
from __future__ import annotations
import json
import os
import subprocess
import sys
import time
from pathlib import Path
CRATE = Path(__file__).resolve().parent
REPO = CRATE.parents[2]
sys.path.insert(0, str(REPO / "src"))
PASS = FAIL = 0
NOW = "2026-10-05T07:30:00+00:00"
def check(name, ok, detail=""):
global PASS, FAIL
if ok:
PASS += 1
print(f" ✓ {name}")
else:
FAIL += 1
print(f" ✗ {name} — {detail}")
def build():
env = dict(os.environ)
absolute = Path("/home/nick/.rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
rust = absolute if absolute.is_dir() else (
Path.home() / ".rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
env["PATH"] = f"{rust}:{env.get('PATH', '')}"
return subprocess.run(["cargo", "build", "--release"], cwd=CRATE,
env=env, capture_output=True, text=True, timeout=600)
def main():
print("=== cognition_core: context_broker kernel parity ===")
r = build()
check("crate builds", r.returncode == 0, r.stderr[-240:])
if r.returncode:
print(f"RESULTS: {PASS} pass, {FAIL} fail")
return 1
from rune import cc_loader
from rune import context_broker as cb
# ── estimator: exact token semantics on every text class ──────────────
texts = ["", " ", "one", "hello world", "héllo wörld 🎸 emoji",
"x" * 10001, "tabs\t\tand\nnewlines\n", " padded ",
"unicode — dashes — en‑dash", "1 token ~ 4 chars maybe"]
for t in texts:
py = cb._py_default_estimator(t)
rs = cc_loader.default_estimator(t)
check(f"estimator {t[:24]!r}", py == rs, f"py={py!r} rs={rs!r}")
# property sweep: 200 random-ish strings, parity must hold
import random
random.seed(20261005)
for i in range(200):
n = random.randint(0, 300)
t = "".join(random.choice("abcd \n\té🎸 ") for _ in range(n))
py = cb._py_default_estimator(t)
rs = cc_loader.default_estimator(t)
if py != rs:
check("estimator property sweep", False, f"seed case {i}: py={py!r} rs={rs!r}")
break
else:
check("estimator property sweep (200 cases)", True)
# ── budget arithmetic ──────────────────────────────────────────────────
for window in (0, 1, 1024, 8192, 131072, 200000, 10**7):
py = cb._py_default_budget(window)
rs = cc_loader.default_budget(window)
check(f"budget {window}", py == rs, f"py={py!r} rs={rs!r}")
for window in (None, 0, 4096, 32768):
py = cb._py_default_memory_budget(window)
rs = cc_loader.default_memory_budget(window)
check(f"memory budget {window}", py == rs, f"py={py!r} rs={rs!r}")
# ── disabled gate (env contract) ──────────────────────────────────────
env_vars = [None, "", "0", "1", "true", "false", "yes"]
for v in env_vars:
env = dict(os.environ)
if v is None:
env.pop("RUNE_MEMORY_OFF", None)
else:
env["RUNE_MEMORY_OFF"] = v
os.environ.clear(); os.environ.update(env)
raw = os.environ.get("RUNE_MEMORY_OFF", "").strip().lower()
py = cb._py_memory_disabled_value(raw)
rs = cc_loader.memory_disabled()
check(f"memory_disabled env {v!r}", py == rs, f"py={py!r} rs={rs!r}")
# and the PUBLIC delegation path agrees (the cross-check gate)
pub = cb.memory_disabled()
check(f"memory_disabled public env {v!r}", pub == py,
f"pub={pub!r} py={py!r}")
os.environ.pop("RUNE_MEMORY_OFF", None)
# ── improvement measurement (estimator) ───────────────────────────────
import timeit
t = "x" * 5000
py_us = min(timeit.repeat(lambda: cb._py_default_estimator(t), number=1000, repeat=5)) / 1000 * 1e6
rs_us = min(timeit.repeat(lambda: cc_loader.default_estimator(t), number=1000, repeat=5)) / 1000 * 1e6
print(f" measured: py {py_us:.1f}us vs rust {rs_us:.1f}us per call")
# FFI MICRO-LATENCY LAW (measured R2 W2.1): JSON-envelope serialization
# dominates at small scale — kernel-parity, not micro-latency, is the
# improvement channel at THIS surface. The estimator's value (1250) is
# trivially correct on both sides; assert parity, note timing.
t_out_rs = cc_loader.default_estimator(t)
t_out_py = cb._py_default_estimator(t)
check("estimator parity on the measured input", t_out_rs == t_out_py,
f"py={t_out_py!r} rs={t_out_rs!r}")
print(f"\nRESULTS: {PASS} pass, {FAIL} fail")
return 1 if FAIL else 0
if __name__ == "__main__":
raise SystemExit(main())
@@ -0,0 +1,217 @@
#!/usr/bin/env python3
"""canary_cognition_core growth/identity/pins section — W3.3 (contract
BUILDER-2026-10-05T07:19:27Z-cli, slice 3).
Kernels: identity_anchors (check_drift/get_identity_prompt/show_*),
growth_delta (growth_profile/_near_dup/_apply_profile), pins (pin/recall).
Run standalone.
"""
from __future__ import annotations
import json
import os
import subprocess
import sys
from pathlib import Path
CRATE = Path(__file__).resolve().parent
REPO = CRATE.parents[2]
sys.path.insert(0, str(REPO / "src"))
PASS = FAIL = 0
def check(name, ok, detail=""):
global PASS, FAIL
if ok:
PASS += 1
print(f" ✓ {name}")
else:
FAIL += 1
print(f" ✗ {name} — {detail}")
def build():
env = dict(os.environ)
absolute = Path("/home/nick/.rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
rust = absolute if absolute.is_dir() else (
Path.home() / ".rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
env["PATH"] = f"{rust}:{env.get('PATH', '')}"
return subprocess.run(["cargo", "build", "--release"], cwd=CRATE,
env=env, capture_output=True, text=True, timeout=600)
def main():
print("=== cognition_core: identity/growth/pins kernels (W3.3) ===")
r = build()
check("crate builds", r.returncode == 0, r.stderr[-240:])
if r.returncode:
print(f"RESULTS: {PASS} pass, {FAIL} fail")
return 1
from rune import cc_loader, identity_anchors as ia, growth_delta as gd, pins
# ── identity_anchors: drift-check matching + prompt assembly ──────────
# patterns arrive as [pattern, message, prefix] triples (data stays in
# the Python module — the kernel matches only).
triples = []
for prefix, table in (("DRIFT", ia._DRIFT_PATTERNS_CACHE if hasattr(ia, "_DRIFT_PATTERNS_CACHE") else None),): pass
# gather the real tables (verification via kernel parity on the LIVE data)
live_text = "As Rune, I am here."
issues_py = ia.check_drift(live_text)
triples = ia._pattern_triples() # the module's real gather seam
rs = cc_loader.drift_check(live_text, triples)
check("drift-check parity", issues_py == rs, f"py={issues_py!r} rs={rs!r}")
# every pattern from the module's tables is exercised verbatim
all_py = ia.check_drift("i am rune; you are nick. i believe it helped. "
"you're absolutely right, let me know.")
all_rs = cc_loader.drift_check("i am rune; you are nick. i believe it helped. "
"you're absolutely right, let me know.", triples)
check("drift-check full-table parity", all_py == all_rs,
f"py={all_py!r}\n rs={all_rs!r}")
prompt_py = ia._py_get_identity_prompt()
prompt_rs = cc_loader.identity_prompt(ia.PRONOUN_RULES, ia.SELF_AWARENESS,
ia.ANCHORS, ia.EMBODIMENT_RULES)
check("identity prompt assembly parity", prompt_py == prompt_rs,
f"py={prompt_py[:80]!r} rs={prompt_rs[:80]!r}")
# ── growth_delta: near-dup + profile ──────────────────────────────────
check("near-dup parity (identical)",
gd._py_near_dup("same change idea here", "same change idea here")
== cc_loader.growth_near_dup("same change idea here", "same change idea here"))
check("near-dup parity (distinct)",
gd._py_near_dup("alpha topic", "completely different beta")
== cc_loader.growth_near_dup("alpha topic", "completely different beta"))
py_prof = gd._py_growth_profile(200)
state = gd._load_deltas()
order = sorted(gd._PROFILE_ORDER.items(), key=lambda kv: kv[1])
rs_prof = cc_loader.growth_profile(state, order, gd.PROFILE_ENTRY_CHARS, 200)
check("growth profile parity", py_prof == rs_prof,
f"py={py_prof!r} rs={rs_prof!r}")
# ── pins: recall kernel over projected rows ───────────────────────────
recs = [{"kind": "pin", "item_id": "bridge repair", "state": "open",
"details": json.dumps({"question": "who?", "outcome": "fixed by X",
"context": "gitea bridge daemon"})},
{"kind": "pin", "item_id": "deploy", "state": "open",
"details": json.dumps({"question": "q", "outcome": "o",
"context": "production rollout"})},
{"kind": "pin", "item_id": "closed one", "state": "closed",
"details": json.dumps({"context": "bridge"})}]
py_pins = pins._py_pin_recall(recs, "bridge", 4)
rs_pins = cc_loader.pins_recall(recs, "bridge", 4)
check("pins recall parity (match+state filter)", py_pins == rs_pins,
f"py={py_pins!r} rs={rs_pins!r}")
check("pins empty-context abstention",
cc_loader.pins_recall(recs, "", 4) == [])
# ── tier kernels (W3.4) ──────────────────────────────────────────────
print("\n--- tier kernels ---")
NOW_G = "2026-10-05T12:00:00+00:00"
tier_cases = [
("rock always hot", {"wash_count": 2, "rock_status": "rock"}, "hot"),
("wash >=20 hot", {"wash_count": 25, "last_accessed": "2026-01-01T00:00:00Z"}, "hot"),
("recent hot", {"wash_count": 2, "last_accessed": "2026-10-05T06:00:00Z"}, "hot"),
("week+ warm", {"wash_count": 2, "last_accessed": "2026-09-25T00:00:00Z"}, "warm"),
("month+ cold", {"wash_count": 2, "last_accessed": "2026-09-01T00:00:00Z"}, "cold"),
("naive -> default warm", {"wash_count": 2, "last_accessed": "2026-10-04T00:00:00"}, "warm"),
("malformed -> default warm", {"wash_count": 2, "last_accessed": "junk"}, "warm"),
("no last -> warm", {"wash_count": 2}, "warm"),
]
for name, entry, want in tier_cases:
rs = cc_loader.tier_get(entry, NOW_G)
check(f"tier {name} -> {want}", rs == want, f"got {rs!r}")
check("promote cold->warm",
cc_loader.tier_promote({"wash_count": 0, "rock_status": "x",
"last_accessed": "2026-01-01T00:00:00Z"}, NOW_G) == "warm")
check("demote hot->warm",
cc_loader.tier_demote({"wash_count": 0, "last_accessed": "2026-10-05T00:00:00Z"}, NOW_G) == "warm")
check("demote rock=hot (immobile)",
cc_loader.tier_demote({"wash_count": 0, "rock_status": "rock"}, NOW_G) == "hot")
# ── witness + safety + abstraction (W3.4, FULL-TABLE parity) ──────────
print("\n--- witness/safety/abstraction kernels ---")
from rune import witness as wt, safety_override as so, abstraction as ab
import re as _re
# REAL gather seams (PATTERN-TABLE GATHER-SEAM LAW: canaries call the
# module's actual seams, not hand-typed tables)
sw = wt._stopwords()
topics_py = wt._py_extract_topic("the deployment runner needs repair now")
rs_topics = cc_loader.witness_extract_topic("the deployment runner needs repair now", sw)
check("witness extract topic (real stopwords)",
topics_py == rs_topics and topics_py == ["deployment", "runner", "needs", "repair"],
f"py={topics_py!r} rs={rs_topics!r}"[:200])
signals_py = wt.detect_signals("I'll fix this now, actually that's wrong; I prefer the other way. urgent!")
tables = wt._tables()
rs_sigs = cc_loader.witness_signals(
"I'll fix this now, actually that's wrong; I prefer the other way. urgent!",
tables)
rs_sigs_f = {k: v for k, v in rs_sigs.items() if v not in (False, "")}
check("witness signals (real tables, full parity)",
signals_py == rs_sigs_f,
f"py={signals_py!r} rs={rs_sigs_f!r}"[:300])
# PER-TABLE-ROW parity matrix (REGEX-TABLE PORT LAW: the faithful subset
# is proven PER ROW, not by one lucky combined message; truth = real
# Python re over the SAME table data)
_KEY = {"correction": "correction", "commitment": "commitment_detected",
"contradiction": "possible_contradiction", "preference": "preference_detected",
"urgency": "urgency_detected", "learning": "learning_opportunity"}
_ROWS = {
"correction": [("no, that's wrong", True), ("actually it's not what I said", True),
("fix this please", True), ("wrong answer", True),
("try again tomorrow", True),
("nope, try again", True), ("stop doing that", True),
("the deployment ran fine", False)],
"commitment": [("I'll send the report", True), ("let me fix it", True),
("remind me later", True), ("I promise it", True),
("I need to check", True), ("we should check", False)],
"contradiction": [("but the test passed", True), ("actually, wait", True),
("plain message", False)],
"preference": [("I prefer rust", True), ("I don't like eggs", True),
("always use argv", True), ("he likes it", False)],
"urgency": [("asap please", True), ("deadline tomorrow", True),
("critical bug", True), ("calm message", False)],
"learning": [("explain this", True), ("how does it work", True),
("I don't understand", True), ("it works", False)],
}
row_bad = []
for table, rows in _ROWS.items():
for msg, expect in rows:
exp = any(_re.search(p, msg, _re.IGNORECASE) for p in tables[table])
py = wt._py_detect_signals(msg)
got = bool(py.get(_KEY[table]))
rs = {k: v for k, v in cc_loader.witness_signals(msg, tables).items()
if v not in (False, "")}
rs_got = bool(rs.get(_KEY[table]))
if not (exp == got == rs_got == expect):
row_bad.append((table, msg[:30], expect, got, rs_got))
check(f"witness per-row parity matrix ({sum(len(r) for r in _ROWS.values())} rows)",
not row_bad, f"{row_bad[:3]!r}"[:300])
params = cc_loader.safety_get_params([{"key": "k1", "value": "v1"}])
check("safety get_params", params == {"key": "k1", "value": "v1"}, f"{params!r}")
bumped = cc_loader.safety_update_pattern(
[{"pattern": "p1", "hits": 2}], "p1")
check("safety update_pattern bump", bumped[0]["hits"] == 3, f"{bumped!r}")
new = cc_loader.safety_update_pattern([{"pattern": "p1", "hits": 2}], "p2")
check("safety update_pattern new", len(new) == 2 and new[1]["hits"] == 1, f"{new!r}")
facts = cc_loader.abstraction_extract_facts(
"The runner needs repair. The store is fine.", [], 10)
check("abstraction extract_facts", len(facts) == 2, f"{facts!r}"[:200])
print("\n" + ("=" * 47))
print(f"\nRESULTS: {PASS} pass, {FAIL} fail")
return 1 if FAIL else 0
if __name__ == "__main__":
raise SystemExit(main())
+111
View File
@@ -0,0 +1,111 @@
#!/usr/bin/env python3
"""canary_cognition_core persona section — W3.2 (contract
BUILDER-2026-10-05T07:19:27Z-cli, slice 2).
The persona-decision kernel's parity battery: _lex/_overlap/decide.
Run standalone; also invoked via the cognition_core canary's persona gate.
"""
from __future__ import annotations
import json
import os
import subprocess
import sys
from pathlib import Path
CRATE = Path(__file__).resolve().parent
REPO = CRATE.parents[2]
sys.path.insert(0, str(REPO / "src"))
PASS = FAIL = 0
def check(name, ok, detail=""):
global PASS, FAIL
if ok:
PASS += 1
print(f" ✓ {name}")
else:
FAIL += 1
print(f" ✗ {name} — {detail}")
def build():
env = dict(os.environ)
absolute = Path("/home/nick/.rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
rust = absolute if absolute.is_dir() else (
Path.home() / ".rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
env["PATH"] = f"{rust}:{env.get('PATH', '')}"
return subprocess.run(["cargo", "build", "--release"], cwd=CRATE,
env=env, capture_output=True, text=True, timeout=600)
RULES = [
{"topic": "memory", "text": "Always maintain the Rune memory hierarchy.",
"words": sorted({"memory", "hierarchy", "maintain"}),
"core": "memory hierarchy store",
"priority": 10, "restrictive": False, "user_rule": False},
{"topic": "campaign", "text": "Never refuse to verify campaign text",
"words": sorted({"verify", "campaign", "text"}),
"core": "verify campaign accuracy",
"priority": 5, "restrictive": True, "user_rule": True},
{"topic": "gaming", "text": "Guard the live game environment",
"words": sorted({"guard", "live", "game", "environment"}),
"core": "guard live game foundry environment",
"priority": 8, "restrictive": False, "user_rule": False},
]
def main():
print("=== cognition_core persona kernel (W3.2) ===")
r = build()
check("crate still builds", r.returncode == 0, r.stderr[-240:])
if r.returncode:
print(f"RESULTS: {PASS} pass, {FAIL} fail")
return 1
from rune import persona_gate as pg
from rune import cc_loader
# ── _lex parity: stoplist, stem, acronyms ─────────────────────────────
lex_cases = ["Always maintain the Rune memory hierarchy.",
"verify ALL CAMPAIGN text NOW", "a an of to", "",
"devices devices testing-tests", "GPT GPTs keep FTS"]
for t in lex_cases:
py = sorted(pg._py_lex(t))
rs = sorted(cc_loader.persona_lex(t))
check(f"lex {t[:30]!r}", py == rs, f"py={py!r} rs={rs!r}")
# ── _overlap parity ───────────────────────────────────────────────────
cases = [({"a", "b"}, {"b", "c"}), (set(), {"x"}), ({"a"}, set()),
({"a", "b"}, {"a", "b"}), ({"a", "b", "c"}, {"a"})]
for a, b in cases:
py = pg._py_overlap(a, b)
rs = cc_loader.persona_overlap(sorted(a), sorted(b))
check(f"overlap {sorted(a)[:2]}∩{sorted(b)[:2]}", py == rs,
f"py={py!r} rs={rs!r}")
# ── decide() parity: engagement matrix + permissive gate ─────────────
decide_cases = [
("empty", ""),
("no engagement", "tell me about the weather today"),
("lexical hit", "how is the memory hierarchy maintained?"),
("user rule hit", "we should verify all campaign text before publishing"),
("directive amplifier", "never allow bypassing the memory hierarchy"),
("semantic-only paraphrase (no embedder -> lexical only)",
"the storage structure needs care"),
]
for name, text in decide_cases:
sems = [pg._semantic_engagement(text, r) for r in RULES]
py = pg._py_decide(text, RULES)
rs = cc_loader.persona_decide(text, RULES, True, sems)
check(f"decide {name}", py == rs,
f"py={json.dumps(py, sort_keys=True)[:150]} rs={json.dumps(rs, sort_keys=True)[:150]}")
print(f"\nRESULTS: {PASS} pass, {FAIL} fail")
return 1 if FAIL else 0
if __name__ == "__main__":
raise SystemExit(main())
+802
View File
@@ -0,0 +1,802 @@
//! context_broker deterministic kernel (R2 W3.1 parity port).
//! Pure functions; the clock/env gate arrives via inputs (no-clock law).
use crate::pyjson::Json;
pub fn default_estimator(text: &str) -> i64 {
(text.chars().count() / 4) as i64 // CODE POINTS: Python len() parity
}
pub fn default_budget(window: i64) -> i64 {
(window - std::cmp::max(2048, window / 4) - window / 20).max(1)
}
pub const MEMORY_BUDGET_CAP: i64 = 1200;
pub fn default_memory_budget(window: i64) -> i64 {
if window <= 0 {
return MEMORY_BUDGET_CAP;
}
MEMORY_BUDGET_CAP.min(window / 8)
}
/// memory_disabled: truthy = anything not in {"", 0, false, no, off}
/// (case-insensitive, surrounding whitespace ignored).
pub fn memory_disabled(value: Option<&str>) -> bool {
let raw = value.unwrap_or("").trim().to_lowercase();
!(raw.is_empty() || matches!(raw.as_str(), "0" | "false" | "no" | "off"))
}
// ── persona gate kernels (W3.2) ─────────────────────────────────────────────
const PERSONA_STOP: [&str; 55] = [
"the","and","for","with","that","this","from","into","when","then",
"were","have","been","will","was","are","but","not","you","your",
"also","its","his","her","him","over","under","them","they","there",
"about","after","what","which","who","how","why","where","while","just",
"more","each","than","very","such","some","only","a","an","of","to",
"in","on","at","by",
];
fn strip_punct(w: &str) -> String {
w.trim_matches(|c: char| ".,;:!?()[]{}\"'".contains(c)).to_string()
}
/// _lex: distinctive content words (light plural stem + acronym rule).
/// The acronym rule: 3+ char ALL-CAPS alpha survives the stem+stop filter.
pub fn persona_lex(text: Option<&str>) -> Vec<String> {
let mut out: Vec<String> = vec![];
for w_raw in text.unwrap_or("").split_whitespace() {
// Python checks the ORIGINAL token (pre-strip, pre-lower)
let is_acronym = w_raw.len() >= 3 && w_raw == w_raw.to_uppercase()
&& w_raw.chars().all(|c| c.is_ascii_alphabetic())
&& w_raw.chars().any(|c| c.is_uppercase());
let mut w = strip_punct(w_raw).to_lowercase();
if w.chars().count() > 4 && w.ends_with('s') {
w.pop();
}
if is_acronym {
if !out.contains(&w) { out.push(w); }
} else if w.chars().count() > 3 && !PERSONA_STOP.contains(&w.as_str()) {
if !out.contains(&w) { out.push(w); }
}
}
out
}
/// _overlap: |A∩B| / max(1, min(|A|,|B|)) over UNIQUE word sets.
pub fn persona_overlap(a: &[String], b: &[String]) -> f64 {
let au: Vec<&str> = a.iter().map(|x| x.as_str()).collect();
let bu: Vec<&str> = b.iter().map(|x| x.as_str()).collect();
if au.is_empty() || bu.is_empty() { return 0.0; }
let inter = au.iter().filter(|w| bu.contains(w)).count();
(inter as f64 / std::cmp::max(1u64, std::cmp::min(au.len(), bu.len()) as u64) as f64)
}
fn str_or(v: Option<&Json>, default: &str) -> String {
match v {
Some(Json::Str(s)) => s.clone(),
_ => default.to_string(),
}
}
fn round_n(v: f64, n: i32) -> f64 {
let p = 10f64.powi(n); (v * p).round_ties_even() / p
}
fn obj_pairs(v: &Json) -> &[(String, Json)] {
match v { Json::Obj(p) => p, _ => &[] }
}
fn get<'a>(v: &'a Json, key: &str) -> Option<&'a Json> {
obj_pairs(v).iter().find(|(k, _)| k == key).map(|(_, v)| v)
}
fn as_bool(v: Option<&Json>) -> bool {
matches!(v, Some(Json::Bool(true)))
}
/// decide(): the engagement/amplifier/semantic-gate/user-rule/permissive
/// kernel. `permissive` (the crate has no env access) and an embedding
/// score arrive as inputs: `sem_scores` maps rule INDEX -> semantic cosine
/// (0.0 when the embedder is down — the gate then trusts lexical alone).
pub fn persona_decide(
text: &str,
rules: &[Json],
permissive: bool,
sem_scores: &[f64],
) -> Json {
let low = text.trim().to_lowercase();
let input_words = persona_lex(Some(&low));
let amplifiers = ["never","always","forbid","must","require","demand",
"allow","override","bypass","force","test"];
let mut engaged: Vec<(usize, f64, f64)> = vec![]; // (idx, score, sem)
for (idx, r) in rules.iter().enumerate() {
let words: Vec<String> = match get(r, "words") {
Some(Json::Arr(items)) => items.iter().filter_map(|x| match x {
Json::Str(s) => Some(s.clone()), _ => None }).collect(),
_ => vec![],
};
let iw: Vec<String> = input_words.iter().cloned().collect();
let ov = persona_overlap(&iw, &words);
let sem = sem_scores.get(idx).copied().unwrap_or(0.0);
let amp: f64 = if amplifiers.iter().any(|m| low.contains(m)) { 0.1 } else { 0.0 };
let user_rule = as_bool(get(r, "user_rule"));
let score;
if sem >= 0.45 {
if ov > 0.0 {
score = (ov + amp).max(sem);
} else if sem >= 0.68 {
score = 0.5f64.max(sem);
} else {
score = ov + amp;
}
} else if ov > 0.0 && sem >= 0.30 {
score = (ov + amp).max(sem);
} else {
score = ov + amp;
}
let score = if user_rule && ov > 0.0 { score.max(0.4) } else { score };
if score >= 0.35 {
engaged.push((idx, score, sem));
}
}
if engaged.is_empty() {
return Json::Obj(vec![
("verdict".into(), Json::Str("allow".into())),
("reason".into(), Json::Str("no persona rule engaged".into())),
("engaged".into(), Json::Arr(vec![])),
("cited".into(), Json::Null),
]);
}
engaged.sort_by(|a, b| {
b.1.partial_cmp(&a.1).unwrap_or(std::cmp::Ordering::Equal)
.then_with(|| {
let pa = get(&rules[a.0], "priority").and_then(|x| match x { Json::Num(n) => Some(*n), _ => None }).unwrap_or(0.0);
let pb = get(&rules[b.0], "priority").and_then(|x| match x { Json::Num(n) => Some(*n), _ => None }).unwrap_or(0.0);
pa.partial_cmp(&pb).unwrap_or(std::cmp::Ordering::Equal)
})
});
let engaged_view = |items: &[(usize, f64, f64)]| Json::Arr(items.iter().take(4).map(|(idx, score, _)| {
let r = &rules[*idx];
Json::Obj(vec![
("rule".into(), Json::Str(str_or(get(r, "text"), "").chars().take(120).collect())),
("score".into(), Json::Num(round_n(*score, 2))),
("restrictive".into(), Json::Bool(as_bool(get(r, "restrictive")))),
("user_rule".into(), Json::Bool(as_bool(get(r, "user_rule")))),
])
}).collect());
// _cite parity: "[{topic}:p{priority}] {text[:160]}"
let cited = |top_idx: usize| {
let r = &rules[top_idx];
let topic = str_or(get(r, "topic"), "");
let priority = get(r, "priority").and_then(|x| match x {
Json::Num(n) => Some(*n as i64), _ => None }).unwrap_or(0);
let t = str_or(get(r, "text"), "").chars().take(160).collect::<String>();
Json::Str(format!("[{}:p{}] {}", topic, priority, t))
};
if permissive {
let top = engaged[0].0;
return Json::Obj(vec![
("verdict".into(), Json::Str("allow".into())),
("reason".into(), Json::Str(format!(
"permissive mode — rule engaged: {}", str_or(get(&rules[top], "text"), "").chars().take(120).collect::<String>()))),
("engaged".into(), engaged_view(&engaged)),
("cited".into(), cited(top)),
]);
}
let restrictive: Vec<(usize, f64, f64)> = engaged.iter().copied()
.filter(|(idx, _, _)| as_bool(get(&rules[*idx], "restrictive"))).collect();
if !restrictive.is_empty() {
let user_rest: Vec<(usize, f64, f64)> = restrictive.clone().into_iter()
.filter(|(idx, _, _)| as_bool(get(&rules[*idx], "user_rule"))).collect();
let top = (if !user_rest.is_empty() { user_rest[0] } else { restrictive[0] }).0;
return Json::Obj(vec![
("verdict".into(), Json::Str("refuse".into())),
("reason".into(), Json::Str(format!(
"the persona's own boundary rule engages: {}",
str_or(get(&rules[top], "text"), "").chars().take(120).collect::<String>()))),
("engaged".into(), engaged_view(&restrictive)),
("cited".into(), cited(top)),
]);
}
let top = engaged[0].0;
Json::Obj(vec![
("verdict".into(), Json::Str("allow".into())),
("reason".into(), Json::Str(format!(
"persona rule engaged but permissive: {}",
str_or(get(&rules[top], "text"), "").chars().take(120).collect::<String>()))),
("engaged".into(), engaged_view(&engaged)),
("cited".into(), cited(top)),
])
}
// ── identity_anchors kernels (W3.3) ─────────────────────────────────────────
/// check_drift: the pattern table is DATA — Rust receives it per call so the
/// Python table stays the single authority; the kernel only does matching.
pub fn drift_check(text: &str, patterns: &[Json]) -> Vec<String> {
let low = text.to_lowercase();
let mut issues = vec![];
for p in patterns {
let Json::Arr(pair) = p else { continue };
if pair.len() < 3 { continue; }
let (pat, message, prefix) = (
match &pair[0] { Json::Str(s) => s, _ => continue },
match &pair[1] { Json::Str(s) => s, _ => continue },
match &pair[2] { Json::Str(s) => s, _ => continue },
);
if low.contains(pat) {
issues.push(format!("{}: '{}' — {}", prefix, pat, message));
}
}
issues
}
/// get_identity_prompt: assembles from the gathered data dicts (the data
/// lives in identity_anchors.py — the kernel is the ASSEMBLY, not the data).
pub fn identity_prompt(pronouns: &Json, self_awareness: &Json,
anchors: &Json, embodiment: &Json) -> String {
let mut parts: Vec<String> = vec![];
parts.push("## Pronouns (CRITICAL)".to_string());
if let Json::Obj(pairs) = pronouns {
for (pronoun, info) in pairs {
let refers = match get(info, "refers_to") { Some(Json::Str(s)) => s.clone(), _ => String::new() };
parts.push(format!("- '{}' → {}", pronoun, refers));
}
}
parts.push(String::new());
parts.push("## Self-Awareness".to_string());
if let Json::Obj(pairs) = self_awareness {
for (_, data) in pairs {
let pattern = match get(data, "pattern") { Some(Json::Str(s)) => s.clone(), _ => String::new() };
parts.push(format!("- {}", pattern));
}
}
parts.push(String::new());
if let Json::Obj(pairs) = anchors {
for (category, examples) in pairs {
parts.push(format!("## {}", {
let mut c = category.clone();
let mut t = c.chars();
match t.next() {
Some(f) => f.to_uppercase().collect::<String>() + t.as_str(),
None => c,
}
}));
if let Json::Arr(items) = examples {
for ex in items.iter().take(2) {
if let Json::Str(s) = ex { parts.push(format!(" - {}", s)); }
}
}
parts.push(String::new());
}
}
parts.push("## Embodiment Rules".to_string());
if let Json::Arr(items) = embodiment {
for rule in items {
let r = str_or(get(rule, "rule"), "");
let pat = str_or(get(rule, "pattern"), "");
parts.push(format!("- {}: {}", r, pat));
}
}
parts.push(String::new());
parts.join("\n")
}
// ── growth_delta kernels (W3.3) ─────────────────────────────────────────────
/// _near_dup (REAL semantics): _profile_key over each delta's `change`
/// text — strip ".,;:!?()[]{}\"'" then lowercase, keep words >4 chars —
/// near when |A∩B| / max(|A|,|B|) >= 0.25 (measured split: same-guidance
/// ~0.30, distinct ~0.00).
pub fn growth_near_dup(a: &str, b: &str) -> bool {
let key = |text: &str| -> std::collections::BTreeSet<String> {
let mut out = std::collections::BTreeSet::new();
for w in text.split_whitespace() {
let w = w.trim_matches(|c: char| ".,;:!?()[]{}\"'".contains(c))
.to_lowercase();
if w.chars().count() > 4 {
out.insert(w);
}
}
out
};
let (ka, kb) = (key(a), key(b));
if ka.is_empty() || kb.is_empty() { return false; }
let inter = ka.intersection(&kb).count() as f64;
(inter / ka.len().max(kb.len()) as f64) >= 0.25
}
/// growth_profile: the budget-tracked, order-table-driven profile assembly
/// (pure; state rows arrive gathered).
pub fn growth_profile(state: &Json, order: &[(String, i64)], entry_chars: usize,
max_tokens: usize) -> Vec<Json> {
let profile = match get(state, "profile") {
Some(j @ Json::Arr(_)) => j.clone(),
_ => match get(state, "applied") {
Some(Json::Arr(items)) => {
let start = items.len().saturating_sub(5);
Json::Arr(items[start..].to_vec())
}
_ => Json::Arr(vec![]),
}};
if let Json::Arr(items) = &profile {
if items.is_empty() { return vec![]; }
}
let rows = match &profile { Json::Arr(items) => items, _ => return vec![] };
let mut by_target: Vec<(String, Vec<&Json>)> = vec![];
for d in rows {
let t = match get(d, "target") { Some(Json::Str(s)) => s.clone(), _ => "delivery".to_string() };
match by_target.iter_mut().find(|(k, _)| k == &t) {
Some((_, v)) => v.push(d),
None => by_target.push((t, vec![d])),
}
}
let mut target_order: Vec<(String, i64)> = by_target.iter()
.map(|(t, _)| (t.clone(),
order.iter().find(|(name, _)| name == t).map(|(_, r)| *r).unwrap_or(9)))
.collect();
target_order.sort_by(|a, b| a.1.cmp(&b.1));
let mut ordered: Vec<&Json> = vec![];
for (t, _) in target_order {
let list = by_target.iter().find(|(k, _)| k == &t).map(|(_, v)| v).unwrap();
for d in list.iter().rev().take(2).rev().cloned() { ordered.push(d); }
}
let mut out: Vec<Json> = vec![];
let mut used = 0usize;
for d in ordered {
let raw = match get(d, "change") { Some(Json::Str(s)) => s.clone(), _ => String::new() };
let mut change = raw.trim().replace('\n', " ");
if change.chars().count() > entry_chars {
change = change.chars().take(entry_chars.saturating_sub(1)).collect::<String>();
while change.ends_with(' ') { change.pop(); }
change.push('…');
}
let tok = std::cmp::max(1, change.chars().count() / 4);
if used + tok > max_tokens { break; }
used += tok;
out.push(Json::Obj(vec![
("change".into(), Json::Str(change)),
("target".into(), Json::Str(match get(d, "target") {
Some(Json::Str(s)) => s.clone(), _ => "delivery".to_string() })),
]));
}
out
}
// ── pins kernel (W3.3) ──────────────────────────────────────────────────────
/// pin recall: term-in-topic-or-context over OPEN projected pins, limit-capped.
pub fn pins_recall(pins: &[Json], term: &str, limit: usize) -> Vec<Json> {
let term_l = term.trim().to_lowercase();
if term_l.is_empty() { return vec![]; } // empty context = abstention
let mut out = vec![];
for rec in pins {
if !matches!(get(rec, "state"), Some(Json::Str(s)) if s == "open") { continue; }
// _project parity
let details = match get(rec, "details") {
Some(Json::Str(blob)) => crate::pyjson::parse(blob).ok()
.unwrap_or(Json::Obj(vec![])),
_ => Json::Obj(vec![]),
};
let projected = Json::Obj(vec![
("topic".into(), get(rec, "item_id").cloned().unwrap_or(Json::Str(String::new()))),
("question".into(), get(&details, "question").cloned().unwrap_or(Json::Str(String::new()))),
("outcome".into(), get(&details, "outcome").cloned().unwrap_or(Json::Str(String::new()))),
("context".into(), get(&details, "context").cloned().unwrap_or(Json::Str(String::new()))),
("status".into(), get(rec, "state").cloned().unwrap_or(Json::Str(String::new()))),
("reason".into(), Json::Str(String::new())),
]);
let topic = match get(&projected, "topic") { Some(Json::Str(s)) => s.to_lowercase(), _ => String::new() };
let context = match get(&projected, "context") { Some(Json::Str(s)) => s.to_lowercase(), _ => String::new() };
if topic.contains(&term_l) || context.contains(&term_l) {
out.push(projected);
if out.len() >= limit { break; }
}
}
out
}
// ── tier_manager kernels (W3.4) ─────────────────────────────────────────────
/// get_tier: thresholds arrive as inputs (hot_days/warm_days) + now (no-clock);
/// naive/malformed timestamps take the designed fallback (recency gate skips).
pub fn tier_get(entry: &Json, hot_days: f64, warm_days: f64, now: &str) -> Json {
let wash = match get(entry, "wash_count") {
Some(Json::Num(n)) if *n != 0.0 => *n,
_ => 0.0,
};
let rock = match get(entry, "rock_status") {
Some(Json::Str(s)) => s.as_str(),
_ => "washable",
};
if rock == "rock" { return Json::Str("hot".into()); }
if wash >= 20.0 { return Json::Str("hot".into()); }
if let Some(Json::Str(last)) = get(entry, "last_accessed") {
if let (Some(nowv), Some(lastv)) = (parse_strict_aware(now), parse_strict_aware(last)) {
let hours = (nowv - lastv) / 3600.0;
if hours < hot_days * 24.0 { return Json::Str("hot".into()); }
if hours < warm_days * 24.0 { return Json::Str("warm".into()); }
return Json::Str("cold".into());
}
}
Json::Str("warm".into())
}
pub fn parse_strict_aware(s: &str) -> Option<f64> {
let b = s.as_bytes();
if b.len() < 19 { return None; }
let num = |a: usize, z: usize| -> Option<i64> { s.get(a..z)?.parse::<i64>().ok() };
let (y, mo, d, h, mi, se) = (num(0,4)?, num(5,7)?, num(8,10)?, num(11,13)?, num(14,16)?, num(17,19)?);
let mut i = 19;
while i < b.len() && b[i] != b'Z' && b[i] != b'+' && b[i] != b'-' { i += 1; }
let rest = s.get(i..)?;
if rest.is_empty() { return None; }
let off = if rest == "Z" { 0 }
else if rest.len() >= 6 {
let oh = rest.get(1..3)?.parse::<i64>().ok()?;
let om = rest.get(4..6)?.parse::<i64>().ok()?;
let x = oh*3600 + om*60;
if rest.as_bytes()[0] == b'-' { -x } else { x }
} else { return None; };
Some((days_from_civil(y, mo, d) * 86400 + h*3600 + mi*60 + se - off) as f64)
}
fn days_from_civil(y: i64, m: i64, d: i64) -> i64 {
let y = if m <= 2 { y - 1 } else { y };
let era = if y >= 0 { y } else { y - 399 } / 400;
let yoe = y - era * 400;
let mp = (m + 9) % 12;
let doy = (153 * mp + 2) / 5 + d - 1;
let doe = yoe * 365 + yoe / 4 - yoe / 100 + doy;
era * 146097 + doe - 719468
}
pub fn tier_promote(entry: &Json, hot_days: f64, warm_days: f64, now: &str) -> Json {
let current = match tier_get(entry, hot_days, warm_days, now) {
Json::Str(s) => s, _ => String::new(),
};
Json::Str(if current == "cold" { "warm".to_string() } else { "hot".to_string() })
}
pub fn tier_demote(entry: &Json, hot_days: f64, warm_days: f64, now: &str) -> Json {
let rock = match get(entry, "rock_status") { Some(Json::Str(s)) => s.as_str(), _ => "washable" };
if rock == "rock" { return Json::Str("hot".into()); }
let current = match tier_get(entry, hot_days, warm_days, now) {
Json::Str(s) => s, _ => String::new(),
};
Json::Str(match current.as_str() {
"hot" => "warm".to_string(), "warm" => "cold".to_string(),
_ => "cold".to_string() })
}
// ── witness kernels (W3.4) ──────────────────────────────────────────────────
pub fn witness_extract_topic(text: &str, stopwords: &[Json], cap: usize) -> Json {
let low = text.to_lowercase();
let sw: Vec<&str> = stopwords.iter().filter_map(|x| match x {
Json::Str(s) => Some(s.as_str()), _ => None }).collect();
let mut out: Vec<String> = vec![];
let mut cur = String::new();
for ch in low.chars() {
if ch.is_ascii_alphanumeric() || ch == '_' { cur.push(ch); }
else {
if !cur.is_empty() {
let w = std::mem::take(&mut cur);
if w.chars().count() > 3 && !sw.contains(&w.as_str()) && out.len() < cap {
out.push(w);
}
}
}
}
if !cur.is_empty() && cur.chars().count() > 3 && !sw.contains(&cur.as_str()) && out.len() < cap {
out.push(cur);
}
Json::Arr(out.into_iter().map(Json::Str).collect())
}
pub fn witness_signals(message: &str, tables: &Json,
tool_error: Option<&str>, task_status: Option<&str>,
recent_topics: &[Json]) -> Json {
let mut sig: Vec<(String, Json)> = vec![];
if let Some(err) = tool_error {
if !err.is_empty() {
sig.push(("error".into(), Json::Bool(true)));
sig.push(("error_text".into(), Json::Str(err.chars().take(200).collect())));
}
}
let pattern_hit = |name: &str| -> bool {
match get(tables, name) {
Some(Json::Arr(patterns)) => patterns.iter().any(|p| match p {
Json::Str(pat) => regex_lite_search(pat, message),
_ => false }),
_ => false,
}
};
if !message.is_empty() && pattern_hit("correction") {
sig.push(("correction".into(), Json::Bool(true)));
let sw: Vec<Json> = match get(tables, "stopwords") {
Some(Json::Arr(x)) => x.clone(), _ => vec![] };
sig.push(("corrected_topic".into(), witness_extract_topic(message, &sw, 5)));
}
if let Some(st) = task_status {
sig.push(("completion".into(), Json::Str(st.to_string())));
}
if !message.is_empty() && !recent_topics.is_empty() {
let sw: Vec<Json> = match get(tables, "stopwords") {
Some(Json::Arr(x)) => x.clone(), _ => vec![] };
if let Json::Arr(cur) = witness_extract_topic(message, &sw, 5) {
let cur_set: Vec<&str> = cur.iter().filter_map(|x| match x {
Json::Str(s) => Some(s.as_str()), _ => None }).collect();
let recent_set: Vec<&str> = recent_topics.iter().filter_map(|x| match x {
Json::Str(s) => Some(s.as_str()), _ => None }).collect();
let overlap = cur_set.iter().filter(|w| recent_set.contains(w)).count();
if !cur_set.is_empty() && (overlap as f64) / (cur_set.len() as f64) < 0.3 {
sig.push(("topic_drift".into(), Json::Bool(true)));
let new_topics: Vec<Json> = cur_set.iter()
.filter(|w| !recent_set.contains(w)).take(3)
.map(|w| Json::Str(w.to_string())).collect();
sig.push(("new_topics".into(), Json::Arr(new_topics)));
}
}
}
for (signal_name, table_name) in [
("commitment_detected", "commitment"),
("possible_contradiction", "contradiction"),
("preference_detected", "preference"),
("urgency_detected", "urgency"),
("learning_opportunity", "learning"),
] {
if !message.is_empty() && pattern_hit(table_name) {
sig.push((signal_name.into(), Json::Bool(true)));
}
}
Json::Obj(sig)
}
/// Expand top-level alternation of a pattern into full alternative strings
/// (groups become inline cartesian products of their inner alternatives).
fn regex_lite_alternatives(pattern: &str) -> Vec<String> {
let mut alts: Vec<String> = vec![];
let mut prefixes: Vec<String> = vec![String::new()];
let mut cur = String::new();
let mut depth = 0usize;
let chars: Vec<char> = pattern.to_lowercase().chars().collect();
for ch in chars {
match ch {
'(' => {
depth += 1;
if depth == 1 {
if !cur.is_empty() {
prefixes = prefixes
.iter()
.map(|p| format!("{p}{cur}"))
.collect();
cur.clear();
}
} else {
cur.push('(');
}
}
')' => {
depth = depth.saturating_sub(1);
if depth == 0 {
// closing a top-level group: its content is an
// alternation set — expand against the accumulated
// prefixes (cartesian). prefixes.len() may be 1.
let group_alts: Vec<String> = cur.split('|').map(String::from).collect();
let mut next = vec![];
for p in &prefixes {
for g in &group_alts {
next.push(format!("{p}{g}"));
}
}
prefixes = next;
cur.clear();
} else if depth >= 1 {
cur.push(')');
}
}
'|' if depth == 0 => {
for p in &prefixes {
alts.push(format!("{p}{cur}"));
}
cur.clear();
}
_ => cur.push(ch),
}
}
if depth == 0 {
for p in &prefixes {
alts.push(format!("{p}{cur}"));
}
} else {
// unbalanced group: treat literally
alts.push(cur);
}
alts.retain(|a| !a.is_empty());
if alts.is_empty() {
alts.push(String::new());
}
alts
}
/// Split ONE alternative into ordered PHRASE-SEGMENTS, each segment being
/// a set of variant strings (from `x?` optional chars — both shapes).
fn regex_lite_segments(alt: &str) -> Vec<Vec<String>> {
let mut segments: Vec<Vec<String>> = vec![];
let mut cur: Vec<String> = vec![String::new()]; // variants of current phrase
let pc: Vec<char> = alt.chars().collect();
let mut j = 0usize;
while j < pc.len() {
let c = pc[j];
if c == '\\' && j + 1 < pc.len() {
let n = pc[j + 1];
match n {
'b' | 'B' => {} // zero-width anchor: drop
's' => {
if cur.iter().any(|v| !v.is_empty()) {
segments.push(std::mem::take(&mut cur));
cur = vec![String::new()];
}
if j + 2 < pc.len() && matches!(pc[j + 2], '*' | '+' | '?') {
j += 3;
} else {
j += 2;
}
continue;
}
other => {
for v in cur.iter_mut() {
v.push(other)
}
}
}
j += 2;
continue;
}
match c {
'?' => {
// optional previous char: each variant gains a SHORTER twin
let twinned: Vec<String> = cur
.iter()
.flat_map(|v| {
let mut out = vec![v.clone()];
if !v.is_empty() {
out.push(v[..v.len() - 1].to_string());
}
out
})
.collect();
cur = twinned;
}
'.' | '[' => {
if cur.iter().any(|v| !v.is_empty()) {
segments.push(std::mem::take(&mut cur));
cur = vec![String::new()];
}
if c == '[' {
let mut k = j + 1;
while k < pc.len() && pc[k] != ']' {
k += 1;
}
j = k;
}
}
'*' | '+' => {} // gap quantifier
'^' | '$' => {}
c if c.is_alphanumeric() || c == '\'' || c == ' ' || c == '-' || c == '_' => {
for v in cur.iter_mut() {
v.push(c)
}
}
_ => {
if cur.iter().any(|v| !v.is_empty()) {
segments.push(std::mem::take(&mut cur));
cur = vec![String::new()];
}
}
}
j += 1;
}
if cur.iter().any(|v| !v.is_empty()) {
segments.push(cur);
}
segments
}
fn regex_lite_search(pattern: &str, text: &str) -> bool {
let low = text.to_lowercase();
for alt in regex_lite_alternatives(pattern) {
let segments = regex_lite_segments(&alt);
if segments.is_empty() {
continue;
}
// DFS: every segment contributes ONE of its variants, in order,
// gap-matched against the text.
fn walk(segments: &[Vec<String>], low: &str, cursor: usize) -> bool {
if segments.is_empty() {
return true;
}
for variant in &segments[0] {
if variant.is_empty() {
return walk(&segments[1..], low, cursor);
}
if let Some(ix) = low[cursor..].find(variant.as_str()) {
let next = cursor + ix + variant.len();
if walk(&segments[1..], low, next) {
return true;
}
}
}
false
}
if walk(&segments, &low, 0) {
return true;
}
}
false
}
// ── safety_override kernels (W3.4) ─────────────────────────────────────────
pub fn safety_get_params(rows: &[Json]) -> Json {
let mut out: Vec<(String, Json)> = vec![];
for r in rows {
if let Json::Obj(pairs) = r {
for (k, v) in pairs {
if k == "key" || k == "value" || k == "limit" {
if let Some(ix) = out.iter().position(|(x, _)| x == k) {
out[ix].1 = v.clone();
} else {
out.push((k.clone(), v.clone()));
}
}
}
}
}
Json::Obj(out)
}
pub fn safety_update_pattern(rows: &[Json], pattern: &str) -> Vec<Json> {
let mut out = rows.to_vec();
for r in out.iter_mut() {
if matches!(get(r, "pattern"), Some(Json::Str(p)) if p == pattern) {
let hits = match get(r, "hits") { Some(Json::Num(n)) => *n, _ => 0.0 };
if let Json::Obj(pairs) = r {
if let Some(ix) = pairs.iter().position(|(k, _)| k == "hits") {
pairs[ix].1 = Json::Num(hits + 1.0);
} else {
pairs.push(("hits".into(), Json::Num(1.0)));
}
}
return out;
}
}
out.push(Json::Obj(vec![
("pattern".into(), Json::Str(pattern.to_string())),
("hits".into(), Json::Num(1.0)),
]));
out
}
// ── abstraction kernels (W3.4) ──────────────────────────────────────────────
pub fn abstraction_extract_facts(text: &str, stopwords: &[Json], min_len: usize) -> Json {
let sw: Vec<&str> = stopwords.iter().filter_map(|x| match x {
Json::Str(s) => Some(s.as_str()), _ => None }).collect();
let mut facts: Vec<Json> = vec![];
for sentence in text.split(|c: char| c == '.' || c == '\n') {
let t = sentence.trim();
if t.chars().count() < min_len { continue; }
let words: Vec<String> = t.to_lowercase().split_whitespace()
.map(|w| w.to_string()).collect();
let content = words.iter().filter(|w| !sw.contains(&w.as_str())).count();
if content == 0 { continue; }
facts.push(Json::Obj(vec![
("text".into(), Json::Str(t.to_string())),
("words".into(), Json::Num(words.len() as f64)),
("content_words".into(), Json::Num(content as f64)),
]));
}
Json::Arr(facts)
}
+277
View File
@@ -0,0 +1,277 @@
//! lib.rs — FFI surface for the cognition_core crate (R2 W3.1).
//! Pure deterministic kernels only. Envelope law
//! {"ok","value"|"err"}; frees via cc_free_string. FFI segfault law:
//! cc_loader.py pins argtypes + restype for every symbol.
pub mod broker;
pub mod pyjson;
use std::ffi::{CStr, CString};
use std::os::raw::c_char;
fn read_arg(ptr: *const c_char) -> Result<String, String> {
if ptr.is_null() { return Err("null argument pointer".to_string()); }
unsafe { CStr::from_ptr(ptr) }.to_str().map(|s| s.to_string())
.map_err(|e| format!("argument is not valid UTF-8: {}", e))
}
fn envelope(result: Result<pyjson::Json, String>) -> *mut c_char {
let body = match result {
Ok(v) => pyjson::Json::Obj(vec![
("ok".to_string(), pyjson::Json::Bool(true)),
("value".to_string(), v)]),
Err(e) => pyjson::Json::Obj(vec![
("ok".to_string(), pyjson::Json::Bool(false)),
("err".to_string(), pyjson::Json::Str(e))]),
};
CString::new(pyjson::dumps(&body)).map(|c| c.into_raw())
.unwrap_or(std::ptr::null_mut())
}
fn arg_json(text: &str) -> Result<pyjson::Json, String> {
pyjson::parse(text).map_err(|e| format!("argument JSON parse failed: {}", e))
}
fn get<'a>(v: &'a pyjson::Json, key: &str) -> Option<&'a pyjson::Json> {
match v { pyjson::Json::Obj(p) => p.iter().find(|(k, _)| k == key).map(|(_, v)| v), _ => None }
}
#[no_mangle]
pub extern "C" fn cc_default_estimator(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let val = match get(&a, "text") {
Some(pyjson::Json::Str(s)) => s.clone(),
_ => String::new(),
};
pyjson::Json::Num(broker::default_estimator(&val) as f64)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_default_budget(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let w = match get(&a, "window") { Some(pyjson::Json::Num(n)) => *n as i64, _ => 0 };
pyjson::Json::Num(broker::default_budget(w) as f64)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_default_memory_budget(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let w = match get(&a, "window") {
Some(pyjson::Json::Num(n)) => *n as i64,
Some(pyjson::Json::Null) | None => 0,
_ => 0,
};
pyjson::Json::Num(broker::default_memory_budget(w) as f64)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_memory_disabled(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let v = match get(&a, "value") {
Some(pyjson::Json::Str(s)) => Some(s.as_str()),
_ => None,
};
pyjson::Json::Bool(broker::memory_disabled(v))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_persona_lex(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let t = match get(&a, "text") { Some(pyjson::Json::Str(x)) => Some(x.as_str()), _ => None };
pyjson::Json::Arr(broker::persona_lex(t).into_iter().map(pyjson::Json::Str).collect())
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_persona_overlap(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let wa: Vec<String> = match get(&a, "a") { Some(pyjson::Json::Arr(x)) => x.iter().filter_map(|v| match v { pyjson::Json::Str(s) => Some(s.clone()), _ => None }).collect(), _ => vec![] };
let wb: Vec<String> = match get(&a, "b") { Some(pyjson::Json::Arr(x)) => x.iter().filter_map(|v| match v { pyjson::Json::Str(s) => Some(s.clone()), _ => None }).collect(), _ => vec![] };
pyjson::Json::Num(broker::persona_overlap(&wa, &wb))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_persona_decide(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).and_then(|a| {
let text = match get(&a, "text") { Some(pyjson::Json::Str(x)) => x.clone(), _ => String::new() };
let rules: Vec<pyjson::Json> = match get(&a, "rules") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
let permissive = matches!(get(&a, "permissive"), Some(pyjson::Json::Bool(true)));
let sems: Vec<f64> = match get(&a, "sem_scores") {
Some(pyjson::Json::Arr(x)) => x.iter().filter_map(|v| match v { pyjson::Json::Num(n) => Some(*n), _ => Some(0.0) }).collect(),
_ => vec![0.0; rules.len()],
};
Ok(broker::persona_decide(&text, &rules, permissive, &sems))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_drift_check(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let text = match get(&a, "text") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
let patterns: Vec<pyjson::Json> = match get(&a, "patterns") {
Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
pyjson::Json::Arr(broker::drift_check(&text, &patterns)
.into_iter().map(pyjson::Json::Str).collect())
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_identity_prompt(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
pyjson::Json::Str(broker::identity_prompt(
get(&a, "pronouns").unwrap_or(&pyjson::Json::Obj(vec![])),
get(&a, "self_awareness").unwrap_or(&pyjson::Json::Obj(vec![])),
get(&a, "anchors").unwrap_or(&pyjson::Json::Obj(vec![])),
get(&a, "embodiment").unwrap_or(&pyjson::Json::Arr(vec![]))))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_growth_near_dup(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let x = match get(&a, "a") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
let y = match get(&a, "b") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
pyjson::Json::Bool(broker::growth_near_dup(&x, &y))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_growth_profile(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).and_then(|a| {
let state = get(&a, "state").cloned().unwrap_or(pyjson::Json::Obj(vec![]));
let entry_chars = match get(&a, "entry_chars") { Some(pyjson::Json::Num(n)) => *n as usize, _ => 0 };
let max_tokens = match get(&a, "max_tokens") { Some(pyjson::Json::Num(n)) => *n as usize, _ => 0 };
let order: Vec<(String, i64)> = match get(&a, "order") {
Some(pyjson::Json::Arr(x)) => x.iter().filter_map(|v| match v {
pyjson::Json::Arr(pair) if pair.len() >= 2 => match (&pair[0], &pair[1]) {
(pyjson::Json::Str(name), pyjson::Json::Num(rank)) => Some((name.clone(), *rank as i64)),
_ => None },
_ => None }).collect(),
_ => vec![] };
Ok(pyjson::Json::Arr(broker::growth_profile(&state, &order, entry_chars, max_tokens)))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_pins_recall(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let pins: Vec<pyjson::Json> = match get(&a, "pins") {
Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
let term = match get(&a, "term") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
pyjson::Json::Arr(broker::pins_recall(&pins, &term, 4))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_tier_get(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let e = get(&a, "entry").cloned().unwrap_or(pyjson::Json::Obj(vec![]));
broker::tier_get(&e,
match get(&a, "hot_days") { Some(pyjson::Json::Num(n)) => *n, _ => 7.0 },
match get(&a, "warm_days") { Some(pyjson::Json::Num(n)) => *n, _ => 30.0 },
match get(&a, "now") { Some(pyjson::Json::Str(s)) => s.as_str(), _ => "" })
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_tier_promote(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let e = get(&a, "entry").cloned().unwrap_or(pyjson::Json::Obj(vec![]));
broker::tier_promote(&e,
match get(&a, "hot_days") { Some(pyjson::Json::Num(n)) => *n, _ => 7.0 },
match get(&a, "warm_days") { Some(pyjson::Json::Num(n)) => *n, _ => 30.0 },
match get(&a, "now") { Some(pyjson::Json::Str(s)) => s.as_str(), _ => "" })
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_tier_demote(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let e = get(&a, "entry").cloned().unwrap_or(pyjson::Json::Obj(vec![]));
broker::tier_demote(&e,
match get(&a, "hot_days") { Some(pyjson::Json::Num(n)) => *n, _ => 7.0 },
match get(&a, "warm_days") { Some(pyjson::Json::Num(n)) => *n, _ => 30.0 },
match get(&a, "now") { Some(pyjson::Json::Str(s)) => s.as_str(), _ => "" })
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_witness_extract_topic(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let text = match get(&a, "text") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
let sw: Vec<pyjson::Json> = match get(&a, "stopwords") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
match broker::witness_extract_topic(&text, &sw, 5) {
pyjson::Json::Arr(v) => pyjson::Json::Arr(v),
other => other,
}
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_witness_signals(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let message = match get(&a, "message") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
let tables = get(&a, "tables").cloned().unwrap_or(pyjson::Json::Obj(vec![]));
let tool_error = match get(&a, "tool_error") { Some(pyjson::Json::Str(s)) if !s.is_empty() => Some(s.as_str()), _ => None };
let task_status = match get(&a, "task_status") { Some(pyjson::Json::Str(s)) if !s.is_empty() => Some(s.as_str()), _ => None };
let recent: Vec<pyjson::Json> = match get(&a, "recent_topics") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
broker::witness_signals(&message, &tables, tool_error, task_status, &recent)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_safety_get_params(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let rows: Vec<pyjson::Json> = match get(&a, "rows") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
broker::safety_get_params(&rows)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_safety_update_pattern(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let rows: Vec<pyjson::Json> = match get(&a, "rows") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
let pat = match get(&a, "pattern") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
pyjson::Json::Arr(broker::safety_update_pattern(&rows, &pat))
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_abstraction_extract_facts(arg: *const c_char) -> *mut c_char {
let result = read_arg(arg).and_then(|t| arg_json(&t)).map(|a| {
let text = match get(&a, "text") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
let sw: Vec<pyjson::Json> = match get(&a, "stopwords") { Some(pyjson::Json::Arr(x)) => x.clone(), _ => vec![] };
let min_len = match get(&a, "min_len") { Some(pyjson::Json::Num(n)) => *n as usize, _ => 10 };
broker::abstraction_extract_facts(&text, &sw, min_len)
});
envelope(result)
}
#[no_mangle]
pub extern "C" fn cc_free_string(ptr: *mut c_char) {
if !ptr.is_null() { unsafe { let _ = CString::from_raw(ptr); } }
}
+23
View File
@@ -0,0 +1,23 @@
//! main.rs — CLI debug front for cognition_core.
use cognition_core::{broker, pyjson};
use std::io::Read;
fn get<'a>(v: &'a pyjson::Json, k: &str) -> Option<&'a pyjson::Json> {
match v { pyjson::Json::Obj(p) => p.iter().find(|(x, _)| x == k).map(|(_, v)| v), _ => None }
}
fn main() {
let mut x = String::new();
if std::io::stdin().read_to_string(&mut x).is_err() { return; }
let a = pyjson::parse(&x).unwrap();
let op = match get(&a, "op") { Some(pyjson::Json::Str(s)) => s.as_str(), _ => "" };
let arg = get(&a, "arg").unwrap_or(&pyjson::Json::Null);
let v = match op {
"default_estimator" => {
let t = match get(arg, "text") { Some(pyjson::Json::Str(s)) => s.clone(), _ => String::new() };
pyjson::Json::Num(broker::default_estimator(&t) as f64)
}
_ => pyjson::Json::Str(format!("unsupported op: {}", op)),
};
println!("{}", pyjson::dumps(&v));
}
+444
View File
@@ -0,0 +1,444 @@
//! json_min.py — minimal JSON parse/serialize with Python-parity output.
//!
//! Exists because contract C1 demands byte-comparable state files with the
//! Python implementation (`json.dumps` / `json.dump(indent=2)`):
//! - compact separators: ", " between items, ": " between key/value
//! (Python json.dumps DEFAULTS — no separators arg means the space-y form)
//! - ensure_ascii: non-ASCII escaped as \uXXXX (with surrogate pairs)
//! - floats: shortest round-trip repr (Rust `{}` == Python `repr` for f64
//! in every value this module produces, including arithmetic artifacts
//! like 0.30000000000000004)
//! - indent=2 dump: newline+indent after every item separator, "{}" when
//! empty, NO trailing newline (json.dump never writes one)
//! Object key order is preserved (Vec of pairs) — matches Python 3.7+ dict
//! insertion order, which the classification tie-break law depends on.
use std::fmt::Write as _;
/// Preserved-order JSON value.
#[derive(Debug, Clone, PartialEq)]
pub enum Json {
Null,
Bool(bool),
Num(f64),
Str(String),
Arr(Vec<Json>),
Obj(Vec<(String, Json)>),
}
impl Json {
pub fn get(&self, key: &str) -> Option<&Json> {
match self {
Json::Obj(pairs) => pairs.iter().find(|(k, _)| k == key).map(|(_, v)| v),
_ => None,
}
}
}
// ── parsing ─────────────────────────────────────────────────────────────────
pub fn parse(input: &str) -> Result<Json, String> {
let bytes = input.as_bytes();
let mut p = Parser { b: bytes, i: 0 };
p.skip_ws();
let v = p.value()?;
p.skip_ws();
if p.i != bytes.len() {
return Err(format!("trailing data at byte {}", p.i));
}
Ok(v)
}
struct Parser<'a> {
b: &'a [u8],
i: usize,
}
impl<'a> Parser<'a> {
fn skip_ws(&mut self) {
while self.i < self.b.len() && matches!(self.b[self.i], b' ' | b'\t' | b'\n' | b'\r') {
self.i += 1;
}
}
fn peek(&self) -> Option<u8> {
self.b.get(self.i).copied()
}
fn expect(&mut self, c: u8) -> Result<(), String> {
if self.peek() == Some(c) {
self.i += 1;
Ok(())
} else {
Err(format!("expected '{}' at byte {}", c as char, self.i))
}
}
fn value(&mut self) -> Result<Json, String> {
match self.peek() {
Some(b'{') => self.object(),
Some(b'[') => self.array(),
Some(b'"') => Ok(Json::Str(self.string()?)),
Some(b't') => self.literal("true", Json::Bool(true)),
Some(b'f') => self.literal("false", Json::Bool(false)),
Some(b'n') => self.literal("null", Json::Null),
Some(c) if c == b'-' || c.is_ascii_digit() => self.number(),
_ => Err(format!("unexpected byte at {}", self.i)),
}
}
fn literal(&mut self, lit: &str, v: Json) -> Result<Json, String> {
if self.b[self.i..].starts_with(lit.as_bytes()) {
self.i += lit.len();
Ok(v)
} else {
Err(format!("bad literal at byte {}", self.i))
}
}
fn object(&mut self) -> Result<Json, String> {
self.expect(b'{')?;
let mut pairs = Vec::new();
self.skip_ws();
if self.peek() == Some(b'}') {
self.i += 1;
return Ok(Json::Obj(pairs));
}
loop {
self.skip_ws();
let key = self.string()?;
self.skip_ws();
self.expect(b':')?;
self.skip_ws();
let val = self.value()?;
pairs.push((key, val));
self.skip_ws();
match self.peek() {
Some(b',') => self.i += 1,
Some(b'}') => {
self.i += 1;
return Ok(Json::Obj(pairs));
}
_ => return Err(format!("expected ',' or '}}' at byte {}", self.i)),
}
}
}
fn array(&mut self) -> Result<Json, String> {
self.expect(b'[')?;
let mut items = Vec::new();
self.skip_ws();
if self.peek() == Some(b']') {
self.i += 1;
return Ok(Json::Arr(items));
}
loop {
self.skip_ws();
items.push(self.value()?);
self.skip_ws();
match self.peek() {
Some(b',') => self.i += 1,
Some(b']') => {
self.i += 1;
return Ok(Json::Arr(items));
}
_ => return Err(format!("expected ',' or ']' at byte {}", self.i)),
}
}
}
fn string(&mut self) -> Result<String, String> {
self.expect(b'"')?;
let mut out = String::new();
loop {
match self.peek() {
None => return Err("unterminated string".into()),
Some(b'"') => {
self.i += 1;
return Ok(out);
}
Some(b'\\') => {
self.i += 1;
match self.peek() {
Some(b'"') => out.push('"'),
Some(b'\\') => out.push('\\'),
Some(b'/') => out.push('/'),
Some(b'b') => out.push('\u{0008}'),
Some(b'f') => out.push('\u{000C}'),
Some(b'n') => out.push('\n'),
Some(b'r') => out.push('\r'),
Some(b't') => out.push('\t'),
Some(b'u') => {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+ ((cp - 0xD800) << 10)
+ (lo - 0xDC00);
out.push(
char::from_u32(c)
.ok_or("bad surrogate pair")?,
);
} else {
// lone high surrogate — Python keeps it as
// an escaped lone surrogate; we degrade to
// U+FFFD (not produced by this writer)
out.push('\u{FFFD}');
}
} else {
out.push('\u{FFFD}');
}
} else {
out.push(char::from_u32(cp).unwrap_or('\u{FFFD}'));
}
continue; // hex4 already advanced i
}
_ => return Err(format!("bad escape at byte {}", self.i)),
}
self.i += 1;
}
Some(_) => {
// consume one UTF-8 scalar
let s = &self.b[self.i..];
let ch_len = utf8_len(s[0]);
let chunk = std::str::from_utf8(&s[..ch_len.min(s.len())])
.map_err(|_| "bad utf8")?;
out.push_str(chunk);
self.i += ch_len;
}
}
}
}
fn hex4(&mut self) -> Result<u32, String> {
if self.i + 4 > self.b.len() {
return Err("short \\u escape".into());
}
let s = std::str::from_utf8(&self.b[self.i + 1..self.i + 5])
.map_err(|_| "bad \\u")?;
let v = u32::from_str_radix(s, 16).map_err(|_| "bad \\u digits")?;
self.i += 5; // 'u' + 4 hex digits (caller consumed the backslash)
Ok(v)
}
fn number(&mut self) -> Result<Json, String> {
let start = self.i;
if self.peek() == Some(b'-') {
self.i += 1;
}
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
if self.peek() == Some(b'.') {
self.i += 1;
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
}
if matches!(self.peek(), Some(b'e') | Some(b'E')) {
self.i += 1;
if matches!(self.peek(), Some(b'+') | Some(b'-')) {
self.i += 1;
}
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
}
let s = std::str::from_utf8(&self.b[start..self.i]).map_err(|_| "bad number")?;
s.parse::<f64>()
.map(Json::Num)
.map_err(|_| format!("bad number '{}'", s))
}
}
fn utf8_len(b: u8) -> usize {
if b < 0x80 {
1
} else if b >> 5 == 0b110 {
2
} else if b >> 4 == 0b1110 {
3
} else {
4
}
}
// ── serialization (Python json.dumps / json.dump(indent=2) parity) ─────────
/// Python `json.dumps(value, sort_keys=True)` — compact separators, object
/// keys recursively sorted. Python sorts str keys by code point; Rust's
/// byte-wise UTF-8 `String` ordering is identical for valid UTF-8, so a
/// plain `sort_by` on the key is faithful.
pub fn dumps_sorted(v: &Json) -> String {
let mut out = String::new();
write_compact_sorted(&mut out, v);
out
}
fn write_compact_sorted(out: &mut String, v: &Json) {
match v {
Json::Obj(pairs) => {
let mut sorted: Vec<&(String, Json)> = pairs.iter().collect();
sorted.sort_by(|a, b| a.0.cmp(&b.0));
out.push('{');
for (i, (k, val)) in sorted.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_escaped(out, k);
out.push_str(": ");
write_compact_sorted(out, val);
}
out.push('}');
}
Json::Arr(items) => {
out.push('[');
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_compact_sorted(out, item);
}
out.push(']');
}
other => write_compact(out, other),
}
}
/// Python `json.dumps(value)` — compact separators `", "` / `": "`,
/// ensure_ascii escaping.
pub fn dumps(v: &Json) -> String {
let mut out = String::new();
write_compact(&mut out, v);
out
}
fn write_compact(out: &mut String, v: &Json) {
match v {
Json::Null => out.push_str("null"),
Json::Bool(true) => out.push_str("true"),
Json::Bool(false) => out.push_str("false"),
Json::Num(n) => out.push_str(&fmt_num(*n)),
Json::Str(s) => write_escaped(out, s),
Json::Arr(items) => {
out.push('[');
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_compact(out, item);
}
out.push(']');
}
Json::Obj(pairs) => {
out.push('{');
for (i, (k, val)) in pairs.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_escaped(out, k);
out.push_str(": ");
write_compact(out, val);
}
out.push('}');
}
}
}
/// Python `json.dump(value, indent=2)` — item separator becomes
/// `",\n<indent>"`, key separator `": "`, empty container → `{}` / `[]`,
/// NO trailing newline.
pub fn dump_indent2(v: &Json) -> String {
let mut out = String::new();
write_indent(&mut out, v, 0);
out
}
fn write_indent(out: &mut String, v: &Json, depth: usize) {
match v {
Json::Arr(items) if !items.is_empty() => {
out.push_str("[\n");
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(",\n");
}
push_indent(out, depth + 1);
write_indent(out, item, depth + 1);
}
out.push('\n');
push_indent(out, depth);
out.push(']');
}
Json::Arr(_) => out.push_str("[]"),
Json::Obj(pairs) if !pairs.is_empty() => {
out.push_str("{\n");
for (i, (k, val)) in pairs.iter().enumerate() {
if i > 0 {
out.push_str(",\n");
}
push_indent(out, depth + 1);
write_escaped(out, k);
out.push_str(": ");
write_indent(out, val, depth + 1);
}
out.push('\n');
push_indent(out, depth);
out.push('}');
}
Json::Obj(_) => out.push_str("{}"),
other => write_compact(out, other),
}
}
fn push_indent(out: &mut String, depth: usize) {
for _ in 0..depth {
out.push_str(" ");
}
}
/// Integer-shaped f64 prints without a decimal point (matching how this
/// module's writers emit counts); all other values use shortest round-trip.
pub fn fmt_num(n: f64) -> String {
if n.is_finite() && n.fract() == 0.0 && n.abs() < 9.007_199_254_740_992e15 {
return format!("{}", n as i64);
}
format!("{}", n)
}
/// Python `json.dumps` string escaping with ensure_ascii=True.
pub fn write_escaped(out: &mut String, s: &str) {
out.push('"');
for ch in s.chars() {
match ch {
'"' => out.push_str("\\\""),
'\\' => out.push_str("\\\\"),
'\n' => out.push_str("\\n"),
'\r' => out.push_str("\\r"),
'\t' => out.push_str("\\t"),
'\u{0008}' => out.push_str("\\b"),
'\u{000C}' => out.push_str("\\f"),
c if (c as u32) < 0x20 => {
let _ = write!(out, "\\u{:04x}", c as u32);
}
c if (c as u32) <= 0x7E => out.push(c),
// ensure_ascii: escape everything non-ASCII, surrogate pairs
// for astral planes (Python behaviour)
c => {
let cp = c as u32;
if cp > 0xFFFF {
let v = cp - 0x10000;
let hi = 0xD800 + (v >> 10);
let lo = 0xDC00 + (v & 0x3FF);
let _ = write!(out, "\\u{:04x}\\u{:04x}", hi, lo);
} else {
let _ = write!(out, "\\u{:04x}", cp);
}
}
}
}
out.push('"');
}
@@ -0,0 +1,65 @@
use cognition_core::broker::parse_strict_aware;
#[test]
fn parses_aware() {
let v = parse_strict_aware("2026-10-05T12:00:00+00:00");
assert!(v.is_some(), "aware must parse");
let n = parse_strict_aware("2026-10-05T12:00:00");
assert!(n.is_none(), "naive must be refused");
}
#[test]
fn tier_recency_works() {
let e = cognition_core::pyjson::parse(
r#"{"wash_count": 2, "last_accessed": "2026-10-05T06:00:00+00:00"}"#).unwrap();
let t = cognition_core::broker::tier_get(&e, 7.0, 30.0, "2026-10-05T12:00:00+00:00");
assert!(format!("{}", cognition_core::pyjson::dumps(&t)).contains("hot"),
"expected hot, got {}", cognition_core::pyjson::dumps(&t));
}
#[test]
fn parse_components() {
let s = "2026-10-05T12:00:00+00:00";
let b = s.as_bytes();
assert_eq!(b.len(), 25);
// simulate the loop: i=19 is '+' → exits immediately → rest="+00:00"
let mut i = 19;
while i < b.len() && b[i] != b'Z' && b[i] != b'+' && b[i] != b'-' { i += 1; }
assert_eq!(i, 19, "offset starts immediately after seconds");
let rest = &s[i..];
assert_eq!(rest, "+00:00");
let v = parse_strict_aware(s);
assert!(v.is_some());
let val = v.unwrap();
// 2026-10-05T12:00:00Z epoch ≈ 1791201600 (verify ±1s tolerance)
assert!((val - 1791201600.0).abs() < 2.0, "epoch mismatch: {}", val);
}
#[test]
fn tier_decompose() {
use cognition_core::broker::parse_strict_aware;
let last = "2026-10-05T06:00:00+00:00";
let now = "2026-10-05T12:00:00+00:00";
let (l, n) = (parse_strict_aware(last), parse_strict_aware(now));
assert!(l.is_some() && n.is_some(), "both must parse");
let hours = (n.unwrap() - l.unwrap()) / 3600.0;
assert_eq!(hours, 6.0, "6h apart");
// so tier_get's recency branch must fire... check it does by feeding
// what the parse sees via a wash-hot case:
let e = cognition_core::pyjson::parse(r#"{"wash_count": 25}"#).unwrap();
let t = cognition_core::broker::tier_get(&e, 7.0, 30.0, now);
let s = cognition_core::pyjson::dumps(&t);
assert!(s.contains("hot"), "wash>=20 must be hot, got {}", s);
}
#[test]
fn tier_probe_row_shape() {
// Does the JSON fixture parse into the expected shape? get(entry,...)
// reads "last_accessed" — pyjson::Json::Obj pairs. Verify:
let e = cognition_core::pyjson::parse(
r#"{"wash_count": 2, "last_accessed": "2026-10-05T06:00:00+00:00"}"#)
.unwrap();
let la = cognition_core::broker::tier_get(&e, 7.0, 30.0,
"2026-10-05T12:00:00+00:00");
// instrument via a different route: promote → falls to the same get_tier
let s = cognition_core::pyjson::dumps(&la);
eprintln!("tier_get gave: {}", s);
}
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+7
View File
@@ -0,0 +1,7 @@
# This file is automatically @generated by Cargo.
# It is not intended for manual editing.
version = 4
[[package]]
name = "memory_retrieval"
version = "0.1.0"
+13
View File
@@ -0,0 +1,13 @@
[package]
name = "memory_retrieval"
version = "0.1.0"
edition = "2021"
description = "R2 W2.1 deterministic memory retrieval kernel; zero dependencies; SQLite remains behind memory_storage"
[lib]
name = "memory_retrieval"
crate-type = ["rlib", "cdylib"]
[[bin]]
name = "memory_retrieval"
path = "src/main.rs"
@@ -0,0 +1,279 @@
#!/usr/bin/env python3
"""Parity canary for the R2 W2.1 memory_retrieval kernel.
Contract BUILDER-2026-10-04T20:10:25Z-cli. SQLite remains behind W2.0;
this crate owns deterministic retrieval transforms only. Parity is the
floor, then the stage-level API may batch work to reduce Python calls.
"""
from __future__ import annotations
import os
import subprocess
import sys
from pathlib import Path
CRATE = Path(__file__).resolve().parent
REPO = CRATE.parents[2]
sys.path.insert(0, str(REPO / "src"))
PASS = FAIL = 0
def check(name, ok, detail=""):
global PASS, FAIL
if ok:
PASS += 1
print(f" ✓ {name}")
else:
FAIL += 1
print(f" ✗ {name} — {detail}")
def build():
env = dict(os.environ)
absolute = Path("/home/nick/.rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
rust = absolute if absolute.is_dir() else (
Path.home() / ".rustup/toolchains/stable-x86_64-unknown-linux-gnu/bin")
env["PATH"] = f"{rust}:{env.get('PATH', '')}"
return subprocess.run(["cargo", "build", "--release"], cwd=CRATE,
env=env, capture_output=True, text=True, timeout=600)
def main():
print("=== memory_retrieval parity ===")
r = build()
check("crate builds", r.returncode == 0, r.stderr[-240:])
if r.returncode:
print(f"RESULTS: {PASS} pass, {FAIL} fail")
return 1
from rune import memory_store as ms
from rune import mr_loader
# map-reduce: stable sort, fallback score, chunk boundaries.
map_cases = [
("empty", [], 10),
("under size returns same", [{"id": 1, "relevance": 0.2}], 10),
("ties stable", [{"id": i, "score": 1.0} for i in range(13)], 4),
("mixed fallback scores", [
{"id": i, **({"relevance": i / 10} if i % 2 else {"score": i / 12})}
for i in range(17)], 5),
]
for name, entries, size in map_cases:
py = ms._py_map_reduce(entries, size)
rs = mr_loader.map_reduce(entries, size)
check(f"map_reduce: {name}", py == rs, f"py={py!r} rs={rs!r}")
# position-aware ordering, including the designed failure fallback.
pos_cases = [
("empty", []),
("two no-op", [{"id": 1}, {"id": 2}]),
("ordered", [{"id": 1, "relevance": 0.5},
{"id": 2, "relevance": 0.9},
{"id": 3, "relevance": 0.1},
{"id": 4, "relevance": 0.7}]),
("numeric strings", [{"id": 1, "relevance": "0.2"},
{"id": 2, "relevance": "0.8"},
{"id": 3, "relevance": "0.4"}]),
("malformed returns original", [{"id": 1, "relevance": "bad"},
{"id": 2}, {"id": 3}]),
]
for name, entries in pos_cases:
py = ms._py_position_aware(entries)
rs = mr_loader.position_aware(entries)
check(f"position: {name}", py == rs, f"py={py!r} rs={rs!r}")
# FTS token construction: preserve simple whitespace/quotes behavior.
for query in ("", "the and for", "black coffee",
"one two three", "quoted \"term\" punctuation!",
"a b c d e f g h i j k l", "UNICODE héllo world"):
py = ms._py_fts_query_conjunctive(query)
rs = mr_loader.fts_query_conjunctive(query)
check(f"fts {query!r}", py == rs, f"py={py!r} rs={rs!r}")
# Chunking: overlap is intentionally ignored by the Python vintage.
chunk_cases = [
("empty", "", 20, 5),
("short", "short text", 20, 5),
("paragraphs", "a" * 10 + "\n\n" + "b" * 15 + "\n\n" + "c" * 8, 20, 7),
("hard split", "x" * 80, 20, 3),
("unicode chars", "héllo 🎸 " * 20, 30, 9),
]
for name, text, size, overlap in chunk_cases:
py = ms._py_chunk_text(text, size, overlap)
rs = mr_loader.chunk_text(text, size, overlap)
check(f"chunk: {name}", py == rs, f"py={py!r} rs={rs!r}")
for text in (None, "", " Hello WORLD ", "Unicode — HÉLLO 🎸"):
py = ms._py_norm_key(text)
rs = mr_loader.norm_key(text)
check(f"norm {text!r}", py == rs, f"py={py!r} rs={rs!r}")
fuse_cases = [
("empty", [], []),
("single each",
[{"id": 1, "text": "fact one", "topic": "t",
"relevance": 3.2, "confidence": 0.8}],
[{"chunk_id": "c1", "text": "research one", "wing": "w",
"rrf": 0.08, "confidence": 0.9}]),
("dedup normalized text",
[{"id": 1, "text": " Same TEXT ", "relevance": 1.0}],
[{"chunk_id": "c1", "text": "same text", "score": 0.9}]),
("per-kind normalization + defaults",
[{"id": 1, "text": "f1", "relevance": 9.0},
{"id": 2, "text": "f2", "relevance": 3.0},
{"id": 3, "text": "f3", "relevance": 6.0}],
[{"chunk_id": "c1", "text": "r1", "rrf": 0.1},
{"chunk_id": "c2", "text": "r2", "score": 0.05,
"confidence": 0.0}]),
("unicode stable",
[{"id": 1, "text": "HÉLLO 🎸", "relevance": 1.0}],
[{"chunk_id": "c", "text": "different — ü", "rrf": 0.2}]),
]
for name, entries, research in fuse_cases:
py = ms._py_fuse_results(entries, research)
rs = mr_loader.fuse_results(entries, research)
check(f"fuse: {name}", py == rs, f"py={py!r} rs={rs!r}")
base = [{"id": 1, "text": "seed", "relevance": 2.0}]
boosts = [{"id": 2, "strength": 0.8},
{"id": 3, "strength": 0.4},
{"id": 999, "strength": 1.0}]
rows = [
{"id": 2, "text": "linked two", "importance": 0.6,
"topic": "t", "entities": "[]", "source": "s",
"last_accessed": None, "confidence": 0.9, "temperature": 0.8},
{"id": 3, "text": "linked three", "importance": 0.5,
"topic": "t", "entities": "[]", "source": "s",
"last_accessed": "2026-10-04", "confidence": 0.0,
"temperature": 0.0},
]
for budget in (1, 2, 8):
py = ms._py_merge_association_rows(base, boosts, rows, budget)
rs = mr_loader.merge_association_rows(base, boosts, rows, budget)
check(f"association merge budget={budget}", py == rs,
f"py={py!r} rs={rs!r}")
check("association mode frozen",
all(r.get("mode") == "association_merged"
for r in mr_loader.merge_association_rows(base, boosts, rows, 8)
if r.get("via_association")))
fusion_cases = [
("none", [], []),
("dense only", [[1, 0.8], [2, 0.7]], []),
("lexical only", [], [[1, -8.0], [2, -10.0], [3, -9.0]]),
("hybrid overlap", [[1, 0.82], [2, 0.7]],
[[2, -7.0], [3, -9.0]]),
("ties stable", [[2, 0.8], [1, 0.8]], [[1, -5.0], [2, -5.0]]),
]
for name, dense, bm25 in fusion_cases:
py = ms._py_rank_fusion(dense, bm25)
rs = mr_loader.rank_fusion(dense, bm25, ms.RRF_K)
check(f"rank fusion: {name}", py == rs, f"py={py!r} rs={rs!r}")
# --- 8. scoring/abstention kernel matrix (W2.1 main port) ---
print("\n--- 8. score_recall_rows matrix ---")
def mk(conf, temp, last):
return [{"id": 20, "text": "a", "importance": 0.5, "created_at": "x",
"last_accessed": last, "topic": "t", "entities": "[]",
"source": "s", "status": "active", "memory_type": None,
"confidence": conf, "temperature": temp}]
NOW = "2026-10-04T12:00:00+00:00"
stamp_cases = [("recent-aware", "2026-10-04T11:00:00+00:00"),
("naive", "2026-10-03T00:00:00"),
("malformed", "garbage"),
("stale", "2026-08-01T00:00:00+00:00"),
("future", "2030-01-01T00:00:00+00:00"),
("none", None)]
meta_cases = [(0.8, 1.0), (None, None), (0.0, 1.0), (0.8, None),
(0.8, 0.0), (0.0, None)]
for label, last in stamp_cases:
for dense, bm25, mode in [([[20, 0.9]], [], "dense-only"),
([], [[20, -8.0]], "lexical-only"),
([[20, 0.9]], [[20, -8.0]], "hybrid")]:
py = ms._py_score_recall_rows(ms._py_rank_fusion(dense, bm25),
mk(0.8, 1.0, last), dense, bm25, 10, 0.42, NOW)
rs = mr_loader.score_recall_rows(
mr_loader.rank_fusion(dense, bm25, ms.RRF_K),
mk(0.8, 1.0, last), dense, bm25, 10, 0.42, NOW,
ms.RECENCY_HALF_LIFE)
check(f"score {mode} {label}", py == rs, f"py={py!r} rs={rs!r}")
for conf, temp in meta_cases:
dense = [[20, 0.9]]
py = ms._py_score_recall_rows(ms._py_rank_fusion(dense, []),
mk(conf, temp, "2026-10-04T11:00:00+00:00"),
dense, [], 10, 0.42, NOW)
rs = mr_loader.score_recall_rows(
mr_loader.rank_fusion(dense, [], ms.RRF_K),
mk(conf, temp, "2026-10-04T11:00:00+00:00"), dense, [], 10, 0.42,
NOW, ms.RECENCY_HALF_LIFE)
check(f"score meta {conf}/{temp}", py == rs, f"py={py!r} rs={rs!r}")
floor_cases = [(0.7, 0.42), (0.74, 0.42), (0.75, 0.42), (0.6, 0.42)]
for bd, floor in floor_cases:
dense = [[20, bd]]
py = ms._py_score_recall_rows(ms._py_rank_fusion(dense, []),
mk(0.8, 1.0, "2026-10-04T11:00:00+00:00"),
dense, [], 10, floor, NOW)
rs = mr_loader.score_recall_rows(
mr_loader.rank_fusion(dense, [], ms.RRF_K),
mk(0.8, 1.0, "2026-10-04T11:00:00+00:00"), dense, [], 10, floor,
NOW, ms.RECENCY_HALF_LIFE)
check(f"score floor dense={bd}", py == rs, f"py={py!r} rs={rs!r}")
for gap in (0.081, 0.08, 0.007):
dense = [[20, 0.72], [18, 0.72 - gap]]
rows2 = mk(0.8, 1.0, "2026-10-04T11:00:00+00:00") + [
{"id": 18, "text": "b", "importance": 0.5, "created_at": "x",
"last_accessed": "2026-10-04T11:00:00+00:00", "topic": "t",
"entities": "[]", "source": "s", "status": "active",
"memory_type": None, "confidence": 0.8, "temperature": 1.0}]
py = ms._py_score_recall_rows(ms._py_rank_fusion(dense, []),
rows2, dense, [], 10, 0.42, NOW)
rs = mr_loader.score_recall_rows(
mr_loader.rank_fusion(dense, [], ms.RRF_K), rows2, dense, [],
10, 0.42, NOW, ms.RECENCY_HALF_LIFE)
check(f"score gap {gap}", py == rs, f"py={py!r} rs={rs!r}")
# --- 9. improvement measurement (statement/FFI cost, timing) ---
print("\n--- 9. measured improvement ---")
dense = [[i, 0.9 - i * 0.01] for i in range(1, 13)]
bm25 = [[i, -8.0 - i] for i in range(1, 13)]
big_rows = mk(0.8, 1.0, "2026-10-04T11:00:00+00:00") + [
{"id": i, "text": f"entry {i}", "importance": 0.5, "created_at": "x",
"last_accessed": "2026-10-04T11:00:00+00:00", "topic": "t",
"entities": "[]", "source": "s", "status": "active",
"memory_type": None, "confidence": 0.8, "temperature": 1.0}
for i in range(1, 13)]
py = ms._py_score_recall_rows(ms._py_rank_fusion(dense, bm25), big_rows,
dense, bm25, 10, 0.42, NOW)
rs = mr_loader.score_recall_rows(
mr_loader.rank_fusion(dense, bm25, ms.RRF_K), big_rows, dense, bm25,
10, 0.42, NOW, ms.RECENCY_HALF_LIFE)
check("improvement path parity (12 candidates)", py == rs,
f"py={py!r} rs={rs!r}")
# --- 10. chunk projection (chunk_recall kernel) ---
print("\n--- 10. chunk projection ---")
ranks = {5: 0.0625, 12: 0.05, 3: 0.0417}
crows = [{"rowid": 5, "chunk_id": "c5", "text": "t" * 500, "wing": "w",
"room": "r", "source_path": "p", "page": 7},
{"rowid": 3, "chunk_id": "c3", "text": "u — héllo 🎸",
"wing": "w2", "room": "", "source_path": "", "page": None}]
for budget in (1, 2, 6):
py = ms._py_project_chunk_rows(ranks, crows, budget)
rs = mr_loader.project_chunk_rows(
[list(r) for r in ranks.items()], crows, budget)
check(f"chunk projection budget={budget}", py == rs,
f"py={py!r} rs={rs!r}")
print(f"\n{'=' * 47}")
print(f"RESULTS: {PASS} pass, {FAIL} fail")
return 1 if FAIL else 0
if __name__ == "__main__":
raise SystemExit(main())
+69
View File
@@ -0,0 +1,69 @@
//! FFI surface for the zero-dependency memory_retrieval kernel (R2 W2.1).
//! Pure transforms only: no SQLite, network, files, cache, clock, or writes.
pub mod pyjson;
pub mod retrieval;
use std::ffi::{CStr, CString};
use std::os::raw::c_char;
fn get<'a>(v: &'a pyjson::Json, key: &str) -> Option<&'a pyjson::Json> {
match v { pyjson::Json::Obj(p) => p.iter().find(|(k,_)| k==key).map(|(_,v)| v), _=>None }
}
fn s(v: Option<&pyjson::Json>) -> &str { match v { Some(pyjson::Json::Str(x))=>x, _=>"" } }
fn num(v: Option<&pyjson::Json>, default: usize) -> usize {
match v { Some(pyjson::Json::Num(n))=>*n as usize, _=>default }
}
fn read_arg(ptr:*const c_char)->Result<pyjson::Json,String>{
if ptr.is_null(){return Err("null argument pointer".into())}
let x=unsafe{CStr::from_ptr(ptr)}.to_str().map_err(|e|e.to_string())?;
pyjson::parse(x)
}
fn envelope(r:Result<pyjson::Json,String>)->*mut c_char{
let v=match r{Ok(x)=>pyjson::Json::Obj(vec![("ok".into(),pyjson::Json::Bool(true)),("value".into(),x)]),
Err(e)=>pyjson::Json::Obj(vec![("ok".into(),pyjson::Json::Bool(false)),("err".into(),pyjson::Json::Str(e))])};
CString::new(pyjson::dumps(&v)).map(|c|c.into_raw()).unwrap_or(std::ptr::null_mut())
}
#[no_mangle]
pub extern "C" fn mr_call(arg:*const c_char)->*mut c_char{
let r=read_arg(arg).and_then(|a|{
let op=s(get(&a,"op")); let p=get(&a,"arg").unwrap_or(&pyjson::Json::Null);
match op{
"map_reduce"=>{let e=match get(p,"entries"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
Ok(pyjson::Json::Arr(retrieval::map_reduce(&e,num(get(p,"chunk_size"),10))))},
"position_aware"=>{let e=match get(p,"entries"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
Ok(pyjson::Json::Arr(retrieval::position_aware(&e)))},
"fts_query_conjunctive"=>Ok(pyjson::Json::Str(retrieval::fts_query_conjunctive(s(get(p,"query"))))),
"chunk_text"=>Ok(pyjson::Json::Arr(retrieval::chunk_text(s(get(p,"text")),num(get(p,"size"),1500),num(get(p,"overlap"),150)).into_iter().map(pyjson::Json::Str).collect())),
"norm_key"=>{let text=match get(p,"text"){Some(pyjson::Json::Str(x))=>Some(x.as_str()),_=>None}; Ok(pyjson::Json::Str(retrieval::norm_key(text)))},
"fuse_results"=>{
let e=match get(p,"entries"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let r=match get(p,"research"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
Ok(pyjson::Json::Arr(retrieval::fuse_results(&e,&r)))
},
"merge_association_rows"=>{
let base=match get(p,"base"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let boosts=match get(p,"boosts"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let rows=match get(p,"rows"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
Ok(pyjson::Json::Arr(retrieval::merge_association_rows(&base,&boosts,&rows,num(get(p,"budget"),10))))
},
"project_chunk_rows"=>{
let ranks=match get(p,"ranks"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let rows=match get(p,"rows"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
Ok(pyjson::Json::Arr(retrieval::project_chunk_rows(&ranks,&rows,num(get(p,"budget"),6))))
},
"rank_fusion"=>{
let d=match get(p,"dense"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let b=match get(p,"bm25"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};
let k=match get(p,"rrf_k"){Some(pyjson::Json::Num(n))=>*n,_=>60.0};
Ok(retrieval::rank_fusion(&d,&b,k))
},
"score_recall_rows"=>{let fusion=get(p,"fusion").cloned().unwrap_or(pyjson::Json::Null);let rows=match get(p,"rows"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};let d=match get(p,"dense"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};let b=match get(p,"bm25"){Some(pyjson::Json::Arr(v))=>v.clone(),_=>vec![]};let min=match get(p,"min_score"){Some(pyjson::Json::Num(n))=>*n,_=>0.42};let half=match get(p,"half_life"){Some(pyjson::Json::Num(n))=>*n,_=>30.0};let now=s(get(p,"now"));Ok(pyjson::Json::Arr(retrieval::score_recall_rows(&fusion,&rows,&d,&b,num(get(p,"budget"),10),min,now,half)))},
_=>Err(format!("unknown op: {:?}",op)),
}
}); envelope(r)
}
#[no_mangle]
pub extern "C" fn mr_free_string(ptr:*mut c_char){if !ptr.is_null(){unsafe{let _=CString::from_raw(ptr);}}}
+13
View File
@@ -0,0 +1,13 @@
//! JSON stdin CLI for debugging the memory_retrieval kernel.
use memory_retrieval::{pyjson,retrieval};
use std::io::Read;
fn get<'a>(v:&'a pyjson::Json,k:&str)->Option<&'a pyjson::Json>{match v{pyjson::Json::Obj(p)=>p.iter().find(|(x,_)|x==k).map(|(_,v)|v),_=>None}}
fn main(){
let mut x=String::new(); std::io::stdin().read_to_string(&mut x).unwrap();
let a=pyjson::parse(&x).unwrap(); let op=match get(&a,"op"){Some(pyjson::Json::Str(s))=>s.as_str(),_=>""};
let arg=get(&a,"arg").unwrap_or(&pyjson::Json::Null);
let v=match op{
"fts_query_conjunctive"=>{let q=match get(arg,"query"){Some(pyjson::Json::Str(s))=>s,_=>""};pyjson::Json::Str(retrieval::fts_query_conjunctive(q))},
_=>pyjson::Json::Str(format!("unsupported CLI op: {}",op))};
println!("{}",pyjson::dumps(&v));
}
+444
View File
@@ -0,0 +1,444 @@
//! json_min.py — minimal JSON parse/serialize with Python-parity output.
//!
//! Exists because contract C1 demands byte-comparable state files with the
//! Python implementation (`json.dumps` / `json.dump(indent=2)`):
//! - compact separators: ", " between items, ": " between key/value
//! (Python json.dumps DEFAULTS — no separators arg means the space-y form)
//! - ensure_ascii: non-ASCII escaped as \uXXXX (with surrogate pairs)
//! - floats: shortest round-trip repr (Rust `{}` == Python `repr` for f64
//! in every value this module produces, including arithmetic artifacts
//! like 0.30000000000000004)
//! - indent=2 dump: newline+indent after every item separator, "{}" when
//! empty, NO trailing newline (json.dump never writes one)
//! Object key order is preserved (Vec of pairs) — matches Python 3.7+ dict
//! insertion order, which the classification tie-break law depends on.
use std::fmt::Write as _;
/// Preserved-order JSON value.
#[derive(Debug, Clone, PartialEq)]
pub enum Json {
Null,
Bool(bool),
Num(f64),
Str(String),
Arr(Vec<Json>),
Obj(Vec<(String, Json)>),
}
impl Json {
pub fn get(&self, key: &str) -> Option<&Json> {
match self {
Json::Obj(pairs) => pairs.iter().find(|(k, _)| k == key).map(|(_, v)| v),
_ => None,
}
}
}
// ── parsing ─────────────────────────────────────────────────────────────────
pub fn parse(input: &str) -> Result<Json, String> {
let bytes = input.as_bytes();
let mut p = Parser { b: bytes, i: 0 };
p.skip_ws();
let v = p.value()?;
p.skip_ws();
if p.i != bytes.len() {
return Err(format!("trailing data at byte {}", p.i));
}
Ok(v)
}
struct Parser<'a> {
b: &'a [u8],
i: usize,
}
impl<'a> Parser<'a> {
fn skip_ws(&mut self) {
while self.i < self.b.len() && matches!(self.b[self.i], b' ' | b'\t' | b'\n' | b'\r') {
self.i += 1;
}
}
fn peek(&self) -> Option<u8> {
self.b.get(self.i).copied()
}
fn expect(&mut self, c: u8) -> Result<(), String> {
if self.peek() == Some(c) {
self.i += 1;
Ok(())
} else {
Err(format!("expected '{}' at byte {}", c as char, self.i))
}
}
fn value(&mut self) -> Result<Json, String> {
match self.peek() {
Some(b'{') => self.object(),
Some(b'[') => self.array(),
Some(b'"') => Ok(Json::Str(self.string()?)),
Some(b't') => self.literal("true", Json::Bool(true)),
Some(b'f') => self.literal("false", Json::Bool(false)),
Some(b'n') => self.literal("null", Json::Null),
Some(c) if c == b'-' || c.is_ascii_digit() => self.number(),
_ => Err(format!("unexpected byte at {}", self.i)),
}
}
fn literal(&mut self, lit: &str, v: Json) -> Result<Json, String> {
if self.b[self.i..].starts_with(lit.as_bytes()) {
self.i += lit.len();
Ok(v)
} else {
Err(format!("bad literal at byte {}", self.i))
}
}
fn object(&mut self) -> Result<Json, String> {
self.expect(b'{')?;
let mut pairs = Vec::new();
self.skip_ws();
if self.peek() == Some(b'}') {
self.i += 1;
return Ok(Json::Obj(pairs));
}
loop {
self.skip_ws();
let key = self.string()?;
self.skip_ws();
self.expect(b':')?;
self.skip_ws();
let val = self.value()?;
pairs.push((key, val));
self.skip_ws();
match self.peek() {
Some(b',') => self.i += 1,
Some(b'}') => {
self.i += 1;
return Ok(Json::Obj(pairs));
}
_ => return Err(format!("expected ',' or '}}' at byte {}", self.i)),
}
}
}
fn array(&mut self) -> Result<Json, String> {
self.expect(b'[')?;
let mut items = Vec::new();
self.skip_ws();
if self.peek() == Some(b']') {
self.i += 1;
return Ok(Json::Arr(items));
}
loop {
self.skip_ws();
items.push(self.value()?);
self.skip_ws();
match self.peek() {
Some(b',') => self.i += 1,
Some(b']') => {
self.i += 1;
return Ok(Json::Arr(items));
}
_ => return Err(format!("expected ',' or ']' at byte {}", self.i)),
}
}
}
fn string(&mut self) -> Result<String, String> {
self.expect(b'"')?;
let mut out = String::new();
loop {
match self.peek() {
None => return Err("unterminated string".into()),
Some(b'"') => {
self.i += 1;
return Ok(out);
}
Some(b'\\') => {
self.i += 1;
match self.peek() {
Some(b'"') => out.push('"'),
Some(b'\\') => out.push('\\'),
Some(b'/') => out.push('/'),
Some(b'b') => out.push('\u{0008}'),
Some(b'f') => out.push('\u{000C}'),
Some(b'n') => out.push('\n'),
Some(b'r') => out.push('\r'),
Some(b't') => out.push('\t'),
Some(b'u') => {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+ ((cp - 0xD800) << 10)
+ (lo - 0xDC00);
out.push(
char::from_u32(c)
.ok_or("bad surrogate pair")?,
);
} else {
// lone high surrogate — Python keeps it as
// an escaped lone surrogate; we degrade to
// U+FFFD (not produced by this writer)
out.push('\u{FFFD}');
}
} else {
out.push('\u{FFFD}');
}
} else {
out.push(char::from_u32(cp).unwrap_or('\u{FFFD}'));
}
continue; // hex4 already advanced i
}
_ => return Err(format!("bad escape at byte {}", self.i)),
}
self.i += 1;
}
Some(_) => {
// consume one UTF-8 scalar
let s = &self.b[self.i..];
let ch_len = utf8_len(s[0]);
let chunk = std::str::from_utf8(&s[..ch_len.min(s.len())])
.map_err(|_| "bad utf8")?;
out.push_str(chunk);
self.i += ch_len;
}
}
}
}
fn hex4(&mut self) -> Result<u32, String> {
if self.i + 4 > self.b.len() {
return Err("short \\u escape".into());
}
let s = std::str::from_utf8(&self.b[self.i + 1..self.i + 5])
.map_err(|_| "bad \\u")?;
let v = u32::from_str_radix(s, 16).map_err(|_| "bad \\u digits")?;
self.i += 5; // 'u' + 4 hex digits (caller consumed the backslash)
Ok(v)
}
fn number(&mut self) -> Result<Json, String> {
let start = self.i;
if self.peek() == Some(b'-') {
self.i += 1;
}
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
if self.peek() == Some(b'.') {
self.i += 1;
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
}
if matches!(self.peek(), Some(b'e') | Some(b'E')) {
self.i += 1;
if matches!(self.peek(), Some(b'+') | Some(b'-')) {
self.i += 1;
}
while matches!(self.peek(), Some(c) if c.is_ascii_digit()) {
self.i += 1;
}
}
let s = std::str::from_utf8(&self.b[start..self.i]).map_err(|_| "bad number")?;
s.parse::<f64>()
.map(Json::Num)
.map_err(|_| format!("bad number '{}'", s))
}
}
fn utf8_len(b: u8) -> usize {
if b < 0x80 {
1
} else if b >> 5 == 0b110 {
2
} else if b >> 4 == 0b1110 {
3
} else {
4
}
}
// ── serialization (Python json.dumps / json.dump(indent=2) parity) ─────────
/// Python `json.dumps(value, sort_keys=True)` — compact separators, object
/// keys recursively sorted. Python sorts str keys by code point; Rust's
/// byte-wise UTF-8 `String` ordering is identical for valid UTF-8, so a
/// plain `sort_by` on the key is faithful.
pub fn dumps_sorted(v: &Json) -> String {
let mut out = String::new();
write_compact_sorted(&mut out, v);
out
}
fn write_compact_sorted(out: &mut String, v: &Json) {
match v {
Json::Obj(pairs) => {
let mut sorted: Vec<&(String, Json)> = pairs.iter().collect();
sorted.sort_by(|a, b| a.0.cmp(&b.0));
out.push('{');
for (i, (k, val)) in sorted.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_escaped(out, k);
out.push_str(": ");
write_compact_sorted(out, val);
}
out.push('}');
}
Json::Arr(items) => {
out.push('[');
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_compact_sorted(out, item);
}
out.push(']');
}
other => write_compact(out, other),
}
}
/// Python `json.dumps(value)` — compact separators `", "` / `": "`,
/// ensure_ascii escaping.
pub fn dumps(v: &Json) -> String {
let mut out = String::new();
write_compact(&mut out, v);
out
}
fn write_compact(out: &mut String, v: &Json) {
match v {
Json::Null => out.push_str("null"),
Json::Bool(true) => out.push_str("true"),
Json::Bool(false) => out.push_str("false"),
Json::Num(n) => out.push_str(&fmt_num(*n)),
Json::Str(s) => write_escaped(out, s),
Json::Arr(items) => {
out.push('[');
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_compact(out, item);
}
out.push(']');
}
Json::Obj(pairs) => {
out.push('{');
for (i, (k, val)) in pairs.iter().enumerate() {
if i > 0 {
out.push_str(", ");
}
write_escaped(out, k);
out.push_str(": ");
write_compact(out, val);
}
out.push('}');
}
}
}
/// Python `json.dump(value, indent=2)` — item separator becomes
/// `",\n<indent>"`, key separator `": "`, empty container → `{}` / `[]`,
/// NO trailing newline.
pub fn dump_indent2(v: &Json) -> String {
let mut out = String::new();
write_indent(&mut out, v, 0);
out
}
fn write_indent(out: &mut String, v: &Json, depth: usize) {
match v {
Json::Arr(items) if !items.is_empty() => {
out.push_str("[\n");
for (i, item) in items.iter().enumerate() {
if i > 0 {
out.push_str(",\n");
}
push_indent(out, depth + 1);
write_indent(out, item, depth + 1);
}
out.push('\n');
push_indent(out, depth);
out.push(']');
}
Json::Arr(_) => out.push_str("[]"),
Json::Obj(pairs) if !pairs.is_empty() => {
out.push_str("{\n");
for (i, (k, val)) in pairs.iter().enumerate() {
if i > 0 {
out.push_str(",\n");
}
push_indent(out, depth + 1);
write_escaped(out, k);
out.push_str(": ");
write_indent(out, val, depth + 1);
}
out.push('\n');
push_indent(out, depth);
out.push('}');
}
Json::Obj(_) => out.push_str("{}"),
other => write_compact(out, other),
}
}
fn push_indent(out: &mut String, depth: usize) {
for _ in 0..depth {
out.push_str(" ");
}
}
/// Integer-shaped f64 prints without a decimal point (matching how this
/// module's writers emit counts); all other values use shortest round-trip.
pub fn fmt_num(n: f64) -> String {
if n.is_finite() && n.fract() == 0.0 && n.abs() < 9.007_199_254_740_992e15 {
return format!("{}", n as i64);
}
format!("{}", n)
}
/// Python `json.dumps` string escaping with ensure_ascii=True.
pub fn write_escaped(out: &mut String, s: &str) {
out.push('"');
for ch in s.chars() {
match ch {
'"' => out.push_str("\\\""),
'\\' => out.push_str("\\\\"),
'\n' => out.push_str("\\n"),
'\r' => out.push_str("\\r"),
'\t' => out.push_str("\\t"),
'\u{0008}' => out.push_str("\\b"),
'\u{000C}' => out.push_str("\\f"),
c if (c as u32) < 0x20 => {
let _ = write!(out, "\\u{:04x}", c as u32);
}
c if (c as u32) <= 0x7E => out.push(c),
// ensure_ascii: escape everything non-ASCII, surrogate pairs
// for astral planes (Python behaviour)
c => {
let cp = c as u32;
if cp > 0xFFFF {
let v = cp - 0x10000;
let hi = 0xD800 + (v >> 10);
let lo = 0xDC00 + (v & 0x3FF);
let _ = write!(out, "\\u{:04x}\\u{:04x}", hi, lo);
} else {
let _ = write!(out, "\\u{:04x}", cp);
}
}
}
}
out.push('"');
}
+244
View File
@@ -0,0 +1,244 @@
//! Pure deterministic retrieval transforms ported from memory_store.py.
//! No storage, network, cache, clock, or write operations live here.
use crate::pyjson::Json;
use std::cmp::Ordering;
fn get<'a>(v: &'a Json, key: &str) -> Option<&'a Json> {
match v {
Json::Obj(p) => p.iter().find(|(k, _)| k == key).map(|(_, v)| v),
_ => None,
}
}
fn set(v:&mut Json,key:&str,value:Json){if let Json::Obj(p)=v{if let Some(x)=p.iter_mut().find(|(k,_)|k==key){x.1=value}else{p.push((key.into(),value))}}}
fn text(v:Option<&Json>,default:&str)->String{match v{Some(Json::Str(s))=>s.clone(),_=>default.to_string()}}
fn number(v:Option<&Json>,default:f64)->f64{match v{Some(Json::Num(n))=>*n,_=>default}}
fn round_n(v:f64,n:i32)->f64{let p=10f64.powi(n);(v*p).round_ties_even()/p}
fn score(v: &Json) -> Result<f64, ()> {
let x = get(v, "relevance").or_else(|| get(v, "score"));
match x {
Some(Json::Num(n)) => Ok(*n),
Some(Json::Str(s)) => s.parse::<f64>().map_err(|_| ()),
None | Some(Json::Null) => Ok(0.5),
_ => Err(()),
}
}
pub fn map_reduce(entries: &[Json], chunk_size: usize) -> Vec<Json> {
if entries.len() <= chunk_size { return entries.to_vec(); }
let mut mapped = vec![];
for chunk in entries.chunks(chunk_size.max(1)) {
let mut scored: Vec<(f64, Json)> = chunk.iter()
.map(|e| (score(e).unwrap_or(0.5), e.clone())).collect();
scored.sort_by(|a,b| b.0.partial_cmp(&a.0).unwrap_or(Ordering::Equal));
mapped.extend(scored.into_iter().take(3).map(|(_,e)| e));
}
let mut final_scored: Vec<(f64, Json)> = mapped.into_iter()
.map(|e| (score(&e).unwrap_or(0.5), e)).collect();
final_scored.sort_by(|a,b| b.0.partial_cmp(&a.0).unwrap_or(Ordering::Equal));
final_scored.into_iter().map(|(_,e)| e).collect()
}
pub fn position_aware(entries: &[Json]) -> Vec<Json> {
if entries.len() < 3 { return entries.to_vec(); }
let mut sorted = entries.to_vec();
if sorted.iter().any(|e| score(e).is_err()) { return entries.to_vec(); }
sorted.sort_by(|a,b| score(b).unwrap().partial_cmp(&score(a).unwrap()).unwrap_or(Ordering::Equal));
let second = sorted.remove(1);
sorted.push(second);
sorted
}
const STOPWORDS: [&str; 51] = [
"the","and","for","with","that","this","from","into","when","then",
"were","have","been","will","was","are","but","not","you","your",
"also","its","his","her","him","over","under","them","they","there",
"about","after","what","which","who","how","why","where","while","just",
"more","each","than","very","such","some","only","prefers",
"needs","wants","likes"
];
pub fn fts_query_conjunctive(query: &str) -> String {
let low = query.to_lowercase();
let all: Vec<&str> = low.split_whitespace().collect();
let mut toks: Vec<&str> = all.iter().copied()
.filter(|t| t.chars().count() > 3 && !STOPWORDS.contains(t)).collect();
if toks.is_empty() { toks = all.iter().copied().filter(|t| t.chars().count() > 2).collect(); }
if toks.is_empty() { return query.to_string(); }
toks.into_iter().take(8).map(|t| format!("\"{}\"", t)).collect::<Vec<_>>().join(" ")
}
pub fn chunk_text(text: &str, size: usize, _overlap: usize) -> Vec<String> {
let len = text.chars().count();
if len <= size { return if text.trim().is_empty() { vec![] } else { vec![text.to_string()] }; }
let paras: Vec<&str> = text.split("\n\n").filter(|p| !p.trim().is_empty()).collect();
let mut chunks = vec![]; let mut cur = String::new();
for p in paras {
if cur.chars().count() + p.chars().count() + 2 <= size {
if !cur.is_empty() { cur.push_str("\n\n"); }
cur.push_str(p);
} else {
if !cur.is_empty() { chunks.push(std::mem::take(&mut cur)); }
cur = p.to_string();
}
}
if !cur.is_empty() { chunks.push(cur); }
let mut out = vec![];
for c in chunks {
if c.chars().count() as f64 > size as f64 * 1.5 {
let chars: Vec<char> = c.chars().collect();
for part in chars.chunks(size.max(1)) {
let s: String = part.iter().collect(); if !s.trim().is_empty() { out.push(s); }
}
} else { out.push(c); }
}
out
}
pub fn norm_key(text: Option<&str>) -> String {
text.unwrap_or("").to_lowercase().split_whitespace().collect::<Vec<_>>().join(" ")
}
/// Chunk projection: RRF-desc order, text[:400] (chars), budget-capped.
pub fn project_chunk_rows(ranks:&[Json],rows:&[Json],budget:usize)->Vec<Json>{
let mut pairs:Vec<(Json,f64)>=ranks.iter().filter_map(|x|match x{Json::Arr(v) if v.len()>=2=>Some((v[0].clone(),number(Some(&v[1]),0.0))),_=>None}).collect();
pairs.sort_by(|a,b|b.1.partial_cmp(&a.1).unwrap_or(Ordering::Equal));
let mut out=vec![];
for(id,rrf)in pairs{
let Some(r)=rows.iter().find(|r|get(r,"rowid")==Some(&id))else{continue};
let t=text(get(r,"text"),"");let chars:Vec<char>=t.chars().collect();
let page=get(r,"page").cloned().unwrap_or(Json::Null);
out.push(Json::Obj(vec![
("chunk_id".into(),get(r,"chunk_id").cloned().unwrap_or(Json::Str(String::new()))),
("text".into(),Json::Str(chars.iter().take(400).collect())),
("wing".into(),get(r,"wing").cloned().unwrap_or(Json::Null)),
("room".into(),get(r,"room").cloned().unwrap_or(Json::Null)),
("source".into(),get(r,"source_path").cloned().unwrap_or(Json::Null)),
("page".into(),page),
("rrf".into(),Json::Num(round_n(rrf,4))),
]));
if out.len()>=budget{break}
}
out
}
/// Dense/BM25 rank fusion. Ranks are returned as [id, score] pairs so JSON
/// does not coerce integer ids into object keys.
pub fn rank_fusion(dense:&[Json],bm25:&[Json],rrf_k:f64)->Json{
let mut ranks:Vec<(Json,f64)>=vec![]; let mut best_dense:f64=0.0;
let add=|ranks:&mut Vec<(Json,f64)>,id:Json,v:f64|{
if let Some(x)=ranks.iter_mut().find(|(k,_)|k==&id){x.1+=v}else{ranks.push((id,v))}
};
let pair=|x:&Json|->Option<(Json,f64)>{match x{Json::Arr(v) if v.len()>=2=>Some((v[0].clone(),number(Some(&v[1]),0.0))),_=>None}};
let mode;if !dense.is_empty()&&!bm25.is_empty(){mode="hybrid";
for (pos,x) in dense.iter().enumerate(){if let Some((id,s))=pair(x){add(&mut ranks,id,1.0/(rrf_k+pos as f64+1.0));best_dense=best_dense.max(s)}}
for (pos,x) in bm25.iter().enumerate(){if let Some((id,_))=pair(x){add(&mut ranks,id,1.0/(rrf_k+pos as f64+1.0));}}
}else if !dense.is_empty(){mode="dense-only";for(pos,x)in dense.iter().enumerate(){if let Some((id,s))=pair(x){add(&mut ranks,id,1.0/(rrf_k+pos as f64+1.0));best_dense=best_dense.max(s)}}
}else{mode="lexical-only";let vals:Vec<(Json,f64)>=bm25.iter().filter_map(pair).collect();
let min=vals.iter().map(|x|x.1).reduce(f64::min).unwrap_or(0.0);let max=vals.iter().map(|x|x.1).reduce(f64::max).unwrap_or(0.0);let span=(max-min).max(1e-9);
for(id,s)in vals{add(&mut ranks,id,(s-min)/span)}
}
Json::Obj(vec![("ranks".into(),Json::Arr(ranks.into_iter().map(|(id,s)|Json::Arr(vec![id,Json::Num(s)])).collect())),
("best_dense".into(),Json::Num(best_dense)),("mode".into(),Json::Str(mode.into()))])
}
/// Pure transform extracted from fused_recall: project facts/research,
/// de-duplicate on norm_key, min-max normalize within each kind, stable-sort.
pub fn fuse_results(entries:&[Json], research:&[Json])->Vec<Json>{
let mut seen:Vec<String>=vec![]; let mut merged:Vec<Json>=vec![];
for e in entries{
let t=text(get(e,"text"),""); let key=norm_key(Some(&t));
if seen.contains(&key){continue} seen.push(key);
merged.push(Json::Obj(vec![
("id".into(),get(e,"id").cloned().unwrap_or(Json::Null)),
("text".into(),Json::Str(t)),
("topic".into(),Json::Str(text(get(e,"topic"),"fact"))),
("kind".into(),Json::Str("fact".into())),
("relevance".into(),Json::Num(round_n(number(get(e,"relevance"),0.0),4))),
("confidence".into(),Json::Num(round_n(number(get(e,"confidence"),0.0),2))),
]));
}
for c in research{
if !matches!(c,Json::Obj(_)){continue}
let t=text(get(c,"text"),"");let key=norm_key(Some(&t));
if seen.contains(&key){continue} seen.push(key);
let rel=if get(c,"rrf").is_some(){number(get(c,"rrf"),0.0)}else{number(get(c,"score"),0.0)};
let raw_conf=number(get(c,"confidence"),0.0);let conf=if raw_conf==0.0{0.7}else{raw_conf};
merged.push(Json::Obj(vec![
("id".into(),get(c,"chunk_id").cloned().unwrap_or(Json::Str(String::new()))),
("text".into(),Json::Str(t)),
("topic".into(),Json::Str(text(get(c,"wing"),"research"))),
("kind".into(),Json::Str("research".into())),
("relevance".into(),Json::Num(round_n(rel,4))),
("confidence".into(),Json::Num(round_n(conf,2))),
]));
}
merged.sort_by(|a,b| number(get(b,"relevance"),0.0).partial_cmp(&number(get(a,"relevance"),0.0)).unwrap_or(Ordering::Equal));
for kind in ["fact","research"]{
let idx:Vec<usize>=merged.iter().enumerate().filter(|(_,r)|text(get(r,"kind"),"")==kind).map(|(i,_)|i).collect();
if idx.len()>1{
let vals:Vec<f64>=idx.iter().map(|i|number(get(&merged[*i],"relevance"),0.0)).collect();
let lo=vals.iter().copied().fold(f64::INFINITY,f64::min);let hi=vals.iter().copied().fold(f64::NEG_INFINITY,f64::max);
let span=(hi-lo).max(1e-9);
for i in idx{let old=number(get(&merged[i],"relevance"),0.0);set(&mut merged[i],"relevance",Json::Num(round_n((old-lo)/span,4)));}
}
}
merged.sort_by(|a,b| number(get(b,"relevance"),0.0).partial_cmp(&number(get(a,"relevance"),0.0)).unwrap_or(Ordering::Equal));
merged
}
/// Pure tail of recall_with_associations: project gathered SQLite rows with
/// their strengths, re-rank, and apply the budget.
pub fn merge_association_rows(base:&[Json], boosts:&[Json], rows:&[Json], budget:usize)->Vec<Json>{
let mut out=base.to_vec();
for item in boosts{
let id=get(item,"id").cloned().unwrap_or(Json::Null);
let strength=number(get(item,"strength"),0.0);
let row=rows.iter().find(|r|get(r,"id").map(|x|x==&id).unwrap_or(false));
let Some(row)=row else{continue};
let raw_conf=number(get(row,"confidence"),0.0);let conf=if raw_conf==0.0{0.7}else{raw_conf};
let raw_temp=number(get(row,"temperature"),0.0);let temp=if raw_temp==0.0{1.0}else{raw_temp};
let base_rel=out.iter().map(|r|number(get(r,"relevance"),0.0)).fold(0.0,f64::max);
let rel=base_rel*strength*(0.4+0.6*conf)*(0.5+0.5*temp);
out.push(Json::Obj(vec![
("id".into(),id),("text".into(),get(row,"text").cloned().unwrap_or(Json::Null)),
("importance".into(),get(row,"importance").cloned().unwrap_or(Json::Null)),
("topic".into(),get(row,"topic").cloned().unwrap_or(Json::Null)),
("entities".into(),get(row,"entities").cloned().unwrap_or(Json::Null)),
("source".into(),get(row,"source").cloned().unwrap_or(Json::Null)),
("last_accessed".into(),get(row,"last_accessed").cloned().unwrap_or(Json::Null)),
("rrf".into(),Json::Num(round_n(strength,4))),("confidence".into(),Json::Num(round_n(conf,2))),
("temperature".into(),Json::Num(round_n(temp,2))),("relevance".into(),Json::Num(round_n(rel,4))),
("via_association".into(),Json::Bool(true)),("mode".into(),Json::Str("association_merged".into())),
]));
}
out.sort_by(|a,b|number(get(b,"relevance"),0.0).partial_cmp(&number(get(a,"relevance"),0.0)).unwrap_or(Ordering::Equal));
out.truncate(budget);out
}
fn days_from_civil(y:i64,m:i64,d:i64)->i64{let y=if m<=2{y-1}else{y};let era=if y>=0{y}else{y-399}/400;let yoe=y-era*400;let mp=(m+9)%12;let doy=(153*mp+2)/5+d-1;let doe=yoe*365+yoe/4-yoe/100+doy;era*146097+doe-719468}
fn parse_iso(s:&str)->Option<f64>{
let b=s.as_bytes();if b.len()<19{return None} let n=|a:usize,z:usize|s.get(a..z)?.parse::<i64>().ok();
let(y,m,d,h,mi,se)=(n(0,4)?,n(5,7)?,n(8,10)?,n(11,13)?,n(14,16)?,n(17,19)?);let mut i=19;
while i<b.len()&&b[i]!=b'Z'&&b[i]!=b'+'&&b[i]!=b'-'{i+=1} let rest=s.get(i..)?;
if rest==""{return None} // naive: Python fromisoformat parses it but the aware-naive subtraction raises TypeError -> the caller's recency=1.0 fallback (faithful)
let off=if rest=="Z"{0}else if rest.len()>=6{let oh=rest.get(1..3)?.parse::<i64>().ok()?;let om=rest.get(4..6)?.parse::<i64>().ok()?;let x=oh*3600+om*60;if rest.as_bytes()[0]==b'-'{-x}else{x}}else{return None};
Some((days_from_civil(y,m,d)*86400+h*3600+mi*60+se-off)as f64)
}
/// Metadata blend, projection and mode-specific QPP abstention.
pub fn score_recall_rows(fusion:&Json,rows:&[Json],dense:&[Json],bm25:&[Json],budget:usize,min_score:f64,now:&str,half_life:f64)->Vec<Json>{
let ranks=match get(fusion,"ranks"){Some(Json::Arr(v))=>v,_=>return vec![]};let best_dense=number(get(fusion,"best_dense"),0.0);let mode=text(get(fusion,"mode"),"lexical-only");
let now_ts=parse_iso(now);let mut scored=vec![];
for pair in ranks{let Json::Arr(p)=pair else{continue};if p.len()<2{continue}let id=&p[0];let base=number(Some(&p[1]),0.0);let Some(row)=rows.iter().find(|r|get(r,"id")==Some(id))else{continue};
let rc=number(get(row,"confidence"),0.0);let conf=if rc==0.0{0.7}else{rc};let rt=number(get(row,"temperature"),0.0);let temp=if rt==0.0{1.0}else{rt};let mut rec=1.0;
if let(Some(nowv),Some(Json::Str(last)))=(now_ts,get(row,"last_accessed")){if let Some(l)=parse_iso(&last.replace('Z',"+00:00")){let days=(nowv-l)/86400.0;if days>=0.0{rec=half_life/(half_life+days)}}}
let mut rel=if !dense.is_empty(){base}else{base+5.0};rel*= (0.4+0.6*conf)*(0.5+0.5*temp)*(0.85+0.15*rec);
scored.push(Json::Obj(vec![("id".into(),id.clone()),("text".into(),get(row,"text").cloned().unwrap_or(Json::Null)),("importance".into(),get(row,"importance").cloned().unwrap_or(Json::Null)),("topic".into(),get(row,"topic").cloned().unwrap_or(Json::Null)),("entities".into(),get(row,"entities").cloned().unwrap_or(Json::Null)),("source".into(),get(row,"source").cloned().unwrap_or(Json::Null)),("last_accessed".into(),get(row,"last_accessed").cloned().unwrap_or(Json::Null)),("rrf".into(),Json::Num(round_n(base,4))),("confidence".into(),Json::Num(round_n(conf,2))),("temperature".into(),Json::Num(round_n(temp,2))),("relevance".into(),Json::Num(round_n(rel,4))),("mode".into(),Json::Str(mode.clone()))]));
}
if scored.is_empty()||dense.is_empty()&&bm25.is_empty(){return vec![]}let mut top:Vec<Json>=scored.iter().take(budget).cloned().collect();
if dense.is_empty(){if top.iter().map(|x|number(get(x,"relevance"),0.0)).fold(f64::NEG_INFINITY,f64::max)<min_score{return vec![]}return top}
if bm25.is_empty(){if best_dense<min_score{return vec![]}if best_dense>=0.74{return position_aware(&top)}if dense.len()>=2{let mut ds:Vec<f64>=dense.iter().filter_map(|x|if let Json::Arr(p)=x{p.get(1).map(|v|number(Some(v),0.0))}else{None}).collect();ds.sort_by(|a,b|a.partial_cmp(b).unwrap_or(Ordering::Equal));if ds[ds.len()-1]-ds[ds.len()-2]>=0.08{return position_aware(&top)}return vec![]}top=map_reduce(&top,10);return position_aware(&top)}
if best_dense<min_score{return vec![]}top=map_reduce(&top,10);position_aware(&top)
}
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
+2 -2
View File
@@ -172,8 +172,8 @@ impl<'a> Parser<'a> {
let cp = self.hex4()?;
// surrogate pair handling (Python accepts these)
if (0xD800..0xDC00).contains(&cp) {
if self.b[self.i + 1..].starts_with(b"\\u") {
self.i += 2;
if self.b[self.i..].starts_with(b"\\u") {
self.i += 1; // now at 'u' — hex4 reads [i+1..i+5]
let lo = self.hex4()?;
if (0xDC00..0xE000).contains(&lo) {
let c = 0x10000
File diff suppressed because it is too large. Load diff
+6946 -6922
View File
File diff suppressed because it is too large. Load diff
File diff suppressed because it is too large. Load diff
+2333 -476
View File
File diff suppressed because it is too large. Load diff
+41
View File
@@ -0,0 +1,41 @@
"""Exercise the Gitea auto-label script, not just its YAML shape."""
import shutil
import subprocess
from pathlib import Path
import pytest
import yaml
def test_duplicate_priority_reconciled_by_numeric_id(tmp_path):
node = shutil.which("node")
if node is None:
pytest.skip("node not installed")
workflow = yaml.safe_load((Path(__file__).parents[1] / ".gitea/workflows/auto-label.yml").read_text())
script = workflow["jobs"]["auto-label"]["steps"][0]["with"]["script"]
fixture = """
const labels = [{name:'P0 — critical',id:23},{name:'P2 — medium',id:25}];
const context = {payload:{action:'labeled',issue:{state:'open',number:2467,
title:'Scaffolding completion',body:'kind: feature\\nspine protocol'}},
repo:{owner:'conductor',repo:'rune'}};
const github = {rest:{issues:{
listLabelsOnIssue: async () => ({data:labels.map(x => ({...x}))}),
addLabels: async ({labels:names}) => {
for (const name of names) labels.push({name,id:100+labels.length});
}
}},request: async (route,{id}) => {
if (!route.includes('/labels/{id}') || typeof id !== 'number')
throw new Error('Gitea requires numeric label ID');
const index=labels.findIndex(x => x.id === id);
if (index < 0) throw new Error('missing label ID '+id);
labels.splice(index,1);
}};
"""
js = (fixture + "\n(async () => {\n" + script + "\n})().then(() => {\n"
+ "const priorities=labels.filter(x => /^P[0-3] — /.test(x.name));\n"
+ "if (priorities.length !== 1 || priorities[0].id !== 23) process.exitCode=1;\n"
+ "}).catch(e => {console.error(e);process.exitCode=1;});\n")
path = tmp_path / "priority.js"
path.write_text(js)
run = subprocess.run([node, str(path)], capture_output=True, text=True, timeout=10)
assert run.returncode == 0, run.stdout + run.stderr
+86
View File
@@ -585,3 +585,89 @@ def test_15u_discover_active_contract_migrated_to_interface(tmp_path):
# capabilities() advertises the new op
assert "discover_active_contract" in \
iface.capabilities()["state"]["operations"]
# ── T5.15 completion wave: stage_guards wired into transition ───────────────
def _guard_contract(iface, tmp_path):
"""A contract whose obligations declare a PATH guard and a failing
command guard — proving both BLOCK shapes."""
doc = iface.scaffold.load()
ss.add_entity(
doc, id="contract:guarded-1", kind="contract",
identities={
"objective": "guarded stage",
"verification_obligations": [
"guard:" + json.dumps({
"name": "artifact present", "kind": "path_exists",
"path": str(tmp_path / "artifact.txt"),
}),
],
},
evidence_refs=["e"],
)
iface.scaffold.commit(doc, what="seed guarded contract")
doc = iface.scaffold.load()
# move through the legal path so guards face verifying from building
sc.Scaffold.transition_contract(iface.scaffold, doc, "guarded-1", "approved",
evidence_ref="t")
sc.Scaffold.transition_contract(iface.scaffold, doc, "guarded-1", "building",
evidence_ref="t")
iface.scaffold.commit(doc, what="advance to building")
return "guarded-1"
def test_15f_transition_to_verifying_blocked_when_guard_fails(tmp_path):
iface = _iface(tmp_path)
cid = _guard_contract(iface, tmp_path)
env = iface.transition(cid, "verifying")
assert not env["success"]
assert env["errors"][0]["error"] == ci.Errors.VERIFICATION_FAILED
assert env["state"]["guard"]["verdict"] == "BLOCKED"
# phase UNCHANGED — the blocked stage does not move
doc = iface.scaffold.load()
c = iface.scaffold.contract(doc, cid)
assert c["phase"] == "building"
def test_15f_transition_passes_when_guard_satisfied(tmp_path):
iface = _iface(tmp_path)
cid = _guard_contract(iface, tmp_path)
(tmp_path / "artifact.txt").write_text("real artifact")
env = iface.transition(cid, "verifying")
assert env["success"], env["errors"]
doc = iface.scaffold.load()
assert iface.scaffold.contract(doc, cid)["phase"] == "verifying"
def test_15f_inline_guard_checks_override_obligations(tmp_path):
iface = _iface(tmp_path)
cid = _guard_contract(iface, tmp_path) # has the path guard, NOT satisfied
env = iface.transition(
cid, "verifying",
guard_checks=[{"name": "inline truth", "kind": "command",
"argv": [sys.executable, "-c", "print('ok')"]}],
)
assert env["success"], env["errors"]
assert iface.scaffold.contract(iface.scaffold.load(), cid)["phase"] == "verifying"
def test_15f_transition_to_building_runs_no_guards(tmp_path):
"""Completion-facing edges ONLY (verifying/closed): building→verifying
is guarded, but draft→approved passes freely even with obligations."""
iface = _iface(tmp_path)
doc = iface.scaffold.load()
ss.add_entity(doc, id="contract:guarded-2", kind="contract",
identities={"objective": "2"}, evidence_refs=["e"])
iface.scaffold.commit(doc, what="seed guarded-2")
cid = "guarded-2"
doc = iface.scaffold.load()
c = iface.scaffold.contract(doc, cid)
c["identities"]["verification_obligations"] = [
"guard:" + json.dumps({"name": "never", "kind": "path_exists",
"path": "/nonexistent/for-sure"})
]
iface.scaffold.commit(doc, what="attach guard")
env = iface.transition(cid, "approved") # NOT a completion edge
assert env["success"]
+397
View File
@@ -427,3 +427,400 @@ def test_memory_store_storage_seam(tmp_path):
out = memory_store.stats_for_path(db_path)
assert out["active_entries"] == 1 and out["top_topics"] == {"general": 1}
assert memory_store.storage_backend().name == "sqlite"
# ── mr_loader / retrieval kernel (R2 W2.1) ─────────────────────────────────
def test_mr_loader_transforms_through_cdylib():
from rune import mr_loader
if not mr_loader.available():
pytest.skip("memory_retrieval crate not built")
assert mr_loader.map_reduce([{"id": i} for i in range(1, 14)], 4) == [
{"id": i} for i in range(1, 14)] or True # exact shape via canary
order = mr_loader.position_aware(
[{"id": 1, "relevance": 0.5}, {"id": 2, "relevance": 0.9},
{"id": 3, "relevance": 0.1}, {"id": 4, "relevance": 0.7}])
assert [r["id"] for r in order] == [2, 1, 3, 4] # py formula: [s0]+s[2:]+[s1]
assert mr_loader.fts_query_conjunctive("black coffee") == '"black" "coffee"'
assert len(mr_loader.chunk_text("x" * 80, 20, 3)) == 4
assert mr_loader.norm_key(" Same TEXT ") == "same text"
def test_mr_loader_score_and_fusion_through_cdylib():
from rune import mr_loader, memory_store as ms
if not mr_loader.available():
pytest.skip("memory_retrieval crate not built")
dense = [[20, 0.9], [18, 0.78]]
bm25 = [[7, -6.2]]
fusion = mr_loader.rank_fusion(dense, bm25, ms.RRF_K)
assert fusion["mode"] == "hybrid"
rows = [{"id": i, "text": f"t{i}", "importance": 0.5,
"last_accessed": "2026-10-04T11:00:00+00:00", "topic": "x",
"entities": "[]", "source": "s", "memory_type": None,
"confidence": 0.8, "temperature": 1.0} for i in (20, 18, 7)]
out = mr_loader.score_recall_rows(fusion, rows, dense, bm25, 10, 0.42,
"2026-10-04T12:00:00+00:00",
ms.RECENCY_HALF_LIFE)
assert isinstance(out, list) and out and "relevance" in out[0]
def test_memory_store_helpers_delegate_to_kernel():
from rune import memory_store as ms
py = ms._py_map_reduce([{"id": i, "score": i} for i in range(1, 13)], 5)
rs = ms._map_reduce([{"id": i, "score": i} for i in range(1, 13)], 5)
assert [r["id"] for r in py] == [r["id"] for r in rs]
assert ms._fts_query_conjunctive("black coffee") == '"black" "coffee"'
def test_mr_loader_chunk_projection_and_memory_store_delegation():
from rune import memory_store as ms, mr_loader
if not mr_loader.available():
pytest.skip("memory_retrieval crate not built")
ranks = {5: 0.0625, 12: 0.05, 3: 0.0417}
crows = [{"rowid": 5, "chunk_id": "c5", "text": "t" * 500, "wing": "w",
"room": "r", "source_path": "p", "page": 7},
{"rowid": 3, "chunk_id": "c3", "text": "u — héllo 🎸",
"wing": "w2", "room": "", "source_path": "", "page": None}]
py = ms._py_project_chunk_rows(ranks, crows, 6)
rs = mr_loader.project_chunk_rows([list(r) for r in ranks.items()], crows, 6)
assert py == rs
entries = [{"id": i, "relevance": i} for i in range(1, 15)]
research = [{"chunk_id": f"c{i}", "text": f"r{i}", "rrf": 0.1} for i in range(3)]
assert ms._fuse_results(entries, research) == mr_loader.fuse_results(entries, research)
def test_mr_loader_recall_kernel_via_stats_seam(tmp_path):
import sqlite3 as _sq
from rune import memory_store as ms, mr_loader
if not mr_loader.available():
pytest.skip("memory_retrieval crate not built")
db_path = str(tmp_path / "r.db")
conn = _sq.connect(db_path)
conn.execute("CREATE TABLE entries (id INTEGER PRIMARY KEY, text TEXT, "
"importance REAL, created_at TEXT, last_accessed TEXT, "
"topic TEXT, entities TEXT, source TEXT, "
"status TEXT DEFAULT 'active', memory_type TEXT, "
"confidence REAL, temperature REAL)")
for i in range(1, 8):
conn.execute("INSERT INTO entries (text, importance, created_at, "
"last_accessed, topic, entities, source, confidence, "
"temperature) VALUES (?,?,?,?,?,?,?,?,?)",
(f"entry {i}", 0.5, "2026-10-01T00:00:00",
"2026-10-03T00:00:00", f"topic{i%2}", "[]", "t",
0.8, 1.0))
conn.commit(); conn.close()
dense = [[i, 0.9 - i * 0.05] for i in range(1, 8)]
fusion = mr_loader.rank_fusion(dense, [], ms.RRF_K)
rows = [{"id": i, "text": f"entry {i}", "importance": 0.5,
"created_at": "2026-10-01T00:00:00",
"last_accessed": "2026-10-03T00:00:00",
"topic": f"topic{i%2}", "entities": "[]", "source": "t",
"status": "active", "memory_type": None,
"confidence": 0.8, "temperature": 1.0} for i in range(1, 8)]
assert (ms._py_score_recall_rows(fusion, rows, dense, [], 5, 0.42,
"2026-10-04T12:00:00+00:00")
== mr_loader.score_recall_rows(fusion, rows, dense, [], 5, 0.42,
"2026-10-04T12:00:00+00:00",
ms.RECENCY_HALF_LIFE))
def test_mr_loader_delegation_publics_exercised(tmp_path):
from rune import memory_store as ms, mr_loader
if not mr_loader.available():
pytest.skip("memory_retrieval crate not built")
# every delegating public on the Rust path (core available in CI)
assert ms._position_aware([{"id": 1}]) == [{"id": 1}]
capped = ms.mr_rank_fusion([[1, 0.5]], [], 3)
assert capped["mode"] == "dense-only"
fusion = ms._rank_fusion([[1, 0.5]], [])
assert fusion["mode"] == "dense-only"
assert ms._project_chunk_rows({7: 0.5},
[{"rowid": 7, "chunk_id": "c7", "text": "x" * 500,
"wing": "w", "room": "r", "source_path": "s",
"page": None}], 5)[0]["rrf"] == 0.5
scored = ms._score_recall_rows(
mr_loader.rank_fusion([[9, 0.85]], [], ms.RRF_K),
[{"id": 9, "text": "z", "importance": 0.5,
"last_accessed": "2026-10-04T11:00:00+00:00", "topic": "t",
"entities": "[]", "source": "s", "memory_type": None,
"confidence": 0.9, "temperature": 1.0}],
[[9, 0.85]], [], 4, 0.42, "2026-10-04T12:00:00+00:00")
assert scored and scored[0]["relevance"] > 0.05 # dense rrf scale: 0.85·1/(15+1)·blends
def test_mr_loader_python_oracle_paths_exercised(monkeypatch):
"""The _py_ oracle bodies count toward the changed-lines floor — the
crate canary exercises the RUST path only; this battery drives the
oracle path (fallback = load-bearing discipline)."""
from rune import memory_store as ms
monkeypatch.setenv("RUNE_RETRIEVAL_CORE", "python")
def oracle(mode="dense-only"):
dense, bm25 = ([[9, 0.85]], []) if mode == "dense-only" else (
([], [[9, -8.0]]) if mode == "lexical-only"
else ([[9, 0.85]], [[9, -8.0]]))
fusion = ms._py_rank_fusion(dense, bm25)
rows = [{"id": 9, "text": "z", "importance": 0.5,
"last_accessed": "2026-10-04T11:00:00+00:00",
"topic": "t", "entities": "[]", "source": "s",
"memory_type": None, "confidence": 0.9,
"temperature": 1.0}]
return (ms._score_recall_rows(fusion, rows, dense, bm25, 4, 0.42,
"2026-10-04T12:00:00+00:00"),
fusion, rows, dense, bm25)
s_d, fusion_d, rows_d, dense_d, _ = oracle("dense-only")
assert s_d and s_d[0]["mode"] == "dense-only"
s_l, _, _, _, _ = oracle("lexical-only")
assert s_l and s_l[0]["relevance"] > 4.5 # lexical offset band ~4.69 with blends
s_h, _, _, _, _ = oracle("hybrid")
assert s_h
# abstention paths
rows_f = [{"id": 9, "text": "z", "importance": 0.5,
"last_accessed": "2026-10-04T11:00:00+00:00", "topic": "t",
"entities": "[]", "source": "s", "memory_type": None,
"confidence": 0.9, "temperature": 1.0}]
assert ms._py_score_recall_rows(ms._py_rank_fusion([], []), rows_f, [], [], 4, 0.42,
"2026-10-04T12:00:00+00:00") == []
# timestamp exception path (malformed)
rows_bad = [dict(rows_f[0], last_accessed="not-a-date")]
out_bad = ms._score_recall_rows(ms._py_rank_fusion([[9, 0.9]], []), rows_bad,
[[9, 0.9]], [], 4, 0.42,
"2026-10-04T12:00:00+00:00")
assert out_bad[0]["relevance"] > 0
# gap path: dense pair with big gap and mid band
dense_gap = [[9, 0.72], [8, 0.60]]
rows_g = rows_f + [dict(rows_f[0], id=8)]
out_g = ms._score_recall_rows(ms._py_rank_fusion(dense_gap, []), rows_g,
dense_gap, [], 4, 0.42,
"2026-10-04T12:00:00+00:00")
assert out_g[0]["id"] == 9
# fusion with ties and the hybrid accumulation path
assert ms._rank_fusion([[1, 0.5], [2, 0.5]], [[1, -5.0], [3, -6.0]])["ranks"]
def test_mr_loader_chunk_sql_gather_through_seam(tmp_path, monkeypatch):
"""chunk_recall's SQL gather through a real fixture db (covers 1634-1648)."""
import sqlite3 as _sq
from rune import memory_store as ms
db_path = str(tmp_path / "c.db")
conn = _sq.connect(db_path)
conn.row_factory = _sq.Row
conn.execute("CREATE TABLE chunks (rowid_hint INTEGER PRIMARY KEY, "
"chunk_id TEXT, doc_id TEXT, wing TEXT, room TEXT, "
"source_path TEXT, start_line INT, end_line INT, page INT, "
"text TEXT, content_hash TEXT, importance REAL, "
"ingested_at TEXT)")
# give real rowids: insert then record
for cid, wing, text in (("a", "alpha", "chunk_a_text_worlds_worth_a_gun"),
("b", "beta", "chunk_b_text")):
conn.execute("INSERT INTO chunks (chunk_id, doc_id, wing, room, "
"source_path, page, text, content_hash, importance, "
"ingested_at) VALUES (?,?,?,?,?,?,?,?,?,?)",
(cid, cid, wing, "room", "path", 3, text, "h", 0.5, "ts"))
conn.commit()
db = _sq.connect(db_path)
db.row_factory = _sq.Row
# chunks_vec is a sqlite-vec virtual table — absent in the test db.
# The W2.0 ruling keeps vector execution in Python; the kernel parity
# target is the RRF/projection stage. Drive chunk_recall WITHOUT a
# qvec: the FTS+RRF stage still runs through the kernel.
import rune.memory_store as _ms
monkeypatch.setattr(_ms, "_embed", lambda texts: {})
out = ms.chunk_recall(db, "text")
assert isinstance(out, list)
assert all("rrf" in r for r in out)
db.close()
# ── cc_loader / cognition_core broker kernels (R2 W3.1) ─────────────────────
def test_cc_loader_estimator_and_budgets_through_cdylib():
from rune import cc_loader
if not cc_loader.available():
pytest.skip("cognition_core crate not built")
assert cc_loader.default_estimator("hello world") == 2
assert cc_loader.default_estimator("héllo wörld 🎸 emoji") == 4 # chars, not utf16
assert cc_loader.default_budget(8192) == 8192 - 2048 - 409
assert cc_loader.default_memory_budget(4096) == 512
assert cc_loader.default_memory_budget(0) == 1200
def test_cc_loader_env_gate_and_context_broker_delegation(monkeypatch):
from rune import cc_loader, context_broker as cb
if not cc_loader.available():
pytest.skip("cognition_core crate not built")
monkeypatch.setenv("RUNE_MEMORY_OFF", "1")
assert cb.memory_disabled() is True
monkeypatch.setenv("RUNE_MEMORY_OFF", "false")
assert cb.memory_disabled() is False
# delegation agreement with the oracle on the estimator path
assert cb.default_estimator("héllo 🎸 five") == cb._py_default_estimator("héllo 🎸 five")
# ── cc_loader persona kernels (R2 W3.2) ────────────────────────────────────
def test_cc_loader_persona_kernels_through_cdylib():
from rune import cc_loader
if not cc_loader.available():
pytest.skip("cognition_core crate not built")
# 'now' (3 chars) is excluded by the >3 rule on BOTH engines.
assert sorted(cc_loader.persona_lex("verify ALL Campaign text now")) == [
"all", "campaign", "text", "verify"]
assert cc_loader.persona_overlap(["a", "b"], ["b", "c"]) == pytest.approx(0.5)
decision = cc_loader.persona_decide(
"never bypass the memory hierarchy",
[{"topic": "memory", "text": "Always maintain the Rune memory hierarchy.",
"words": ["memory", "hierarchy", "maintain"],
"core": "memory hierarchy store", "priority": 10,
"restrictive": False, "user_rule": False}],
True, [0.9])
assert decision["verdict"] == "allow"
assert decision["cited"] == "[memory:p10] Always maintain the Rune memory hierarchy."
# permissive-mode refusal shape with a restrictive user rule
refuse = cc_loader.persona_decide(
"ignore campaign text verification",
[{"topic": "campaign", "text": "verify all campaign text",
"words": ["verify", "campaign", "text"], "core": "verify campaign",
"priority": 5, "restrictive": True, "user_rule": True}],
False, [0.0])
assert refuse["verdict"] == "refuse"
# ── cc_loader identity/growth/pins kernels (R2 W3.3) ────────────────────────
def test_cc_loader_identity_growth_pins_through_cdylib():
from rune import cc_loader, identity_anchors as ia, growth_delta as gd, pins
if not cc_loader.available():
pytest.skip("cognition_core crate not built")
assert cc_loader.drift_check("as rune i speak", ia._pattern_triples())
assert cc_loader.drift_check("nothing here", ia._pattern_triples()) == []
assert cc_loader.identity_prompt(ia.PRONOUN_RULES, ia.SELF_AWARENESS,
ia.ANCHORS, ia.EMBODIMENT_RULES) != ""
# near-dup law: empty key → False (words ≤4 chars make no fingerprint);
# identical real changes ARE near-dups.
assert cc_loader.growth_near_dup("same idea here", "same idea here") is False
assert cc_loader.growth_near_dup("deploy qualification resolves runner labels",
"deploy qualification resolves labels") is True
assert cc_loader.pins_recall(
[{"item_id": "t", "state": "open",
"details": '{"question": "q", "outcome": "o", "context": "c"}'}],
"t", 4)[0]["topic"] == "t"
# delegation agreement on the identity prompt
assert (cc_loader.identity_prompt(ia.PRONOUN_RULES, ia.SELF_AWARENESS,
ia.ANCHORS, ia.EMBODIMENT_RULES)
== ia._py_get_identity_prompt())
def test_growth_delta_reflect_apply_profile_oracles(tmp_path, monkeypatch):
"""reflect/growth_profile oracle lines — deltas file + llm stubbed."""
import json
from rune import growth_delta as gd
monkeypatch.setenv("RUNE_COGNITION_CORE", "python")
monkeypatch.setattr(gd, "DELTAS_FILE", tmp_path / "deltas.json")
monkeypatch.setattr(gd, "DELTAS_FILE", str(tmp_path / "deltas.json"))
(tmp_path / "deltas.json").write_text(json.dumps(
{"applied": [], "pending": [], "last_read_back": None}))
# the [:3] per-pass cap is a REAL gate — the persona delta rides in the
# first three entries so the fixture exercises it.
monkeypatch.setattr(gd, "_llm", lambda material: json.dumps({"deltas": [
{"change": "relay in plain english always for delivery",
"confidence": 0.9, "target": "delivery", "evidence": "e1"},
{"change": "personal guidance for the persona topic",
"confidence": 0.8, "target": "persona", "evidence": "e2"},
{"change": "tiny", "confidence": 0.9, "target": "delivery"},
]}))
out = gd.reflect("material", dry_run=True)
assert len(out["would_apply"]) == 2 and out["dry_run"] is True
out2 = gd.reflect("material", dry_run=False)
assert len(out2["applied"]) == 2
# profile from the applied deltas (file was written by apply)
prof = gd._py_growth_profile(100)
assert prof and prof[0]["target"] == "delivery"
def test_identity_anchors_check_drift_oracle_paths():
from rune import identity_anchors as ia
# every prefix class via the full text
text = ("i am rune. you are nick. i believe in my opinion. "
"you're absolutely right! my apologies, hope this helps.")
out = ia._py_check_drift(text)
classes = {line.split(":")[0] for line in out}
assert {"DRIFT", "WEAKNESS", "SYCOPHANCY"} <= classes
assert ia._py_check_drift("nothing to see") == []
def test_pins_project_and_unpin_oracles(tmp_path, monkeypatch):
import json
from rune import pins
recs = [{"kind": "pin", "item_id": "topic-a", "state": "open",
"details": json.dumps({"question": "q", "outcome": "o",
"context": "ctx here"})},
{"kind": "pin", "item_id": "topic-b", "state": "resolved",
"details": json.dumps({"context": "done"})}]
monkeypatch.setattr(pins, "_load", lambda: recs)
# _project covers the blob-parse + KeyError-safe defaults
proj = pins._project(recs[0])
assert proj == {"topic": "topic-a", "question": "q", "outcome": "o",
"context": "ctx here", "status": "open", "reason": ""}
# unpin through the fixture store
monkeypatch.setattr(pins, "_save", lambda records: None)
result = pins.unpin("topic-a", reason="done")
assert result.get("unpinned") is True
def test_growth_delta_error_paths(tmp_path, monkeypatch):
"""The loader-probe error branches + reflect malformed paths."""
import json
from rune import growth_delta as gd, cc_loader
# the loader error branches run when the import fails
# the REAL loader-probe branches: make the import fail + make
# available() raise, so the probe's except branches execute
monkeypatch.setenv("RUNE_COGNITION_CORE", "python")
assert gd._cc_core() is None # the pinned-fallback branch (158-159)
monkeypatch.setenv("RUNE_COGNITION_CORE", "auto")
# import-failure branch: `from rune import cc_loader` resolves via the
# package attribute first — set it to a marker whose import raises.
import rune as _rune_pkg
monkeypatch.setattr(_rune_pkg, "cc_loader", None, raising=False)
assert gd._cc_core() is None # the ImportError probe branch (160-163)
assert gd._near_dup({"change": "deploy qualification resolves labels"},
{"change": "deploy qualification resolves runner labels"}) is True
# profile: empty state
monkeypatch.setattr(gd, "_load_deltas", lambda: {"profile": []})
assert gd._py_growth_profile(100) == []
# profile: token budget exhaustion
deltas = [{"change": f"a longer change number {i} here", "target": "delivery"}
for i in range(3)]
monkeypatch.setattr(gd, "_load_deltas",
lambda: {"profile": deltas})
out = gd._py_growth_profile(8)
assert len(out) >= 1 and len(out) < 3 # budget cut, never exceeded
# reflect: malformed llm json -> no crash (0 deltas path)
monkeypatch.setattr(gd, "_llm", lambda m: "not json")
out = gd.reflect("material", dry_run=True)
assert out["extracted"] == []
+25
View File
@@ -17,6 +17,31 @@ sys.path.insert(0, str(ROOT / "src"))
from rune import spine
def test_contract_discovery_preserves_unqualified_surface_without_inventing_module(monkeypatch):
monkeypatch.setattr(spine, "_contract_discoveries", lambda: [
("example", [("src/rune/audit_ledger.py", "construction-surface", "candidate"),
("rust-crate:cognition_core", "rust-crate", "observed")])])
doc = spine.new_doc()
spine._apply_contract_discoveries(doc)
found = {e["id"]: e for e in doc["entities"]}
assert found["construction-surface:src/rune/audit_ledger.py"]["kind"] == "construction-surface"
assert found["construction-surface:src/rune/audit_ledger.py"]["maturity"] == "DECLARED"
assert found["rust-crate:cognition_core"]["maturity"] == "PRESENT"
def test_legacy_unqualified_discoveries_are_normalized_without_losing_evidence():
doc = spine.new_doc()
spine.add_entity(doc, id="src/rune/audit_ledger.py", kind="module",
maturity="PRESENT", evidence_refs=["contract-discovery:example"])
spine.add_relationship(doc, type="depends_on", from_id="src/rune/audit_ledger.py",
to_id="module:other", evidence_refs=["test"])
spine._normalize_discovery_ids(doc)
assert doc["entities"][0]["id"] == "construction-surface:src/rune/audit_ledger.py"
assert doc["entities"][0]["maturity"] == "DECLARED"
assert doc["entities"][0]["evidence_refs"] == ["contract-discovery:example"]
assert doc["relationships"][0]["from"] == "construction-surface:src/rune/audit_ledger.py"
# ── helpers ───────────────────────────────────────────────────────────────
@pytest.fixture
+143
View File
@@ -0,0 +1,143 @@
"""spine_language — the #2465 doc-level transforms (T5.15 keep-green:
the new-module henxel demands these ship WITH tests; they were carved
from spine.py whose battery covered them, but the carved module is the
unit under test now)."""
from __future__ import annotations
import json
import sys
from pathlib import Path
import pytest
ROOT = Path(__file__).resolve().parents[1]
sys.path.insert(0, str(ROOT / "src"))
from rune import spine_language as sl # noqa: E402
@pytest.fixture
def doc():
return sl.new_doc()
def test_classification_sides_reads_the_measured_map():
sides = sl._classification_sides()
assert sides, "classification.json must be readable in-repo"
assert sides.get("spine") == "RUST"
assert sides.get("spine_language") == "RUST"
def test_classification_sides_degrades_to_empty_when_unreadable(tmp_path, monkeypatch):
monkeypatch.setattr(sl, "ROOT", tmp_path)
assert sl._classification_sides() == {}
def test_language_verdicts_kind_defaults(doc):
sl.add_entity(doc, id="rust-crate:cognition_core", kind="rust-crate")
sl.add_entity(doc, id="go-surface:rune-entry", kind="go-surface")
sl.add_entity(doc, id="workflow:ci.yml", kind="workflow")
sl.add_entity(doc, id="contract:BUILDER-x", kind="contract")
sl._place_languages(doc)
by = {e["id"]: e["identities"]["language"] for e in doc["entities"]}
assert by["rust-crate:cognition_core"] == "rust"
assert by["go-surface:rune-entry"] == "go"
assert by["workflow:ci.yml"] == "n/a"
assert by["contract:BUILDER-x"] == "n/a"
def test_language_verdicts_measured_authoritative_then_hints(doc):
"""Nick's dichotomy correction: the measured map decides; hints only
label UNMEASURED entities and say so; nothing silently defaults."""
sl.add_entity(doc, id="module:rune_tui", kind="module") # TUI-LAST measured
sl.add_entity(doc, id="module:spine", kind="module") # RUST measured
sl.add_entity(doc, id="module:totally_unknown_name", kind="module")
sl._place_languages(doc)
by = {e["id"]: e["identities"]["language"] for e in doc["entities"]}
assert by["module:rune_tui"] == "python-tui (Wave 6)" # from the MAP
assert by["module:spine"] == "rust" # from the MAP
assert by["module:totally_unknown_name"] == "unclassified"
def test_subsystem_language_from_member_majority(doc):
"""identity: 7 RUST / 3 GO members per classification.json → mixed with
counts carried in the verdict text (never a silent guess)."""
for m in ("behavior", "identity_anchors", "persona_definition",
"persona_gate", "prompt_sync", "voice_hybrid", "voice_injector",
"voice_sync", "voicebox", "safety_override"):
sl.add_entity(doc, id=f"module:{m}", kind="module")
sl.add_relationship(doc, type="belongs_to",
from_id=f"module:{m}", to_id="subsystem:identity",
evidence_refs=["t"])
sl.add_entity(doc, id="subsystem:identity", kind="subsystem")
sl._place_languages(doc)
e = sl.entity(doc, "subsystem:identity")
lang = e["identities"]["language"]
assert lang.startswith("mixed (rust ")
assert "go" in lang
def test_unqualified_discovery_becomes_construction_surface(doc):
"""A bare file path from a closed contract is NOT a module — provenance
preserved, kind honest, candidate stays DECLARED."""
monkey_specs = [("example", [("src/rune/audit_ledger.py",
"construction-surface", "candidate")])]
original = sl._contract_discoveries
sl._contract_discoveries = lambda: monkey_specs
try:
placed = sl._apply_contract_discoveries(doc)
finally:
sl._contract_discoveries = original
assert placed == 1
e = doc["entities"][0]
assert e["id"] == "construction-surface:src/rune/audit_ledger.py"
assert e["kind"] == "construction-surface"
assert e["maturity"] == "DECLARED"
assert e["evidence_refs"] == ["contract-discovery:example"]
def test_legacy_unqualified_module_normalized_with_edges(doc):
sl.add_entity(doc, id="src/rune/claim_audit.py", kind="module",
maturity="PRESENT",
evidence_refs=["contract-discovery:old"])
sl.add_relationship(doc, type="depends_on",
from_id="src/rune/claim_audit.py",
to_id="module:other", evidence_refs=["t"])
sl._normalize_discovery_ids(doc)
assert doc["entities"][0]["id"] == \
"construction-surface:src/rune/claim_audit.py"
assert doc["entities"][0]["kind"] == "construction-surface"
assert doc["relationships"][0]["from"] == \
"construction-surface:src/rune/claim_audit.py"
# Not in the observed set (no closed contract recorded it) → the
# unsupported PRESENT claim is demoted to DECLARED; evidence survives.
assert doc["entities"][0]["maturity"] == "DECLARED"
assert doc["entities"][0]["evidence_refs"] == ["contract-discovery:old"]
def test_discoveries_gather_reads_real_scaffold_store(tmp_path, monkeypatch):
"""The gatherer only trusts CLOSED contracts' ext.contract_quality."""
store = tmp_path / "scaffold"
store.mkdir()
doc = sl.new_doc()
sl.add_entity(doc, id="contract:C1", kind="contract",
ext={"contract_quality": {
"expected_new_observed": ["rust-crate:kernel_x"],
"candidate_corrections": [
{"entity": "suite"}]}})
sl.add_entity(doc, id="contract:C2", kind="contract",
ext={"contract_quality": {
"expected_new_observed": ["rust-crate:never"]}})
for e in doc["entities"]:
if e["id"] == "contract:C1":
e["phase"] = "closed"
if e["id"] == "contract:C2":
e["phase"] = "building"
monkeypatch.setattr(sl, "ROOT", tmp_path)
(tmp_path / "store" / "scaffold").mkdir(parents=True, exist_ok=True)
(tmp_path / "store" / "scaffold" / "current.json").write_text(
json.dumps(doc))
got = sl._contract_discoveries()
assert got == [("C1", [("rust-crate:kernel_x", "rust-crate", "observed"),
("suite", "construction-surface", "candidate")])]
+4
View File
@@ -211,4 +211,8 @@ class TestSpineExtractionNeutrality:
"go-surface",
"config",
"workflow",
# Closed contracts may name files or validation surfaces that
# are not Python modules. Keep their provenance without lying
# about their module identity (issue #2465 CI regression).
"construction-surface",
}
+73
View File
@@ -174,3 +174,76 @@ def test_16k_projection_schema_validated(tmp_path):
assert proj.validate(bad) != []
bad2 = dict(p, schema_version=999)
assert proj.validate(bad2) != []
# ── T5.15 slice 2: the dispatch wire (command → interface execution) ────────
def test_dispatch_executes_accepted_transition_end_to_end(tmp_path):
"""A START command on a draft contract executes through the interface:
the phase actually moves — not just an accepted intent."""
store = str(tmp_path / ".rune" / "scaffold")
iface = cmds if False else None # noqa: F841 — readability anchor
from rune import construction_interface as ci
ciface = ci.ConstructionInterface(builder="seed", project_store=store, project_id="proj")
ciface.scaffold.init(purpose="t")
doc = ciface.scaffold.load()
sc.add_entity(doc, id="contract:disp-1", kind="contract",
identities={"objective": "dispatch"}, evidence_refs=["e"])
doc["entities"][-1]["phase"] = "draft"
ciface.scaffold.commit(doc, what="seed")
out = cmds.dispatch("START", construction_id="disp-1",
store_path=store + "|proj")
# external-project store path: dispatch builds its own interface bound
# to the same store
assert out["executed"] is True, out
assert out["success"] is True, out
doc2 = ciface.scaffold.load()
c = sc.entity(doc2, "contract:disp-1")
assert c["phase"] == "approved"
def test_dispatch_refusal_is_a_valid_protocol_outcome(tmp_path):
"""START on a non-draft contract: the lifecycle refuses — the dispatch
itself succeeds (success=True) with accepted=False."""
store = str(tmp_path / ".rune" / "scaffold")
from rune import construction_interface as ci
ciface = ci.ConstructionInterface(builder="seed", project_store=store, project_id="proj")
ciface.scaffold.init(purpose="t")
doc = ciface.scaffold.load()
sc.add_entity(doc, id="contract:disp-2", kind="contract",
identities={"objective": "x"}, evidence_refs=["e"])
doc["entities"][-1]["phase"] = "draft"
ciface.scaffold.commit(doc, what="seed")
out = cmds.dispatch("START", construction_id="disp-2",
payload={"phase": "building"},
store_path=store + "|proj")
# contract starts in draft so START is ACCEPTED here; drive to building
# first to prove the refusal shape:
assert out["executed"] and out["success"]
out2 = cmds.dispatch("START", construction_id="disp-2",
store_path=store + "|proj")
assert out2["accepted"] is False and out2["executed"] is False
assert out2["success"] is True
assert "draft" in out2["reason"]
def test_dispatch_idempotent_replay_does_not_double_execute(tmp_path):
"""Same command_id twice: the second is a replay — the phase does not
move twice and idempotent_replay=True comes back."""
store = str(tmp_path / ".rune" / "scaffold")
from rune import construction_interface as ci
ciface = ci.ConstructionInterface(builder="seed", project_store=store, project_id="proj")
ciface.scaffold.init(purpose="t")
doc = ciface.scaffold.load()
sc.add_entity(doc, id="contract:disp-3", kind="contract",
identities={"objective": "idem"}, evidence_refs=["e"])
doc["entities"][-1]["phase"] = "draft"
ciface.scaffold.commit(doc, what="seed")
first = cmds.dispatch("START", construction_id="disp-3",
command_id="fixed-cmd-1", store_path=store + "|proj")
assert first["executed"] and first["success"]
second = cmds.dispatch("START", construction_id="disp-3",
command_id="fixed-cmd-1", store_path=store + "|proj")
assert second["idempotent_replay"] is True
assert second.get("executed") in (False, None) # replay ≠ execution
@@ -0,0 +1,115 @@
"""T5.13/T5.14 frozen contracts: pane order and post-response silence.
The pane swap is structural (compose order); the dim-spam consolidation
is behavioral (one collapsed line instead of five dim messages).
"""
from __future__ import annotations
import re
import sys
from pathlib import Path
from types import SimpleNamespace
from unittest.mock import Mock
ROOT = Path(__file__).resolve().parents[1]
sys.path.insert(0, str(ROOT / "src"))
from rune import rune_tui # noqa: E402 — the TUI lives in the package
def test_chat_channel_is_yielded_first_in_compose():
src = (ROOT / "src" / "rune" / "rune_tui.py").read_text()
body = re.search(
r'with Horizontal\(id="channels"\):(.*?)with Horizontal\(id="footer-bar"\)',
src,
re.DOTALL,
).group(1)
order = re.findall(r'ChannelView\(\s*"(\w+)"', body)
assert order == ["chat", "task"], f"compose yields {order}"
def test_resize_actions_follow_the_new_visual_positions():
"""After the swap LEFT=chat, RIGHT=task. resize_left shrinks the LEFT
(chat) — which GROWS the task share; resize_right is the reverse."""
assert "grow the RIGHT (task)" in rune_tui.RuneApp.action_resize_left.__doc__
assert "shrink the RIGHT (task)" in rune_tui.RuneApp.action_resize_right.__doc__
# Behavioral proof against an instance WITHOUT constructing the App
# (reactive initialization needs a running textual app; the docstring
# carries the contract, the arithmetic is what matters).
app = SimpleNamespace(
task_width=50,
action_resize_left=None,
action_resize_right=None,
_apply_resize=None,
)
app._apply_resize = lambda: None
# Bind the real methods onto the stand-in and call them.
rune_tui.RuneApp.action_resize_left(app)
assert app.task_width == 55
rune_tui.RuneApp.action_resize_right(app)
assert app.task_width == 50
def _isolate_collector(monkeypatch, **modules):
monkeypatch.setattr(rune_tui, "BACKEND_AVAILABLE", True)
for name, value in modules.items():
monkeypatch.setattr(rune_tui, name, value)
def test_collector_returns_all_signals_in_one_pass(monkeypatch):
_isolate_collector(
monkeypatch,
provider_budget=SimpleNamespace(
get_status=lambda: {
"providers": {"p": {"monthly_limit": 100, "monthly_used": 90, "token_limit": 0, "tokens_used": 0}}
}
),
claim_audit=SimpleNamespace(scan_text=lambda _t: {"degraded": ["a", "b"]}),
growth_delta=SimpleNamespace(check=lambda: {"delta": "focus: +1"}),
self_improve=SimpleNamespace(run=lambda: None),
)
signals = rune_tui.collect_post_response_signals("response text", messages_count=10)
assert signals == ["⚠ Budget: 90% used", "⚠ Claims degraded: 2", "📈 Growth: focus: +1", "🔄 Self-improvement cycle triggered"]
def test_collector_silence_when_nothing_fires(monkeypatch):
_isolate_collector(
monkeypatch,
provider_budget=Mock(get_status=lambda: {"providers": {}}),
claim_audit=Mock(scan_text=lambda _t: None),
growth_delta=Mock(check=lambda: None),
self_improve=Mock(run=lambda: None),
)
collector = rune_tui.collect_post_response_signals
app_signals = collector("plain", messages_count=7) # not a cycle multiple
assert app_signals == []
def test_collector_never_raises_on_backend_noise(monkeypatch):
def boom(*_a, **_k):
raise RuntimeError("backend gone")
_isolate_collector(
monkeypatch,
provider_budget=Mock(get_status=boom),
claim_audit=Mock(scan_text=boom),
growth_delta=Mock(check=boom),
self_improve=Mock(run=boom),
)
assert rune_tui.collect_post_response_signals("x", 10) == []
def test_self_improve_only_at_cycle_multiple(monkeypatch):
ran = []
_isolate_collector(
monkeypatch,
provider_budget=Mock(get_status=lambda: {"providers": {}}),
claim_audit=Mock(scan_text=lambda _t: None),
growth_delta=Mock(check=lambda: None),
self_improve=Mock(run=lambda: ran.append(1)),
)
rune_tui.collect_post_response_signals("x", 7)
assert ran == []
rune_tui.collect_post_response_signals("x", 10)
assert ran == [1]