ouroboros-ai 0.2.0__tar.gz → 0.2.2__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.
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/PKG-INFO +1 -1
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/pyproject.toml +1 -1
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/bigbang/ambiguity.py +26 -17
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/bigbang/test_ambiguity.py +9 -9
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/uv.lock +1 -1
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/.gitignore +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/.pre-commit-config.yaml +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/.python-version +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/CHANGELOG.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/LICENSE +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/PR-43-CODE-REVIEW-REPORT.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/README.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/github-issue-mapping.yaml +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/sprint-status.yaml +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-1-project-initialization-with-uv.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-2-core-types-and-error-handling.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-3-event-store-with-sqlalchemy-core.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-4-configuration-and-credentials-management.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-5-llm-provider-adapter-with-litellm.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-6-cli-skeleton-with-typer-and-rich.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-7-structured-logging-with-structlog.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-8-checkpoint-and-recovery-system.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/0-9-context-compression-engine.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/1-1-interview-protocol-engine.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/1-2-ambiguity-score-calculation.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/1-3-immutable-seed-generation.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/2-1-three-tier-model-configuration.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/2-2-complexity-based-routing.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/2-3-escalation-on-failure.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/2-4-downgrade-on-success.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/3-1-double-diamond-cycle-implementation.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/3-2-hierarchical-ac-decomposition.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/3-3-atomicity-detection.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/3-4-subagent-isolation.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/4-1-stagnation-detection-4-patterns.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/4-2-lateral-thinking-personas.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/4-3-persona-rotation-strategy.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/5-1-stage-1-mechanical-verification.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/5-2-stage-2-semantic-evaluation.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/5-3-stage-3-multi-model-consensus.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/5-4-consensus-trigger-matrix.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/6-1-drift-measurement-engine.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/6-2-automatic-retrospective.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/7-1-todo-registry.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/stories/7-2-secondary-loop-batch-processing.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/planning-artifacts/architecture.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/planning-artifacts/bmm-workflow-status.yaml +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/planning-artifacts/epics.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/update-stories.sh +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/docs/running-with-claude-code.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/project-context.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/requirement/1_EXECUTIVE_SUMMARY.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/requirement/2_FULL_SPECIFICATION.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/requirement/3_CONFIG_TEMPLATE.yaml +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/requirement/4_REDDIT_EXAMPLE.md +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/__main__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/bigbang/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/bigbang/interview.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/bigbang/seed_generator.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/commands/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/commands/config.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/commands/init.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/commands/run.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/commands/status.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/formatters/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/formatters/panels.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/formatters/progress.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/formatters/tables.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/cli/main.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/config/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/config/loader.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/config/models.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/ac_tree.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/context.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/errors.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/security.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/seed.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/core/types.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/consensus.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/mechanical.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/models.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/pipeline.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/semantic.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/evaluation/trigger.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/events/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/events/base.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/events/decomposition.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/events/evaluation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/execution/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/execution/atomicity.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/execution/decomposition.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/execution/double_diamond.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/execution/subagent.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/observability/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/observability/drift.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/observability/logging.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/observability/retrospective.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/orchestrator/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/orchestrator/adapter.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/orchestrator/events.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/orchestrator/runner.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/orchestrator/session.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/checkpoint.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/event_store.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/migrations/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/migrations/runner.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/migrations/scripts/001_initial.sql +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/schema.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/persistence/uow.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/providers/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/providers/base.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/providers/claude_code_adapter.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/providers/litellm_adapter.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/py.typed +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/resilience/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/resilience/lateral.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/resilience/stagnation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/complexity.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/downgrade.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/escalation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/router.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/routing/tiers.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/secondary/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/secondary/scheduler.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/src/ouroboros/secondary/todo_registry.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/conftest.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/integration/test_entry_point.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/bigbang/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/bigbang/test_interview.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/bigbang/test_seed_generator.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/formatters/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/formatters/test_console.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/formatters/test_panels.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/formatters/test_progress.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/formatters/test_tables.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/cli/test_main.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/config/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/config/test_loader.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/config/test_models.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_ac_tree.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_context.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_errors.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_security.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_seed.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/core/test_types.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/test_consensus.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/test_mechanical.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/test_models.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/test_semantic.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/evaluation/test_trigger.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/events/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/events/test_base.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/events/test_decomposition_events.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/execution/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/execution/test_atomicity.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/execution/test_decomposition.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/execution/test_double_diamond.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/execution/test_subagent_isolation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/observability/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/observability/test_drift.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/observability/test_logging.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/observability/test_retrospective.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/orchestrator/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/orchestrator/test_adapter.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/orchestrator/test_events.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/orchestrator/test_runner.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/orchestrator/test_session.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/persistence/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/persistence/test_checkpoint.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/persistence/test_event_store.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/persistence/test_schema.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/persistence/test_uow.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/providers/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/providers/test_base.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/providers/test_litellm_adapter.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/resilience/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/resilience/test_lateral.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/resilience/test_stagnation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/test_complexity.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/test_downgrade.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/test_escalation.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/test_router.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/routing/test_tiers.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/secondary/__init__.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/secondary/test_scheduler.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/secondary/test_todo_registry.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/test_dependencies_configured.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/test_main_entry_point.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/test_module_structure.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/test_project_initialization.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tests/unit/test_tooling_configuration.py +0 -0
- {ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/tools/sync_github_project.py +0 -0
|
@@ -36,8 +36,8 @@ DEFAULT_MODEL = "openrouter/google/gemini-2.0-flash-001"
|
|
|
36
36
|
# Temperature for reproducible scoring
|
|
37
37
|
SCORING_TEMPERATURE = 0.1
|
|
38
38
|
|
|
39
|
-
# Maximum token limit
|
|
40
|
-
MAX_TOKEN_LIMIT =
|
|
39
|
+
# Maximum token limit (None = no limit, rely on model's context window)
|
|
40
|
+
MAX_TOKEN_LIMIT: int | None = None
|
|
41
41
|
|
|
42
42
|
|
|
43
43
|
class ComponentScore(BaseModel):
|
|
@@ -110,15 +110,15 @@ class AmbiguityScorer:
|
|
|
110
110
|
from interview conversation, producing reproducible scores.
|
|
111
111
|
|
|
112
112
|
Uses adaptive token allocation: starts with `initial_max_tokens` and
|
|
113
|
-
doubles on truncation up to `MAX_TOKEN_LIMIT`. Retries
|
|
114
|
-
|
|
113
|
+
doubles on truncation up to `MAX_TOKEN_LIMIT`. Retries until success
|
|
114
|
+
by default (unlimited), or up to `max_retries` if specified.
|
|
115
115
|
|
|
116
116
|
Attributes:
|
|
117
117
|
llm_adapter: The LLM adapter for completions.
|
|
118
118
|
model: Model identifier to use.
|
|
119
119
|
temperature: Temperature for reproducibility (default 0.1).
|
|
120
120
|
initial_max_tokens: Starting token limit (default 2048).
|
|
121
|
-
max_retries: Maximum retry attempts (default
|
|
121
|
+
max_retries: Maximum retry attempts, or None for unlimited (default).
|
|
122
122
|
|
|
123
123
|
Example:
|
|
124
124
|
scorer = AmbiguityScorer(llm_adapter=LiteLLMAdapter())
|
|
@@ -138,7 +138,7 @@ class AmbiguityScorer:
|
|
|
138
138
|
model: str = DEFAULT_MODEL
|
|
139
139
|
temperature: float = SCORING_TEMPERATURE
|
|
140
140
|
initial_max_tokens: int = 2048
|
|
141
|
-
max_retries: int =
|
|
141
|
+
max_retries: int | None = None # None = unlimited retries
|
|
142
142
|
|
|
143
143
|
async def score(
|
|
144
144
|
self, state: InterviewState
|
|
@@ -180,8 +180,15 @@ class AmbiguityScorer:
|
|
|
180
180
|
current_max_tokens = self.initial_max_tokens
|
|
181
181
|
last_error: Exception | ProviderError | None = None
|
|
182
182
|
last_response: str = ""
|
|
183
|
+
attempt = 0
|
|
184
|
+
|
|
185
|
+
while True:
|
|
186
|
+
# Check retry limit if set
|
|
187
|
+
if self.max_retries is not None and attempt >= self.max_retries:
|
|
188
|
+
break
|
|
189
|
+
|
|
190
|
+
attempt += 1
|
|
183
191
|
|
|
184
|
-
for attempt in range(self.max_retries):
|
|
185
192
|
config = CompletionConfig(
|
|
186
193
|
model=self.model,
|
|
187
194
|
temperature=self.temperature,
|
|
@@ -190,15 +197,15 @@ class AmbiguityScorer:
|
|
|
190
197
|
|
|
191
198
|
result = await self.llm_adapter.complete(messages, config)
|
|
192
199
|
|
|
193
|
-
#
|
|
200
|
+
# Retry on provider errors (rate limits, transient failures)
|
|
194
201
|
if result.is_err:
|
|
195
202
|
last_error = result.error
|
|
196
203
|
log.warning(
|
|
197
204
|
"ambiguity.scoring.provider_error_retrying",
|
|
198
205
|
interview_id=state.interview_id,
|
|
199
206
|
error=str(result.error),
|
|
200
|
-
attempt=attempt
|
|
201
|
-
max_retries=self.max_retries,
|
|
207
|
+
attempt=attempt,
|
|
208
|
+
max_retries=self.max_retries or "unlimited",
|
|
202
209
|
)
|
|
203
210
|
continue
|
|
204
211
|
|
|
@@ -221,7 +228,7 @@ class AmbiguityScorer:
|
|
|
221
228
|
constraint_clarity=breakdown.constraint_clarity.clarity_score,
|
|
222
229
|
success_criteria_clarity=breakdown.success_criteria_clarity.clarity_score,
|
|
223
230
|
tokens_used=current_max_tokens,
|
|
224
|
-
attempt=attempt
|
|
231
|
+
attempt=attempt,
|
|
225
232
|
)
|
|
226
233
|
|
|
227
234
|
return Result.ok(ambiguity_score)
|
|
@@ -230,17 +237,19 @@ class AmbiguityScorer:
|
|
|
230
237
|
last_error = e
|
|
231
238
|
last_response = result.value.content
|
|
232
239
|
|
|
233
|
-
#
|
|
240
|
+
# Only increase tokens if response was truncated
|
|
234
241
|
is_truncated = result.value.finish_reason == "length"
|
|
235
242
|
|
|
236
243
|
if is_truncated:
|
|
237
|
-
#
|
|
238
|
-
next_tokens =
|
|
244
|
+
# Double tokens on truncation, capped at MAX_TOKEN_LIMIT if set
|
|
245
|
+
next_tokens = current_max_tokens * 2
|
|
246
|
+
if MAX_TOKEN_LIMIT is not None:
|
|
247
|
+
next_tokens = min(next_tokens, MAX_TOKEN_LIMIT)
|
|
239
248
|
log.warning(
|
|
240
249
|
"ambiguity.scoring.truncated_retrying",
|
|
241
250
|
interview_id=state.interview_id,
|
|
242
251
|
error=str(e),
|
|
243
|
-
attempt=attempt
|
|
252
|
+
attempt=attempt,
|
|
244
253
|
current_tokens=current_max_tokens,
|
|
245
254
|
next_tokens=next_tokens,
|
|
246
255
|
)
|
|
@@ -251,11 +260,11 @@ class AmbiguityScorer:
|
|
|
251
260
|
"ambiguity.scoring.format_error_retrying",
|
|
252
261
|
interview_id=state.interview_id,
|
|
253
262
|
error=str(e),
|
|
254
|
-
attempt=attempt
|
|
263
|
+
attempt=attempt,
|
|
255
264
|
finish_reason=result.value.finish_reason,
|
|
256
265
|
)
|
|
257
266
|
|
|
258
|
-
# All retries exhausted
|
|
267
|
+
# All retries exhausted (only reached if max_retries is set)
|
|
259
268
|
log.warning(
|
|
260
269
|
"ambiguity.scoring.failed",
|
|
261
270
|
interview_id=state.interview_id,
|
|
@@ -302,7 +302,7 @@ class TestAmbiguityScorerInit:
|
|
|
302
302
|
assert scorer.model == "openrouter/google/gemini-2.0-flash-001"
|
|
303
303
|
assert scorer.temperature == SCORING_TEMPERATURE
|
|
304
304
|
assert scorer.initial_max_tokens == 2048
|
|
305
|
-
assert scorer.max_retries
|
|
305
|
+
assert scorer.max_retries is None # Unlimited by default
|
|
306
306
|
|
|
307
307
|
def test_scorer_custom_values(self) -> None:
|
|
308
308
|
"""AmbiguityScorer accepts custom values."""
|
|
@@ -1078,13 +1078,13 @@ class TestMaxTokenLimit:
|
|
|
1078
1078
|
"""Test MAX_TOKEN_LIMIT constant."""
|
|
1079
1079
|
|
|
1080
1080
|
def test_max_token_limit_value(self) -> None:
|
|
1081
|
-
"""MAX_TOKEN_LIMIT
|
|
1082
|
-
assert MAX_TOKEN_LIMIT
|
|
1081
|
+
"""MAX_TOKEN_LIMIT is None (no limit, rely on model's context window)."""
|
|
1082
|
+
assert MAX_TOKEN_LIMIT is None
|
|
1083
1083
|
|
|
1084
|
-
async def
|
|
1085
|
-
"""Token growth
|
|
1084
|
+
async def test_token_growth_unbounded_when_no_limit(self) -> None:
|
|
1085
|
+
"""Token growth doubles without cap when MAX_TOKEN_LIMIT is None."""
|
|
1086
1086
|
mock_adapter = MagicMock()
|
|
1087
|
-
# All calls fail with truncation - tokens should
|
|
1087
|
+
# All calls fail with truncation - tokens should keep doubling
|
|
1088
1088
|
mock_adapter.complete = AsyncMock(
|
|
1089
1089
|
return_value=Result.ok(
|
|
1090
1090
|
create_mock_completion_response(
|
|
@@ -1094,7 +1094,7 @@ class TestMaxTokenLimit:
|
|
|
1094
1094
|
)
|
|
1095
1095
|
)
|
|
1096
1096
|
|
|
1097
|
-
# Start with 4096, should try 4096 -> 8192 ->
|
|
1097
|
+
# Start with 4096, should try 4096 -> 8192 -> 16384 (no cap)
|
|
1098
1098
|
scorer = AmbiguityScorer(
|
|
1099
1099
|
llm_adapter=mock_adapter, initial_max_tokens=4096, max_retries=3
|
|
1100
1100
|
)
|
|
@@ -1104,8 +1104,8 @@ class TestMaxTokenLimit:
|
|
|
1104
1104
|
|
|
1105
1105
|
assert result.is_err # All retries fail
|
|
1106
1106
|
assert mock_adapter.complete.call_count == 3
|
|
1107
|
-
# Verify token progression: 4096 -> 8192 ->
|
|
1107
|
+
# Verify token progression: 4096 -> 8192 -> 16384 (no cap)
|
|
1108
1108
|
configs = [call[0][1] for call in mock_adapter.complete.call_args_list]
|
|
1109
1109
|
assert configs[0].max_tokens == 4096
|
|
1110
1110
|
assert configs[1].max_tokens == 8192 # Doubled
|
|
1111
|
-
assert configs[2].max_tokens ==
|
|
1111
|
+
assert configs[2].max_tokens == 16384 # Doubled again, no cap
|
|
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.2.0 → ouroboros_ai-0.2.2}/_bmad-output/implementation-artifacts/sprint-status.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
|
|
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
|
{ouroboros_ai-0.2.0 → ouroboros_ai-0.2.2}/_bmad-output/planning-artifacts/bmm-workflow-status.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
|
|
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
|
|
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
|
|
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
|
|
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
|
|
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
|
|
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
|
|
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
|