ouroboros-ai 0.31.2.dev14__tar.gz → 0.31.2.dev16__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of ouroboros-ai might be problematic. Click here for more details.
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/PKG-INFO +1 -1
- ouroboros_ai-0.31.2.dev16/docs/rfc/mesh.md +272 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/_version.py +2 -2
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/codex_cli_adapter.py +41 -2
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_codex_cli_adapter.py +154 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.claude/settings.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.claude-plugin/.mcp.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.claude-plugin/marketplace.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.claude-plugin/plugin.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.env.example +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/bug_report.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/config.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/feature_request.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/question.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/workflows/dev-publish.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/workflows/lint.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/workflows/release.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/workflows/test.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.gitignore +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.mcp.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.ouroboros/mechanical.toml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.ouroboros/seeds/seed_73827177a2a3.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.ouroboros/seeds/seed_78c8e6e41813.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.pre-commit-config.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.python-version +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/CHANGELOG.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/CLAUDE.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/CODE_OF_CONDUCT.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/CONTRIBUTING.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/Code-Review-Claude.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/Code-Review-Codex.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/HANDOFF.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/LICENSE +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/README.ko.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/SECURITY.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/UNINSTALL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/cancel.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/evaluate.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/evolve.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/help.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/interview.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/ralph.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/run.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/seed.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/setup.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/status.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/tutorial.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/unstuck.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/commands/welcome.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/.gitignore +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/Cargo.lock +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/Cargo.toml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/db.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/main.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/mock.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/state.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/dashboard.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/execution.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/lineage.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/logs.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/mod.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/crates/ouroboros-tui/src/views/session_selector.rs +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/api/README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/api/core.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/api/mcp.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/architecture.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/cli-reference.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/config-reference.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/agent-os-kernel-terminology.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/architecture-overview.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/findings-registry.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/issue-quality-policy.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/key-patterns.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/contributing/testing-guide.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/events.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/examples/mcp-config.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/examples/workflows/design-code-verify.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/examples/workflows/research-to-deliverable.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/getting-started.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/evaluation-pipeline.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/evolution-loop.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/issue-176-subagent-mcp-inheritance.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/mcp-best-practices.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/mcp-bridge.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/ooo-skill-dispatch-router.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/opencode-subagent-bridge.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/qa-backends.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/seed-authoring.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/guides/tui-usage.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/images/PLACEHOLDER_README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/images/ouroboros.png +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/platform-support.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-capability-matrix.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-guides/claude-code.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-guides/codex.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-guides/gemini.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-guides/hermes.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/docs/runtime-guides/opencode.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/coordinator_test_seed.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/dummy_seed.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/parallel_subac_test_seed.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/subac_test_seed.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/README.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/__main__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/cli.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/task_manager/storage.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/examples/test_display.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/hooks/hooks.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/llms-full.txt +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/llms.txt +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/project-context.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/pyproject.toml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/drift-monitor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/install.sh +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/keyword-detector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/mcp-serve.sh +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/ralph-rewind.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/ralph.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/ralph.sh +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/session-start.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/sync-plugin-version.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/scripts/version-check.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/brownfield/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/cancel/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/evaluate/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/evolve/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/help/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/interview/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/pm/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/publish/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/qa/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/ralph/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/resume-session/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/run/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/seed/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/setup/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/status/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/tutorial/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/unstuck/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/update/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/skills/welcome/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/__main__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/advocate.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/analysis-agent.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/architect.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/breadth-keeper.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/code-executor.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/codebase-explorer.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/consensus-reviewer.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/contrarian.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/evaluator.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/hacker.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/judge.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/loader.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/ontologist.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/ontology-analyst.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/qa-judge.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/research-agent.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/researcher.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/seed-architect.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/seed-closer.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/semantic-evaluator.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/simplifier.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/agents/socratic-interviewer.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/ambiguity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/brownfield.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/explore.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/interview.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/pm_completion.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/pm_document.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/pm_interview.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/pm_seed.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/question_classifier.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/bigbang/seed_generator.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/claude_permissions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/cancel.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/codex.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/detect.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/init.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/mcp.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/mcp_doctor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/pm.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/resume.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/run.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/setup.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/status.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/tui.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/commands/uninstall.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/panels.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/progress.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/prompting.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/tables.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/formatters/workflow_display.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/jsonc.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/main.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/cli/opencode_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/codex/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/codex/artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/codex/cli_policy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/codex/ouroboros.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/codex_permissions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/config/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/config/loader.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/config/models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/ac_tree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/directive.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/errors.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/file_lock.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/git_workflow.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/initial_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/json_utils.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/lineage.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/ontology_aspect.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/ontology_questions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/project_paths.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/retry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/security.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/seed.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/seed_contract.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/seed_contract_prompt.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/text.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/ttl_cache.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/core/worktree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/artifact_collector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/checklist.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/consensus.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/detector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/json_utils.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/languages.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/mechanical.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/pipeline.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/semantic.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/trigger.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evaluation/verification_artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/base.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/control.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/decomposition.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/evaluation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/interview.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/lineage.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/events/ontology.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/convergence.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/loop.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/projector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/reflect.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/regression.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/evolution/wonder.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/execution/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/execution/atomicity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/execution/decomposition.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/execution/double_diamond.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/execution/subagent.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/hermes/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/hermes/artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/bridge/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/bridge/bridge.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/bridge/config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/bridge/factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/client/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/client/adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/client/manager.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/client/protocol.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/errors.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/job_manager.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/resources/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/resources/handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/server/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/server/adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/server/protocol.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/server/security.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/ac_tree_hud_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/ac_tree_hud_render.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/authoring_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/bridge_mixin.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/brownfield_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/dashboard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/definitions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/evaluation_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/evolution_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/execution_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/job_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/pm_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/qa.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/query_handlers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/tools/subagent.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/mcp/types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/observability/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/observability/drift.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/observability/logging.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/observability/retrospective.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/opencode-plugin.d.ts +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/ouroboros-bridge.test.ts +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/ouroboros-bridge.ts +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/package.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/opencode/plugin/tsconfig.json +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/capabilities.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/codex_cli_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/command_dispatcher.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/control_plane.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/coordinator.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/dependency_analyzer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/execution_runtime_scope.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/execution_strategy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/gemini_cli_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/heartbeat.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/hermes_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/level_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/mcp_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/mcp_tools.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/opencode_event_normalizer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/opencode_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/parallel_executor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/parallel_executor_models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/policy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/rate_limit.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/runner.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/runtime_factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/runtime_message_projection.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/session.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/orchestrator/workflow_state.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/brownfield.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/checkpoint.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/event_store.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/migrations/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/migrations/runner.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/migrations/scripts/001_initial.sql +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/migrations/scripts/002_brownfield.sql +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/schema.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/persistence/uow.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/agents/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/agents/pool.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/agents/registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/orchestration/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/orchestration/router.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/orchestration/scheduler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/skills/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/skills/docs.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/skills/executor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/skills/keywords.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/plugin/skills/registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/pm/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/pm/handoff.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/pm/renderer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/anthropic_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/base.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/claude_code_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/codex_cli_stream.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/gemini_cli_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/gemini_event_normalizer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/litellm_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/opencode_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/py.typed +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/resilience/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/resilience/lateral.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/resilience/recovery.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/resilience/stagnation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/router/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/router/command_parser.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/router/dispatch.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/router/registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/router/types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/complexity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/downgrade.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/escalation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/router.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/routing/tiers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/sandbox.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/secondary/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/secondary/scheduler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/secondary/todo_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/skills/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/skills/artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/strategies/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/strategies/devil_advocate.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/app.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/components/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/components/agents_panel.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/components/event_log.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/components/progress.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/components/token_tracker.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/confirm_rewind.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/dashboard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/dashboard_v2.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/dashboard_v3.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/debug.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/execution.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/hud_dashboard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/lineage_detail.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/lineage_selector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/logs.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/screens/session_selector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/ac_progress.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/ac_tree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/agent_activity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/cost_tracker.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/drift_meter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/lineage_tree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/parallel_graph.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/tui/widgets/phase_progress.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/verification/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/verification/extractor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/verification/models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/verification/verifier.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/mcp_bridge_test_config.yaml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/test_cli_commands.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/test_full_workflow.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/e2e/test_session_persistence.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/fixtures/router/skills/frontmatter-body/run/SKILL.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/fixtures/test_atomicity_seed.yml +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/bridge/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/bridge/test_bridge_server_to_server.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/test_client_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/test_client_manager.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/mcp/test_server_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/plugin/test_orchestration.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/test_cancel_subprocess_termination.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/test_codex_cli_passthrough_smoke.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/test_codex_skill_fallback.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/test_codex_skill_smoke.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/integration/test_entry_point.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/test-execution-plan.md +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/agents/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/agents/test_loader.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_ambiguity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_brownfield.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_classifier_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_decide_later_items.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_explore.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_interview.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_interview_async_io.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_interview_no_web_search_hint.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_interview_research_prefix.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_completion.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_document_generator.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_document_writer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_interview.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_interview_brownfield_db.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_seed_ac12.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_pm_seed_save.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_question_classifier.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/bigbang/test_seed_generator.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/commands/test_tui_command.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_console.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_panels.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_progress.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_prompting.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_tables.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/formatters/test_workflow_display.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_bridge_plugin_hardening.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_bridge_plugin_lifecycle.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_cancel.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_codex_command.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_doc_commands.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_init_pm_seed_detection.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_init_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_jsonc.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_main.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_mcp_doctor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_mcp_nested_guard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_mcp_shell_env.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_mcp_startup_cleanup.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_mcp_validate_transport_stderr.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_opencode_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_brownfield.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_completion.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_interactive_logging.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_missing_litellm.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_overwrite.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_runtime_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_pm_select_repos.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_resume.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_run_qa.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_setup.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/cli/test_uninstall.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/codex/test_cli_policy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/config/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/config/test_loader.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/config/test_loader_env.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/config/test_models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_ac_tree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_directive.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_errors.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_file_lock.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_git_workflow.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_initial_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_lineage.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_ontology_aspect.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_ontology_questions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_retry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_security.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_seed.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_ttl_cache.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/core/test_worktree.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_artifact_collector_file_prefix.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_checklist.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_consensus.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_detector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_json_utils.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_languages.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_mechanical.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_models.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_pipeline_stage1_reuse.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_pipeline_trigger_consensus.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_review_fixes.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_semantic.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_trigger.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_trigger_consensus.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evaluation/test_verification_artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/events/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/events/test_base.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/events/test_control_events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/events/test_decomposition_events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/evolution/test_wonder_scope.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/execution/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/execution/test_atomicity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/execution/test_decomposition.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/execution/test_double_diamond.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/execution/test_subagent_isolation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/hermes/test_artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/test_bridge.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/test_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/test_factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/test_handler_wiring.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/bridge/test_stability.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/client/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/client/test_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/client/test_adapter_transport_lifecycle.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/client/test_manager.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/server/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/server/test_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/server/test_security.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/test_errors.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/test_job_manager.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/test_types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/conftest.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_footer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler_completed.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler_cursor_changed.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler_invalid_session.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler_no_execution.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_handler_waiting.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_max_nodes.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_render_depth2.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_render_depth3.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_status_icons.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_ac_tree_hud_truncation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_brownfield_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_checklist_verify.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_definitions.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_evaluate_multi_ac.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_handler_subagent_wiring.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_interview_done_streak.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_interview_reopen_seed_ready.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_lateral_think_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_mcp_manager_wiring.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_pm_handler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_pm_handler_pending_reframe.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_qa_parser.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_round5_fixes.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/mcp/tools/test_subagent.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/observability/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/observability/test_drift.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/observability/test_logging.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/observability/test_retrospective.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_capabilities.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_codex_cli_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_codex_recursion_guard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_command_dispatcher.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_control_plane.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_coordinator.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_dependency_analyzer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_execution_runtime_scope.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_execution_strategy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_gemini_cli_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_hermes_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_inflight_cancellation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_level_context.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_mcp_config.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_mcp_tools.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_opencode_runtime.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_parallel_executor.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_parallel_executor_atomic_judgment.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_parallel_executor_recursive_depth.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_parallel_executor_retry_resume.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_policy.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_rate_limit.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_runner.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_runner_cancellation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_runtime_factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_runtime_message_projection.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_sandbox_class.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_seed_prompt.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_session.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/orchestrator/test_workflow_state.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/test_brownfield_store.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/test_checkpoint.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/test_event_store.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/test_schema.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/persistence/test_uow.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/agents/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/agents/test_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/orchestration/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/orchestration/test_model_router.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/skills/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/skills/test_keywords.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/plugin/skills/test_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/pm/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/pm/test_renderer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_base.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_claude_code_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_factory.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_gemini_cli_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_litellm_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/providers/test_opencode_adapter.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/resilience/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/resilience/test_lateral.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/resilience/test_recovery.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/resilience/test_stagnation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_command_parser.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_dispatch.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_dispatch_result_shapes.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_extract_first_argument.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_invalid_dispatch_input_types.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_malformed_unknown_dispatch_errors.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_not_handled_resolution.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_repository_dispatch_guard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_router_resolution_pipeline.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_typed_frontmatter_fields.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/router/test_valid_dispatch_normalization.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/test_complexity.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/test_downgrade.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/test_escalation.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/test_router.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/routing/test_tiers.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/scripts/test_keyword_detector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/scripts/test_session_start.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/scripts/test_version_check.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/secondary/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/secondary/test_scheduler.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/secondary/test_todo_registry.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/skills/test_skill_artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_artifact_collector.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_codex_artifacts.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_convergence.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_dashboard.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_dependencies_configured.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_evolve_rewind.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_evolve_step.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_graceful_shutdown.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_main_entry_point.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_module_structure.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_project_initialization.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_projector_rewind.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_ralph_parser.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_ralph_rewind.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_regression.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_tooling_configuration.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/test_verification.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/__init__.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_app.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_cancelled_display.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_events.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_lineage_viewer.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_screens.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_session_selector_replay.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tests/unit/tui/test_widgets.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/tools/sync_github_project.py +0 -0
- {ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/uv.lock +0 -0
|
@@ -0,0 +1,272 @@
|
|
|
1
|
+
# RFC — MCP Mesh wire format and Coordinator handshake
|
|
2
|
+
|
|
3
|
+
> Status: **Accepted** (Phase 2 of #476 Agent OS roadmap).
|
|
4
|
+
> Closes [#511](https://github.com/Q00/ouroboros/issues/511).
|
|
5
|
+
> Related: [#471](https://github.com/Q00/ouroboros/issues/471) (Control vs Capability plane), [#476](https://github.com/Q00/ouroboros/issues/476) Q4 (dynamic MCP invariant), [#492](https://github.com/Q00/ouroboros/pull/492) (`control.directive.emitted`), [#436](https://github.com/Q00/ouroboros/pull/436) (`event_version`), [#517](https://github.com/Q00/ouroboros/issues/517), [#518](https://github.com/Q00/ouroboros/issues/518), [#519](https://github.com/Q00/ouroboros/issues/519).
|
|
6
|
+
|
|
7
|
+
## Summary
|
|
8
|
+
|
|
9
|
+
This RFC specifies the **wire layer** of the Mesh — the IPC-style channel that lets every harness (Claude Code, Codex CLI, OpenCode, Gemini CLI, Hermes, LiteLLM) attach to a single in-process Coordinator through one envelope shape, one polling discipline, and one ordering rule. It establishes the contract that Phase 3 implementation issues build against, and it formalizes how the runtime of the Phase-2 Agent OS (#476) actually moves bytes.
|
|
10
|
+
|
|
11
|
+
The RFC settles the *how* of the Mesh; the *what* (Contract = OS, Mesh = IPC, sub-agents as disposable processes) is settled by #476 itself.
|
|
12
|
+
|
|
13
|
+
## Scope
|
|
14
|
+
|
|
15
|
+
This document **does** decide:
|
|
16
|
+
- Transport, envelope schema, polling/push discipline, Coordinator topology, runtime registration handshake, ordering guarantees, and timeout/failure semantics.
|
|
17
|
+
|
|
18
|
+
This document **does not** decide:
|
|
19
|
+
- Per-runtime profile mappings (deferred to [#519](https://github.com/Q00/ouroboros/issues/519)).
|
|
20
|
+
- Disposable Memory's process model and artifact backend (deferred to [#512](https://github.com/Q00/ouroboros/issues/512); the companion RFC lands separately).
|
|
21
|
+
- Contract Ledger schema (deferred to [#513](https://github.com/Q00/ouroboros/issues/513); the companion RFC lands separately).
|
|
22
|
+
- The migration of `mcp_manager` plumbing to `AgentRuntimeContext + ControlBus` (tracked in [#474](https://github.com/Q00/ouroboros/issues/474) / [#475](https://github.com/Q00/ouroboros/issues/475)).
|
|
23
|
+
|
|
24
|
+
## Constraints inherited from #476
|
|
25
|
+
|
|
26
|
+
- **Local-first cooperative trust.** No daemon, no SaaS, no cross-tenant boundary. A misbehaving runtime *can* forge directives; the RFC does not police identity.
|
|
27
|
+
- **4-verb filter.** Every Mesh decision must strengthen exactly one of `replay / explain / steer / compose`. Decisions that fail this filter are rejected.
|
|
28
|
+
- **Tier-4 Won't.** The Mesh does not introduce real-time guarantees, multi-tenant isolation, or BFT.
|
|
29
|
+
- **Additive-only schemas.** [#436](https://github.com/Q00/ouroboros/pull/436)'s `event_version` rule applies to every envelope field added later.
|
|
30
|
+
|
|
31
|
+
## Decisions
|
|
32
|
+
|
|
33
|
+
### D1 — Transport: streamable-http (primary) + stdio multiplex (sub-process fallback)
|
|
34
|
+
|
|
35
|
+
**Decision.** All Mesh traffic flows over the `streamable-http` transport that ouroboros already uses for MCP ([#339](https://github.com/Q00/ouroboros/pull/339), [#485](https://github.com/Q00/ouroboros/pull/485)). For runtimes that already speak stdin/stdout (Codex CLI, Hermes, OpenCode, Gemini CLI), `stdio multiplex` is the local fallback. The Mesh adapter normalizes both into the same envelope shape so callers do not branch on transport.
|
|
36
|
+
|
|
37
|
+
**Stdio framing.** Stdio multiplex uses newline-delimited JSON frames with an explicit `frame` discriminator:
|
|
38
|
+
|
|
39
|
+
- Coordinator → runtime: one `{"frame":"request","body": <request envelope>}`.
|
|
40
|
+
- Runtime → Coordinator: zero or more `{"frame":"event","body": <BaseEvent-compatible event>}` frames.
|
|
41
|
+
- Runtime → Coordinator: exactly one `{"frame":"result","body": <result envelope>}` frame, then EOF for that contract invocation.
|
|
42
|
+
|
|
43
|
+
The stdio adapter owns per-invocation process startup and maps these frames to the same logical stream the HTTP adapter exposes. Registration for stdio runtimes is not performed on this one-shot invocation stream; the adapter obtains capabilities from a static descriptor or a separate short-lived `{"frame":"register"}` discovery process before any contract dispatch. There is no `/mesh/contract` URL on stdio; the request envelope is the dispatch boundary.
|
|
44
|
+
|
|
45
|
+
**Rationale.** Reusing `streamable-http` keeps a single transport story across the codebase; UDS would force a Windows-incompatible split; raw TCP would invite firewall prompts on every workstation; SSE alone cannot carry bidirectional traffic; long-poll would require its own tuning loop. `stdio multiplex` covers exactly the runtimes whose existing pattern already speaks stdio.
|
|
46
|
+
|
|
47
|
+
**Risks.**
|
|
48
|
+
- Coupling to MCP's transport spec. Mitigation: a thin adapter layer quarantines `streamable-http` details so MCP changes only touch one file.
|
|
49
|
+
- Operator confusion when both transports are visible. Mitigation: `ouroboros mcp doctor` ([#445](https://github.com/Q00/ouroboros/pull/445)) prints the active transport per runtime in the resolved table.
|
|
50
|
+
|
|
51
|
+
### D2 — Envelope schema: ULID id + target binding + additive `extra` slot
|
|
52
|
+
|
|
53
|
+
Two envelopes — request (Coordinator → runtime) and result (runtime → Coordinator) — versioned and additive-only.
|
|
54
|
+
|
|
55
|
+
**Request envelope.**
|
|
56
|
+
|
|
57
|
+
```jsonc
|
|
58
|
+
{
|
|
59
|
+
"schema_version": 1,
|
|
60
|
+
"contract_id": "01HXAB...", // ULID, 26 chars, sortable, no extra dependency
|
|
61
|
+
"correlation_id": "01HXAC...", // attempt id within this contract
|
|
62
|
+
"parent_correlation_id": null, // set on retry attempts
|
|
63
|
+
"target_type": "lineage", // open string; known values live in events/control.py
|
|
64
|
+
"target_id": "ralph-...-v3",
|
|
65
|
+
"directive": "evaluate", // core.directive.Directive.value (lowercase)
|
|
66
|
+
"emitted_by": "orchestrator",
|
|
67
|
+
"deadline_ms": 60000, // relative timeout duration in milliseconds
|
|
68
|
+
"extra": {} // additive-only growth slot
|
|
69
|
+
}
|
|
70
|
+
```
|
|
71
|
+
|
|
72
|
+
**Result envelope.**
|
|
73
|
+
|
|
74
|
+
```jsonc
|
|
75
|
+
{
|
|
76
|
+
"schema_version": 1,
|
|
77
|
+
"contract_id": "01HXAB...", // mirrored from request
|
|
78
|
+
"correlation_id": "01HXAC...", // mirrored from request
|
|
79
|
+
"parent_correlation_id": null, // mirrored from request when present
|
|
80
|
+
"result": {
|
|
81
|
+
"status": "ok", // "ok" | "error"
|
|
82
|
+
"next_directive": "converge", // required: see state-machine table below
|
|
83
|
+
"artifact_ref": "sha256:abc123...", // content hash; body fetched separately
|
|
84
|
+
"error": null // Error object below when status="error"
|
|
85
|
+
},
|
|
86
|
+
"runtime_id": "codex_cli", // which harness produced the result
|
|
87
|
+
"duration_ms": 12345,
|
|
88
|
+
"runtime_events_emitted_count": 17, // runtime-reported event frames sent before result
|
|
89
|
+
"extra": {}
|
|
90
|
+
}
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
**Error object.** When `result.status="error"`, `result.error` MUST be an object with at least:
|
|
94
|
+
|
|
95
|
+
```jsonc
|
|
96
|
+
{
|
|
97
|
+
"code": "deadline_exceeded", // stable machine-readable discriminator
|
|
98
|
+
"message": "runtime exceeded deadline",
|
|
99
|
+
"retryable": true, // Coordinator policy input
|
|
100
|
+
"details": {} // additive-only diagnostic slot
|
|
101
|
+
}
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
The Coordinator uses `retryable` plus its own retry budget to decide whether to emit `retry` or accept the runtime's terminal `cancel`; runtimes do not decide budget state.
|
|
105
|
+
|
|
106
|
+
**Result state machine.** Legal combinations are intentionally small:
|
|
107
|
+
|
|
108
|
+
| `result.status` | `result.next_directive` | Meaning |
|
|
109
|
+
|---|---|---|
|
|
110
|
+
| `ok` | `continue` | Successful non-terminal progress; Coordinator journals `continue` |
|
|
111
|
+
| `ok` | `converge` | Successful terminal completion; Coordinator journals `converge` |
|
|
112
|
+
| `ok` | `wait` | Runtime needs external input; Coordinator journals `wait` |
|
|
113
|
+
| `error` | `cancel` | Runtime failed this attempt; Coordinator either journals `cancel` or, when `error.retryable=true` and budget remains, fences this attempt and journals `retry` for a new correlation id |
|
|
114
|
+
|
|
115
|
+
All other combinations are schema-invalid. In particular, `wait` is a directive, not a third status value, and error results always include the typed `error` object above.
|
|
116
|
+
|
|
117
|
+
**Why ULID.** Sortable, log-friendly, 26-char ASCII, and synthesizable in 10 lines without a new dependency. Replaces UUIDv4 wherever event chains need to be reconstructed in order. `parent_correlation_id` is nullable on first attempt and set to the previous attempt's `correlation_id` when the Coordinator dispatches a retry, so retry ancestry is represented in-band.
|
|
118
|
+
|
|
119
|
+
**Why `runtime_events_emitted_count` instead of inline events.** Disposable Memory's promise is that the *main session ledger holds only `contract_id + artifact_ref`*. Streaming the runtime-reported frame count keeps the wire small and gives the Coordinator a sanity check against the events it actually persisted; the authoritative body is fetched from the EventStore by a projector when needed. The Coordinator's post-result lifecycle directive is not included in this runtime-authored count. This preserves the bloat-guard invariant from [#512](https://github.com/Q00/ouroboros/issues/512) at the wire layer.
|
|
120
|
+
|
|
121
|
+
**Final directive mapping.** The runtime sets `result.next_directive` according to the state-machine table above. Retry-budget decisions remain Coordinator/resilience-layer policy; a retryable runtime failure is reported as `status="error"`, `next_directive="cancel"`, and `error.retryable=true`, and the Coordinator decides whether to emit `retry` and dispatch another attempt instead of accepting the cancellation. `result.status` remains the coarse transport/result class; `next_directive` is the normative journal mapping unless Coordinator retry policy overrides a retryable error.
|
|
122
|
+
|
|
123
|
+
**`extra` governance.** Adding a key to `extra` requires a one-line justification in the PR body, identical to the narrow-membership commitment for `AgentRuntimeContext` in #476 Q1. This stops slot sprawl over time.
|
|
124
|
+
|
|
125
|
+
### D3 — Polling vs push: streamable-http hybrid
|
|
126
|
+
|
|
127
|
+
**Decision.** The Coordinator is the client for contract dispatch. For streamable-http runtimes it opens `POST /mesh/contract` against the selected runtime endpoint. For stdio runtimes it writes the D1 request frame to the child process. In both cases the runtime streams *intermediate events* (`tool.call.*`, `llm.call.*` from [#517](https://github.com/Q00/ouroboros/issues/517)) and the *final result envelope* on the same logical channel, then closes. Runtimes never POST new work back to the Coordinator in this phase.
|
|
128
|
+
|
|
129
|
+
**Rationale.** The slide framing of *"tool schema, polling, ResultEvent that act like IPC"* maps cleanly onto streamable-http: polling is implicit in the runtime's streaming response to the Coordinator's dispatch request. No long-poll loop to tune, no SSE-only one-way limitation, no command channel separate from the data channel.
|
|
130
|
+
|
|
131
|
+
**Risks.**
|
|
132
|
+
- A single long-running stream ties up one connection per in-flight contract. Mitigation: `deadline_ms` is enforced server-side as a relative timeout from request receipt; abandoned streams are closed when the timeout expires regardless of client behavior.
|
|
133
|
+
- Reconnect semantics. Mitigation: the Coordinator reconnects to the same streamable-http runtime endpoint with the same `(contract_id, correlation_id)` after ordinary HTTP transport drops; D6 stream replay and Coordinator-side duplicate suppression make reconnection safe. Stdio EOF/pipe loss is treated as runtime process loss unless the adapter can prove the child is still alive and can accept a fresh request frame.
|
|
134
|
+
|
|
135
|
+
### D4 — Coordinator topology: embedded with abstract interface
|
|
136
|
+
|
|
137
|
+
**Decision.** The `Coordinator` lives inside the orchestrator process. A `Coordinator` Protocol/ABC isolates the in-process implementation from the rest of the orchestrator so a future daemon implementation can be substituted without touching call sites.
|
|
138
|
+
|
|
139
|
+
**Rationale.** Tier-4 Won'ts (no SaaS, no real-time, single-machine) make a separate daemon infrastructure for goals we have explicitly declined. The abstract interface keeps the door open for a Phase 4+ multi-machine extraction at exactly one cost: the day someone wants distributed runtimes, they replace one implementation.
|
|
140
|
+
|
|
141
|
+
**Risks.**
|
|
142
|
+
- Single-process bottleneck. Mitigation: Tier-4 Won't makes this a non-goal; the abstract interface is the planned escape valve.
|
|
143
|
+
- Implicit lifetime coupling between Coordinator and orchestrator session. Mitigation: the abstract interface defines lifetime hooks (`start()`, `stop()`) so a future daemon does not need to inherit session boundaries.
|
|
144
|
+
|
|
145
|
+
### D5 — Runtime registration: startup + #476 Q4 invariant verbatim
|
|
146
|
+
|
|
147
|
+
**Startup handshake.** At orchestrator start, the Coordinator reads the binding table from [#519](https://github.com/Q00/ouroboros/issues/519) (`runtime_profile.stages`) and resolves capabilities per runtime. Streamable-http runtimes use a persistent registration channel. Stdio runtimes register through the Mesh adapter's static descriptor or a separate short-lived discovery process; the one-shot contract invocation stream from D1 is not held open for registration. Each runtime advertises:
|
|
148
|
+
|
|
149
|
+
```jsonc
|
|
150
|
+
{
|
|
151
|
+
"runtime_id": "codex_cli",
|
|
152
|
+
"version": "0.31.0",
|
|
153
|
+
"accepted_input_directives": ["continue", "evaluate", "evolve", "unstuck", "retry", "compact", "wait", "cancel", "converge"],
|
|
154
|
+
"emitted_result_directives": ["continue", "converge", "wait", "cancel"],
|
|
155
|
+
"supported_target_types": ["lineage", "execution", "agent_process"],
|
|
156
|
+
"capabilities": [/* CapabilityRegistry wire format */]
|
|
157
|
+
}
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
`accepted_input_directives` names the `core.directive.Directive.value` inputs this runtime can be asked to handle. `emitted_result_directives` names the smaller set this runtime may place in `result.next_directive`; it is result-side metadata, not an additional dispatch vocabulary.
|
|
161
|
+
|
|
162
|
+
**Dynamic addition** reuses the contract from #476 Q4 verbatim. This RFC does not invent anything new on this path — it simply requires the Mesh to honor the existing invariant.
|
|
163
|
+
|
|
164
|
+
```
|
|
165
|
+
1. mcp_bridge.add_server(config) — transport + discovery
|
|
166
|
+
2. CapabilityRegistry.sync_from(bridge) — typed capabilities
|
|
167
|
+
3. PolicyEngine.evaluate(role, phase, ...) — policy decision set
|
|
168
|
+
4. Emit policy.capabilities.changed — diff summary event
|
|
169
|
+
5. ControlBus subscribers re-read on next turn
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
**Invariant.** *If step 4 did not emit, step 5 must not see the capability.*
|
|
173
|
+
|
|
174
|
+
### D6 — Ordering: FIFO per `contract_id` + at-least-once + idempotent handlers
|
|
175
|
+
|
|
176
|
+
This is the single decision that introduces fresh semantics; all others either inherit or follow naturally.
|
|
177
|
+
|
|
178
|
+
**Decision.**
|
|
179
|
+
|
|
180
|
+
- **FIFO per `contract_id`.** Directives within one contract chain are delivered and journaled in emission order. Cross-contract ordering is *not* guaranteed; that is the parallelism unlock.
|
|
181
|
+
- **At-least-once delivery with fencing.** Timeout → the Coordinator first fences the timed-out `(contract_id, correlation_id)` so any later frames from that attempt are ignored, emits `retry` while budget remains, and dispatches a fresh attempt under the same `contract_id` with a new `correlation_id` and `parent_correlation_id` pointing at the fenced attempt. No exactly-once machinery.
|
|
182
|
+
- **Idempotency obligation on handlers.** A handler that receives a duplicate `(contract_id, correlation_id)` replays the cached stream and final result for that exact attempt instead of re-executing. Cache lifetime equals the contract's lifetime (cleared at completion or cancellation).
|
|
183
|
+
- **Stream replay on reconnect.** For streamable-http runtimes, the runtime cache is append-only per `(contract_id, correlation_id)` and contains every emitted intermediate event plus the final envelope once available. A reconnect for the same unfenced attempt receives the cached prefix first, with the original event ids/call ids, then resumes streaming only if the original attempt is still running. The Coordinator appends by stable event identity, treats duplicate streamed events as no-ops, and drops all frames from fenced attempts. For stdio runtimes, replay is only available when the adapter can prove the subprocess is still alive and can accept a duplicate request frame; otherwise EOF/pipe loss is D7 runtime loss, not reconnect.
|
|
184
|
+
- **LLM non-determinism resolution.** Duplicate delivery of the same `(contract_id, correlation_id)` returns the cache; retry execution gets a new `correlation_id` so it can run fresh while remaining under the same contract. *Intentional* user re-execution allocates a new `contract_id` (matches `--force-rerun` semantics in [#512](https://github.com/Q00/ouroboros/issues/512) C5).
|
|
185
|
+
|
|
186
|
+
**Cache backend.** Filesystem-keyed under `.ouroboros/cache/contracts/<contract_id>/` so it aligns with Disposable Memory's content-addressed `artifact_ref` story. SQLite-backed alternatives are deferred until usage evidence demands them.
|
|
187
|
+
|
|
188
|
+
**Why this matters.** Replay from the journal is the *replay* verb in #476's north star. If FIFO per contract is not honored, replays diverge from the recorded run. If at-least-once is not honored, transient failures produce silent gaps. If idempotency is not enforced, retries produce duplicate work and user-visible non-determinism. All three exist together or not at all.
|
|
189
|
+
|
|
190
|
+
**Risks.**
|
|
191
|
+
- Idempotency cache vs. genuine re-execution intent. Mitigation: the rule "duplicate deliveries reuse the cache; timeout retries get a new `correlation_id`; user-requested reruns allocate a new `contract_id`" is documented in this RFC and enforced by the Disposable Memory replay default.
|
|
192
|
+
- Cache eviction during a long contract. Mitigation: cache lifetime = contract lifetime, not a TTL; eviction only happens on contract completion or cancellation.
|
|
193
|
+
|
|
194
|
+
### D7 — Timeout and failure: per-stage policy + Directive mapping
|
|
195
|
+
|
|
196
|
+
Configurable per stage via the binding table from [#519](https://github.com/Q00/ouroboros/issues/519):
|
|
197
|
+
|
|
198
|
+
```toml
|
|
199
|
+
[orchestrator.runtime_profile.stages.evaluate]
|
|
200
|
+
runtime = "claude_code"
|
|
201
|
+
timeout_ms = 90000
|
|
202
|
+
retry_budget = 2
|
|
203
|
+
on_timeout = "retry" # "retry" or "cancel"
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
**Failure → Directive mapping.**
|
|
207
|
+
|
|
208
|
+
| Failure mode | Directive | Notes |
|
|
209
|
+
|---|---|---|
|
|
210
|
+
| Runtime exceeded `deadline_ms` | Coordinator emits `retry` with a new `correlation_id` while budget remains, then `cancel` | Budget owned by the existing resilience layer; runtime does not decide retry budget |
|
|
211
|
+
| Streamable-http connection drop while runtime remains alive | no new directive; reconnect via D6 | Coordinator replays cached prefix and resumes the in-flight stream for the same `(contract_id, correlation_id)` |
|
|
212
|
+
| Stdio EOF/pipe loss or runtime process crash / lost runtime identity | `cancel` immediately | Cooperative trust: do not assume retry safety after process death; this is not the D6 reconnect path |
|
|
213
|
+
| Schema validation failure on result envelope | `cancel` | Malformed envelope is not retryable |
|
|
214
|
+
| Runtime explicitly returned `wait` | propagate `wait` | External input dependency surfaced to operator |
|
|
215
|
+
|
|
216
|
+
The retry budget reuses the existing resilience layer's accounting — no new budget surface is introduced. Attempt fencing is Coordinator-owned and keyed by `(contract_id, correlation_id)` so FIFO per contract is preserved even if a timed-out runtime later writes to the old stream.
|
|
217
|
+
|
|
218
|
+
## Sequence diagram — one contract round trip
|
|
219
|
+
|
|
220
|
+
```mermaid
|
|
221
|
+
sequenceDiagram
|
|
222
|
+
participant O as Orchestrator
|
|
223
|
+
participant C as Coordinator (embedded)
|
|
224
|
+
participant R as Runtime (e.g. codex_cli)
|
|
225
|
+
participant E as EventStore
|
|
226
|
+
|
|
227
|
+
O->>C: spawn(intent, AgentRuntimeContext)
|
|
228
|
+
C->>R: POST /mesh/contract\nrequest envelope (contract_id, target=lineage/<id>, directive=evaluate)
|
|
229
|
+
R-->>C: stream: llm.call.requested
|
|
230
|
+
C->>E: append (target_type=lineage, target_id=<id>)
|
|
231
|
+
R-->>C: stream: llm.call.returned (prompt_hash, completion_preview)
|
|
232
|
+
C->>E: append
|
|
233
|
+
R-->>C: stream: tool.call.started + tool.call.returned
|
|
234
|
+
C->>E: append (×2)
|
|
235
|
+
R-->>C: result envelope (status=ok, next_directive=converge, artifact_ref="sha256:...", runtime_events_emitted_count=4)
|
|
236
|
+
C->>E: append (control.directive.emitted converge)
|
|
237
|
+
C-->>O: AgentProcessHandle(replay-able by contract_id)
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
## Cross-RFC consistency
|
|
241
|
+
|
|
242
|
+
| Subject | Source | This RFC's behaviour |
|
|
243
|
+
|---|---|---|
|
|
244
|
+
| `contract_id = ULID` | this RFC, D2 | Inherited by [#513](https://github.com/Q00/ouroboros/issues/513) |
|
|
245
|
+
| `artifact_ref = "sha256:..."` | [#512](https://github.com/Q00/ouroboros/issues/512) C2 | Used in result envelope (D2) |
|
|
246
|
+
| Replay does not re-execute LLM calls | #476 M3 + #518 | Honored by D6 idempotency cache |
|
|
247
|
+
| `target_type` vocabulary | events/control.py (#492) | Open string with known values documented there; this RFC must not close the set |
|
|
248
|
+
| `policy.capabilities.changed` invariant | #476 Q4 | Reused verbatim in D5 |
|
|
249
|
+
|
|
250
|
+
## Pre-merge checklist
|
|
251
|
+
|
|
252
|
+
- [ ] All 7 decisions present, each with option, rationale, risks
|
|
253
|
+
- [ ] Envelope JSONC blocks lint as valid JSON when comments are stripped
|
|
254
|
+
- [ ] Sequence diagram renders (mermaid) and matches the textual description
|
|
255
|
+
- [ ] Cross-references resolve to existing issues / lines
|
|
256
|
+
- [ ] At least two maintainer approvals on the docs PR
|
|
257
|
+
- [ ] D6 sub-thread (idempotency cache backend) resolved; resolution captured here
|
|
258
|
+
- [ ] D2 `extra` slot governance rule explicitly stated
|
|
259
|
+
- [ ] `contract_id = ULID` matches what `contract-ledger.md` (#513) inherits
|
|
260
|
+
- [ ] `artifact_ref = "sha256:..."` matches what `disposable-memory.md` (#512) chose
|
|
261
|
+
- [ ] Failure → Directive mapping matches the body of [#518](https://github.com/Q00/ouroboros/issues/518) cancellation discipline
|
|
262
|
+
|
|
263
|
+
## Post-merge checklist
|
|
264
|
+
|
|
265
|
+
- [ ] `docs/rfc/mesh.md` reachable from the docs site (or the README index when it lands)
|
|
266
|
+
- [ ] Issue [#511](https://github.com/Q00/ouroboros/issues/511) closed with a back-link to this PR
|
|
267
|
+
- [ ] At least three Phase 3 implementation issues opened referencing this RFC by section (Coordinator service, ResultEvent envelope, runtime registration handshake)
|
|
268
|
+
- [ ] `policy.capabilities.changed` invariant from D5 confirmed against the existing dynamic-MCP code path with one manual smoke run
|
|
269
|
+
|
|
270
|
+
## Rollback
|
|
271
|
+
|
|
272
|
+
The deliverable is a docs PR with no runtime impact. Rollback = revert the docs PR. No data, schema, or behavior change to undo. The proposal comment in [#511](https://github.com/Q00/ouroboros/issues/511) remains as the working draft so subsequent attempts can iterate from the same starting point.
|
|
@@ -18,7 +18,7 @@ version_tuple: tuple[int | str, ...]
|
|
|
18
18
|
commit_id: str | None
|
|
19
19
|
__commit_id__: str | None
|
|
20
20
|
|
|
21
|
-
__version__ = version = '0.31.2.
|
|
22
|
-
__version_tuple__ = version_tuple = (0, 31, 2, '
|
|
21
|
+
__version__ = version = '0.31.2.dev16'
|
|
22
|
+
__version_tuple__ = version_tuple = (0, 31, 2, 'dev16')
|
|
23
23
|
|
|
24
24
|
__commit_id__ = commit_id = None
|
{ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/src/ouroboros/providers/codex_cli_adapter.py
RENAMED
|
@@ -484,6 +484,39 @@ class CodexCliLLMAdapter:
|
|
|
484
484
|
|
|
485
485
|
return stderr.strip()
|
|
486
486
|
|
|
487
|
+
def _extract_stdout_errors(self, stdout_lines: list[str]) -> list[str]:
|
|
488
|
+
"""Pull error event messages from a Codex JSONL stdout stream.
|
|
489
|
+
|
|
490
|
+
Codex CLI 0.128+ emits in-flight failures (provider 502s, model
|
|
491
|
+
registry mismatches, auth issues, retry exhaustion) as JSONL events
|
|
492
|
+
on stdout with ``type`` of ``"error"`` or ``"turn.failed"``. The
|
|
493
|
+
process eventually exits with rc != 0 and only the static startup
|
|
494
|
+
banner ("Reading prompt from stdin...") on stderr — so any error
|
|
495
|
+
report that forwards just stderr loses every actionable detail.
|
|
496
|
+
|
|
497
|
+
This helper reads ``stdout_lines`` in arrival order and returns the
|
|
498
|
+
textual ``message`` from each terminal/error event, preserving order
|
|
499
|
+
so callers can use ``[-1]`` for the most recent (final) error.
|
|
500
|
+
"""
|
|
501
|
+
errors: list[str] = []
|
|
502
|
+
for line in stdout_lines:
|
|
503
|
+
event = self._parse_json_event(line)
|
|
504
|
+
if not event:
|
|
505
|
+
continue
|
|
506
|
+
event_type = event.get("type")
|
|
507
|
+
if event_type not in {"error", "turn.failed"}:
|
|
508
|
+
continue
|
|
509
|
+
|
|
510
|
+
payload = event.get("error") if event_type == "turn.failed" else event
|
|
511
|
+
if isinstance(payload, dict):
|
|
512
|
+
msg = payload.get("message")
|
|
513
|
+
if isinstance(msg, str) and msg.strip():
|
|
514
|
+
errors.append(msg.strip())
|
|
515
|
+
continue
|
|
516
|
+
if isinstance(payload, str) and payload.strip():
|
|
517
|
+
errors.append(payload.strip())
|
|
518
|
+
return errors
|
|
519
|
+
|
|
487
520
|
def _format_tool_info(self, tool_name: str, tool_input: dict[str, Any]) -> str:
|
|
488
521
|
"""Format tool name and input details for debug callbacks."""
|
|
489
522
|
detail = ""
|
|
@@ -728,15 +761,18 @@ class CodexCliLLMAdapter:
|
|
|
728
761
|
)
|
|
729
762
|
|
|
730
763
|
if process.returncode != 0:
|
|
764
|
+
stdout_errors = self._extract_stdout_errors(stdout_lines)
|
|
731
765
|
return Result.err(
|
|
732
766
|
ProviderError(
|
|
733
|
-
message=
|
|
767
|
+
message=(stdout_errors[-1] if stdout_errors else None)
|
|
768
|
+
or content
|
|
734
769
|
or f"{self._display_name} exited with code {process.returncode}",
|
|
735
770
|
provider=self._provider_name,
|
|
736
771
|
details={
|
|
737
772
|
"returncode": process.returncode,
|
|
738
773
|
"session_id": session_id,
|
|
739
774
|
"stderr": "\n".join(stderr_lines).strip(),
|
|
775
|
+
"stdout_errors": stdout_errors,
|
|
740
776
|
},
|
|
741
777
|
)
|
|
742
778
|
)
|
|
@@ -889,15 +925,18 @@ class CodexCliLLMAdapter:
|
|
|
889
925
|
content = last_content or self._fallback_content(stdout_lines, "\n".join(stderr_lines))
|
|
890
926
|
|
|
891
927
|
if process.returncode != 0:
|
|
928
|
+
stdout_errors = self._extract_stdout_errors(stdout_lines)
|
|
892
929
|
return Result.err(
|
|
893
930
|
ProviderError(
|
|
894
|
-
message=
|
|
931
|
+
message=(stdout_errors[-1] if stdout_errors else None)
|
|
932
|
+
or content
|
|
895
933
|
or f"{self._display_name} exited with code {process.returncode}",
|
|
896
934
|
provider=self._provider_name,
|
|
897
935
|
details={
|
|
898
936
|
"returncode": process.returncode,
|
|
899
937
|
"session_id": session_id,
|
|
900
938
|
"stderr": "\n".join(stderr_lines).strip(),
|
|
939
|
+
"stdout_errors": stdout_errors,
|
|
901
940
|
},
|
|
902
941
|
)
|
|
903
942
|
)
|
|
@@ -93,6 +93,27 @@ class _FakeProcess:
|
|
|
93
93
|
self.returncode = self._final_returncode
|
|
94
94
|
|
|
95
95
|
|
|
96
|
+
class _LegacyFakeProcess:
|
|
97
|
+
"""Process stub that exercises the communicate() fallback branch."""
|
|
98
|
+
|
|
99
|
+
def __init__(
|
|
100
|
+
self,
|
|
101
|
+
*,
|
|
102
|
+
stdout: str = "",
|
|
103
|
+
stderr: str = "",
|
|
104
|
+
returncode: int = 0,
|
|
105
|
+
) -> None:
|
|
106
|
+
self.stdin = _FakeStdin()
|
|
107
|
+
self._stdout = stdout.encode("utf-8")
|
|
108
|
+
self._stderr = stderr.encode("utf-8")
|
|
109
|
+
self.returncode = returncode
|
|
110
|
+
self.communicate_calls = 0
|
|
111
|
+
|
|
112
|
+
async def communicate(self, _input: bytes | None = None) -> tuple[bytes, bytes]:
|
|
113
|
+
self.communicate_calls += 1
|
|
114
|
+
return self._stdout, self._stderr
|
|
115
|
+
|
|
116
|
+
|
|
96
117
|
class TestCodexCliLLMAdapter:
|
|
97
118
|
"""Tests for CodexCliLLMAdapter."""
|
|
98
119
|
|
|
@@ -607,6 +628,139 @@ class TestCodexCliLLMAdapter:
|
|
|
607
628
|
assert result.error.details["overflow_stage"] == "stream_capture"
|
|
608
629
|
assert result.error.details["capture_limit_bytes"] == 8
|
|
609
630
|
|
|
631
|
+
@pytest.mark.asyncio
|
|
632
|
+
async def test_complete_surfaces_stdout_error_events_on_nonzero_exit(self) -> None:
|
|
633
|
+
"""Codex emits in-flight failures as JSONL on stdout — those messages must
|
|
634
|
+
reach ProviderError.message and details, not just the static stderr banner.
|
|
635
|
+
|
|
636
|
+
Regression for #560: previously the adapter forwarded only stderr so all
|
|
637
|
+
codex failures looked identical regardless of root cause.
|
|
638
|
+
"""
|
|
639
|
+
adapter = CodexCliLLMAdapter(cli_path="codex")
|
|
640
|
+
|
|
641
|
+
async def fake_create_subprocess_exec(*command: str, **kwargs: Any) -> _FakeProcess:
|
|
642
|
+
output_index = command.index("--output-last-message") + 1
|
|
643
|
+
Path(command[output_index]).write_text("", encoding="utf-8")
|
|
644
|
+
return _FakeProcess(
|
|
645
|
+
stdout="\n".join(
|
|
646
|
+
[
|
|
647
|
+
json.dumps({"type": "thread.started", "thread_id": "t1"}),
|
|
648
|
+
json.dumps({"type": "turn.started"}),
|
|
649
|
+
json.dumps(
|
|
650
|
+
{
|
|
651
|
+
"type": "error",
|
|
652
|
+
"message": "Reconnecting... 1/5 (502 Bad Gateway)",
|
|
653
|
+
}
|
|
654
|
+
),
|
|
655
|
+
json.dumps(
|
|
656
|
+
{
|
|
657
|
+
"type": "turn.failed",
|
|
658
|
+
"error": {"message": "502 Bad Gateway final"},
|
|
659
|
+
}
|
|
660
|
+
),
|
|
661
|
+
]
|
|
662
|
+
),
|
|
663
|
+
stderr="Reading prompt from stdin...",
|
|
664
|
+
returncode=1,
|
|
665
|
+
)
|
|
666
|
+
|
|
667
|
+
with patch(
|
|
668
|
+
"ouroboros.providers.codex_cli_adapter.asyncio.create_subprocess_exec",
|
|
669
|
+
side_effect=fake_create_subprocess_exec,
|
|
670
|
+
):
|
|
671
|
+
result = await adapter.complete(
|
|
672
|
+
[Message(role=MessageRole.USER, content="Reflect on the run.")],
|
|
673
|
+
CompletionConfig(model="default"),
|
|
674
|
+
)
|
|
675
|
+
|
|
676
|
+
assert result.is_err
|
|
677
|
+
assert result.error.provider == "codex_cli"
|
|
678
|
+
assert "502 Bad Gateway final" in result.error.message
|
|
679
|
+
stdout_errors = result.error.details["stdout_errors"]
|
|
680
|
+
assert len(stdout_errors) == 2
|
|
681
|
+
assert "Reconnecting... 1/5" in stdout_errors[0]
|
|
682
|
+
assert "502 Bad Gateway final" in stdout_errors[1]
|
|
683
|
+
assert result.error.details["stderr"] == "Reading prompt from stdin..."
|
|
684
|
+
|
|
685
|
+
@pytest.mark.asyncio
|
|
686
|
+
async def test_legacy_complete_surfaces_stdout_error_events_on_nonzero_exit(
|
|
687
|
+
self,
|
|
688
|
+
) -> None:
|
|
689
|
+
"""The communicate() fallback reports stdout JSONL errors like the streaming path."""
|
|
690
|
+
adapter = CodexCliLLMAdapter(cli_path="codex")
|
|
691
|
+
process_holder: dict[str, _LegacyFakeProcess] = {}
|
|
692
|
+
|
|
693
|
+
async def fake_create_subprocess_exec(*command: str, **kwargs: Any) -> _LegacyFakeProcess:
|
|
694
|
+
output_index = command.index("--output-last-message") + 1
|
|
695
|
+
Path(command[output_index]).write_text("", encoding="utf-8")
|
|
696
|
+
process = _LegacyFakeProcess(
|
|
697
|
+
stdout="\n".join(
|
|
698
|
+
[
|
|
699
|
+
json.dumps({"type": "thread.started", "thread_id": "legacy-thread"}),
|
|
700
|
+
json.dumps(
|
|
701
|
+
{
|
|
702
|
+
"type": "error",
|
|
703
|
+
"message": "legacy transient failure",
|
|
704
|
+
}
|
|
705
|
+
),
|
|
706
|
+
json.dumps(
|
|
707
|
+
{
|
|
708
|
+
"type": "turn.failed",
|
|
709
|
+
"error": {"message": "legacy final failure"},
|
|
710
|
+
}
|
|
711
|
+
),
|
|
712
|
+
]
|
|
713
|
+
),
|
|
714
|
+
stderr="Reading prompt from stdin...",
|
|
715
|
+
returncode=1,
|
|
716
|
+
)
|
|
717
|
+
process_holder["process"] = process
|
|
718
|
+
return process
|
|
719
|
+
|
|
720
|
+
with patch(
|
|
721
|
+
"ouroboros.providers.codex_cli_adapter.asyncio.create_subprocess_exec",
|
|
722
|
+
side_effect=fake_create_subprocess_exec,
|
|
723
|
+
):
|
|
724
|
+
result = await adapter.complete(
|
|
725
|
+
[Message(role=MessageRole.USER, content="Reflect on the legacy run.")],
|
|
726
|
+
CompletionConfig(model="default"),
|
|
727
|
+
)
|
|
728
|
+
|
|
729
|
+
assert result.is_err
|
|
730
|
+
assert result.error.provider == "codex_cli"
|
|
731
|
+
assert result.error.message == "legacy final failure"
|
|
732
|
+
assert result.error.details["session_id"] == "legacy-thread"
|
|
733
|
+
assert result.error.details["stdout_errors"] == [
|
|
734
|
+
"legacy transient failure",
|
|
735
|
+
"legacy final failure",
|
|
736
|
+
]
|
|
737
|
+
assert result.error.details["stderr"] == "Reading prompt from stdin..."
|
|
738
|
+
assert process_holder["process"].communicate_calls == 1
|
|
739
|
+
|
|
740
|
+
def test_extract_stdout_errors_returns_messages_in_arrival_order(self) -> None:
|
|
741
|
+
"""Helper extracts only error/turn.failed events and preserves order."""
|
|
742
|
+
adapter = CodexCliLLMAdapter(cli_path="codex")
|
|
743
|
+
stdout_lines = [
|
|
744
|
+
json.dumps({"type": "thread.started", "thread_id": "t1"}),
|
|
745
|
+
json.dumps({"type": "turn.started"}),
|
|
746
|
+
json.dumps({"type": "error", "message": "first transient"}),
|
|
747
|
+
json.dumps({"type": "item.completed", "item": {"text": "ignored"}}),
|
|
748
|
+
json.dumps({"type": "error", "message": "second transient"}),
|
|
749
|
+
json.dumps({"type": "turn.failed", "error": {"message": "final fatal"}}),
|
|
750
|
+
"not-a-json-line",
|
|
751
|
+
]
|
|
752
|
+
errors = adapter._extract_stdout_errors(stdout_lines)
|
|
753
|
+
assert errors == ["first transient", "second transient", "final fatal"]
|
|
754
|
+
|
|
755
|
+
def test_extract_stdout_errors_handles_empty_and_malformed(self) -> None:
|
|
756
|
+
"""Empty input and malformed events do not crash."""
|
|
757
|
+
adapter = CodexCliLLMAdapter(cli_path="codex")
|
|
758
|
+
assert adapter._extract_stdout_errors([]) == []
|
|
759
|
+
assert adapter._extract_stdout_errors([json.dumps({"type": "error"})]) == []
|
|
760
|
+
assert adapter._extract_stdout_errors(
|
|
761
|
+
[json.dumps({"type": "turn.failed", "error": "string fatal"})]
|
|
762
|
+
) == ["string fatal"]
|
|
763
|
+
|
|
610
764
|
|
|
611
765
|
class TestLazyImport:
|
|
612
766
|
"""Test lazy import of CodexCliLLMAdapter from providers package."""
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/bug_report.yml
RENAMED
|
File without changes
|
|
File without changes
|
{ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.github/ISSUE_TEMPLATE/feature_request.yml
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.ouroboros/seeds/seed_73827177a2a3.yaml
RENAMED
|
File without changes
|
{ouroboros_ai-0.31.2.dev14 → ouroboros_ai-0.31.2.dev16}/.ouroboros/seeds/seed_78c8e6e41813.yaml
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|