Merge remote-tracking branch 'origin/main'

This commit is contained in:
dullfig 2025-12-30 23:35:46 -08:00
commit 3ebf72bfb5
2 changed files with 94 additions and 13 deletions

View file

@ -1,11 +1,13 @@
""" """
Core base class for all listeners in the organism. Core base class for all listeners in the xml-pipeline organism.
All capabilities personalities, tools, gateways inherit from this class.
""" """
from __future__ import annotations from __future__ import annotations
import logging import logging
from typing import List, Dict, Any, Optional from typing import List, Optional, Dict, Any
from lxml import etree from lxml import etree
@ -17,13 +19,14 @@ class XMLListener:
Base class for all capabilities (personalities, tools, gateways). Base class for all capabilities (personalities, tools, gateways).
Subclasses must: Subclasses must:
- Define `listens_to` (list of root tags they handle) - Define `listens_to` as a class attribute (list of root tags they handle)
- Implement `async handle()` - Implement `async handle()` method
The `convo_id` received in handle() MUST be preserved in any response payload. The `convo_id` received in handle() MUST be preserved in any response payload
(via make_response() helper or manually).
""" """
listens_to: List[str] = [] # Must be overridden in subclass listens_to: List[str] = [] # Must be overridden in subclass — required
def __init__( def __init__(
self, self,
@ -32,6 +35,11 @@ class XMLListener:
config: Optional[Dict[str, Any]] = None, config: Optional[Dict[str, Any]] = None,
**kwargs, **kwargs,
): ):
"""
Args:
name: Optional explicit name (defaults to class name)
config: Owner-provided configuration from privileged registration
"""
self.name = name or self.__class__.__name__ self.name = name or self.__class__.__name__
self.config = config or {} self.config = config or {}
self.logger = logging.getLogger(f"{__name__}.{self.name}") self.logger = logging.getLogger(f"{__name__}.{self.name}")
@ -40,14 +48,14 @@ class XMLListener:
self, msg: etree.Element, convo_id: str self, msg: etree.Element, convo_id: str
) -> Optional[etree.Element]: ) -> Optional[etree.Element]:
""" """
Handle a message whose root tag matches this listener. Process an incoming message whose root tag matches this listener.
Args: Args:
msg: The payload element (repaired and C14N'd) msg: The payload element (already repaired and C14N'd)
convo_id: Thread/conversation UUID must be preserved in response convo_id: Thread/conversation UUID must be preserved in any response
Returns: Returns:
Response payload element with the same convo_id, or None Response payload element (with convo_id preserved), or None if no response
""" """
raise NotImplementedError( raise NotImplementedError(
f"{self.__class__.__name__}.handle() must be implemented" f"{self.__class__.__name__}.handle() must be implemented"
@ -62,8 +70,9 @@ class XMLListener:
**attribs, **attribs,
) -> etree.Element: ) -> etree.Element:
""" """
Helper to create a response element with a preserved convo_id attribute. Convenience helper to create a response element with preserved convo_id.
Recommended for all listeners.
Strongly recommended for all listeners to ensure thread continuity.
""" """
elem = etree.Element(tag, convo_id=convo_id, **attribs) elem = etree.Element(tag, convo_id=convo_id, **attribs)
if text is not None: if text is not None:
@ -71,4 +80,4 @@ class XMLListener:
return elem return elem
def __repr__(self) -> str: def __repr__(self) -> str:
return f"<{self.__class__.__name__} listens_to={self.listens_to}>" return f"<{self.__class__.__name__} name='{self.name}' listens_to={self.listens_to}>"

View file

@ -0,0 +1,72 @@
# Executive Summary: Self-Calling Iteration Framework in xml-pipeline
**Date**: December 29, 2025
**Component**: Core reasoning mechanism for LLM personalities
### Principle
In xml-pipeline, **multi-step reasoning, planning, tool use, and iteration are implemented through open, auditable self-calls** — not hidden loops or state machines.
The LLM personality participates in the conversation exactly like any other listener: it can send messages to its own root tag.
### How It Works
1. **Conversation thread = memory**
Every message (user, personality, tool) is appended to history keyed by `convo_id`.
2. **Self-reflection = self-message**
To think step-by-step, the LLM emits its own root tag with the same `convo_id`:
```xml
<ask-grok convo_id="123">
First, let's outline the steps...
</ask-grok>
```
3. **MessageBus routes it back** to the same personality instance.
4. **Personality appends its own message** to history and calls the LLM again.
5. **LLM sees full context** — including its previous thoughts — and continues.
6. **Iteration emerges naturally** from repeated self-calls until final response.
### Key Properties
- **No hidden state** — the thread history is the only memory
- **No special controller** — MessageBus and `convo_id` do all coordination
- **Fully auditable** — every thought, plan, and intermediate step is a logged message
- **Tool use fits identically** — tool calls are messages to other root tags
- **Termination is natural** — LLM decides when to emit final response tag (e.g., `<grok-response>`)
### Structured Planning Support
Personalities are encouraged to use visible structures:
```xml
<todo-until condition="all primes under 100 listed">
<step done="true">List 2</step>
<step done="true">List 3</step>
<step done="false">List 5</step>
</todo-until>
```
This enables:
- Self-coordination (LLM reads its own plan)
- GUI progress rendering
- Explicit termination conditions
### Owner Control
- `iteration-capacity` config (`high`/`medium`/`low`/`none`) tunes how strongly the personality is prompted to iterate
- All behavior governed by owner-provided prompts and response templates
- No personality can loop indefinitely without owner consent
### Result
The framework turns **conversation into computation**.
Loops, conditionals, and planning become **visible message patterns** rather than hidden code.
The organism reasons by talking to itself in the open — producing a complete, transparent trace of thought at every step.
This is the core iteration mechanism for all LLM personalities in xml-pipeline.