agno 2.2.0__py3-none-any.whl → 2.2.1__py3-none-any.whl
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.
- agno/agent/agent.py +16 -1
- agno/knowledge/knowledge.py +11 -0
- agno/knowledge/reader/pptx_reader.py +101 -0
- agno/knowledge/reader/reader_factory.py +14 -0
- agno/knowledge/types.py +1 -0
- agno/models/base.py +4 -4
- agno/run/agent.py +5 -0
- agno/run/team.py +5 -0
- agno/run/workflow.py +15 -5
- agno/team/team.py +29 -9
- agno/utils/message.py +60 -0
- agno/workflow/workflow.py +86 -1
- {agno-2.2.0.dist-info → agno-2.2.1.dist-info}/METADATA +4 -1
- {agno-2.2.0.dist-info → agno-2.2.1.dist-info}/RECORD +17 -16
- {agno-2.2.0.dist-info → agno-2.2.1.dist-info}/WHEEL +0 -0
- {agno-2.2.0.dist-info → agno-2.2.1.dist-info}/licenses/LICENSE +0 -0
- {agno-2.2.0.dist-info → agno-2.2.1.dist-info}/top_level.txt +0 -0
agno/agent/agent.py
CHANGED
|
@@ -117,7 +117,7 @@ from agno.utils.log import (
|
|
|
117
117
|
set_log_level_to_info,
|
|
118
118
|
)
|
|
119
119
|
from agno.utils.merge_dict import merge_dictionaries
|
|
120
|
-
from agno.utils.message import get_text_from_message
|
|
120
|
+
from agno.utils.message import filter_tool_calls, get_text_from_message
|
|
121
121
|
from agno.utils.print_response.agent import (
|
|
122
122
|
aprint_response,
|
|
123
123
|
aprint_response_stream,
|
|
@@ -203,6 +203,8 @@ class Agent:
|
|
|
203
203
|
add_history_to_context: bool = False
|
|
204
204
|
# Number of historical runs to include in the messages
|
|
205
205
|
num_history_runs: int = 3
|
|
206
|
+
# Maximum number of tool calls to include from history (None = no limit)
|
|
207
|
+
max_tool_calls_from_history: Optional[int] = None
|
|
206
208
|
|
|
207
209
|
# --- Knowledge ---
|
|
208
210
|
knowledge: Optional[Knowledge] = None
|
|
@@ -419,6 +421,7 @@ class Agent:
|
|
|
419
421
|
session_summary_manager: Optional[SessionSummaryManager] = None,
|
|
420
422
|
add_history_to_context: bool = False,
|
|
421
423
|
num_history_runs: int = 3,
|
|
424
|
+
max_tool_calls_from_history: Optional[int] = None,
|
|
422
425
|
store_media: bool = True,
|
|
423
426
|
store_tool_messages: bool = True,
|
|
424
427
|
store_history_messages: bool = True,
|
|
@@ -520,6 +523,7 @@ class Agent:
|
|
|
520
523
|
|
|
521
524
|
self.add_history_to_context = add_history_to_context
|
|
522
525
|
self.num_history_runs = num_history_runs
|
|
526
|
+
self.max_tool_calls_from_history = max_tool_calls_from_history
|
|
523
527
|
|
|
524
528
|
self.store_media = store_media
|
|
525
529
|
self.store_tool_messages = store_tool_messages
|
|
@@ -1995,6 +1999,9 @@ class Agent:
|
|
|
1995
1999
|
run_response=run_response,
|
|
1996
2000
|
run_input=run_input,
|
|
1997
2001
|
session=agent_session,
|
|
2002
|
+
session_state=session_state,
|
|
2003
|
+
dependencies=dependencies,
|
|
2004
|
+
metadata=metadata,
|
|
1998
2005
|
user_id=user_id,
|
|
1999
2006
|
debug_mode=debug_mode,
|
|
2000
2007
|
**kwargs,
|
|
@@ -7321,6 +7328,10 @@ class Agent:
|
|
|
7321
7328
|
for _msg in history_copy:
|
|
7322
7329
|
_msg.from_history = True
|
|
7323
7330
|
|
|
7331
|
+
# Filter tool calls from history if limit is set (before adding to run_messages)
|
|
7332
|
+
if self.max_tool_calls_from_history is not None:
|
|
7333
|
+
filter_tool_calls(history_copy, self.max_tool_calls_from_history)
|
|
7334
|
+
|
|
7324
7335
|
log_debug(f"Adding {len(history_copy)} messages from history")
|
|
7325
7336
|
|
|
7326
7337
|
run_messages.messages += history_copy
|
|
@@ -7514,6 +7525,10 @@ class Agent:
|
|
|
7514
7525
|
for _msg in history_copy:
|
|
7515
7526
|
_msg.from_history = True
|
|
7516
7527
|
|
|
7528
|
+
# Filter tool calls from history if limit is set (before adding to run_messages)
|
|
7529
|
+
if self.max_tool_calls_from_history is not None:
|
|
7530
|
+
filter_tool_calls(history_copy, self.max_tool_calls_from_history)
|
|
7531
|
+
|
|
7517
7532
|
log_debug(f"Adding {len(history_copy)} messages from history")
|
|
7518
7533
|
|
|
7519
7534
|
run_messages.messages += history_copy
|
agno/knowledge/knowledge.py
CHANGED
|
@@ -547,6 +547,8 @@ class Knowledge:
|
|
|
547
547
|
reader = self.pdf_reader
|
|
548
548
|
elif file_extension == ".docx":
|
|
549
549
|
reader = self.docx_reader
|
|
550
|
+
elif file_extension == ".pptx":
|
|
551
|
+
reader = self.pptx_reader
|
|
550
552
|
elif file_extension == ".json":
|
|
551
553
|
reader = self.json_reader
|
|
552
554
|
elif file_extension == ".markdown":
|
|
@@ -835,6 +837,8 @@ class Knowledge:
|
|
|
835
837
|
reader = self.csv_reader
|
|
836
838
|
elif s3_object.uri.endswith(".docx"):
|
|
837
839
|
reader = self.docx_reader
|
|
840
|
+
elif s3_object.uri.endswith(".pptx"):
|
|
841
|
+
reader = self.pptx_reader
|
|
838
842
|
elif s3_object.uri.endswith(".json"):
|
|
839
843
|
reader = self.json_reader
|
|
840
844
|
elif s3_object.uri.endswith(".markdown"):
|
|
@@ -917,6 +921,8 @@ class Knowledge:
|
|
|
917
921
|
reader = self.csv_reader
|
|
918
922
|
elif gcs_object.name.endswith(".docx"):
|
|
919
923
|
reader = self.docx_reader
|
|
924
|
+
elif gcs_object.name.endswith(".pptx"):
|
|
925
|
+
reader = self.pptx_reader
|
|
920
926
|
elif gcs_object.name.endswith(".json"):
|
|
921
927
|
reader = self.json_reader
|
|
922
928
|
elif gcs_object.name.endswith(".markdown"):
|
|
@@ -1893,6 +1899,11 @@ class Knowledge:
|
|
|
1893
1899
|
"""Docx reader - lazy loaded via factory."""
|
|
1894
1900
|
return self._get_reader("docx")
|
|
1895
1901
|
|
|
1902
|
+
@property
|
|
1903
|
+
def pptx_reader(self) -> Optional[Reader]:
|
|
1904
|
+
"""PPTX reader - lazy loaded via factory."""
|
|
1905
|
+
return self._get_reader("pptx")
|
|
1906
|
+
|
|
1896
1907
|
@property
|
|
1897
1908
|
def json_reader(self) -> Optional[Reader]:
|
|
1898
1909
|
"""JSON reader - lazy loaded via factory."""
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
import asyncio
|
|
2
|
+
from pathlib import Path
|
|
3
|
+
from typing import IO, Any, List, Optional, Union
|
|
4
|
+
from uuid import uuid4
|
|
5
|
+
|
|
6
|
+
from agno.knowledge.chunking.document import DocumentChunking
|
|
7
|
+
from agno.knowledge.chunking.strategy import ChunkingStrategy, ChunkingStrategyType
|
|
8
|
+
from agno.knowledge.document.base import Document
|
|
9
|
+
from agno.knowledge.reader.base import Reader
|
|
10
|
+
from agno.knowledge.types import ContentType
|
|
11
|
+
from agno.utils.log import log_info, logger
|
|
12
|
+
|
|
13
|
+
try:
|
|
14
|
+
from pptx import Presentation # type: ignore
|
|
15
|
+
except ImportError:
|
|
16
|
+
raise ImportError("The `python-pptx` package is not installed. Please install it via `pip install python-pptx`.")
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
class PPTXReader(Reader):
|
|
20
|
+
"""Reader for PPTX files"""
|
|
21
|
+
|
|
22
|
+
def __init__(self, chunking_strategy: Optional[ChunkingStrategy] = DocumentChunking(), **kwargs):
|
|
23
|
+
super().__init__(chunking_strategy=chunking_strategy, **kwargs)
|
|
24
|
+
|
|
25
|
+
@classmethod
|
|
26
|
+
def get_supported_chunking_strategies(self) -> List[ChunkingStrategyType]:
|
|
27
|
+
"""Get the list of supported chunking strategies for PPTX readers."""
|
|
28
|
+
return [
|
|
29
|
+
ChunkingStrategyType.DOCUMENT_CHUNKER,
|
|
30
|
+
ChunkingStrategyType.FIXED_SIZE_CHUNKER,
|
|
31
|
+
ChunkingStrategyType.SEMANTIC_CHUNKER,
|
|
32
|
+
ChunkingStrategyType.AGENTIC_CHUNKER,
|
|
33
|
+
ChunkingStrategyType.RECURSIVE_CHUNKER,
|
|
34
|
+
]
|
|
35
|
+
|
|
36
|
+
@classmethod
|
|
37
|
+
def get_supported_content_types(self) -> List[ContentType]:
|
|
38
|
+
return [ContentType.PPTX]
|
|
39
|
+
|
|
40
|
+
def read(self, file: Union[Path, IO[Any]], name: Optional[str] = None) -> List[Document]:
|
|
41
|
+
"""Read a pptx file and return a list of documents"""
|
|
42
|
+
try:
|
|
43
|
+
if isinstance(file, Path):
|
|
44
|
+
if not file.exists():
|
|
45
|
+
raise FileNotFoundError(f"Could not find file: {file}")
|
|
46
|
+
log_info(f"Reading: {file}")
|
|
47
|
+
presentation = Presentation(str(file))
|
|
48
|
+
doc_name = name or file.stem
|
|
49
|
+
else:
|
|
50
|
+
log_info(f"Reading uploaded file: {getattr(file, 'name', 'pptx_file')}")
|
|
51
|
+
presentation = Presentation(file)
|
|
52
|
+
doc_name = name or (
|
|
53
|
+
getattr(file, "name", "pptx_file").split(".")[0] if hasattr(file, "name") else "pptx_file"
|
|
54
|
+
)
|
|
55
|
+
|
|
56
|
+
# Extract text from all slides
|
|
57
|
+
slide_texts = []
|
|
58
|
+
for slide_number, slide in enumerate(presentation.slides, 1):
|
|
59
|
+
slide_text = f"Slide {slide_number}:\n"
|
|
60
|
+
|
|
61
|
+
# Extract text from shapes that contain text
|
|
62
|
+
text_content = []
|
|
63
|
+
for shape in slide.shapes:
|
|
64
|
+
if hasattr(shape, "text") and shape.text.strip():
|
|
65
|
+
text_content.append(shape.text.strip())
|
|
66
|
+
|
|
67
|
+
if text_content:
|
|
68
|
+
slide_text += "\n".join(text_content)
|
|
69
|
+
else:
|
|
70
|
+
slide_text += "(No text content)"
|
|
71
|
+
|
|
72
|
+
slide_texts.append(slide_text)
|
|
73
|
+
|
|
74
|
+
doc_content = "\n\n".join(slide_texts)
|
|
75
|
+
|
|
76
|
+
documents = [
|
|
77
|
+
Document(
|
|
78
|
+
name=doc_name,
|
|
79
|
+
id=str(uuid4()),
|
|
80
|
+
content=doc_content,
|
|
81
|
+
)
|
|
82
|
+
]
|
|
83
|
+
|
|
84
|
+
if self.chunk:
|
|
85
|
+
chunked_documents = []
|
|
86
|
+
for document in documents:
|
|
87
|
+
chunked_documents.extend(self.chunk_document(document))
|
|
88
|
+
return chunked_documents
|
|
89
|
+
return documents
|
|
90
|
+
|
|
91
|
+
except Exception as e:
|
|
92
|
+
logger.error(f"Error reading file: {e}")
|
|
93
|
+
return []
|
|
94
|
+
|
|
95
|
+
async def async_read(self, file: Union[Path, IO[Any]], name: Optional[str] = None) -> List[Document]:
|
|
96
|
+
"""Asynchronously read a pptx file and return a list of documents"""
|
|
97
|
+
try:
|
|
98
|
+
return await asyncio.to_thread(self.read, file, name)
|
|
99
|
+
except Exception as e:
|
|
100
|
+
logger.error(f"Error reading file asynchronously: {e}")
|
|
101
|
+
return []
|
|
@@ -58,6 +58,18 @@ class ReaderFactory:
|
|
|
58
58
|
config.update(kwargs)
|
|
59
59
|
return DocxReader(**config)
|
|
60
60
|
|
|
61
|
+
@classmethod
|
|
62
|
+
def _get_pptx_reader(cls, **kwargs) -> Reader:
|
|
63
|
+
"""Get PPTX reader instance."""
|
|
64
|
+
from agno.knowledge.reader.pptx_reader import PPTXReader
|
|
65
|
+
|
|
66
|
+
config: Dict[str, Any] = {
|
|
67
|
+
"name": "PPTX Reader",
|
|
68
|
+
"description": "Extracts text content from Microsoft PowerPoint presentations (.pptx format)",
|
|
69
|
+
}
|
|
70
|
+
config.update(kwargs)
|
|
71
|
+
return PPTXReader(**config)
|
|
72
|
+
|
|
61
73
|
@classmethod
|
|
62
74
|
def _get_json_reader(cls, **kwargs) -> Reader:
|
|
63
75
|
"""Get JSON reader instance."""
|
|
@@ -202,6 +214,8 @@ class ReaderFactory:
|
|
|
202
214
|
return cls.create_reader("csv")
|
|
203
215
|
elif extension in [".docx", ".doc", "application/vnd.openxmlformats-officedocument.wordprocessingml.document"]:
|
|
204
216
|
return cls.create_reader("docx")
|
|
217
|
+
elif extension == ".pptx":
|
|
218
|
+
return cls.create_reader("pptx")
|
|
205
219
|
elif extension == ".json":
|
|
206
220
|
return cls.create_reader("json")
|
|
207
221
|
elif extension in [".md", ".markdown"]:
|
agno/knowledge/types.py
CHANGED
agno/models/base.py
CHANGED
|
@@ -1237,8 +1237,8 @@ class Model(ABC):
|
|
|
1237
1237
|
if function_call.function.show_result:
|
|
1238
1238
|
yield ModelResponse(content=item.content)
|
|
1239
1239
|
|
|
1240
|
-
|
|
1241
|
-
|
|
1240
|
+
if isinstance(item, CustomEvent):
|
|
1241
|
+
function_call_output += str(item)
|
|
1242
1242
|
|
|
1243
1243
|
# Yield the event itself to bubble it up
|
|
1244
1244
|
yield item
|
|
@@ -1626,8 +1626,8 @@ class Model(ABC):
|
|
|
1626
1626
|
await event_queue.put(ModelResponse(content=item.content))
|
|
1627
1627
|
continue
|
|
1628
1628
|
|
|
1629
|
-
|
|
1630
|
-
|
|
1629
|
+
if isinstance(item, CustomEvent):
|
|
1630
|
+
function_call_output += str(item)
|
|
1631
1631
|
|
|
1632
1632
|
# Put the event into the queue to be yielded
|
|
1633
1633
|
await event_queue.put(item)
|
agno/run/agent.py
CHANGED
|
@@ -385,6 +385,11 @@ class OutputModelResponseCompletedEvent(BaseAgentRunEvent):
|
|
|
385
385
|
class CustomEvent(BaseAgentRunEvent):
|
|
386
386
|
event: str = RunEvent.custom_event.value
|
|
387
387
|
|
|
388
|
+
def __init__(self, **kwargs):
|
|
389
|
+
# Store arbitrary attributes directly on the instance
|
|
390
|
+
for key, value in kwargs.items():
|
|
391
|
+
setattr(self, key, value)
|
|
392
|
+
|
|
388
393
|
|
|
389
394
|
RunOutputEvent = Union[
|
|
390
395
|
RunStartedEvent,
|
agno/run/team.py
CHANGED
|
@@ -368,6 +368,11 @@ class OutputModelResponseCompletedEvent(BaseTeamRunEvent):
|
|
|
368
368
|
class CustomEvent(BaseTeamRunEvent):
|
|
369
369
|
event: str = TeamRunEvent.custom_event.value
|
|
370
370
|
|
|
371
|
+
def __init__(self, **kwargs):
|
|
372
|
+
# Store arbitrary attributes directly on the instance
|
|
373
|
+
for key, value in kwargs.items():
|
|
374
|
+
setattr(self, key, value)
|
|
375
|
+
|
|
371
376
|
|
|
372
377
|
TeamRunOutputEvent = Union[
|
|
373
378
|
RunStartedEvent,
|
agno/run/workflow.py
CHANGED
|
@@ -6,9 +6,9 @@ from typing import TYPE_CHECKING, Any, Dict, List, Optional, Union
|
|
|
6
6
|
from pydantic import BaseModel
|
|
7
7
|
|
|
8
8
|
from agno.media import Audio, Image, Video
|
|
9
|
-
from agno.run.agent import RunOutput
|
|
9
|
+
from agno.run.agent import RunEvent, RunOutput, run_output_event_from_dict
|
|
10
10
|
from agno.run.base import BaseRunOutputEvent, RunStatus
|
|
11
|
-
from agno.run.team import TeamRunOutput
|
|
11
|
+
from agno.run.team import TeamRunEvent, TeamRunOutput, team_run_output_event_from_dict
|
|
12
12
|
|
|
13
13
|
if TYPE_CHECKING:
|
|
14
14
|
from agno.workflow.types import StepOutput, WorkflowMetrics
|
|
@@ -388,6 +388,11 @@ class CustomEvent(BaseWorkflowRunOutputEvent):
|
|
|
388
388
|
|
|
389
389
|
event: str = WorkflowRunEvent.custom_event.value
|
|
390
390
|
|
|
391
|
+
def __init__(self, **kwargs):
|
|
392
|
+
# Store arbitrary attributes directly on the instance
|
|
393
|
+
for key, value in kwargs.items():
|
|
394
|
+
setattr(self, key, value)
|
|
395
|
+
|
|
391
396
|
|
|
392
397
|
# Union type for all workflow run response events
|
|
393
398
|
WorkflowRunOutputEvent = Union[
|
|
@@ -442,10 +447,15 @@ WORKFLOW_RUN_EVENT_TYPE_REGISTRY = {
|
|
|
442
447
|
|
|
443
448
|
def workflow_run_output_event_from_dict(data: dict) -> BaseWorkflowRunOutputEvent:
|
|
444
449
|
event_type = data.get("event", "")
|
|
445
|
-
|
|
446
|
-
|
|
450
|
+
if event_type in {e.value for e in RunEvent}:
|
|
451
|
+
return run_output_event_from_dict(data) # type: ignore
|
|
452
|
+
elif event_type in {e.value for e in TeamRunEvent}:
|
|
453
|
+
return team_run_output_event_from_dict(data) # type: ignore
|
|
454
|
+
else:
|
|
455
|
+
event_class = WORKFLOW_RUN_EVENT_TYPE_REGISTRY.get(event_type)
|
|
456
|
+
if not event_class:
|
|
447
457
|
raise ValueError(f"Unknown workflow event type: {event_type}")
|
|
448
|
-
return
|
|
458
|
+
return event_class.from_dict(data) # type: ignore
|
|
449
459
|
|
|
450
460
|
|
|
451
461
|
@dataclass
|
agno/team/team.py
CHANGED
|
@@ -111,7 +111,7 @@ from agno.utils.log import (
|
|
|
111
111
|
use_team_logger,
|
|
112
112
|
)
|
|
113
113
|
from agno.utils.merge_dict import merge_dictionaries
|
|
114
|
-
from agno.utils.message import get_text_from_message
|
|
114
|
+
from agno.utils.message import filter_tool_calls, get_text_from_message
|
|
115
115
|
from agno.utils.print_response.team import (
|
|
116
116
|
aprint_response,
|
|
117
117
|
aprint_response_stream,
|
|
@@ -189,12 +189,6 @@ class Team:
|
|
|
189
189
|
# If True, cache the current Team session in memory for faster access
|
|
190
190
|
cache_session: bool = False
|
|
191
191
|
|
|
192
|
-
# --- Team history settings ---
|
|
193
|
-
# add_history_to_context=true adds messages from the chat history to the messages list sent to the Model. This only applies to the team leader, not the members.
|
|
194
|
-
add_history_to_context: bool = False
|
|
195
|
-
# Number of historical runs to include in the messages
|
|
196
|
-
num_history_runs: int = 3
|
|
197
|
-
|
|
198
192
|
# Add this flag to control if the workflow should send the team history to the members. This means sending the team-level history to the members, not the agent-level history.
|
|
199
193
|
add_team_history_to_members: bool = False
|
|
200
194
|
# Number of historical runs to include in the messages sent to the members
|
|
@@ -354,6 +348,14 @@ class Team:
|
|
|
354
348
|
# If True, the team adds session summaries to the context
|
|
355
349
|
add_session_summary_to_context: Optional[bool] = None
|
|
356
350
|
|
|
351
|
+
# --- Team History ---
|
|
352
|
+
# add_history_to_context=true adds messages from the chat history to the messages list sent to the Model.
|
|
353
|
+
add_history_to_context: bool = False
|
|
354
|
+
# Number of historical runs to include in the messages
|
|
355
|
+
num_history_runs: int = 3
|
|
356
|
+
# Maximum number of tool calls to include from history (None = no limit)
|
|
357
|
+
max_tool_calls_from_history: Optional[int] = None
|
|
358
|
+
|
|
357
359
|
# --- Team Storage ---
|
|
358
360
|
# Metadata stored with this team
|
|
359
361
|
metadata: Optional[Dict[str, Any]] = None
|
|
@@ -421,8 +423,6 @@ class Team:
|
|
|
421
423
|
overwrite_db_session_state: bool = False,
|
|
422
424
|
resolve_in_context: bool = True,
|
|
423
425
|
cache_session: bool = False,
|
|
424
|
-
add_history_to_context: bool = False,
|
|
425
|
-
num_history_runs: int = 3,
|
|
426
426
|
add_team_history_to_members: bool = False,
|
|
427
427
|
num_team_history_runs: int = 3,
|
|
428
428
|
search_session_history: Optional[bool] = False,
|
|
@@ -458,6 +458,8 @@ class Team:
|
|
|
458
458
|
store_tool_messages: bool = True,
|
|
459
459
|
store_history_messages: bool = True,
|
|
460
460
|
send_media_to_model: bool = True,
|
|
461
|
+
add_history_to_context: bool = False,
|
|
462
|
+
num_history_runs: int = 3,
|
|
461
463
|
tools: Optional[List[Union[Toolkit, Callable, Function, Dict]]] = None,
|
|
462
464
|
tool_call_limit: Optional[int] = None,
|
|
463
465
|
tool_choice: Optional[Union[str, Dict[str, Any]]] = None,
|
|
@@ -480,6 +482,7 @@ class Team:
|
|
|
480
482
|
enable_session_summaries: bool = False,
|
|
481
483
|
session_summary_manager: Optional[SessionSummaryManager] = None,
|
|
482
484
|
add_session_summary_to_context: Optional[bool] = None,
|
|
485
|
+
max_tool_calls_from_history: Optional[int] = None,
|
|
483
486
|
metadata: Optional[Dict[str, Any]] = None,
|
|
484
487
|
reasoning: bool = False,
|
|
485
488
|
reasoning_model: Optional[Model] = None,
|
|
@@ -591,6 +594,9 @@ class Team:
|
|
|
591
594
|
self.enable_session_summaries = enable_session_summaries
|
|
592
595
|
self.session_summary_manager = session_summary_manager
|
|
593
596
|
self.add_session_summary_to_context = add_session_summary_to_context
|
|
597
|
+
self.add_history_to_context = add_history_to_context
|
|
598
|
+
self.num_history_runs = num_history_runs
|
|
599
|
+
self.max_tool_calls_from_history = max_tool_calls_from_history
|
|
594
600
|
self.metadata = metadata
|
|
595
601
|
|
|
596
602
|
self.reasoning = reasoning
|
|
@@ -1320,6 +1326,9 @@ class Team:
|
|
|
1320
1326
|
hooks=self.post_hooks, # type: ignore
|
|
1321
1327
|
run_output=run_response,
|
|
1322
1328
|
session=session,
|
|
1329
|
+
session_state=session_state,
|
|
1330
|
+
dependencies=dependencies,
|
|
1331
|
+
metadata=metadata,
|
|
1323
1332
|
user_id=user_id,
|
|
1324
1333
|
debug_mode=debug_mode,
|
|
1325
1334
|
**kwargs,
|
|
@@ -2133,6 +2142,9 @@ class Team:
|
|
|
2133
2142
|
hooks=self.post_hooks, # type: ignore
|
|
2134
2143
|
run_output=run_response,
|
|
2135
2144
|
session=team_session,
|
|
2145
|
+
session_state=session_state,
|
|
2146
|
+
dependencies=dependencies,
|
|
2147
|
+
metadata=metadata,
|
|
2136
2148
|
user_id=user_id,
|
|
2137
2149
|
debug_mode=debug_mode,
|
|
2138
2150
|
**kwargs,
|
|
@@ -5824,6 +5836,10 @@ class Team:
|
|
|
5824
5836
|
for _msg in history_copy:
|
|
5825
5837
|
_msg.from_history = True
|
|
5826
5838
|
|
|
5839
|
+
# Filter tool calls from history messages
|
|
5840
|
+
if self.max_tool_calls_from_history is not None:
|
|
5841
|
+
filter_tool_calls(history_copy, self.max_tool_calls_from_history)
|
|
5842
|
+
|
|
5827
5843
|
log_debug(f"Adding {len(history_copy)} messages from history")
|
|
5828
5844
|
|
|
5829
5845
|
# Extend the messages with the history
|
|
@@ -5951,6 +5967,10 @@ class Team:
|
|
|
5951
5967
|
for _msg in history_copy:
|
|
5952
5968
|
_msg.from_history = True
|
|
5953
5969
|
|
|
5970
|
+
# Filter tool calls from history messages
|
|
5971
|
+
if self.max_tool_calls_from_history is not None:
|
|
5972
|
+
filter_tool_calls(history_copy, self.max_tool_calls_from_history)
|
|
5973
|
+
|
|
5954
5974
|
log_debug(f"Adding {len(history_copy)} messages from history")
|
|
5955
5975
|
|
|
5956
5976
|
# Extend the messages with the history
|
agno/utils/message.py
CHANGED
|
@@ -1,8 +1,68 @@
|
|
|
1
|
+
from copy import deepcopy
|
|
1
2
|
from typing import Dict, List, Union
|
|
2
3
|
|
|
3
4
|
from pydantic import BaseModel
|
|
4
5
|
|
|
5
6
|
from agno.models.message import Message
|
|
7
|
+
from agno.utils.log import log_debug
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def filter_tool_calls(messages: List[Message], max_tool_calls: int) -> None:
|
|
11
|
+
"""
|
|
12
|
+
Filter messages (in-place) to keep only the most recent N tool calls.
|
|
13
|
+
|
|
14
|
+
Args:
|
|
15
|
+
messages: List of messages to filter (modified in-place)
|
|
16
|
+
max_tool_calls: Number of recent tool calls to keep
|
|
17
|
+
"""
|
|
18
|
+
# Count total tool calls
|
|
19
|
+
tool_call_count = sum(1 for m in messages if m.role == "tool")
|
|
20
|
+
|
|
21
|
+
# No filtering needed
|
|
22
|
+
if tool_call_count <= max_tool_calls:
|
|
23
|
+
return
|
|
24
|
+
|
|
25
|
+
# Collect tool_call_ids to keep (most recent N)
|
|
26
|
+
tool_call_ids_list: List[str] = []
|
|
27
|
+
for msg in reversed(messages):
|
|
28
|
+
if msg.role == "tool" and len(tool_call_ids_list) < max_tool_calls:
|
|
29
|
+
if msg.tool_call_id:
|
|
30
|
+
tool_call_ids_list.append(msg.tool_call_id)
|
|
31
|
+
|
|
32
|
+
tool_call_ids_to_keep: set[str] = set(tool_call_ids_list)
|
|
33
|
+
|
|
34
|
+
# Filter messages in-place
|
|
35
|
+
filtered_messages = []
|
|
36
|
+
for msg in messages:
|
|
37
|
+
if msg.role == "tool":
|
|
38
|
+
# Keep only tool results in our window
|
|
39
|
+
if msg.tool_call_id in tool_call_ids_to_keep:
|
|
40
|
+
filtered_messages.append(msg)
|
|
41
|
+
elif msg.role == "assistant" and msg.tool_calls:
|
|
42
|
+
# Filter tool_calls within the assistant message
|
|
43
|
+
# Use deepcopy to ensure complete isolation of the filtered message
|
|
44
|
+
filtered_msg = deepcopy(msg)
|
|
45
|
+
# Filter tool_calls
|
|
46
|
+
if filtered_msg.tool_calls is not None:
|
|
47
|
+
filtered_msg.tool_calls = [
|
|
48
|
+
tc for tc in filtered_msg.tool_calls if tc.get("id") in tool_call_ids_to_keep
|
|
49
|
+
]
|
|
50
|
+
|
|
51
|
+
if filtered_msg.tool_calls:
|
|
52
|
+
# Has tool_calls remaining, keep it
|
|
53
|
+
filtered_messages.append(filtered_msg)
|
|
54
|
+
# skip empty messages
|
|
55
|
+
elif filtered_msg.content:
|
|
56
|
+
filtered_msg.tool_calls = None
|
|
57
|
+
filtered_messages.append(filtered_msg)
|
|
58
|
+
else:
|
|
59
|
+
filtered_messages.append(msg)
|
|
60
|
+
|
|
61
|
+
messages[:] = filtered_messages
|
|
62
|
+
|
|
63
|
+
# Log filtering information
|
|
64
|
+
num_filtered = tool_call_count - len(tool_call_ids_to_keep)
|
|
65
|
+
log_debug(f"Filtered {num_filtered} tool calls, kept {len(tool_call_ids_to_keep)}")
|
|
6
66
|
|
|
7
67
|
|
|
8
68
|
def get_text_from_message(message: Union[List, Dict, str, Message, BaseModel]) -> str:
|
agno/workflow/workflow.py
CHANGED
|
@@ -29,7 +29,7 @@ from agno.exceptions import InputCheckError, OutputCheckError, RunCancelledExcep
|
|
|
29
29
|
from agno.media import Audio, File, Image, Video
|
|
30
30
|
from agno.models.message import Message
|
|
31
31
|
from agno.models.metrics import Metrics
|
|
32
|
-
from agno.run.agent import RunEvent
|
|
32
|
+
from agno.run.agent import RunContentEvent, RunEvent
|
|
33
33
|
from agno.run.base import RunStatus
|
|
34
34
|
from agno.run.cancel import (
|
|
35
35
|
cancel_run as cancel_run_global,
|
|
@@ -39,6 +39,7 @@ from agno.run.cancel import (
|
|
|
39
39
|
raise_if_cancelled,
|
|
40
40
|
register_run,
|
|
41
41
|
)
|
|
42
|
+
from agno.run.team import RunContentEvent as TeamRunContentEvent
|
|
42
43
|
from agno.run.team import TeamRunEvent
|
|
43
44
|
from agno.run.workflow import (
|
|
44
45
|
StepOutputEvent,
|
|
@@ -1177,6 +1178,15 @@ class Workflow:
|
|
|
1177
1178
|
logger.error(f"Function signature inspection failed: {e}. Falling back to original calling convention.")
|
|
1178
1179
|
return func(**kwargs)
|
|
1179
1180
|
|
|
1181
|
+
def _accumulate_partial_step_data(
|
|
1182
|
+
self, event: Union[RunContentEvent, TeamRunContentEvent], partial_step_content: str
|
|
1183
|
+
) -> str:
|
|
1184
|
+
"""Accumulate partial step data from streaming events"""
|
|
1185
|
+
if isinstance(event, (RunContentEvent, TeamRunContentEvent)) and event.content:
|
|
1186
|
+
if isinstance(event.content, str):
|
|
1187
|
+
partial_step_content += event.content
|
|
1188
|
+
return partial_step_content
|
|
1189
|
+
|
|
1180
1190
|
def _execute(
|
|
1181
1191
|
self,
|
|
1182
1192
|
session: WorkflowSession,
|
|
@@ -1400,11 +1410,22 @@ class Workflow:
|
|
|
1400
1410
|
|
|
1401
1411
|
early_termination = False
|
|
1402
1412
|
|
|
1413
|
+
# Track partial step data in case of cancellation
|
|
1414
|
+
current_step_name = ""
|
|
1415
|
+
current_step = None
|
|
1416
|
+
partial_step_content = ""
|
|
1417
|
+
|
|
1403
1418
|
for i, step in enumerate(self.steps): # type: ignore[arg-type]
|
|
1404
1419
|
raise_if_cancelled(workflow_run_response.run_id) # type: ignore
|
|
1405
1420
|
step_name = getattr(step, "name", f"step_{i + 1}")
|
|
1406
1421
|
log_debug(f"Streaming step {i + 1}/{self._get_step_count()}: {step_name}")
|
|
1407
1422
|
|
|
1423
|
+
# Track current step for cancellation handler
|
|
1424
|
+
current_step_name = step_name
|
|
1425
|
+
current_step = step
|
|
1426
|
+
# Reset partial data for this step
|
|
1427
|
+
partial_step_content = ""
|
|
1428
|
+
|
|
1408
1429
|
# Create enhanced StepInput
|
|
1409
1430
|
step_input = self._create_step_input(
|
|
1410
1431
|
execution_input=execution_input,
|
|
@@ -1433,6 +1454,10 @@ class Workflow:
|
|
|
1433
1454
|
num_history_runs=self.num_history_runs,
|
|
1434
1455
|
):
|
|
1435
1456
|
raise_if_cancelled(workflow_run_response.run_id) # type: ignore
|
|
1457
|
+
|
|
1458
|
+
# Accumulate partial data from streaming events
|
|
1459
|
+
partial_step_content = self._accumulate_partial_step_data(event, partial_step_content) # type: ignore
|
|
1460
|
+
|
|
1436
1461
|
# Handle events
|
|
1437
1462
|
if isinstance(event, StepOutput):
|
|
1438
1463
|
step_output = event
|
|
@@ -1547,6 +1572,29 @@ class Workflow:
|
|
|
1547
1572
|
logger.info(f"Workflow run {workflow_run_response.run_id} was cancelled during streaming")
|
|
1548
1573
|
workflow_run_response.status = RunStatus.cancelled
|
|
1549
1574
|
workflow_run_response.content = str(e)
|
|
1575
|
+
|
|
1576
|
+
# Capture partial progress from the step that was cancelled mid-stream
|
|
1577
|
+
if partial_step_content:
|
|
1578
|
+
logger.info(
|
|
1579
|
+
f"Step with name '{current_step_name}' was cancelled. Setting its partial progress as step output."
|
|
1580
|
+
)
|
|
1581
|
+
partial_step_output = StepOutput(
|
|
1582
|
+
step_name=current_step_name,
|
|
1583
|
+
step_id=getattr(current_step, "step_id", None) if current_step else None,
|
|
1584
|
+
step_type=StepType.STEP,
|
|
1585
|
+
executor_type=getattr(current_step, "executor_type", None) if current_step else None,
|
|
1586
|
+
executor_name=getattr(current_step, "executor_name", None) if current_step else None,
|
|
1587
|
+
content=partial_step_content,
|
|
1588
|
+
success=False,
|
|
1589
|
+
error="Cancelled during execution",
|
|
1590
|
+
)
|
|
1591
|
+
collected_step_outputs.append(partial_step_output)
|
|
1592
|
+
|
|
1593
|
+
# Preserve all progress (completed steps + partial step) before cancellation
|
|
1594
|
+
if collected_step_outputs:
|
|
1595
|
+
workflow_run_response.step_results = collected_step_outputs
|
|
1596
|
+
workflow_run_response.metrics = self._aggregate_workflow_metrics(collected_step_outputs)
|
|
1597
|
+
|
|
1550
1598
|
cancelled_event = WorkflowCancelledEvent(
|
|
1551
1599
|
run_id=workflow_run_response.run_id or "",
|
|
1552
1600
|
workflow_id=self.id,
|
|
@@ -1922,12 +1970,22 @@ class Workflow:
|
|
|
1922
1970
|
|
|
1923
1971
|
early_termination = False
|
|
1924
1972
|
|
|
1973
|
+
# Track partial step data in case of cancellation
|
|
1974
|
+
current_step_name = ""
|
|
1975
|
+
current_step = None
|
|
1976
|
+
partial_step_content = ""
|
|
1977
|
+
|
|
1925
1978
|
for i, step in enumerate(self.steps): # type: ignore[arg-type]
|
|
1926
1979
|
if workflow_run_response.run_id:
|
|
1927
1980
|
raise_if_cancelled(workflow_run_response.run_id)
|
|
1928
1981
|
step_name = getattr(step, "name", f"step_{i + 1}")
|
|
1929
1982
|
log_debug(f"Async streaming step {i + 1}/{self._get_step_count()}: {step_name}")
|
|
1930
1983
|
|
|
1984
|
+
current_step_name = step_name
|
|
1985
|
+
current_step = step
|
|
1986
|
+
# Reset partial data for this step
|
|
1987
|
+
partial_step_content = ""
|
|
1988
|
+
|
|
1931
1989
|
# Create enhanced StepInput
|
|
1932
1990
|
step_input = self._create_step_input(
|
|
1933
1991
|
execution_input=execution_input,
|
|
@@ -1957,6 +2015,10 @@ class Workflow:
|
|
|
1957
2015
|
):
|
|
1958
2016
|
if workflow_run_response.run_id:
|
|
1959
2017
|
raise_if_cancelled(workflow_run_response.run_id)
|
|
2018
|
+
|
|
2019
|
+
# Accumulate partial data from streaming events
|
|
2020
|
+
partial_step_content = self._accumulate_partial_step_data(event, partial_step_content) # type: ignore
|
|
2021
|
+
|
|
1960
2022
|
if isinstance(event, StepOutput):
|
|
1961
2023
|
step_output = event
|
|
1962
2024
|
collected_step_outputs.append(step_output)
|
|
@@ -2073,6 +2135,29 @@ class Workflow:
|
|
|
2073
2135
|
logger.info(f"Workflow run {workflow_run_response.run_id} was cancelled during streaming")
|
|
2074
2136
|
workflow_run_response.status = RunStatus.cancelled
|
|
2075
2137
|
workflow_run_response.content = str(e)
|
|
2138
|
+
|
|
2139
|
+
# Capture partial progress from the step that was cancelled mid-stream
|
|
2140
|
+
if partial_step_content:
|
|
2141
|
+
logger.info(
|
|
2142
|
+
f"Step with name '{current_step_name}' was cancelled. Setting its partial progress as step output."
|
|
2143
|
+
)
|
|
2144
|
+
partial_step_output = StepOutput(
|
|
2145
|
+
step_name=current_step_name,
|
|
2146
|
+
step_id=getattr(current_step, "step_id", None) if current_step else None,
|
|
2147
|
+
step_type=StepType.STEP,
|
|
2148
|
+
executor_type=getattr(current_step, "executor_type", None) if current_step else None,
|
|
2149
|
+
executor_name=getattr(current_step, "executor_name", None) if current_step else None,
|
|
2150
|
+
content=partial_step_content,
|
|
2151
|
+
success=False,
|
|
2152
|
+
error="Cancelled during execution",
|
|
2153
|
+
)
|
|
2154
|
+
collected_step_outputs.append(partial_step_output)
|
|
2155
|
+
|
|
2156
|
+
# Preserve all progress (completed steps + partial step) before cancellation
|
|
2157
|
+
if collected_step_outputs:
|
|
2158
|
+
workflow_run_response.step_results = collected_step_outputs
|
|
2159
|
+
workflow_run_response.metrics = self._aggregate_workflow_metrics(collected_step_outputs)
|
|
2160
|
+
|
|
2076
2161
|
cancelled_event = WorkflowCancelledEvent(
|
|
2077
2162
|
run_id=workflow_run_response.run_id or "",
|
|
2078
2163
|
workflow_id=self.id,
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: agno
|
|
3
|
-
Version: 2.2.
|
|
3
|
+
Version: 2.2.1
|
|
4
4
|
Summary: Agno: a lightweight library for building Multi-Agent Systems
|
|
5
5
|
Author-email: Ashpreet Bedi <ashpreet@agno.com>
|
|
6
6
|
Project-URL: homepage, https://agno.com
|
|
@@ -238,6 +238,8 @@ Requires-Dist: pypdf; extra == "pdf"
|
|
|
238
238
|
Requires-Dist: rapidocr_onnxruntime; extra == "pdf"
|
|
239
239
|
Provides-Extra: docx
|
|
240
240
|
Requires-Dist: python-docx; extra == "docx"
|
|
241
|
+
Provides-Extra: pptx
|
|
242
|
+
Requires-Dist: python-pptx; extra == "pptx"
|
|
241
243
|
Provides-Extra: text
|
|
242
244
|
Requires-Dist: aiofiles; extra == "text"
|
|
243
245
|
Provides-Extra: csv
|
|
@@ -346,6 +348,7 @@ Requires-Dist: agno[upstash]; extra == "vectordbs"
|
|
|
346
348
|
Provides-Extra: knowledge
|
|
347
349
|
Requires-Dist: agno[pdf]; extra == "knowledge"
|
|
348
350
|
Requires-Dist: agno[docx]; extra == "knowledge"
|
|
351
|
+
Requires-Dist: agno[pptx]; extra == "knowledge"
|
|
349
352
|
Requires-Dist: agno[text]; extra == "knowledge"
|
|
350
353
|
Requires-Dist: agno[csv]; extra == "knowledge"
|
|
351
354
|
Requires-Dist: agno[markdown]; extra == "knowledge"
|
|
@@ -4,7 +4,7 @@ agno/exceptions.py,sha256=7xqLur8sWHugnViIJz4PvPKSHljSiVKNAqaKQOJgZiU,4982
|
|
|
4
4
|
agno/media.py,sha256=eTfYb_pwhX_PCIVPSrW4VYRqmoxKABEF1aZClrVvQ30,16500
|
|
5
5
|
agno/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
6
6
|
agno/agent/__init__.py,sha256=s7S3FgsjZxuaabzi8L5n4aSH8IZAiZ7XaNNcySGR-EQ,1051
|
|
7
|
-
agno/agent/agent.py,sha256=
|
|
7
|
+
agno/agent/agent.py,sha256=YcP5yKxsxLb4KoxNr7H4SDGu27dwtqsXQ9clDzZl3bw,449829
|
|
8
8
|
agno/api/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
9
9
|
agno/api/agent.py,sha256=fKlQ62E_C9Rjd7Zus3Gs3R1RG-IhzFV-ICpkb6SLqYc,932
|
|
10
10
|
agno/api/api.py,sha256=Z7iWbrjheJcGLeeDYrtTCWiKTVqjH0uJI35UNWOtAXw,973
|
|
@@ -106,8 +106,8 @@ agno/integrations/discord/__init__.py,sha256=MS08QSnegGgpDZd9LyLjK4pWIk9dXlbzgD7
|
|
|
106
106
|
agno/integrations/discord/client.py,sha256=2IWkA-kCDsDXByKOGq2QJG6MtFsbouzNN105rsXn95A,8375
|
|
107
107
|
agno/knowledge/__init__.py,sha256=PJCt-AGKGFztzR--Ok2TNKW5QEqllZzqiI_7f8-1u80,79
|
|
108
108
|
agno/knowledge/content.py,sha256=q2bjcjDhfge_UrQAcygrv5R9ZTk7vozzKnQpatDQWRo,2295
|
|
109
|
-
agno/knowledge/knowledge.py,sha256
|
|
110
|
-
agno/knowledge/types.py,sha256=
|
|
109
|
+
agno/knowledge/knowledge.py,sha256=-VhXpz2SuKysPiANF6lff3v61P5HJKr-HKc17WwBOC0,78546
|
|
110
|
+
agno/knowledge/types.py,sha256=4NnkL_h2W-7GQnHW-yIqMNPUCWLzo5qBXF99gfsMe08,773
|
|
111
111
|
agno/knowledge/utils.py,sha256=_uhEFtz4p7-cIKffdj5UZ__c-u96rs2UWP6dv5HpOMk,6490
|
|
112
112
|
agno/knowledge/chunking/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
113
113
|
agno/knowledge/chunking/agentic.py,sha256=OksjCXySqu0vRseQsFgsOdfD0lXqXHP_SGJ6G8Tecbc,3059
|
|
@@ -148,7 +148,8 @@ agno/knowledge/reader/firecrawl_reader.py,sha256=SCbcRLkMrUb2WiC6SPuAoZULtHITa2V
|
|
|
148
148
|
agno/knowledge/reader/json_reader.py,sha256=KfDgHno_XHORIGaoA1Q2Y5M7nkcTFM9IUzWXkjVjYKQ,3245
|
|
149
149
|
agno/knowledge/reader/markdown_reader.py,sha256=HoSEkX2Svl2tEMDyzAmRNmwxsterb3i3-1-EQR6N4IU,5272
|
|
150
150
|
agno/knowledge/reader/pdf_reader.py,sha256=F1Zx5i5jTUbuuKEPEnlnzMgCAweJMehYY0igRFHuHf4,17206
|
|
151
|
-
agno/knowledge/reader/
|
|
151
|
+
agno/knowledge/reader/pptx_reader.py,sha256=q0VAszrLry1ZhTOYXFRt6TVMAw12pAK64frYRvMNACo,3929
|
|
152
|
+
agno/knowledge/reader/reader_factory.py,sha256=18H8FQHIZf4SECZls1AwpMAzrS1FSOEuTkgJqbv0-HE,10783
|
|
152
153
|
agno/knowledge/reader/s3_reader.py,sha256=j_xBDWV9l5Uhsr88glQ0dCMS-ijvqw8gdMc1Bzfm394,3547
|
|
153
154
|
agno/knowledge/reader/text_reader.py,sha256=Vkk3mWhjyazPv77Z9PGO1nRVk8cmVkUFIWZFCVqTkOI,4444
|
|
154
155
|
agno/knowledge/reader/web_search_reader.py,sha256=GMc59AxwS1zTyBEmnwzJCEbPmK4ut1eWy8EV5XXTRSk,14585
|
|
@@ -165,7 +166,7 @@ agno/knowledge/reranker/sentence_transformer.py,sha256=ZN4SqnMZsUhg5G7AzlONM1_Uj
|
|
|
165
166
|
agno/memory/__init__.py,sha256=XWKJU5SJObYZqEKMZ2XYwgH8-YeuWUoSRfT4dEI5HnY,101
|
|
166
167
|
agno/memory/manager.py,sha256=IWMnFxRF604zLY1jQArOggMwLjUUKXiPWt7RtLlpHUk,51907
|
|
167
168
|
agno/models/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
168
|
-
agno/models/base.py,sha256=
|
|
169
|
+
agno/models/base.py,sha256=Tifu_fMGiWgwGMMoB6ww_BjrZ7cOb73V1oqZCU9PXJk,85198
|
|
169
170
|
agno/models/defaults.py,sha256=1_fe4-ZbNriE8BgqxVRVi4KGzEYxYKYsz4hn6CZNEEM,40
|
|
170
171
|
agno/models/message.py,sha256=HMlY71ZCDWCUrNTqIbRezWZK5FfWcvcs5eg_hhjbuqo,19023
|
|
171
172
|
agno/models/metrics.py,sha256=81IILXZwGmOTiWK003bi5mg4bM1f4LCWbwyamjFzp18,4500
|
|
@@ -314,19 +315,19 @@ agno/reasoning/openai.py,sha256=JYk-mR9cMf1ibprX3MdL8oeCEDyQ3XaJw9PAIYvWeGk,3234
|
|
|
314
315
|
agno/reasoning/step.py,sha256=6DaOb_0DJRz9Yh1w_mxcRaOSVzIQDrj3lQ6rzHLdIwA,1220
|
|
315
316
|
agno/reasoning/vertexai.py,sha256=O9ntvalkIY2jLmWviEH1DnecMskqTL-mRZQBZohoHiU,2974
|
|
316
317
|
agno/run/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
|
317
|
-
agno/run/agent.py,sha256=
|
|
318
|
+
agno/run/agent.py,sha256=0Je28vN3tFW5YdhcU-YAXZHT16wFSWKbE5zkAu9E3bo,25631
|
|
318
319
|
agno/run/base.py,sha256=x37ecdhKdb3dbW23d8t2JPBZwrwIC93lRvT1-76CK0c,7059
|
|
319
320
|
agno/run/cancel.py,sha256=yoSj3fnx8D7Gf-fSngVIgd3GOp3tRaDhHH_4QeHDoAk,2667
|
|
320
321
|
agno/run/messages.py,sha256=rAC4CLW-xBA6qFS1BOvcjJ9j_qYf0a7sX1mcdY04zMU,1126
|
|
321
|
-
agno/run/team.py,sha256=
|
|
322
|
-
agno/run/workflow.py,sha256=
|
|
322
|
+
agno/run/team.py,sha256=_6MhyeDvP2pO6dqA0U8yxqxwpmX6q0eBfhLjrsOY1Fc,26082
|
|
323
|
+
agno/run/workflow.py,sha256=DHnRDjtWlMXwoG0jGkk332hFbhqRKav3zUlb7dYrps4,23201
|
|
323
324
|
agno/session/__init__.py,sha256=p6eqzWcLSHiMex2yZvkwv2yrFUNdGs21TGMS49xrEC4,376
|
|
324
325
|
agno/session/agent.py,sha256=vut3IwCivUu0vvuht_1c3rUhW61NZee6whxDQUsEkUM,9756
|
|
325
326
|
agno/session/summary.py,sha256=5lKMepDMh3bp1Uo8EJMvHHQRwLiB14eF53iMkg0wumM,10012
|
|
326
327
|
agno/session/team.py,sha256=e1GagwJOwmhjvijUiCitOu0YCuf_BadAtG2KC4n34ic,13390
|
|
327
328
|
agno/session/workflow.py,sha256=tluE_3ERMBYJtffpwlrhdETWlzJk6Xw2x06FZ1Y3fXg,7397
|
|
328
329
|
agno/team/__init__.py,sha256=toHidBOo5M3n_TIVtIKHgcDbLL9HR-_U-YQYuIt_XtE,847
|
|
329
|
-
agno/team/team.py,sha256=
|
|
330
|
+
agno/team/team.py,sha256=RNOMWDWHaOPt7MBT2oVuhGis1M5aKiRgvpzXASWYHx4,391440
|
|
330
331
|
agno/tools/__init__.py,sha256=jNll2sELhPPbqm5nPeT4_uyzRO2_KRTW-8Or60kioS0,210
|
|
331
332
|
agno/tools/agentql.py,sha256=S82Z9aTNr-E5wnA4fbFs76COljJtiQIjf2grjz3CkHU,4104
|
|
332
333
|
agno/tools/airflow.py,sha256=uf2rOzZpSU64l_qRJ5Raku-R3Gky-uewmYkh6W0-oxg,2610
|
|
@@ -471,7 +472,7 @@ agno/utils/log.py,sha256=Ycg4_MEkXyOz25OkY272JHWxIZP1nB4OScwJ-r8BMGk,7791
|
|
|
471
472
|
agno/utils/mcp.py,sha256=v5juISDNtdQaUK1DmJnAAGuNiSp0491TDwErgjEdhF8,5113
|
|
472
473
|
agno/utils/media.py,sha256=Lk0sbSHmoKlQi3hLKorowCKGF74xdeMfqIj6Gt21Zek,5891
|
|
473
474
|
agno/utils/merge_dict.py,sha256=K_dZdwi46gjDFn7wgqZ9_fycRIZGJCnUxFVKCrQ6PYc,1490
|
|
474
|
-
agno/utils/message.py,sha256=
|
|
475
|
+
agno/utils/message.py,sha256=jIcSe79WmfpbbYowy0C57ZzRBd9ENj-hyj3TQw_9vsg,4684
|
|
475
476
|
agno/utils/openai.py,sha256=quhHsggz0uSZc9Lt-aVsveHSS1LT2r1fMgC0IpG43Tg,10300
|
|
476
477
|
agno/utils/pickle.py,sha256=Ip6CPNxAWF3MVrUhMTW7e3IcpKhYG0IA-NKbdUYr94c,1008
|
|
477
478
|
agno/utils/pprint.py,sha256=aTg3gfib3x3VK3E-xJrbBeufK7s77ebTVtWoa2VrYgU,7762
|
|
@@ -555,9 +556,9 @@ agno/workflow/router.py,sha256=q2nuFMEAUQwVTZGncFCwlOsdOw-4nHt5QNJQgEdhv6I,29707
|
|
|
555
556
|
agno/workflow/step.py,sha256=gD9Nw3jYk6jsTTko3Ab0pRmMZ2ReOhcCzCgHZA7EcSc,60533
|
|
556
557
|
agno/workflow/steps.py,sha256=O3lbKw56ziSnuJndAGm8hjlEwdTh2jQXf1s0587Va3M,25671
|
|
557
558
|
agno/workflow/types.py,sha256=DutB4UkEppJoWRiNaGEnPk6xFNpg0oCBwOb7VJ8T_xE,18646
|
|
558
|
-
agno/workflow/workflow.py,sha256=
|
|
559
|
-
agno-2.2.
|
|
560
|
-
agno-2.2.
|
|
561
|
-
agno-2.2.
|
|
562
|
-
agno-2.2.
|
|
563
|
-
agno-2.2.
|
|
559
|
+
agno/workflow/workflow.py,sha256=LBy_jVjvglRE4sOLAITZGaOJctJYbP59oV0HvuiHopA,147346
|
|
560
|
+
agno-2.2.1.dist-info/licenses/LICENSE,sha256=QwcOLU5TJoTeUhuIXzhdCEEDDvorGiC6-3YTOl4TecE,11356
|
|
561
|
+
agno-2.2.1.dist-info/METADATA,sha256=C28Hn25iN0DTL3dfdB_4qm3pY0ygTuXVWQqzyQFuyJ0,28076
|
|
562
|
+
agno-2.2.1.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
|
|
563
|
+
agno-2.2.1.dist-info/top_level.txt,sha256=MKyeuVesTyOKIXUhc-d_tPa2Hrh0oTA4LM0izowpx70,5
|
|
564
|
+
agno-2.2.1.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|