Commit Graph

28243 Commits

Author SHA1 Message Date
Teknium da388692e4 refactor(agent/aux): one _field accessor for dict/object wire payloads 2026-09-02 13:32:58 -07:00
Teknium 6320c54552 refactor(agent/aux): _to_async_client header selection via _endpoint_default_headers 2026-09-02 13:32:56 -07:00
Teknium 0d41e9bdbc refactor(agent/aux): shared pool loader; restore @_relay_auxiliary_call placement on call_llm 2026-09-02 13:32:55 -07:00
Teknium 14ec5874a5 refactor(agent/aux): collapse cancel-check readers and Codex-route model predicates 2026-09-02 13:32:53 -07:00
Teknium c90af45f57 refactor(web): unify the three post-config gateway auto-restart helpers 2026-09-02 13:32:52 -07:00
Teknium b40d76823f refactor(agent/aux): shared creds-pair and Nous pool entry-state helpers 2026-09-02 13:32:51 -07:00
Teknium f2c506845b refactor(web): unify device-code poller lifecycle into _oauth_poller decorator 2026-09-02 13:32:49 -07:00
Teknium 9001ed2365 refactor(agent/aux): shared _prepare_aux_request head for call_llm/async_call_llm 2026-09-02 13:32:49 -07:00
Teknium ba4f4b8161 refactor(web): collapse try/except-HTTPException/log/raise boilerplate into _common.http_failure; trim unused fastapi imports 2026-09-02 13:32:46 -07:00
Teknium d46aa77cde refactor(agent/aux): extract named-custom credential resolution, Bedrock and Vertex client builders out of resolve_provider_client 2026-09-02 13:32:45 -07:00
Teknium 8ac12223bb refactor(web): late() proxies replace per-handler lazy web_server imports in extracted routers 2026-09-02 13:32:45 -07:00
Teknium e3d352872b refactor(agent/aux): shared chain-label aliases, context-window screen, event-loop helper 2026-09-02 13:32:41 -07:00
Teknium 575cd5f34e refactor(agent/aux): shared hook ticker and _is_specialized_aux_client predicate 2026-09-02 13:32:41 -07:00
Teknium ba91166b1c refactor(web): hoist stdlib imports in extracted routers; drop unused web_server imports 2026-09-02 13:32:28 -07:00
Teknium ff660354f3 refactor(kanban): CLI micro-helpers, action dispatch tables, shared triage helpers; active_sessions dedupe
hermes_cli/kanban.py 3,565 -> 2,912; kanban_diagnostics 1,216 -> 996;
kanban_decompose 468 -> 393; kanban_transfer 478 -> 443; kanban_specify
264 -> 229; kanban_swarm 390 -> 378; active_sessions 871 -> 775. `hermes kanban
[sub] --help` byte-identical for all 55 parsers.

- kanban.py: _err / _print_json / _json_out / _fmt_counts / _bulk_apply /
  _obj_dict field tuples replace repeated print/JSON/exit-code blocks; action
  and board subcommand routing via dict dispatch; shared run-state and
  triage-sweep argparse blocks; argparse declarations re-packed (AST-identical).
- specify/decompose: one _run_triage_sweep driver, shared _extract_json_blob /
  _truncate / _profile_author / _title_body / _resolve_profile_from_cfg.
- diagnostics: rule helpers (_first_field / _latest_event_ts / _log_hint_action
  / _error_snippet), _rows_by_task fleet fetch; unreferenced DIAGNOSTIC_KINDS dropped.
- swarm: graph nodes share one create_task kwarg set.
- active_sessions: one _flock per platform, _pid_alive via _pid_liveness,
  shared _read_live_entries / _without_lease / _clean_metadata, table-driven
  strict registry validation.
- Docstrings/comments hand-compacted (AST-identical), invariants kept.
2026-09-02 13:32:14 -07:00
Teknium 841c975d43 refactor(kanban): unify kanban_db SQL/row/JSON/env/git boilerplate; table-drive migrations
hermes_cli/kanban_db.py 12,153 -> 11,157 LOC, behavior-neutral.

- _row_get / _json_or / _json_dict / _env_int / _git_out applied at every
  duplicate site; Event/Comment/Attachment.from_row row mapping.
- Scalar-read helpers (_task_status, _latest_event, _scratch_workspace,
  _has_spawnable, _current_run_id, _parents_satisfied) replace repeated
  conn.execute(...).fetchone() blocks.
- _migrate_add_optional_columns and add_notify_sub column refreshes are
  table-driven (same statements, same order).
- _dispatch_lane_task unifies the ready/review lane tails; _claim_and_open_run
  and _reclaim_dangling_run shared by claim paths; block_task's three UPDATE
  branches and complete_task's UPDATEs collapsed to one statement each.
- connect() PRAGMA/WAL setup shared via _open_configured; _probe_integrity
  shared by the health guard and repair; _try_lock_nb/_unlock shared by the
  init and dispatch file locks; _insert_comment for in-transaction audit rows.
- Dead: parent_results (zero refs).
- Long docstrings hand-compacted, every invariant kept. Schema SQL untouched.
2026-09-02 13:32:14 -07:00
Teknium d15c61b5dc refactor(state): split SessionDB into domain mixins and free-function modules; unify SQL boilerplate
hermes_state.py 17,220 -> 6,442 LOC. Behavior-neutral: every moved body is
AST-identical to the original, verified per extraction.

SessionDB core
- _write_sql / _write_rowcount / _read_one / _read_all replace ~120 copies of
  the `def _do(conn): conn.execute(...)` + `_execute_write(_do)` and
  `with self._read_ctx() as conn: row = conn.execute(...).fetchone()` shapes.
- _set_lineage_column replaces four copies of the recursive compression-lineage
  UPDATE (archived / pinned / hidden / last_read_at).
- _read_session_number unifies the three compression counter readers.
- Dead (zero refs repo-wide): restore_rewound, delete_gateway_routing_entries,
  _is_duplicate_replayed_user_message, SessionPortabilityMixin.get_first_assistant_text.

New mixins bound onto SessionDB via the MRO (logger name stays "hermes_state"):
  hermes_state_messages    SessionMessagesMixin       48 methods
  hermes_state_compression SessionCompressionMixin    30
  hermes_state_gateway     SessionGatewayMixin        26
  hermes_state_maintenance SessionMaintenanceMixin    13
  hermes_state_usage       SessionUsageMixin          12
  hermes_state_titles      SessionTitlesMixin         13
  hermes_state_telegram    SessionTelegramTopicsMixin 11
Origin-internal symbols resolve through a lazy `from hermes_state import ...`
inside the few methods that need them (no import cycle).

New free-function modules, every name re-imported into hermes_state so
`hermes_state.<name>` (and test monkeypatches on it) keep working; intra-module
calls to patched helpers go through the lazy origin import:
  hermes_state_repair   repair/backup/preflight (43 defs)
  hermes_state_wal      journal-mode / PRAGMA policy (33 defs)
  hermes_state_dbfile   header probes, zeroed-db quarantine, stats, holders (21 defs)

Existing mixins: search — shared FTS MATCH/LIKE builders, unified rebuild
status/step/finish engines, state_meta helpers; schema — one legacy/v23 FTS init
branch, shared _live_pk_columns, Row/tuple dual access dropped; portability —
shared _PREVIEW_RAW_SUBQUERY_SQL and _rich_row; common — single
stat_db_file_identity (was 3 copies), AUTO_VACUUM_MIN_FREELIST_RATIO.

Docstrings/comments hand-compacted (AST-identical) keeping every invariant,
ordering rule, failure mode and WHY. Schema SQL, migration order and PRAGMAs
untouched. test_repair_path_has_no_bare_connects repointed to hermes_state_repair.
2026-09-02 13:32:13 -07:00
Teknium 5dfda6a615 refactor(agent/aux): compact _fallback_destination 2026-09-02 13:32:12 -07:00
Teknium 28c3cb1561 refactor(agent/aux): shared _endpoint_default_headers, single primary-attempt closure in call_llm impls, vision tail dedupe 2026-09-02 13:32:09 -07:00
Teknium e4d8a78967 refactor(web): move /api/logs into web_routers/status.py (logs_router) 2026-09-02 13:32:08 -07:00
Teknium 936c8bb626 refactor(agent/aux): split _CodexCompletionsAdapter.create into request build / final-response parse; dedupe stream/client close paths 2026-09-02 13:32:07 -07:00
Teknium de109d4097 refactor(web): extract chat-tab WebSocket routes into web_routers/chat_ws.py 2026-09-02 13:32:06 -07:00
Teknium 4bae44d654 refactor(web): extract dashboard theme/font/plugin routes into web_routers/dashboard_ui.py 2026-09-02 13:32:05 -07:00
Teknium 312378d9b1 refactor(agent/aux): unify _read_main_{model,provider,api_key,base_url} and relay call-context builders 2026-09-02 13:32:03 -07:00
Teknium 94309ad40a refactor(web): extract raw-config + analytics routes into web_routers/analytics.py 2026-09-02 13:32:02 -07:00
Teknium 067028eb22 refactor(web): extract OAuth provider routes into web_routers/oauth.py 2026-09-02 13:32:01 -07:00
Teknium 4022e69e69 refactor(agent/aux): lift max_tokens forwarding policy and Nous dual-wire check out of _build_call_kwargs 2026-09-02 13:32:00 -07:00
Teknium dcbf263a09 refactor(agent/aux): unify same-provider retry and fallback-candidate prep across sync/async (_prepare_same_provider_retry, _plan_fallback_candidate) 2026-09-02 13:31:57 -07:00
Teknium 127a179ae5 refactor(agent/aux): share call_llm/async_call_llm route resolution (_resolve_call_client) and recovery ladder (_aux_recovery_ladder generator) across sync/async wires 2026-09-02 13:31:57 -07:00
Teknium 659c6b9fff refactor(gateway): simplify session, status, stream_consumer, kanban_watchers, relay adapter, hosted-room driver/discussion/replicas, shutdown/lifecycle, pairing, channel_directory, control_socket and small modules 2026-09-02 13:31:54 -07:00
Teknium aed6720dab refactor(gateway/run, slash_commands): dispatch tables, helper unification and hand-reviewed comment compaction
run.py:
- built-in adapter creation: 9-branch if/elif -> _BUILTIN_ADAPTERS table
- idle slash-command routing: 35 `if canonical == ...` branches -> _gateway_idle_command_handlers()
- shared helpers: _send_command_ack (4 sites), _command_origin_for_source (2), _session_entry_for_manager
  (goal/heartbeat), _toggle_adapter_auto_tts_set (2), _load_env_or_agent_cfg_timeout (2), _float_env reuse (2),
  _resolve_session_key_or_none (3), _running_agent_ids (4), _schedule_rename_from_title_thread (2),
  _write_runtime_status_quiet (5), _AUTO_RESET_CONTEXT_NOTES/_auto_reset_reason_text
- ruff SIM102/SIM103/SIM105/SIM108/SIM118 + F401 across gateway/ (semantics re-reviewed; sqlite Row
  `.keys()` and side-effecting assignments kept)
- two hand-reviewed comment/docstring compaction passes (AST-identical, rationale kept)

slash_commands.py:
- /model: typed path and picker callback shared one 200-line commit block -> _perform_model_switch +
  _commit_model_switch
- comment/docstring compaction (AST-identical)
2026-09-02 13:31:53 -07:00
Teknium cc9ef82355 refactor(gateway-cli): dispatch-table subcommands and shared service helpers in hermes_cli/gateway.py
hermes_cli/gateway.py (9178 -> 6906):
- `hermes gateway` subcommand routing: if/elif chain -> _GATEWAY_SUBCOMMANDS dispatch table of
  _cmd_* handlers; _stop_installed_service and _refuse_from_inside_gateway unify the
  stop/restart/uninstall service-stop and self-target guards.
- One systemd unit template; _systemctl_show, systemctl reset+action, is-active probes,
  _installed_service_kind ladder (3 sites), launchctl-list PID probe, launchd bootstrap+kickstart
  helper, legacy-unit removal loop, loop-tick witness ping, ps/wmic line parsers, planned-stop
  marker helper, _CAPTURE_TEXT subprocess kwargs (21 sites), _gw_windows() accessor (15 lazy
  imports).
- run_gateway startup helpers, reaper exclusion set, Windows process listing extracted; wizard
  service actions and platform-setup prompts unified (_setup_service_action).
- Dead: _windows_scheduled_task_running (test-only), _container_systemd_operational (inlined),
  whatsapp/email/matrix built-in status branches (those platforms are registry plugins).
- try/except-pass around single statements -> contextlib.suppress; comments/docstrings compacted
  to the WHY (bounded_probe_run vs subprocess.run on Windows, pythonw launcher-stub filtering,
  raw-record vs validated-probe exclusion in the orphan reaper, Scheduled-Task Ready-vs-Running).
- `hermes gateway --help` byte-identical.
2026-09-02 13:31:44 -07:00
Teknium 75bafc197a refactor(plugins): unify provider registration and unload paths in hermes_cli/plugins.py
hermes_cli/plugins.py (7193 -> 4961):
- _register_scoped_provider: one body for the 8 scope-keyed register_*_provider methods;
  _track_callback/_track_mapping_entry unify manager-mapping lease tracking (4 sites);
  _track_scoped_registration for the ownership ledger. Public method names, signatures,
  return values and warning strings unchanged.
- Manifest v2 type checks table-driven (_manifest_field_of_type); _unload_scoped split into
  _unload_target_keys + _reset_after_unload_all; _gate_manifest/_record_placeholder out of
  _discover_and_load_inner; _track_tool_override_policy/_attribute_registrations out of
  _load_plugin_scoped; bounded hook worker lifted into _run_hook_callback_bounded;
  prompt-section rendering extracted; resolve_pre_tool_block delegates to
  _dispatch_pre_tool_call_hooks; _evict_modules (3 sites); _remove_name_if_unowned and
  _nowait_plugin_set unify unowned-name cleanup and *_nowait probes.
- Dead (zero references outside their own test): unload_plugins, has_portable_mcp_servers,
  _classify_entrypoint_kind, _reset_event_bus, get_plugin_subscriptions,
  get_telegram_handler_factories, pass-through _restore_* helpers; _env_enabled is now an alias
  of utils.env_var_enabled (plugins/memory still imports it).
- Docstrings/comments compacted; contract sentences and rationale kept (multi-profile ledger
  keying, persistent auth-provider registration, capability declaration is not a grant).
2026-09-02 13:31:44 -07:00
Teknium 13fb87af92 refactor(cron): decompose scheduler run_job/_deliver_result and dedupe delivery lanes
cron/scheduler.py (8535 -> 6353):
- _deliver_result split into per-target helpers: _resolve_target_transport (live/relay/standalone
  transport + enablement), _deliver_via_live_adapter (_live_route_metadata for Telegram DM-topic
  vs forum routing, _live_send_text with the cancel()-based timeout disambiguation,
  _live_send_media, _seed_live_delivery_sessions), _standalone_send/_deliver_standalone. The
  three interpreter-shutdown skip branches and the repeated log+append+continue pattern collapse
  into one _note_target_error / one shutdown message; _TargetDelivery carries per-target state.
- Thread/channel session seeding unified into _seed_cron_session (was two near-identical
  functions).
- run_job decomposed into _run_no_agent_job, _apply_monitor_gate, _load_cron_job_config
  (_CronJobConfig), _resolve_job_runtime, _check_model_drift, _open_cron_session_db,
  _run_agent_with_watchdog, _finalize_cron_session, plus one _run_doc_header and one _audit
  closure for the success/failure paths.
- _run_one_job_body: ownership-lost bookkeeping, delivery composition and outcome classification
  extracted; tick: _acquire_tick_lock/_release_tick_lock, _maybe_reap_dead_owners,
  _sweep_stale_inflight_for_tick, _process_due_job, _submit_with_guard.
- _build_job_prompt: context_from injection and skill loading extracted; one
  _prepend_context_block for the four fenced-data blocks.
- One _start_heartbeat_thread for the script- and fire-claim heartbeat threads.
- Dropped unreachable return in SharedRouteAdapters.get; boolean-return and nested-if shapes
  collapsed.
- Comments/docstrings compacted by hand, rationale kept (fd-leak reason for the late SessionDB
  close callback, title-persistence rules, no_agent classification gate, inactivity-vs-provider
  timeout ordering, stale-claim force-release, interruption token keying).
2026-09-02 13:31:43 -07:00
Teknium d3b768232e refactor(web): extract status/health/curator/learning/portal routes into web_routers/status.py 2026-09-02 13:30:56 -07:00
Teknium 094dba5a2f refactor(web): extract gateway/update/action-status routes into web_routers/actions.py 2026-09-02 13:30:55 -07:00
Teknium 401efb0b2b refactor(cli): decompose _cmd_update_impl into phase helpers, unify duplicated update helpers, compact comments
hermes_cli/update_cmd.py 11217 -> 10204 LOC; _cmd_update_impl 2797 -> 521 LOC.

Decomposition (behavior-neutral, AST free-name verified) — _cmd_update_impl is
now a thin orchestrator calling, in order:
  _clear_windows_venv_holders_or_exit -> _prepare_checkout_for_update
  (-> _CheckoutPlan) -> _repair_current_checkout | _pull_updates ->
  _sync_python_dependencies_after_pull -> _run_post_update_maintenance ->
  _restart_gateway_fleet_after_update (-> _GatewayRestartOutcome;
  _restart_systemd_gateway_units) -> _resume_windows_gateways_and_merge_outcome
  -> _verify_fleet_after_update. _resolve_manage_cmd hoisted to module level.

Unified helpers: _git_run (49 captured git subprocess.run sites),
_systemctl / _systemctl_reset_and_restart (17 sites + 2 pairs),
_sweep_bytecode_after_update (3x), _print_bundled_skills_sync_report (ZIP+git),
_ensure_venv_pip (ZIP+git), _self_and_non_gateway_ancestor_pids (2x),
_record_update_step (4x), _write_gateway_update_exit_code for the 3 inline
".update_exit_code" writes. Dropped duplicate nested copies of
_wait_for_service_active/_service_restart_sec/_print_items, dead
upstream_exists, a dead if/pass branch and unused imports.

Comments/docstrings hand-compacted (236 blocks, AST-identical with docstrings
normalized); rationale/invariant sentences kept.

Tests: source-inspection guards repointed to the helper that now owns the code
(test_update_self_lock, test_update_fleet_check_fail_closed,
test_update_apply_shallow_count); new regression test drives the real Windows
resume/merge helper.
2026-09-02 13:30:54 -07:00
Teknium 9de17448dd refactor(web): extract audio/TTS routes into web_routers/audio.py 2026-09-02 13:30:53 -07:00
Teknium feeb1074a3 refactor(web): extract config/env/custom-endpoint routes into web_routers/config_env.py 2026-09-02 13:30:53 -07:00
Teknium 1f4ab19eae refactor(web): extract model assignment routes into web_routers/models.py 2026-09-02 13:30:53 -07:00
Teknium 11bc6bbe11 refactor(web): extract memory-provider setup routes into web_routers/memory_providers.py 2026-09-02 13:30:51 -07:00
Teknium ffd628c3ee refactor(gateway/config): table-drive _apply_env_overrides via env-extra/home-channel helpers; extract plugin enable pass 2026-09-02 13:30:50 -07:00
Teknium 1f77a129da refactor(web): extract messaging onboarding/platform routes into web_routers/messaging.py 2026-09-02 13:30:50 -07:00
Teknium 3c7069bdcb refactor(gateway): dead-code removal, helper unification, defensive-layer collapse and rationale-preserving comment compaction across 40 modules
authz_mixin, browser_control_broker, delivery, delivery_ledger, display_config, drain_control,
hosted_room_links/peer/policy_checkpoint, hosted_rooms, platform_registry, relay/__init__,
relay/ws_transport, run.py and slash_commands.py (comments), session_context, session_state,
streaming_tts_consumer, turn_lease and small modules.

- HostedRoomPolicyCheckpoint._apply_event -> per-kind handler table
- WebSocketRelayTransport._handle_frame -> frame-handler table
- GatewayAuthorizationMixin: unified adapter setting/flag/extra readers
- dead symbols removed (verified zero references): RoomLinkProbe/select_room_link,
  relay_bot_username, is_restart_loop_tripped, debug_rows, DeadTargetRegistry.all_dead,
  BrowserControlBroker.detach_owner/_prune_tickets, StreamingTTSConsumer.started/_enqueue_done/
  _iter_stream_chunks/_next_stream_chunk, RecoverableHandleCache.status_for, _auth_env,
  _copy_default_catalog, _parse_timestamp_prefix, _present_* helpers, _send_result_error_kind,
  _truthy_env, SessionFieldView/TurnLeaseTokenView dunder shims, and their orphaned tests.
- lost WHY/invariant text from the earlier compaction restored compactly (541 hunks audited)
2026-09-02 13:30:50 -07:00
Teknium 0cca195418 refactor(web): extract pairing/webhooks/credential-pool/memory/ops routes into web_routers/ops.py 2026-09-02 13:30:50 -07:00
Teknium 3b1ecfc0a1 refactor(cli): decompose list_authenticated_providers and switch_model
model_switch.py (4405 -> 3712):
- list_authenticated_providers (1367 lines) is a thin driver over _PickerBuild
  state and one builder per section (_lap_builtin_rows, _lap_overlay_rows,
  _lap_canonical_rows, _lap_user_provider_rows, _lap_bare_custom_row,
  _lap_custom_provider_rows). Credential checks shared with
  _collect_authed_provider_slugs are single-copy helpers
  (_iter_builtin_candidates, _auth_store_has_provider, _raw_pool_usable,
  _pool_usable, _overlay_has_env_creds, _has_aws_sdk_creds_for_listing);
  live/curated lookup (_live_or_curated_ids, _aws_live_or_curated_ids,
  _nous_picker_model_ids), endpoint discovery (_discover_endpoint_models) and
  config-entry parsing are deduped across sections 1/2/2b/3/3b/4.
- switch_model: _switch_fail, _runtime_creds, _entry_configured_key,
  _ollama_configured_base, _unknown_provider_message, _aggregator_alias_error,
  _aggregator_catalog_match, _config_declares_model,
  _apply_direct_alias_endpoint replace inline blocks; four copies of the
  resolve_runtime_provider unpack collapse to one.
- _model_sort_key: one _flush() for the four repeated version-flush blocks
  (identical on 400k random ids).
Row dicts, ordering, error strings and lazy-import patch points unchanged;
picker rows and the interactive hermes model screen byte-identical vs base.
2026-09-02 13:30:39 -07:00
Teknium 369ebf7532 refactor(agent/aux): resolve_provider_client — single _route() for sync/async return, dedupe named-custom OpenAI-wire build 2026-09-02 13:30:38 -07:00
Teknium 313b244e8f refactor(plugins/model-providers): reuse agent.reasoning_effort clamps, per-model dict tables, compact profiles 2026-09-02 13:30:28 -07:00
Teknium c408601937 refactor(agent/review): simplify curator, background_review, verify, insights, title and learning modules (-22% LOC)
Cluster: agent/{curator,curator_backup,background_review,review_engine,
review_idle_queue,insights,learning_graph,learning_graph_render,
learning_mutations,learn_prompt,verification_evidence,verification_stop,
verify_hooks,side_question,title_generator,turn_summary,
manual_compression_feedback,trajectory,moa_trace,trace_upload,verify/*}.
13662 -> 10693 LOC (-2969, -21.7%), behavior-neutral.

- Dead code: 27 private helpers with zero references removed
  (_auto_title_session, _resolve_review_model, _parse_make_targets,
  _filter_verifiable_paths, _find_subsequence, _is_under_root/_temp_dir,
  _merge_runs, learning_graph_render bucket/period/node helpers,
  _memories_dir/_memory_local_index/_node_detail, _cron_jobs_file,
  _retention_cutoff, _scope_for_args, _clean_token, _count_diff_lines,
  _ordered_verbs, _hermes_meta, _iter_skill_files).
- Unified helpers: _read_config_section (curator + curator_backup),
  _write_file/_write_json (4 curator report writers), _msg_text
  (background_review <- side_question), _report_failure/_notify_title
  (title_generator instant/auto paths), _is_under (verification_evidence),
  _scoped SQL pair builder + _query (insights), _optional_lock
  (background_review), verify.recipes table-driven detection.
- if/elif routing -> dict dispatch: side_question role labels,
  curator_backup summary bits, learning_graph_render buckets, insights
  section rendering, verify recipe pickers.
- Redundant defensive layers, single-use wrappers and verbose narrative
  comments collapsed; every non-obvious WHY/invariant kept in compact form.

Verification: parity.py (all REMOVED symbols zero-ref), import smoke for
every module + cli/run_agent/gateway.run/hermes_cli.main/
agent.conversation_loop/tui_gateway.server, old-vs-new fuzz parity on all
shared pure functions, SQL trace parity for insights and
verification_evidence, cluster tests 1354 passed / 0 failed (46 files).
2026-09-02 13:30:25 -07:00
Teknium ab48b1ddc5 refactor(agent): extract per-call API message build into turn_context.build_api_messages 2026-09-02 13:30:23 -07:00