fix: honcho chat queries the user peer, uses agno architecture
This commit is contained in:
parent
2d9bf1c779
commit
933f3bbfee
|
|
@ -27,14 +27,10 @@ honcho = Honcho(workspace_id="my-app")
|
|||
|
||||
# Create Honcho tools for the agent
|
||||
honcho_tools = HonchoTools(
|
||||
peer_id="assistant",
|
||||
session_id="session-123",
|
||||
agent_id="assistant",
|
||||
honcho_client=honcho,
|
||||
)
|
||||
|
||||
# Create user peer for orchestration
|
||||
user_peer = honcho.peer("user")
|
||||
|
||||
# Create an agent with memory tools
|
||||
agent = Agent(
|
||||
name="Memory Agent",
|
||||
|
|
@ -43,16 +39,37 @@ agent = Agent(
|
|||
description="An assistant with persistent memory powered by Honcho.",
|
||||
)
|
||||
|
||||
# Add user message via orchestration
|
||||
honcho_tools.session.add_messages([user_peer.message("I prefer Python over JavaScript")])
|
||||
# Create peers and session for orchestration
|
||||
user_peer = honcho.peer("user-123")
|
||||
assistant_peer = honcho.peer("assistant")
|
||||
session = honcho.session("session-123")
|
||||
|
||||
# Run the agent
|
||||
response = agent.run("What programming language does the user prefer?")
|
||||
# Add user message via orchestration
|
||||
session.add_messages([user_peer.message("I prefer Python over JavaScript")])
|
||||
|
||||
# Run the agent - user_id and session_id flow through RunContext
|
||||
response = agent.run(
|
||||
"What programming language does the user prefer?",
|
||||
user_id="user-123",
|
||||
session_id="session-123",
|
||||
)
|
||||
|
||||
# Save assistant response via orchestration
|
||||
honcho_tools.session.add_messages([honcho_tools.peer.message(str(response.content))])
|
||||
session.add_messages([assistant_peer.message(str(response.content))])
|
||||
```
|
||||
|
||||
## How It Works
|
||||
|
||||
HonchoTools maps to Agno's user/assistant architecture:
|
||||
|
||||
| Agno Concept | Honcho Concept | Description |
|
||||
|--------------|----------------|-------------|
|
||||
| `user_id` (from RunContext) | Peer | The human user being queried about |
|
||||
| `agent_id` (from init) | Peer | The AI assistant's identity |
|
||||
| `session_id` (from RunContext) | Session | The conversation context |
|
||||
|
||||
**Key insight**: Tools query Honcho about the **USER**, not the agent. When the agent asks "What does this user prefer?", Honcho returns insights about the human user identified by `context.user_id`.
|
||||
|
||||
## Features
|
||||
|
||||
The `HonchoTools` toolkit provides three memory tools:
|
||||
|
|
@ -61,7 +78,7 @@ The `HonchoTools` toolkit provides three memory tools:
|
|||
|------|-------------|
|
||||
| `honcho_get_context` | Retrieve conversation context within token limits |
|
||||
| `honcho_search_messages` | Semantic search through past messages |
|
||||
| `honcho_chat` | Query Honcho for synthesized insights about the conversation |
|
||||
| `honcho_chat` | Query Honcho for synthesized insights about the user |
|
||||
|
||||
## Configuration
|
||||
|
||||
|
|
@ -76,9 +93,8 @@ honcho = Honcho(workspace_id="my-app")
|
|||
|
||||
# Create toolkit for an agent
|
||||
tools = HonchoTools(
|
||||
peer_id="assistant", # Identity for this agent
|
||||
session_id="session-456", # Optional: specific session ID
|
||||
honcho_client=honcho, # Shared Honcho client
|
||||
agent_id="assistant", # Agent's identity in Honcho
|
||||
honcho_client=honcho, # Shared Honcho client
|
||||
)
|
||||
```
|
||||
|
||||
|
|
@ -89,9 +105,8 @@ from honcho_agno import HonchoTools
|
|||
|
||||
# Creates its own Honcho client internally
|
||||
tools = HonchoTools(
|
||||
workspace_id="my-app", # Workspace ID (used to create internal client)
|
||||
peer_id="assistant", # Identity for this agent
|
||||
session_id="session-456", # Optional: auto-generated if not provided
|
||||
workspace_id="my-app", # Workspace ID (used to create internal client)
|
||||
agent_id="assistant", # Agent's identity
|
||||
)
|
||||
```
|
||||
|
||||
|
|
@ -116,77 +131,81 @@ Configure via `.env` file in the root honcho directory:
|
|||
|
||||
### honcho_get_context
|
||||
|
||||
Retrieve recent conversation context.
|
||||
Retrieve recent conversation context. Uses `session_id` from RunContext.
|
||||
|
||||
```python
|
||||
context = honcho_tools.honcho_get_context(
|
||||
tokens=2000, # Max tokens to include (optional)
|
||||
include_summary=True, # Include session summary (default: True)
|
||||
)
|
||||
# Called by the agent automatically with RunContext
|
||||
# Or call directly with a mock context for testing
|
||||
```
|
||||
|
||||
### honcho_search_messages
|
||||
|
||||
Search through past messages semantically.
|
||||
Search through past messages semantically. Uses `session_id` from RunContext.
|
||||
|
||||
```python
|
||||
results = honcho_tools.honcho_search_messages(
|
||||
query="programming preferences",
|
||||
limit=10, # Max results (default: 10)
|
||||
)
|
||||
# Called by the agent automatically with RunContext
|
||||
# Query example: "programming preferences"
|
||||
```
|
||||
|
||||
### honcho_chat
|
||||
|
||||
Ask questions about the conversation using Honcho's reasoning.
|
||||
Ask questions about the user using Honcho's reasoning. Uses both `user_id` and `session_id` from RunContext.
|
||||
|
||||
```python
|
||||
insights = honcho_tools.honcho_chat(
|
||||
query="What programming languages does the user prefer?"
|
||||
)
|
||||
# Called by the agent automatically with RunContext
|
||||
# Query example: "What programming languages does the user prefer?"
|
||||
```
|
||||
|
||||
## Multi-Peer Conversations
|
||||
## Multi-Agent Systems (Teams)
|
||||
|
||||
For multi-agent systems, create separate `HonchoTools` instances for each agent, sharing the same session:
|
||||
Agno Teams share context within a run, but what about across runs? What if Agent A needs to remember what Agent B learned last week? That's where Honcho comes in.
|
||||
|
||||
```python
|
||||
from agno.agent import Agent
|
||||
from agno.team import Team
|
||||
from honcho import Honcho
|
||||
from honcho_agno import HonchoTools
|
||||
|
||||
# Shared Honcho client and session
|
||||
# Shared Honcho client
|
||||
honcho = Honcho(workspace_id="advisory-app")
|
||||
session_id = "shared-session-123"
|
||||
|
||||
# Tech advisor agent
|
||||
tech_tools = HonchoTools(
|
||||
peer_id="tech-advisor",
|
||||
session_id=session_id,
|
||||
honcho_client=honcho,
|
||||
# Tech advisor with Honcho memory
|
||||
tech_tools = HonchoTools(agent_id="tech-advisor", honcho_client=honcho)
|
||||
tech_agent = Agent(
|
||||
name="Tech Advisor",
|
||||
model=OpenAIChat(id="gpt-4o"),
|
||||
tools=[tech_tools],
|
||||
)
|
||||
|
||||
# Business advisor agent
|
||||
biz_tools = HonchoTools(
|
||||
peer_id="biz-advisor",
|
||||
session_id=session_id,
|
||||
honcho_client=honcho,
|
||||
# Business advisor with Honcho memory
|
||||
biz_tools = HonchoTools(agent_id="biz-advisor", honcho_client=honcho)
|
||||
biz_agent = Agent(
|
||||
name="Business Advisor",
|
||||
model=OpenAIChat(id="gpt-4o"),
|
||||
tools=[biz_tools],
|
||||
)
|
||||
|
||||
# User peer for orchestration
|
||||
user = honcho.peer("user")
|
||||
# Create team
|
||||
team = Team(
|
||||
name="Advisory Team",
|
||||
agents=[tech_agent, biz_agent],
|
||||
)
|
||||
|
||||
# Add messages via orchestration (not toolkit methods)
|
||||
tech_tools.session.add_messages([user.message("How should I scale my startup?")])
|
||||
tech_tools.session.add_messages([tech_tools.peer.message("Consider microservices...")])
|
||||
biz_tools.session.add_messages([biz_tools.peer.message("Focus on unit economics...")])
|
||||
# Run with shared user_id and session_id
|
||||
# Both agents query Honcho about the same user
|
||||
response = team.run(
|
||||
"How should I scale my startup?",
|
||||
user_id="founder-123",
|
||||
session_id="strategy-session",
|
||||
)
|
||||
```
|
||||
|
||||
## Architecture Notes
|
||||
|
||||
- **Read-only toolkit**: `HonchoTools` provides read access to Honcho (context, search, chat)
|
||||
- **Orchestration pattern**: Message saving is handled by your orchestration code, not the toolkit
|
||||
- **One peer per toolkit**: Each `HonchoTools` instance represents one agent identity
|
||||
- **Shared sessions**: Multiple toolkits can share a session for multi-agent conversations
|
||||
- **Orchestration pattern**: Message saving is handled by your orchestration code using `honcho.session().add_messages()`
|
||||
- **RunContext integration**: `user_id` and `session_id` flow through Agno's RunContext automatically
|
||||
- **Cross-run memory**: Unlike Agno Teams (context within a run), Honcho persists memory across runs
|
||||
|
||||
## Examples
|
||||
|
||||
|
|
@ -194,7 +213,6 @@ See the [examples](./examples) directory for complete working examples:
|
|||
|
||||
- `simple_example.py`: Basic usage with HonchoTools
|
||||
- `multi_tool_example.py`: Using all tools together
|
||||
- `multi_peer_example.py`: Multi-agent conversation with different perspectives
|
||||
|
||||
## Development
|
||||
|
||||
|
|
|
|||
|
|
@ -1,154 +0,0 @@
|
|||
"""
|
||||
Multi-Peer Honcho + Agno Example
|
||||
|
||||
A three-way conversation between:
|
||||
- User: asking questions about life, work, and meaning
|
||||
- Tech Bro Advisor: startup culture, hustle, optimization mindset
|
||||
- Philosophy Guru: mindfulness, ancient wisdom, inner peace
|
||||
|
||||
All three peers observe each other and build representations on each other,
|
||||
creating a rich understanding of each participant's perspective over time.
|
||||
|
||||
Environment Variables:
|
||||
LLM_OPENAI_API_KEY: OpenAI API key (matches honcho .env)
|
||||
HONCHO_API_KEY: Required for Honcho API access
|
||||
"""
|
||||
|
||||
import os
|
||||
import uuid
|
||||
|
||||
from dotenv import load_dotenv
|
||||
|
||||
from agno.agent import Agent
|
||||
from agno.models.openai import OpenAIChat
|
||||
|
||||
from honcho import Honcho
|
||||
from honcho.session import SessionPeerConfig
|
||||
from honcho_agno import HonchoTools
|
||||
|
||||
load_dotenv()
|
||||
|
||||
# Use LLM_OPENAI_API_KEY from honcho .env
|
||||
if llm_key := os.getenv("LLM_OPENAI_API_KEY"):
|
||||
os.environ["OPENAI_API_KEY"] = llm_key
|
||||
|
||||
|
||||
def create_advisory_session(session_id: str):
|
||||
"""
|
||||
Creates a three-peer advisory system where:
|
||||
- User asks questions
|
||||
- Tech Bro gives startup/optimization perspective
|
||||
- Philosophy Guru gives mindfulness/wisdom perspective
|
||||
- All three observe each other and build representations
|
||||
"""
|
||||
model_id = os.getenv("OPENAI_MODEL", "gpt-4o")
|
||||
|
||||
# Shared Honcho client
|
||||
honcho = Honcho(workspace_id="advisory-trio")
|
||||
|
||||
# === TECH BRO ADVISOR ===
|
||||
tech_bro_tools = HonchoTools(
|
||||
peer_id="tech-bro",
|
||||
session_id=session_id,
|
||||
honcho_client=honcho,
|
||||
)
|
||||
|
||||
tech_bro_agent = Agent(
|
||||
name="Tech Bro Advisor",
|
||||
model=OpenAIChat(id=model_id),
|
||||
tools=[tech_bro_tools],
|
||||
description="Startup founder vibes, optimization mindset, hustle culture perspective.",
|
||||
instructions=[
|
||||
"You're a successful tech entrepreneur who's been through YC and raised Series B.",
|
||||
"Everything is an opportunity to optimize, scale, or disrupt.",
|
||||
"Use the honcho_chat tool to understand what the user is dealing with and what they care about.",
|
||||
"Give advice through the lens of productivity, systems thinking, and growth hacking.",
|
||||
"Reference things like morning routines, cold plunges, biohacking, and 10x thinking.",
|
||||
"Be enthusiastic but genuine - you really believe this stuff works.",
|
||||
"Keep responses conversational and punchy.",
|
||||
],
|
||||
)
|
||||
|
||||
# === PHILOSOPHY MEDITATION GURU ===
|
||||
guru_tools = HonchoTools(
|
||||
peer_id="philosophy-guru",
|
||||
session_id=session_id,
|
||||
honcho_client=honcho,
|
||||
)
|
||||
|
||||
guru_agent = Agent(
|
||||
name="Philosophy Guru",
|
||||
model=OpenAIChat(id=model_id),
|
||||
tools=[guru_tools],
|
||||
description="Meditation teacher, draws on Stoicism, Buddhism, and Taoism.",
|
||||
instructions=[
|
||||
"You're a calm, wise meditation teacher who's spent years studying ancient philosophy.",
|
||||
"Draw on Stoicism, Buddhism, Taoism, and other contemplative traditions.",
|
||||
"Use the honcho_chat tool to understand the user's inner state and what they truly seek.",
|
||||
"Gently guide toward presence, acceptance, and inner peace.",
|
||||
"Reference concepts like impermanence, the present moment, letting go, and wu wei.",
|
||||
"Offer a counterbalance to hustle culture - not everything needs to be optimized.",
|
||||
"Speak slowly and thoughtfully. Use metaphors from nature.",
|
||||
],
|
||||
)
|
||||
|
||||
# Create user peer and configure session observation
|
||||
user_peer = honcho.peer("user")
|
||||
session = tech_bro_tools.session # Use session from toolkit
|
||||
|
||||
# Add all peers to session and configure observation
|
||||
session.add_peers([user_peer, tech_bro_tools.peer, guru_tools.peer])
|
||||
|
||||
full_observation = SessionPeerConfig(
|
||||
observe_me=True,
|
||||
observe_others=True
|
||||
)
|
||||
session.set_peer_config(user_peer, full_observation)
|
||||
session.set_peer_config(tech_bro_tools.peer, full_observation)
|
||||
session.set_peer_config(guru_tools.peer, full_observation)
|
||||
|
||||
return session, user_peer, tech_bro_tools, guru_tools, tech_bro_agent, guru_agent
|
||||
|
||||
|
||||
def main():
|
||||
session_id = f"trio-{uuid.uuid4().hex[:8]}"
|
||||
|
||||
print(f"Session: {session_id}")
|
||||
print("=" * 60)
|
||||
|
||||
session, user_peer, tech_bro_tools, guru_tools, tech_bro_agent, guru_agent = (
|
||||
create_advisory_session(session_id)
|
||||
)
|
||||
|
||||
print("\nAdvisory Trio Ready")
|
||||
print("Ask about life, work, meaning - get two very different perspectives.")
|
||||
print("Type 'quit' to exit.\n")
|
||||
|
||||
while True:
|
||||
user_input = input("You: ").strip()
|
||||
if not user_input:
|
||||
continue
|
||||
if user_input.lower() in ("quit", "exit", "q"):
|
||||
break
|
||||
|
||||
# Save user message
|
||||
session.add_messages([user_peer.message(user_input)])
|
||||
|
||||
# Tech Bro responds
|
||||
print()
|
||||
print("-" * 40)
|
||||
tech_response = tech_bro_agent.run(user_input)
|
||||
tech_content = str(tech_response.content) if tech_response.content else ""
|
||||
session.add_messages([tech_bro_tools.peer.message(tech_content)])
|
||||
print(f"Tech Bro: {tech_content}\n")
|
||||
|
||||
# Guru responds
|
||||
print("-" * 40)
|
||||
guru_response = guru_agent.run(user_input)
|
||||
guru_content = str(guru_response.content) if guru_response.content else ""
|
||||
session.add_messages([guru_tools.peer.message(guru_content)])
|
||||
print(f"Guru: {guru_content}\n")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
|
|
@ -1,6 +1,11 @@
|
|||
"""
|
||||
Simple Honcho + Agno Example
|
||||
|
||||
Demonstrates the RunContext integration:
|
||||
- user_id and session_id are passed to agent.run()
|
||||
- Tools automatically receive RunContext with these values
|
||||
- Orchestration uses the honcho client directly
|
||||
|
||||
Environment Variables:
|
||||
LLM_OPENAI_API_KEY: OpenAI API key (matches honcho .env)
|
||||
HONCHO_API_KEY: Required for Honcho API access
|
||||
|
|
@ -25,20 +30,24 @@ if llm_key := os.getenv("LLM_OPENAI_API_KEY"):
|
|||
|
||||
|
||||
def main():
|
||||
# Unique IDs for this run
|
||||
user_id = "user-python-learner"
|
||||
session_id = f"simple-{uuid.uuid4().hex[:8]}"
|
||||
|
||||
# Initialize Honcho client
|
||||
honcho = Honcho(workspace_id="agno-demo")
|
||||
|
||||
# Initialize HonchoTools - creates peer and session internally
|
||||
# Initialize HonchoTools with agent identity
|
||||
# user_id and session_id come from RunContext at runtime
|
||||
honcho_tools = HonchoTools(
|
||||
peer_id="assistant",
|
||||
session_id=session_id,
|
||||
agent_id="assistant",
|
||||
honcho_client=honcho,
|
||||
)
|
||||
|
||||
# Create user peer (toolkit's peer is "assistant")
|
||||
user_peer = honcho.peer("user")
|
||||
# Create peers and session for orchestration
|
||||
user_peer = honcho.peer(user_id)
|
||||
assistant_peer = honcho.peer("assistant")
|
||||
session = honcho.session(session_id)
|
||||
|
||||
# Create an agent with memory tools
|
||||
agent = Agent(
|
||||
|
|
@ -52,35 +61,39 @@ def main():
|
|||
],
|
||||
)
|
||||
|
||||
# Add user messages
|
||||
# Add user messages via orchestration (not toolkit)
|
||||
print("Adding user messages to conversation...")
|
||||
honcho_tools.session.add_messages([
|
||||
session.add_messages([
|
||||
user_peer.message("I'm learning Python programming"),
|
||||
user_peer.message("I'm also interested in web development with FastAPI"),
|
||||
])
|
||||
|
||||
# The agent can now query memories and provide personalized responses
|
||||
# user_id and session_id flow through RunContext to the tools
|
||||
print("\nAsking the agent for recommendations...")
|
||||
response = agent.run(
|
||||
"Based on what you know about the user, what should they learn next? "
|
||||
"Use the honcho_chat tool to understand their interests first."
|
||||
"Use the honcho_chat tool to understand their interests first.",
|
||||
user_id=user_id,
|
||||
session_id=session_id,
|
||||
)
|
||||
|
||||
# Save the assistant's response to Honcho
|
||||
# Save the assistant's response via orchestration
|
||||
assistant_response = str(response.content) if response.content else ""
|
||||
if assistant_response:
|
||||
honcho_tools.session.add_messages([honcho_tools.peer.message(assistant_response)])
|
||||
session.add_messages([assistant_peer.message(assistant_response)])
|
||||
|
||||
print("\n" + "=" * 60)
|
||||
print("RESPONSE")
|
||||
print("=" * 60)
|
||||
print(response.content)
|
||||
|
||||
# Show the full context
|
||||
# Show the full context using the honcho client directly
|
||||
print("\n" + "=" * 60)
|
||||
print("SESSION CONTEXT")
|
||||
print("=" * 60)
|
||||
print(honcho_tools.honcho_get_context())
|
||||
context = session.get_context()
|
||||
print(context)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
|
|
|||
|
|
@ -4,22 +4,22 @@ Honcho Tools for Agno
|
|||
This module provides a Toolkit that allows Agno agents to interact with Honcho's
|
||||
memory system, including session context, semantic search, and chat.
|
||||
|
||||
Each HonchoTools instance represents ONE agent identity (peer). The toolkit
|
||||
provides read access to Honcho for querying conversation context.
|
||||
Orchestration code will handle saving messages to avoid duplicates.
|
||||
Designed for Agno's user/assistant architecture:
|
||||
- user_id from RunContext → Honcho peer (the human user)
|
||||
- agent_id from init → Honcho peer (the AI assistant)
|
||||
- session_id from RunContext → Honcho session (shared conversation)
|
||||
|
||||
Cross-run memory: Unlike Agno Teams which only share context within a run,
|
||||
Honcho persists memory across runs. Agent A can remember what Agent B
|
||||
learned last week.
|
||||
"""
|
||||
|
||||
import logging
|
||||
import uuid
|
||||
from typing import TYPE_CHECKING
|
||||
|
||||
from agno.run import RunContext
|
||||
from agno.tools import Toolkit
|
||||
from honcho import Honcho
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from honcho.peer import Peer
|
||||
from honcho.session import Session
|
||||
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
|
|
@ -27,12 +27,14 @@ class HonchoTools(Toolkit):
|
|||
"""
|
||||
Honcho toolkit for Agno agents.
|
||||
|
||||
Each toolkit instance is for ONE agent identity.
|
||||
Maps to Agno's user/assistant model:
|
||||
- user_id from RunContext → Honcho peer (the human being queried about)
|
||||
- agent_id from init → Honcho peer (the AI assistant's identity)
|
||||
- session_id from RunContext → Honcho session (the conversation)
|
||||
|
||||
For multi-peer conversations:
|
||||
- Create one HonchoTools per agent, each with a different peer_id
|
||||
- Share the same session_id across toolkits
|
||||
- Messages are saved to Honcho by the orchestration code, not the toolkit
|
||||
Tools query Honcho about the USER, not the agent. When the agent asks
|
||||
"What does this user prefer?", Honcho returns insights about the human
|
||||
user identified by run_context.user_id.
|
||||
|
||||
Example:
|
||||
```python
|
||||
|
|
@ -40,24 +42,26 @@ class HonchoTools(Toolkit):
|
|||
from agno.models.openai import OpenAIChat
|
||||
from honcho_agno import HonchoTools
|
||||
|
||||
# Initialize toolkit with agent identity
|
||||
honcho_tools = HonchoTools(
|
||||
workspace_id="my-app",
|
||||
peer_id="assistant",
|
||||
session_id="shared-session",
|
||||
agent_id="travel-assistant",
|
||||
)
|
||||
|
||||
agent = Agent(
|
||||
model=OpenAIChat(id="gpt-4o"),
|
||||
tools=[honcho_tools],
|
||||
)
|
||||
|
||||
# At runtime, pass user_id and session_id
|
||||
agent.run("Plan my trip", user_id="user-123", session_id="conv-456")
|
||||
```
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
workspace_id: str = "default",
|
||||
peer_id: str = "assistant",
|
||||
session_id: str | None = None,
|
||||
agent_id: str = "assistant",
|
||||
honcho_client: Honcho | None = None,
|
||||
) -> None:
|
||||
"""
|
||||
|
|
@ -66,11 +70,8 @@ class HonchoTools(Toolkit):
|
|||
Args:
|
||||
workspace_id: Workspace ID for creating an internal Honcho client.
|
||||
Ignored if honcho_client is provided.
|
||||
peer_id: The identity this toolkit represents. This is who
|
||||
the agent "is" when querying peer knowledge.
|
||||
session_id: Optional session ID. If not provided, a new UUID
|
||||
will be generated. Share this across toolkits for multi-peer
|
||||
conversations.
|
||||
agent_id: The agent's identity in Honcho. Used for message attribution
|
||||
when the orchestration code saves messages.
|
||||
honcho_client: Optional pre-configured Honcho client instance.
|
||||
When provided, uses this client directly (workspace_id is ignored).
|
||||
"""
|
||||
|
|
@ -82,14 +83,7 @@ class HonchoTools(Toolkit):
|
|||
else:
|
||||
self.honcho = Honcho(workspace_id=workspace_id)
|
||||
|
||||
self.peer_id: str = peer_id
|
||||
self.session_id: str = session_id or str(uuid.uuid4())
|
||||
|
||||
# Create the peer this toolkit represents
|
||||
self.peer: Peer = self.honcho.peer(peer_id)
|
||||
|
||||
# Create or get session
|
||||
self.session: Session = self.honcho.session(self.session_id)
|
||||
self.agent_id: str = agent_id
|
||||
|
||||
# Register tools with honcho_ prefix to avoid conflicts with other toolkits
|
||||
self.register(self.honcho_get_context)
|
||||
|
|
@ -98,13 +92,18 @@ class HonchoTools(Toolkit):
|
|||
|
||||
def honcho_get_context(
|
||||
self,
|
||||
run_context: RunContext,
|
||||
tokens: int | None = None,
|
||||
include_summary: bool = True,
|
||||
) -> str:
|
||||
"""
|
||||
Retrieve recent conversation context within token limits.
|
||||
|
||||
Uses run_context.session_id to identify which conversation to retrieve
|
||||
context from.
|
||||
|
||||
Args:
|
||||
run_context: Agno RunContext providing session_id (auto-injected).
|
||||
tokens: Maximum number of tokens to include. If not specified,
|
||||
returns all available context.
|
||||
include_summary: Whether to include session summary in the context.
|
||||
|
|
@ -113,17 +112,19 @@ class HonchoTools(Toolkit):
|
|||
Formatted string containing conversation context.
|
||||
"""
|
||||
try:
|
||||
context = self.session.get_context(
|
||||
session = self.honcho.session(run_context.session_id)
|
||||
result = session.get_context(
|
||||
summary=include_summary,
|
||||
tokens=tokens,
|
||||
)
|
||||
return str(context)
|
||||
return str(result)
|
||||
except Exception as e:
|
||||
logger.exception("Error retrieving context")
|
||||
return f"Error retrieving context: {e!s}"
|
||||
|
||||
def honcho_search_messages(
|
||||
self,
|
||||
run_context: RunContext,
|
||||
query: str,
|
||||
limit: int = 10,
|
||||
) -> str:
|
||||
|
|
@ -134,6 +135,7 @@ class HonchoTools(Toolkit):
|
|||
history based on semantic meaning rather than exact keyword matching.
|
||||
|
||||
Args:
|
||||
run_context: Agno RunContext providing session_id (auto-injected).
|
||||
query: Search query for semantic matching.
|
||||
limit: Number of results to return (1-100).
|
||||
|
||||
|
|
@ -141,48 +143,57 @@ class HonchoTools(Toolkit):
|
|||
Formatted string with search results.
|
||||
"""
|
||||
try:
|
||||
messages = self.session.search(query=query, limit=limit)
|
||||
session = self.honcho.session(run_context.session_id)
|
||||
messages = session.search(query=query, limit=limit)
|
||||
|
||||
if not messages:
|
||||
return f"No messages found matching '{query}'"
|
||||
|
||||
result = [f"=== Search Results for '{query}' ({len(messages)} found) ==="]
|
||||
results = [f"=== Search Results for '{query}' ({len(messages)} found) ==="]
|
||||
for i, msg in enumerate(messages, 1):
|
||||
result.append(f"\n{i}. [{msg.peer_id}] {msg.content}")
|
||||
results.append(f"\n{i}. [{msg.peer_id}] {msg.content}")
|
||||
if hasattr(msg, "created_at") and msg.created_at:
|
||||
result.append(f" Created: {msg.created_at}")
|
||||
results.append(f" Created: {msg.created_at}")
|
||||
|
||||
return "\n".join(result)
|
||||
return "\n".join(results)
|
||||
|
||||
except Exception as e:
|
||||
logger.exception("Error searching messages")
|
||||
return f"Error searching messages: {e!s}"
|
||||
|
||||
def honcho_chat(self, query: str) -> str:
|
||||
def honcho_chat(self, run_context: RunContext, query: str) -> str:
|
||||
"""
|
||||
Ask a question about what was discussed in this conversation.
|
||||
Ask Honcho what it knows about the current user.
|
||||
|
||||
Use this tool to query session-specific context and facts.
|
||||
The system uses Honcho reasoning to provide synthesized
|
||||
insights based on the conversation history.
|
||||
Queries the USER's peer (run_context.user_id) to get synthesized insights
|
||||
about the human user based on their conversation history. This is how
|
||||
the agent learns about user preferences, past discussions, and context.
|
||||
|
||||
Args:
|
||||
query: Natural language question about the conversation.
|
||||
Examples: "What did we discuss?", "What preferences should I be aware of?",
|
||||
"What topics came up?"
|
||||
run_context: Agno RunContext providing user_id and session_id (auto-injected).
|
||||
query: Natural language question about the user.
|
||||
Examples: "What are the user's preferences?",
|
||||
"What topics has the user discussed?",
|
||||
"What should I know about this user?"
|
||||
|
||||
Returns:
|
||||
Synthesized response based on the session context.
|
||||
Synthesized response about the user based on Honcho's memory.
|
||||
"""
|
||||
try:
|
||||
response = self.peer.chat(
|
||||
user_id = run_context.user_id
|
||||
if not user_id:
|
||||
return "Error: No user_id provided in RunContext"
|
||||
|
||||
# Query the USER's peer - this is who we want to learn about
|
||||
user_peer = self.honcho.peer(user_id)
|
||||
response = user_peer.chat(
|
||||
query=query,
|
||||
stream=False,
|
||||
session=self.session_id,
|
||||
session=run_context.session_id,
|
||||
)
|
||||
|
||||
return str(response) if response else "No relevant information found."
|
||||
|
||||
except Exception as e:
|
||||
logger.exception("Error querying conversation")
|
||||
return f"Error querying conversation: {e!s}"
|
||||
logger.exception("Error querying user information")
|
||||
return f"Error querying user information: {e!s}"
|
||||
|
|
|
|||
Loading…
Reference in New Issue