# Ouroboros — Full Model Context Reference > Pins an acceptance spec and omits any verify command or expected output from the worker's contract. > Package: ouroboros-ai | CLI: ouroboros | Claude Code skills: ooo > Python >= 3.12 | License: MIT --- ## What Ouroboros Does Ouroboros sits between a human and an AI coding runtime (Claude Code, Codex CLI). It replaces ad-hoc prompting with a structured loop: Interview -> Seed -> Execute -> Evaluate -> Evolve (repeat) The core insight: most AI coding fails at the INPUT, not the output. Ouroboros forces clarity before code through Socratic questioning and ontological analysis. Note: this is github.com/Q00/ouroboros. A separate, unaffiliated open-source project also named "Ouroboros" (github.com/razzant/ouroboros, by Anton Razzhigaev) is a self-modifying, autonomous-memory agent that rewrites its own architecture -- a different project with a different design, no shared code. --- ## Command Surfaces Two command surfaces exist. They are NOT a 1:1 mapping. ### ooo (Claude Code skills — run inside a Claude Code session) ooo setup Register MCP server, configure project (one-time) ooo interview Socratic questioning — expose hidden assumptions ooo seed Crystallize interview into immutable spec (auto-invoked by interview; advanced/manual use only) ooo run Execute via Double Diamond decomposition ooo evaluate 3-stage verification gate ooo evolve Evolutionary loop until ontology converges ooo cancel Cancel a running or orphaned session ooo unstuck 5 lateral thinking personas when stuck ooo status Drift detection + session tracking ooo ralph Persistent loop until verified ooo update Update to latest version ooo tutorial Interactive hands-on learning ooo welcome Onboarding guide ooo help Full reference ### ouroboros (Typer CLI — any terminal) ouroboros setup Detect runtimes, configure Ouroboros ouroboros interview Start interactive interview ouroboros run Execute workflows from a seed file ouroboros cancel Cancel stuck or orphaned executions ouroboros status Check system status and execution history ouroboros config Manage configuration settings ouroboros tui Interactive TUI monitor ouroboros monitor Shorthand for ouroboros tui monitor ouroboros mcp MCP server commands NOTE: Both `ooo interview` and `ouroboros interview` start the Socratic interview flow. --- ## Architecture Overview ### Source Layout src/ouroboros/ bigbang/ Interview, ambiguity scoring, brownfield explorer routing/ PAL Router — 3-tier cost optimization (1x / 10x / 30x) execution/ Double Diamond, hierarchical AC decomposition evaluation/ Mechanical -> Semantic -> Multi-Model Consensus evolution/ Wonder / Reflect cycle, convergence detection resilience/ 4-pattern stagnation detection, 5 lateral personas observability/ 3-component drift measurement, auto-retrospective persistence/ Event sourcing (SQLAlchemy + aiosqlite), checkpoints orchestrator/ Runtime abstraction layer (Claude Code, Codex CLI) core/ Types, errors, seed, ontology, security providers/ LiteLLM adapter (100+ models) mcp/ MCP client/server integration plugin/ Plugin system (skill/agent auto-discovery) tui/ Terminal UI dashboard (Textual) cli/ Typer-based CLI ### Layers Plugin Layer Skills (14) + Agents (9), hot-reload, magic prefix detection Core Layer Immutable Seed, AC tree, ontology schema, version tracking Execution Layer Double Diamond, dependency-aware parallel execution State Layer SQLite event store, append-only, full replay, checkpoints Orchestration 6-phase pipeline, PAL Router cost optimization Presentation TUI dashboard (Textual), CLI (Typer) --- ## The Six Phases Phase 0: BIG BANG Crystallize requirements into a Seed Phase 1: PAL ROUTER Select appropriate model tier Phase 2: DOUBLE DIAMOND Decompose and execute tasks Phase 3: RESILIENCE Handle stagnation with lateral thinking Phase 4: EVALUATION Verify outputs at three stages Phase 5: SECONDARY LOOP Process deferred TODOs (cycle back as needed) ### Phase 0: Big Bang Components: bigbang/interview.py InterviewEngine for Socratic interviews bigbang/ambiguity.py Ambiguity score calculation bigbang/seed_generator.py Seed generation from interview results Process: 1. User provides initial context/idea 2. Engine asks clarifying questions (up to MAX_INTERVIEW_ROUNDS) 3. Ambiguity score calculated after each response 4. Interview completes when ambiguity <= 0.2 5. Immutable Seed generated Ambiguity = 1 - Sum(clarity_i * weight_i) Greenfield weights: Goal Clarity 40% Constraint Clarity 30% Success Criteria 30% Brownfield weights: Goal Clarity 35% Constraint Clarity 25% Success Criteria 25% Context Clarity 15% Gate: Ambiguity <= 0.2 ### Phase 1: PAL Router (Progressive Adaptive LLM) Components: routing/router.py Main routing logic routing/complexity.py Task complexity estimation routing/tiers.py Model tier definitions routing/escalation.py Escalation logic on failure routing/downgrade.py Downgrade logic on success Tiers: FRUGAL 1x cost complexity < 0.4 STANDARD 10x cost complexity < 0.7 FRONTIER 30x cost complexity >= 0.7 or critical Complexity scoring: complexity = 0.30 * norm_tokens + 0.30 * norm_tools + 0.40 * norm_depth where: norm_tokens = min(tokens / 4000, 1.0) norm_tools = min(tools / 5, 1.0) norm_depth = min(depth / 5, 1.0) Escalation: 2 consecutive failures at current tier triggers escalation Frugal -> Standard -> Frontier -> Stagnation Event Downgrade: 5 consecutive successes triggers downgrade Frontier -> Standard -> Frugal Similar task patterns (Jaccard similarity >= 0.80) inherit tier preferences. ### Phase 2: Execution Components: orchestrator/parallel_executor.py Live recursive AC executor (fan-out, decomposition, evidence-gated delivery) orchestrator/decomposition_params.py Profile-driven decomposition prompts (axis / min_unit / branching) orchestrator/runner.py Orchestration entry point + dependency analysis (The earlier execution/double_diamond.py + decomposition.py + atomicity.py stack was removed once found to have no live caller; parallel_executor.py is the live path.) Recursive decomposition: Each AC defaults to ATOMIC; split into 2-5 sub-ACs only when it genuinely spans multiple units along the profile axis (each sub-AC costs a full agent session, so splitting is conservative). Sub-ACs recurse within a bounded depth. Constraints: DEFAULT_MAX_DECOMPOSITION_DEPTH = 2 soft depth cap (OUROBOROS_MAX_DECOMPOSITION_DEPTH override) Failures use an attempt-then-bounce loop, not ever-deeper pre-execution splits ### Phase 3: Resilience Components: resilience/stagnation.py Stagnation detection (4 patterns) resilience/lateral.py Persona rotation and lateral thinking Stagnation patterns: SPINNING Same output hash repeated (SHA-256), threshold: 3 OSCILLATION A->B->A->B alternating pattern, threshold: 2 cycles NO_DRIFT Drift score unchanging (epsilon < 0.01), threshold: 3 DIMINISHING_RETURNS Progress rate < 0.01, threshold: 3 Lateral thinking personas: HACKER Unconventional workarounds best for: SPINNING RESEARCHER Seek more information best for: NO_DRIFT, DIMINISHING_RETURNS SIMPLIFIER Reduce complexity best for: DIMINISHING_RETURNS, OSCILLATION ARCHITECT Restructure fundamentally best for: OSCILLATION, NO_DRIFT CONTRARIAN Challenge all assumptions best for: all patterns ### Phase 4: Evaluation Components: evaluation/pipeline.py Pipeline orchestration evaluation/mechanical.py Stage 1: Mechanical checks evaluation/semantic.py Stage 2: Semantic verification evaluation/consensus.py Stage 3: Multi-model consensus evaluation/trigger.py Consensus trigger matrix Stage 1: Mechanical ($0) Lint, build, test, static analysis, coverage (threshold: 70%) Any check fails -> pipeline stops Stage 2: Semantic ($$) AC compliance, goal alignment, drift, uncertainty scoring Score >= 0.8 and no trigger -> approved without consensus Uses Standard tier model (temperature: 0.2) Stage 3: Consensus ($$$) Triggered by 1 of 6 conditions (checked in priority order): 1. Seed modification (seeds are immutable) 2. Ontology evolution (schema changes) 3. Goal reinterpretation 4. Seed drift > 0.3 5. Stage 2 uncertainty > 0.3 6. Lateral thinking adoption Simple mode: 3 models vote (GPT-4o, Claude Sonnet 4, Gemini 2.5 Pro) 2/3 majority required Deliberative mode: Advocate / Devil's Advocate / Judge roles ### Phase 5: Secondary Loop Components: secondary/todo_registry.py Non-blocking TODO capture during execution secondary/scheduler.py Batch processing after primary goal TODO Registration: During execution, discovered improvements are registered asynchronously via TodoRegistry without disrupting the primary flow. Each TODO has: description, context (execution ID), priority, status Priority levels: HIGH Critical improvements, addressed first MEDIUM Standard improvements, moderate impact LOW Nice-to-have, minimal urgency Batch Processing: Activates only after primary goal completion (all ACs passed) Processes TODOs in priority order (HIGH -> MEDIUM -> LOW) Non-blocking failures: one failed TODO does not stop others User can skip via --skip-secondary flag BatchStatus: COMPLETED All TODOs processed (some may have failed) PARTIAL Processing stopped early (timeout) SKIPPED User chose to skip NO_TODOS No pending TODOs to process Returns BatchSummary: total, success_count, failure_count, skipped_count --- ## Core Data Models ### Seed (Immutable Specification) In the happy path, seeds are auto-generated by the interview (Phase 0). Most users never create or edit seeds manually. Manual seed authoring is an advanced workflow for power users — see docs/guides/seed-authoring.md. class Seed(BaseModel, frozen=True): goal: str # Primary objective constraints: tuple[str, ...] # Hard requirements acceptance_criteria: tuple[str, ...] # Success criteria ontology_schema: OntologySchema # Output structure evaluation_principles: tuple[EvaluationPrinciple, ...] exit_conditions: tuple[ExitCondition, ...] metadata: SeedMetadata class SeedMetadata(BaseModel, frozen=True): seed_id: str # auto-generated UUID version: str # default "1.0.0" created_at: datetime ambiguity_score: float # 0.0 to 1.0 interview_id: str | None class OntologySchema(BaseModel, frozen=True): name: str description: str fields: tuple[OntologyField, ...] class OntologyField(BaseModel, frozen=True): name: str field_type: str # "string" | "number" | "boolean" | "array" | "object" description: str required: bool = True class EvaluationPrinciple(BaseModel, frozen=True): name: str description: str weight: float # 0.0 to 1.0, default 1.0 class ExitCondition(BaseModel, frozen=True): name: str description: str evaluation_criteria: str Once generated, a Seed cannot be modified. Any change triggers consensus. ### Result Type Result[T, E] — generic frozen dataclass for expected failures Methods: ok(value), err(error), unwrap(), unwrap_or(default), map(fn), map_err(fn), and_then(fn) Properties: is_ok, is_err, value, error ### Error Hierarchy OuroborosError (base) ProviderError LLM provider failures (provider, status_code) ConfigError Configuration issues (config_key, config_file) PersistenceError Database/storage issues (operation, table) ValidationError Data validation failures (field, value, safe_value) --- ## Event Sourcing All state changes are immutable events in a single SQLite table (events): Columns: id (UUID), aggregate_type, aggregate_id, event_type, payload (JSON), timestamp, consensus_id Event types use dot-notation past tense: orchestrator.session.started execution.ac.completed Indexes (5): aggregate_type, aggregate_id, composite, event_type, timestamp Features: Append-only writes Unit of Work pattern (events + checkpoint atomic commits) Full replay capability 3-level rollback depth 5-minute periodic checkpointing --- ## Runtime Abstraction ### AgentRuntime Protocol class AgentRuntime(Protocol): def execute_task(prompt, tools, system_prompt, resume_handle) -> AsyncIterator[AgentMessage] async def execute_task_to_result(prompt, tools, system_prompt, resume_handle) -> Result[TaskResult, ProviderError] Key types: AgentMessage Normalized streaming message (backend-neutral) RuntimeHandle Frozen dataclass with session/resume state TaskResult Collected outcome of completed task ### RuntimeHandle @dataclass(frozen=True, slots=True) class RuntimeHandle: backend: str # "claude" | "codex" | custom kind: str = "agent_runtime" native_session_id: str | None conversation_id: str | None previous_response_id: str | None transcript_path: str | None cwd: str | None approval_mode: str | None updated_at: str | None metadata: dict[str, Any] Computed properties: lifecycle_state, is_terminal, can_resume, can_observe, can_terminate Methods: observe(), terminate(), snapshot(), to_dict(), from_dict() ### Shipped Adapters ClaudeAgentAdapter (backend="claude") Module: src/ouroboros/orchestrator/adapter.py Wraps Claude Agent SDK / Claude Code CLI Streaming via claude_agent_sdk.query() Auto transient-error retry, session resumption CodexCliRuntime (backend="codex") Module: src/ouroboros/orchestrator/codex_cli_runtime.py Drives OpenAI Codex CLI as session-oriented runtime Parses newline-delimited JSON from stdout Skill-command interception for deterministic MCP dispatch ### Runtime Factory create_agent_runtime(backend, permission_mode, model, cwd) Backend resolution order: 1. OUROBOROS_AGENT_RUNTIME env var 2. orchestrator.runtime_backend in ~/.ouroboros/config.yaml 3. Explicit backend= parameter Aliases: claude/claude_code, codex/codex_cli --- ## MCP Integration Ouroboros is an MCP Hub (both client and server). ### MCP Server Mode ouroboros mcp serve Exposed tools: ouroboros_execute_seed Execute a seed specification ouroboros_session_status Session status query ouroboros_query_events Event store query ### MCP Client Mode ouroboros run --mcp-config mcp.yaml seed.yaml Tool precedence: 1. Built-in tools always win 2. First MCP server in config wins for duplicates 3. Use --mcp-tool-prefix to namespace ### MCP Types TransportType: stdio | sse | streamable-http ContentType: text | image | resource MCPServerConfig: name, transport, command, args, url, env, timeout, headers MCPToolDefinition: name, description, parameters, server_name MCPToolResult: content, is_error, meta MCPCapabilities: tools, resources, prompts, logging ### MCP Error Hierarchy MCPError (base, extends OuroborosError) MCPClientError MCPConnectionError (transport) MCPTimeoutError (timeout_seconds, operation) MCPProtocolError MCPServerError MCPAuthError MCPResourceNotFoundError MCPToolError (tool_name, error_code) --- ## Drift Control 3-component weighted measurement: Goal drift 50% weight Constraint drift 30% weight Ontology drift 20% weight Drift score: 0.0 to 1.0 Threshold: <= 0.3 (high drift triggers re-examination) Automatic retrospective every N cycles --- ## Ontology Convergence Similarity = 0.5 * name_overlap + 0.3 * type_match + 0.2 * exact_match Convergence threshold: similarity >= 0.95 Hard cap: 30 generations Pathological pattern detection: Stagnation: similarity >= 0.95 for 3 consecutive generations Oscillation: Gen N ~ Gen N-2 (period-2 cycle) Repetitive: >= 70% question overlap across 3 generations --- ## The Nine Agents Loaded on-demand, never preloaded: Socratic Interviewer Questions-only, never builds Ontologist Finds essence, not symptoms Seed Architect Crystallizes specs from dialogue Evaluator 3-stage verification Contrarian Challenges every assumption Hacker Finds unconventional paths Simplifier Removes complexity Researcher Stops coding, starts investigating Architect Identifies structural causes --- ## Configuration ### File Layout ~/.ouroboros/ config.yaml Main configuration credentials.yaml API keys (chmod 600) ouroboros.db SQLite event store seeds/ Generated seed YAML files data/ Reserved for future use logs/ouroboros.log Log output .env Optional, auto-loaded ### Config Sections orchestrator Runtime backend selection, agent permissions llm Model selection, permission mode economics PAL Router tier definitions, escalation thresholds clarification Phase 0 interview settings execution Phase 2 Double Diamond settings resilience Phase 3 stagnation/lateral thinking evaluation Phase 4 evaluation pipeline settings consensus Multi-model consensus settings persistence SQLite event store settings drift Drift monitoring thresholds logging Log level, path, verbosity ### Key Environment Variables ANTHROPIC_API_KEY Claude API key OPENAI_API_KEY OpenAI API key OUROBOROS_AGENT_RUNTIME Runtime backend override (claude | codex) TERM=xterm-256color TUI terminal compatibility ### Minimal config.yaml orchestrator: runtime_backend: claude # claude | codex logging: level: info # debug | info | warning | error persistence: database_path: data/ouroboros.db --- ## Security Limits Input validation constants (core/security.py): MAX_INITIAL_CONTEXT_LENGTH 50,000 chars Interview input limit MAX_USER_RESPONSE_LENGTH 10,000 chars Interview response limit MAX_SEED_FILE_SIZE 1,000,000 bytes Seed YAML file size cap MAX_LLM_RESPONSE_LENGTH 100,000 chars LLM response truncation --- ## Performance Characteristics Event Store: Append latency: < 10ms p99 Query latency: < 50ms for 1000 events Storage: ~1KB per event Compression: 80% reduction at checkpoints TUI: Refresh rate: 500ms polling Event processing: < 100ms per update Memory: Base: 50MB Per session: 10-100MB depending on complexity Concurrency: Agent pool: 2-10 parallel agents Task queue: priority-based async processing --- ## TUI Dashboard Terminal-based real-time workflow monitor (Textual framework). Launch: ouroboros tui monitor (or ouroboros monitor) Screens: 1 Dashboard Phase progress, AC tree, live status 2 Execution Timeline, phase outputs, events 3 Logs Filterable log viewer with level coloring 4 Debug State inspector, raw events, config s Session Browse and switch sessions e Lineage Evolutionary lineage across generations State: TUIState dataclass in events.py, owned by app.py as SSOT Event flow: EventStore -> app._subscribe_to_events() (poll 0.5s) -> create_message_from_event() -> post_message() --- ## Extension Points ### Adding a New Runtime Adapter 1. Create module in src/ouroboros/orchestrator/ 2. Implement AgentRuntime protocol (execute_task, execute_task_to_result) 3. Register in runtime_factory.py (add backend name set, extend resolve) 4. Emit RuntimeHandle with your backend tag 5. Update runtime_backend Literal in config/models.py 6. Write tests verifying AgentRuntime structural subtyping ### Custom Skills Place in skills/ directory with SKILL.md defining: name, version, description, magic_prefixes, triggers, mode, agents, tools ### Custom Agents Place in src/ouroboros/agents/ as bundled markdown files, or in an explicit override directory via OUROBOROS_AGENTS_DIR / .claude-plugin/agents/: role, capabilities, tools ### MCP Server Integration Register custom tool/resource handlers via MCPServerAdapter or use ToolRegistry for the global registry --- ## Design Principles 1. Frugal First Start cheap, escalate only on failure 2. Immutable Seed Direction cannot change; only path adapts 3. Progressive Verification Cheap checks first, consensus at gates 4. Lateral Over Vertical When stuck, change perspective 5. Event-Sourced Every state change is an event; nothing lost --- ## Key File Locations CLAUDE.md Dev environment setup, ooo command routing docs/getting-started.md Onboarding guide (single source of truth) docs/architecture.md Full architecture document docs/config-reference.md Complete config reference docs/api/core.md Core module API reference docs/api/mcp.md MCP module API reference docs/runtime-capability-matrix.md Runtime feature comparison docs/runtime-guides/claude-code.md Claude Code backend guide docs/runtime-guides/codex.md Codex CLI backend guide docs/guides/seed-authoring.md Advanced seed authoring docs/guides/evaluation-pipeline.md Evaluation pipeline details docs/guides/tui-usage.md TUI dashboard reference docs/contributing/ Contributor guides