32 KiB
TinyAgents Migration — Current-State Audit & Consolidated Plan (2026-07-22)
Status: audit + plan (supersedes the stale status/phasing in
tinyagents-port-plan.md, tinyagents-inference-migration-plan.md, and
tinyagents-phase3-router-registry-design.md; the drift ledger
tinyagents-drift-ledger.md remains the row-level ledger but its anchors are
behind — see §2).
Scope: move the remaining generic inference + agent-framework code from
src/openhuman/ down into the vendored tinyagents crate
(vendor/tinyagents), delete the in-tree duplicates, migrate/retire the
affected tests, and clean up every dangling doc/code reference left behind by
earlier phases.
Method: fresh four-way audit of (1) the crate surface, (2)
src/openhuman/inference/, (3) the agent domains + the
src/openhuman/tinyagents/ seam, (4) the existing docs/tests — all against the
working tree at main (5b8a9f269, 2026-07-22).
Execution status: active on feat/tinyagents-provider-cleanup.
WP-0 discovered and corrected an additional cross-crate constraint: once the
vendored manifest honestly reports 2.1, tinyflows must also require
TinyAgents 2.1 or Cargo resolves a second 1.9 copy and splits trait identity.
The deletion ledger is
tinyagents-full-migration-plan/99-deletion-ledger.md.
1. Executive summary
The migration is much further along than any existing doc records, and the remaining work is now well-bounded:
- The agent loop has run on
tinyagentssince #4249/#4399; the drift ledger's Phase 0 rows are all CLOSED and Phase 1 is mostly closed. - Since the docs were last touched, PRs #4769, #4780, #4782, #4783, #4784
landed the model-layer inversion: the managed backend, wire-equivalent BYOK
slugs, and openai/codex/custom slugs are all crate-native
ChatModels; the crateModelRouteris adopted; andcompatible*.rsis already deleted (collapsed into a singlelegacy_provider.rsfacade). - What remains falls into six work packages (§5): finish the model-layer
cutover and delete the legacy
Providerstack (~9–10k LOC); record that the legacyrun_turn_enginewas already retired; consolidaterouting/,tool_timeout/,tool_status/,model_council/onto crate primitives; reconcile the tool model (the one genuinely design-gated package); shrink the seam; and a housekeeping package (version-pin reconciliation + broken-link cleanup) that should go first because the current pin state is misleading.
Nothing in this plan touches the CEF shell, the frontend, or the compile-time feature gates; the crate stays impossible to gate away (26+ domains consume it).
2. Ground truth: version pins (WP-0 reconciled)
| Fact | Value | Where |
|---|---|---|
| Host requirement | tinyagents = { version = "2.1", features = ["sqlite"] } |
root Cargo.toml:107 |
| Path override | [patch.crates-io] tinyagents = { path = "vendor/tinyagents" } |
Cargo.toml:677 |
| Historical fork patch | Removed in WP-0; TinyCortex now declares crates.io 2.1, so the existing host path patch unifies its dependency too |
root and Tauri manifests; TinyCortex #121 |
| Vendored crate | version = "2.1.0", tag v2.1.0 / 2583fcc, edition 2024, GPL-3.0-only |
vendor/tinyagents/Cargo.toml, gitlink |
| Included since the audit | bytes bump (#59), BarrierRelief graph fan-in primitive (#62), v2.0/v2.1 release commits |
submodule history |
| TinyFlows requirement | tinyagents = "2.1"; prevents Cargo resolving a second 1.9 crate |
vendor/tinyflows/Cargo.toml |
| TinyCortex requirement | tinyagents = "2.1"; its repo-local patch serves standalone development while host patches select the canonical copy |
vendor/tinycortex/Cargo.toml |
| Drift ledger | Current pin v2.1.0 / 2583fcc |
docs/tinyagents-drift-ledger.md §Anchors |
WP-0 bumped the gitlink to the released v2.1.0 manifest, regenerated both Cargo worlds, removed the unused fork-source patch, and aligned TinyFlows and TinyCortex to 2.1. Before those transitive alignments, correct dependency resolution introduced separate TinyAgents 1.9 and nested-path 2.0 packages; the lockfiles now prove the root, TinyFlows, and TinyCortex all use the one vendored 2.1 package.
3. What the crate ships (v2.1.0)
Full module map from the crate audit; the items relevant to the remaining work:
- Model layer:
harness::model::{ChatModel<State>, ModelRegistry, ProviderError}(vendor/tinyagents/src/harness/model/types.rs:524,563,450),MODEL_CONTEXT_PATTERNScontext-window table (model/mod.rs:51). - OpenAI-compatible client:
harness::providers::openai::{OpenAiModel, AuthStyle, ReasoningTagExtraction}with SSE streaming, the/v1/responsesAPI + codex knobs (#51), configurable auth styles/static headers (#44), temperature suppression (#47),merge_system_into_user(#48), prompt-guided tool calling for non-native models (#55), stream→JSON fallback (#56), and the whole #57 local-model hardening wave (inline<think>extraction, 400-degrade oftool_choice/json_object, malformed tool-call recovery). This is the replacement for everythinglegacy_provider.rsstill does. - Retry/fallback/error classification:
harness::retry::{RetryPolicy, FallbackPolicy, ProviderFailureClass, classify_provider_failure, is_retryable}(harness/retry/types.rs:28,retry/mod.rs:170,396) — already wired into the crate's transport and SSE paths. - Routing:
registry::router::{ModelRouter, WorkloadRoute}(#54) — adopted host-side by #4783; plusregistry::catalog::ModelCatalog(windows, pricing, capability flags, offline snapshot atdocs/modules/registry/model-catalog.snapshot.json). - Tools:
harness::tool::{Tool<State>, ToolSchema}+ schema validation (harness/tool/types.rs:344,tool/schema.rs),ToolTimeout, tool-policy middleware (harness/middleware/library/tool_policy.rs). - Subagents/orchestration:
harness::subagent::{SubAgent, SubAgentSession, SubAgentTool},graph::orchestration::{TaskStore, SteeringRegistry, OrchestrationTool, InMemoryTaskStore, JsonlTaskStore},graph::subagent_node,graph::parallel::map_reduce, and (post-bump)BarrierRelieffan-in. - Embeddings: provider implementations ported at HEAD (#58 —
openai,cohere,voyage,ollama,cloud, rate-limit/retry-after helpers). - Observability: harness + graph journals/status stores,
JsonlSink,RedactingSink, Langfuse client with nested run trees (#53). - Also present: summarization (
Summarizer,CompressionFailurePolicy), steering, workspace isolation, response cache, cost/usage accounting (parsescached_tokens), graph checkpointing (SQLite via thesqlitefeature the host enables), and offlineMockModel/testkit conventions.
~25 public traits are the extension points; the seam already implements 11 of them (§4.3).
4. Audit: what remains host-side
4.1 src/openhuman/inference/ — 112 files, ~46.5k LOC
The model-layer inversion (#4727 "Motion B") is scaffolded and mostly cut over,
but the legacy Provider stack is still present and still the default
construction path in places:
Still-duplicating cluster (delete in WP-1):
| File | LOC | State |
|---|---|---|
provider/traits.rs (+traits_tests.rs) |
779 + 501 | The Provider trait + ChatMessage/ChatRequest/ChatResponse/ProviderDelta/UsageInfo. Still central; ~10 impls remain. |
provider/reliable.rs (+reliable_tests.rs) |
952 + 1,228 | Retry/backoff Provider wrapper. Crate RetryPolicy covers it; the interactive turn path already stopped wrapping in ReliableProvider (tinyagents/mod.rs:122). |
provider/router.rs (+router_tests.rs) |
310 + 524 | RouterProvider hint-table routing. Crate ModelRouter adopted by #4783; this is the residual legacy path. |
provider/legacy_provider.rs |
343 | The collapsed remnant of the 15 compatible*.rs files (provider/mod.rs:14 aliases pub use legacy_provider as compatible;). Superseded by crate OpenAiModel once WP-1 flips the default. |
provider/error_classify.rs + error_code.rs |
1,001 + 349 | Split (WP-1): generic retryability/status classification → crate classify_provider_failure; openhuman semantics (Sentry demotion, budget messaging, config_rejection.rs, billing_error.rs) stay as a host classifier layered on crate errors. |
provider/crate_provider.rs |
327 | CrateBackedProvider — the temporary reverse adapter (crate ChatModel → legacy Provider). Deleted last, when no consumer needs Provider. |
Crate-native scaffolding already in place (finish in WP-1):
provider/crate_openai.rs(347) — hostAuthStyle→ crateOpenAiModelbuilder; self-described "Status: scaffolding" — complete and unit-tested but not yet the factory default. Flipping it (with per-provider wire parity validation) is the gating step.provider/openhuman_backend_model.rs(325) — managed backend as crateChatModel(cut over; coexists with the legacyopenhuman_backend.rstwin, which can go once nothing constructs it).provider/factory.rs(2,850) — the host↔crate boundary; already returnsArc<dyn ChatModel<()>>viacreate_chat_model*, but bespoke slugs still route "→ aProviderModelover the host provider" (factory.rs:1458-1511).model_context.rs— already falls through to the crate table (context_window_for_model_id,model_context.rs:77); keeps host config overrides. Done; keep the thin shim.ops.rs,local/ops.rs,http/server.rsalready build crateModelRequest/Messagetypes.
Seam concerns mis-housed under provider/ (re-home in WP-1):
temperature.rs (261), thread_context.rs (120), resolved_route.rs (113),
auth_error_registry.rs (166).
Host-owned, stays (no action): all of local/ (~14k — Ollama/LM Studio/
Whisper/Piper runtime + installers + service admin), voice/ (~2.4k),
openai_oauth/ (~1.5k), http/ (0.7k /v1 server), provider/ops/ (RPC),
bespoke Provider/ChatModel impls (claude_code/ ~2.7k,
claude_agent_sdk/, openai_codex.rs, openhuman_backend*.rs), and the root
host files (schemas.rs, presets.rs, model_ids.rs, paths.rs, parse.rs,
sentiment.rs, device.rs).
Blast radius: 187 files import openhuman::inference; 158 import
inference::provider (grown from the old plan's 170/151). Top consumers:
agent/harness/session/tests.rs (33 hits), core/observability.rs (31),
tinyagents/mod.rs (15), web_chat/web_errors.rs, routing/factory.rs,
agent/harness/subagent_runner/ops/{graph,runner}.rs, voice/, flows/ops.rs,
config/ops/model.rs, channels/context.rs.
4.2 Agent domains
| Domain | Files / LOC | Disposition |
|---|---|---|
agent/ |
144 / 66.9k | Mostly stays (product brain). 37 files already crate-backed. WP-3 verified that session/turn/core.rs is the product turn-preparation shell and subagent_runner/ops/graph.rs unconditionally calls run_turn_via_tinyagents_shared; the legacy loops and runtime escape hatches were removed before this audit. Heaviest coupling in the tree (config=31, memory=20, event_bus=13 files). |
agent_orchestration/ |
64 / 27.9k | Engine already on tinyagents::graph (workflow runs, teams, delegation, map_reduce); what remains is the product layer (ledgers, RPC). Residual upstream item: detached-subagent TaskStore lifecycle — WP-5. 25 files crate-backed. |
routing/ |
8 / 2.7k | Deleted in WP-2. A repository-wide reference audit found no consumer outside the module; #4783's crate ModelRouter already owns the live path, so retaining the nominally host-specific health/provider files would preserve an unreachable parallel stack. |
model_council/ + council_registry/ |
8 / 1.7k | Deleted after WP-2 audit. Generic fan-out already used crate parallel::map_reduce; upstream dead-code cleanup removed the remaining unreachable product and registry surfaces. |
tool_timeout/ |
1 / 316 | HOST-OWNED. TinyAgents harness::tool::ToolTimeout is declarative per-tool metadata; it has no process-global value to receive OpenHuman config. This module owns UI/config + env precedence and the actual tokio::time::timeout deadline used by the host-tool adapter — WP-2 audit closed. |
tool_status/ |
3 / 0.7k | HOST-OWNED. Its serialized UI/persistence taxonomy, OpenHuman security markers, retry categories, and user-facing remediation copy are product semantics. TinyAgents tool outcomes remain the generic execution input — WP-2 audit closed. |
tools/ |
98 / 40.9k | The Tool trait + ToolSpec mechanics (traits.rs:255), schema.rs, policy.rs, orchestrator_tools.rs, user_filter.rs are framework-shaped; all of tools/impl/* + RPC (schemas.rs 985, ops.rs 1,407) are product. Design-gated (port-plan §2 blockers still apply) — WP-4. Note: ToolResult/ToolContent are re-exported from skills::types (~236 consumer files) — moving those types is the highest-blast-radius single step in the whole migration and must be its own slice. Security coupling: 49 files. |
tool_registry/ |
7 / 1.8k | Read-only cross-surface discovery + RPC. Stays. |
agent_registry/, agent_experience/, agent_memory/, agent_tool_policy/, agentbox/, orchestration/ |
— | All host/product (definitions-as-data, RPC controllers, marketplace HTTP, remote-brain client — orchestration/ talks to the hosted backend, not the local crate). Stay. agent_tool_policy overlaps crate tool_policy middleware mechanically but encodes host channel-permission policy — stays, mechanism may thin post-WP-4. |
4.3 The seam — src/openhuman/tinyagents/ (25 files, ~17.1k LOC)
The seam is healthy: 23/25 files use the crate; it implements Middleware
(13×), ToolMiddleware (4×), ModelMiddleware (3×), ChatModel (2×),
Summarizer, Tool, EventListener (2×), PayloadSummarizer,
HarnessStatusStore, EmbeddingModel, and GraphEventSink. Post-migration it
shrinks but remains host-owned. Specific shrink targets:
model.rs:ProviderModelis deleted. The formerconvert.rswas split: tool-schema conversion remains as the 34-line WP-4 seam, while durable-message conversion moved toagent/message_convert.rs. The execution audit found thatChatMessageis OpenHuman's versioned JSONL/thread persistence record (including message ids and product metadata), not a duplicate provider request type; replacing it directly with the crate enum would change existing on-disk data.middleware.rs(4,702): the WP-5 audit records all 18 concrete types found at audit time (the tool-exposure shadow was added after the 17-type snapshot) indocs/tinyagents-drift-ledger.md.SchemaGuardis now deleted in favor of TinyAgents 2.1InvalidArgsPolicy::ReturnToolError, leaving 17.ArgRecoveryoverlaps crate #45/#71 normalization.RepeatProgressnow uses the merged #72 crate tracker; only the thin OpenHuman signature/exemption and halt-projection adapter remains. Upstream the generic ones; host-policy ones (ApprovalSecurity, CredentialScrub, CliRpcOnly, MemoryProtocol, CostBudget) stay — WP-5.routes.rsUsageCarry/FallbackObserverthin out as usage/fallback become fully crate-native.
4.4 Broken/dangling references (resolved in WP-0)
WP-0 retargeted SDK-gap references to
vendor/tinyagents/docs/sdk-gaps.md, made the provider schema
src/openhuman/config/schema/cloud_providers.rs authoritative, created
docs/tinyagents-full-migration-plan/99-deletion-ledger.md, replaced the
phantom numbered-plan links with this plan's WP-5/C4 sections, and retargeted
the TinyCortex analogy to this current audit. The three historical plans now
carry explicit superseded banners.
4.5 Test inventory (what moves, dies, or stays)
- Dies with WP-1 (bound to the legacy
Providerstack):provider/traits_tests.rs(501),reliable_tests.rs(1,228),router_tests.rs(524) — these define 10+ mockimpl Providerdoubles.factory_tests.rs(3,149) shrinks and retargets toChatModelconstruction. Intests/raw_coverage/: the threeinference_compatible_*files (~2.2k LOC) are pinned to the deleted wire client — retire or rewrite the still- meaningful assertions againstOpenAiModelvia wiremock. - Retargets:
tests/inference_provider_e2e.rs(568, wiremock-based — OpenAI-compat chat/streaming, Anthropic auth headers, temperature suppression, Ollama/v1) — keep the scenarios, point them at the crate- native factory path; these become the wire-parity gate for flipping the default. - Moves upstream (as crate tests, offline
MockModelconvention): parity coverage for anything upstreamed in WP-2/WP-5 (routing policy/quality, council graph, middleware behaviors). The crate's CI is fmt → clippy (-D warnings, both feature sets) → build →cargo test+--all-features, no network. - Stays host-side: seam tests (
tinyagents/tests.rs799 + 19 inline),tests/agent_harness_e2e.rs(130 KB),tests/json_rpc_e2e.rs(576 KB),agentbox_e2e,orchestration_*,embeddings_rpc_e2e,ollama_lifecycle_e2e,openai_oauth/flow_tests.rs, alllocal/*_tests, and theraw_coveragefamily except the compatible trio. - Runner impact:
scripts/test-rust-with-mock.sh:52had a stale comment advertising removedOPENHUMAN_AGENT_GRAPH_*escape hatches. WP-3 removes that documentation; the runner behavior itself was already crate-only.
5. The plan — six work packages
Ordering rationale: WP-0 is pure hygiene and unblocks honest review of everything else; WP-1 is the largest deletion and already 80% scaffolded; WP-2/WP-3 are independent of each other and of WP-1's tail; WP-4 is the only design-gated package; WP-5 is opportunistic shrink; WP-6 is the exit gate. Every WP follows the repo's standing rules: failing-before/passing-after regression tests, small validated commits on a feature branch per submodule, drift-ledger rows updated before deletions (the ledger's gate rule stays in force).
WP-0 — Version + docs housekeeping (no behavior change)
- Bump
vendor/tinyagentssubmodule to tagv2.1.0(fast-forward; picks upBarrierRelief#62 and the bytes bump). Regenerate root andapp/src-taurilockfiles.cargo checkboth worlds + the slim disabled build (--no-default-features --features tokenjuice-treesitter) per repo convention. - Update
tinyagents-drift-ledger.mdAnchors (pin row → v2.1.0; add rows closing out #4780/#4782/#4783/#4784 which the ledger still lists as pending/deferred; mark the Phase-3 "compatible*.rs remains" text CLOSED). - Stamp superseded-by banners on
tinyagents-port-plan.md,tinyagents-inference-migration-plan.md,tinyagents-phase3-router-registry-design.mdpointing here (keep them — their disposition tables and gap lists are still the reference detail). - Fix the §4.4 broken references, create the deletion ledger, and replace the phantom numbered-plan references with real WP-5/C4 anchors.
- Remove the stale fork-source patch after verifying that no dependency uses
it. Align TinyCortex's nested path dependency through a crates.io
2.1declaration plus its repo-local development patch, so the host's canonical path patch produces one trait identity (TinyCortex #121).
Exit: Cargo.toml, submodule, lockfiles, and ledger all agree on one
version; zero dangling docs/tinyagents* references (grep -rn clean).
WP-1 — Finish the model-layer cutover; delete the legacy Provider stack
The continuation of #4727 Motion B / drift-ledger P1-8/P1-9. Slices:
- Flip the factory default to
crate_openai.rsconstruction for every OpenAI-compatible slug. Gate: the retargetedinference_provider_e2e.rswire-parity suite (§4.5) green against the crate path, per provider family (managed, BYOK, ollama/lm-studio local, codex/responses). - Route bespoke providers as
ChatModels —claude_code,claude_agent_sdk,openai_codex,openhuman_backendget directChatModelimpls (the patternopenhuman_backend_model.rsalready proves), removing the lastfactory.rs:1458-1511ProviderModelwraps. Delete the legacyopenhuman_backend.rstwin when nothing constructs it. - Error-taxonomy split: generic classification call sites move to crate
classify_provider_failure/ProviderError;error_classify.rsshrinks to the openhuman-semantic layer (config_rejection,billing_error, Sentry demotion). Upstream any status codes the crate misclassifies (drift-ledger rows, then crate PR + version bump). - Delete, in dependency order:
router.rs→reliable.rs→legacy_provider.rs(+ theas compatiblealias inprovider/mod.rs:14) →provider/traits.rs→ seamProviderModel/MaxTokensModel(tinyagents/model.rs) → the reverse adaptercrate_provider.rslast. Re-home the durable transcript adapter beside the agent persistence DTO; retain only tool-schema conversion in the seam until WP-4. Each deletion is its own commit with its test fallout (§4.5) handled in the same commit. - Consumer sweep: migrate the 187 importing files to crate types
(
Message,ModelRequest,Usage,TinyAgentsError). Mechanical for most; the hot spots arecore/observability.rs,web_chat/web_errors.rs,voice/,flows/ops.rs,config/ops/model.rs. - Re-home
temperature.rs,thread_context.rs,resolved_route.rs,auth_error_registry.rsout ofprovider/into the seam (or the factory module) soprovider/ends as: factory + bespoke models + ops/RPC.
Exit criteria: no impl Provider anywhere; grep -rn "ProviderModel" src/ empty; inference/provider/ ≤ ~8k LOC (from ~15.9k + tests);
inference_provider_e2e + agent_harness_e2e + full
scripts/test-rust-with-mock.sh green. Estimated net deletion: ~9–10k LOC
(code + dead tests).
WP-2 — Consolidate parallel implementations onto crate primitives
Independent, individually shippable slices:
routing/→registry::router— complete by deletion. The execution audit found the entire module self-contained: no production or test caller outsiderouting/constructed its provider or consumed its health signals. #4783's crateModelRouteralready owns live workload routing, so WP-2 removed the unreachable parallel stack and its self-tests.tool_timeout/— HOST-OWNED (audit closed). The similarly named crateToolTimeoutis per-tool policy metadata, not a global timeout store or executor. OpenHuman must retain config/env precedence, live UI updates, seconds clamping, grace handling, and the adapter's hard deadline. The seam already projects host policy into crateToolRuntime; there is no duplicate crate implementation to delete.model_council/— complete by deletion. Generic member fan-out already ran throughtinyagents::graph::parallel::map_reduce; upstream dead-code cleanup removed the remaining unreachable council and registry product surfaces.tool_status/— HOST-OWNED (audit closed). The classifier is tied to OpenHuman security markers, serialized thread/UI types, retry categories, localized-copy keys, and remediation language. TinyAgents owns generic tool outcomes; mapping those outcomes into product status remains in the host.
Exit: complete. routing/, model_council/, and council_registry/ are
deleted; timeout and status are explicitly HOST-OWNED. Ledger rows record the
audit evidence.
WP-3 — Retire the legacy turn engine
Audit result: complete before this plan was written. The filenames cited by the initial audit survived, but their legacy engines did not:
session/turn/core.rsperforms OpenHuman turn preparation and calls the TinyAgents session path; it contains norun_turn_enginedefinition.subagent_runner/ops/graph.rsdocuments the removedrun_inner_loop/run_turn_engineand unconditionally callsrun_turn_via_tinyagents_shared.- No runtime or test code reads
OPENHUMAN_AGENT_GRAPH_*; only this plan and a stale test-runner comment mentioned those names. The stale comment is now removed.
Exit satisfied: one TinyAgents turn engine; source and scripts contain no
OPENHUMAN_AGENT_GRAPH_* reference. Historical/parity comments mentioning the
former engine remain intentionally as provenance, not executable branches.
WP-4 — Tool-model reconciliation (design-gated; do not start on autopilot)
The openhuman Tool trait (tools/traits.rs:255) vs crate Tool<State>
unification. The port-plan §2 design blockers still stand, plus two audited
constraints:
ToolResult/ToolContentlive inskills::typesas the deliberately ungated type carve-out consumed by ~236 files (MCP, runtime_node, every Tool impl). Any move must preserve that carve-out property (inert, dep-free, compiled in all feature combinations) — either the types move into the crate andskills::typesre-exports them, or they stay and the crate bridge continues viaSharedToolAdapter.tools/has the tree's heaviest security coupling (49 files) — execution gating (classify_command, approval, sandbox) must stay host-side regardless of where the trait lives.
Recommended shape: a short design doc (successor to the port-plan §2 list)
deciding (a) trait unification vs permanent adapter, (b) the
ToolResult/ToolContent home, (c) ToolScope::AgentOnly gating (deferred
"Phase 2" per traits.rs:14-19) — then slices. Until then, the
SharedToolAdapter seam is cheap and correct; do not delete it
prematurely.
The proposed decision is recorded in
tinyagents-tool-model-decision-2026-07-23.md.
It selects a permanent ownership-boundary adapter, keeps the host's structured
result types in the always-compiled carve-out while preserving them through
TinyAgents raw, and defines the required scope-enforcement matrix. WP-4 code
changes remain gated on explicit approval of that proposal.
WP-5 — Seam shrink + orchestration lifecycle upstreaming
- Middleware audit (§4.3): per-middleware ledger rows;
SchemaGuardis deleted through the existing crate invalid-args policy. TinyAgents #72 is merged andRepeatProgressnow delegates generic streak accounting to the crateSuccessfulRepeatTracker; the host duplicate guard and thresholds are deleted, while the thin product adapter remains.ArgRecoverystill awaits the #71 crate equivalent; keep host-policy middlewares. - Detached-subagent lifecycle: move the generic detached-run registry
mechanics (
agent_orchestration/running_subagents.rs,subagent_control.rs) onto crateTaskStore/SteeringRegistryfully; host keeps ledgers + RPC. This restores the lifecycle consolidation intent recorded by the earlier audit without relying on a phantom design doc. Cutover implemented: TinyAgents PR #75 adds the generic ownership-awareDetachedTaskRegistry; OpenHuman now delegates snapshots, waits, steering lookup, cancellation/abort, terminal sweeping, and lock-error handling to it. The host retains durableTaskStoreprojection, product metadata, RPC, and theRunQueuecompatibility fallback. All 17 focusedrunning_subagentstests pass. TinyAgents #75 merged asd548657, and the canonical vendored pointer4358efeincludes it, closing the generic lifecycle cutover. - Finish the C4 journal-progress-parity plan (S2–S6): journal-backed progress
projection, then delete
agent/progress_tracing.rs(1,272) +progress_tracing/langfuse.rs(825) in favor of crate observability — respecting the recorded S2a replayability blocker.
WP-6 — Exit gate
- Full suite:
scripts/test-rust-with-mock.sh(all targets incl.raw_coverage_all),cargo test --all-featuresinvendor/tinyagents, slim disabled build +cargo test --lib --no-default-features --features tokenjuice-treesitter core::(repo standing rule),pnpm rust:check. - Deletion ledger totals reconciled against the port-plan's projection (~30k deleted / ~12–15k upstreamed).
- Docs:
inference/README.md,gitbooks/developing/architecture/ {agent-harness,orchestration,flows-on-tinyagents}.mdupdated to the post-cutover reality; drift ledger phases marked CLOSED; this plan stamped done.
6. Risks and standing gotchas
- Wire parity is the whole risk in WP-1. The legacy client accumulated
provider quirks for years; the crate's #44–#57 wave was built to match them,
but the flip must be gated on the wiremock parity suite per provider family,
not on unit tests. Keep
CrateBackedProvideras the rollback seam until the parity suite has soaked onmain. - GPL/crates.io boundary: tinyagents is publicly redistributed — only genuinely generic code moves down; no product policy, backend phrasing as API, or key material (port-plan rule, still in force).
- Usage fidelity (old gap G1): verify crate
Usagecarries the USD/cached-token fields the cost tracker needs before deletingUsageInfo;routes.rsUsageCarryis the current compensator. RUST_MIN_STACK=16777216in the mock runner exists because of the subagent runner's large futures — deep-graph changes in WP-3/WP-5 can resurface stack overflows on Apple Silicon (seecomposio_list_tools_stack_overflow_regressiontest).- Whisper/GGML on Apple Silicon: any
cargovalidation of the root crate locally needsGGML_NATIVE=OFF(unrelated to this migration but will bite every WP's validation loop). - Two Cargo worlds: every vendor bump must update both the root and
app/src-taurilockfiles (until the workspace convergence tracked in #3877).
7. Quick reference — disposition of every audited module
| Module | Verdict |
|---|---|
inference/provider/{traits,reliable,router,legacy_provider,crate_provider}.rs |
DELETE (WP-1) |
inference/provider/{error_classify,error_code}.rs |
SPLIT: generic → crate; host semantics stay (WP-1) |
inference/provider/{crate_openai,openhuman_backend_model,factory}.rs |
KEEP — becomes the host↔crate boundary (WP-1 finishes) |
inference/provider/{temperature,thread_context,resolved_route,auth_error_registry}.rs |
RE-HOME to seam (WP-1) |
inference/{local,voice,http,openai_oauth}/, provider/ops/, bespoke providers, root host files |
STAYS |
tinyagents/model.rs (ProviderModel) |
DELETED (WP-1) |
tinyagents/convert.rs message layer |
RE-HOMED to agent/message_convert.rs; durable JSONL/thread compatibility is product-owned. Tool-schema conversion remains for WP-4. |
tinyagents/middleware.rs generic middlewares |
UPSTREAM case-by-case (WP-5) |
tinyagents/ remainder (seam) |
STAYS, shrinks |
agent/ legacy run_turn_engine + escape hatches |
ALREADY DELETED; WP-3 corrected the stale audit and runner documentation |
agent/ remainder, agent_registry/, agent_experience/, agent_memory/, agent_tool_policy/, agentbox/, orchestration/, tool_registry/ |
STAYS (product/host) |
routing/ |
DELETED; #4783 crate router already owned the only live path (WP-2) |
tool_timeout/ |
HOST-OWNED: config/env state + hard-deadline enforcement; crate timeout is metadata only (WP-2 closed) |
tool_status/ classification |
HOST-OWNED: OpenHuman UI/security/recovery taxonomy (WP-2 closed) |
model_council/, council_registry/ |
DELETED after crate-backed fan-out audit and upstream dead-code cleanup (WP-2 closed) |
tools/ trait mechanics |
DESIGN-GATED (WP-4) |
tools/impl/*, all schemas.rs RPC controllers |
STAYS |
agent_orchestration/ detached-run mechanics |
UPSTREAM to TaskStore (WP-5) |
agent/progress_tracing* |
DELETE after C4 S2–S6 (WP-5) |