agno 1.7.8__py3-none-any.whl → 1.7.10__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/team/team.py CHANGED
@@ -310,6 +310,7 @@ class Team:
310
310
  model: Optional[Model] = None,
311
311
  name: Optional[str] = None,
312
312
  team_id: Optional[str] = None,
313
+ role: Optional[str] = None,
313
314
  user_id: Optional[str] = None,
314
315
  session_id: Optional[str] = None,
315
316
  session_name: Optional[str] = None,
@@ -390,6 +391,7 @@ class Team:
390
391
 
391
392
  self.name = name
392
393
  self.team_id = team_id
394
+ self.role = role
393
395
 
394
396
  self.user_id = user_id
395
397
  self.session_id = session_id
@@ -1110,16 +1112,21 @@ class Team:
1110
1112
  response_format=response_format,
1111
1113
  stream_intermediate_steps=stream_intermediate_steps,
1112
1114
  ):
1113
- from agno.run.team import RunResponseContentEvent
1115
+ from agno.run.team import IntermediateRunResponseContentEvent, RunResponseContentEvent
1114
1116
 
1115
1117
  if isinstance(event, RunResponseContentEvent):
1116
1118
  if stream_intermediate_steps:
1117
- yield event
1119
+ yield IntermediateRunResponseContentEvent(
1120
+ content=event.content,
1121
+ content_type=event.content_type,
1122
+ )
1118
1123
  else:
1119
1124
  yield event
1120
1125
 
1121
1126
  yield from self._generate_response_with_output_model_stream(
1122
- run_response=run_response, run_messages=run_messages
1127
+ run_response=run_response,
1128
+ run_messages=run_messages,
1129
+ stream_intermediate_steps=stream_intermediate_steps,
1123
1130
  )
1124
1131
 
1125
1132
  # If a parser model is provided, structure the response separately
@@ -1519,19 +1526,28 @@ class Team:
1519
1526
  ):
1520
1527
  yield event
1521
1528
  else:
1522
- from agno.run.team import RunResponseContentEvent
1523
-
1524
- async for event in self._agenerate_response_with_output_model_stream(
1529
+ async for event in self._ahandle_model_response_stream(
1525
1530
  run_response=run_response,
1526
1531
  run_messages=run_messages,
1532
+ response_format=response_format,
1527
1533
  stream_intermediate_steps=stream_intermediate_steps,
1528
1534
  ):
1535
+ from agno.run.team import IntermediateRunResponseContentEvent, RunResponseContentEvent
1536
+
1529
1537
  if isinstance(event, RunResponseContentEvent):
1530
1538
  if stream_intermediate_steps:
1531
- yield event
1539
+ yield IntermediateRunResponseContentEvent(
1540
+ content=event.content,
1541
+ content_type=event.content_type,
1542
+ )
1532
1543
  else:
1533
1544
  yield event
1534
1545
 
1546
+ async for event in self._agenerate_response_with_output_model_stream(
1547
+ run_response=run_response,
1548
+ run_messages=run_messages,
1549
+ stream_intermediate_steps=stream_intermediate_steps,
1550
+ ):
1535
1551
  yield event
1536
1552
 
1537
1553
  # If a parser model is provided, structure the response separately
@@ -2446,10 +2462,9 @@ class Team:
2446
2462
  model_response.content = output_model_response.content
2447
2463
 
2448
2464
  def _generate_response_with_output_model_stream(
2449
- self, run_response: TeamRunResponse, run_messages: RunMessages, stream_intermediate_steps: bool = True
2465
+ self, run_response: TeamRunResponse, run_messages: RunMessages, stream_intermediate_steps: bool = False
2450
2466
  ):
2451
2467
  """Parse the model response using the output model stream."""
2452
-
2453
2468
  from agno.utils.events import (
2454
2469
  create_team_output_model_response_completed_event,
2455
2470
  create_team_output_model_response_started_event,
@@ -2497,7 +2512,7 @@ class Team:
2497
2512
  model_response.content = output_model_response.content
2498
2513
 
2499
2514
  async def _agenerate_response_with_output_model_stream(
2500
- self, run_response: TeamRunResponse, run_messages: RunMessages, stream_intermediate_steps: bool = True
2515
+ self, run_response: TeamRunResponse, run_messages: RunMessages, stream_intermediate_steps: bool = False
2501
2516
  ):
2502
2517
  """Parse the model response using the output model stream."""
2503
2518
  from agno.utils.events import (
@@ -2514,9 +2529,7 @@ class Team:
2514
2529
  messages_for_output_model = self.get_messages_for_output_model(run_messages.messages)
2515
2530
  model_response = ModelResponse(content="")
2516
2531
 
2517
- model_response_stream = self.output_model.aresponse_stream(messages=messages_for_output_model)
2518
-
2519
- async for model_response_event in model_response_stream:
2532
+ async for model_response_event in self.output_model.aresponse_stream(messages=messages_for_output_model):
2520
2533
  for event in self._handle_model_response_chunk(
2521
2534
  run_response=run_response,
2522
2535
  full_model_response=model_response,
@@ -5442,6 +5455,10 @@ class Team:
5442
5455
  if self.description is not None:
5443
5456
  system_message_content += f"<description>\n{self.description}\n</description>\n\n"
5444
5457
 
5458
+ # 3.3.4 Then add the Team role if provided
5459
+ if self.role is not None:
5460
+ system_message_content += f"\n<your_role>\n{self.role}\n</your_role>\n\n"
5461
+
5445
5462
  # 3.3.5 Then add instructions for the Agent
5446
5463
  if len(instructions) > 0:
5447
5464
  system_message_content += "<instructions>"
@@ -5634,7 +5651,7 @@ class Team:
5634
5651
  if isinstance(message, str):
5635
5652
  user_message_content = message
5636
5653
  else:
5637
- user_message_content = "\n".join(message)
5654
+ user_message_content = "\n".join(str(message))
5638
5655
 
5639
5656
  # Add references to user message
5640
5657
  if (
@@ -7141,9 +7158,10 @@ class Team:
7141
7158
  # If the team_session_state is already set, merge the team_session_state from the database with the current team_session_state
7142
7159
  if self.team_session_state is not None and len(self.team_session_state) > 0:
7143
7160
  # This updates team_session_state_from_db
7144
- merge_dictionaries(team_session_state_from_db, self.team_session_state)
7145
- # Update the current team_session_state
7146
- self.team_session_state = team_session_state_from_db
7161
+ merge_dictionaries(self.team_session_state, team_session_state_from_db)
7162
+ else:
7163
+ # Update the current team_session_state
7164
+ self.team_session_state = team_session_state_from_db
7147
7165
 
7148
7166
  if "workflow_session_state" in session.session_data:
7149
7167
  workflow_session_state_from_db = session.session_data.get("workflow_session_state")
@@ -7155,9 +7173,10 @@ class Team:
7155
7173
  # If the workflow_session_state is already set, merge the workflow_session_state from the database with the current workflow_session_state
7156
7174
  if self.workflow_session_state is not None and len(self.workflow_session_state) > 0:
7157
7175
  # This updates workflow_session_state_from_db
7158
- merge_dictionaries(workflow_session_state_from_db, self.workflow_session_state)
7159
- # Update the current workflow_session_state
7160
- self.workflow_session_state = workflow_session_state_from_db
7176
+ merge_dictionaries(self.workflow_session_state, workflow_session_state_from_db)
7177
+ else:
7178
+ # Update the current workflow_session_state
7179
+ self.workflow_session_state = workflow_session_state_from_db
7161
7180
 
7162
7181
  # Get the session_metrics from the database
7163
7182
  if "session_metrics" in session.session_data:
agno/tools/aws_lambda.py CHANGED
@@ -26,6 +26,9 @@ class AWSLambdaTools(Toolkit):
26
26
  super().__init__(name="aws-lambda", tools=tools, **kwargs)
27
27
 
28
28
  def list_functions(self) -> str:
29
+ """
30
+ List all AWS Lambda functions in the configured AWS account.
31
+ """
29
32
  try:
30
33
  response = self.client.list_functions()
31
34
  functions = [func["FunctionName"] for func in response["Functions"]]
@@ -34,6 +37,13 @@ class AWSLambdaTools(Toolkit):
34
37
  return f"Error listing functions: {str(e)}"
35
38
 
36
39
  def invoke_function(self, function_name: str, payload: str = "{}") -> str:
40
+ """
41
+ Invoke a specific AWS Lambda function with an optional JSON payload.
42
+
43
+ Args:
44
+ function_name (str): The name of the Lambda function to invoke.
45
+ payload (str): The JSON payload to send to the function. Defaults to "{}".
46
+ """
37
47
  try:
38
48
  response = self.client.invoke(FunctionName=function_name, Payload=payload)
39
49
  return f"Function invoked successfully. Status code: {response['StatusCode']}, Payload: {response['Payload'].read().decode('utf-8')}"
agno/tools/github.py CHANGED
@@ -458,35 +458,71 @@ class GithubTools(Toolkit):
458
458
  logger.error(f"Error creating issue: {e}")
459
459
  return json.dumps({"error": str(e)})
460
460
 
461
- def list_issues(self, repo_name: str, state: str = "open", limit: int = 20) -> str:
462
- """List issues for a repository.
461
+ def list_issues(self, repo_name: str, state: str = "open", page: int = 1, per_page: int = 20) -> str:
462
+ """List issues for a repository with pagination.
463
463
 
464
464
  Args:
465
465
  repo_name (str): The full name of the repository (e.g., 'owner/repo').
466
466
  state (str, optional): The state of issues to list ('open', 'closed', 'all'). Defaults to 'open'.
467
- limit (int, optional): The maximum number of issues to return. Defaults to 20.
467
+ page (int, optional): Page number of results to return, counting from 1. Defaults to 1.
468
+ per_page (int, optional): Number of results per page. Defaults to 20.
468
469
  Returns:
469
- A JSON-formatted string containing a list of issues.
470
+ A JSON-formatted string containing a list of issues with pagination metadata.
470
471
  """
471
- log_debug(f"Listing issues for repository: {repo_name} with state: {state}")
472
+ log_debug(f"Listing issues for repository: {repo_name} with state: {state}, page: {page}, per_page: {per_page}")
472
473
  try:
473
474
  repo = self.g.get_repo(repo_name)
475
+
474
476
  issues = repo.get_issues(state=state)
477
+
475
478
  # Filter out pull requests after fetching issues
476
- logger.info(f"Issues: {issues}")
477
- filtered_issues = [issue for issue in issues if not issue.pull_request]
479
+ total_issues = 0
480
+ all_issues = []
481
+ for issue in issues:
482
+ if not issue.pull_request:
483
+ all_issues.append(issue)
484
+ total_issues += 1
485
+
486
+ # Calculate pagination metadata
487
+ total_pages = (total_issues + per_page - 1) // per_page
488
+
489
+ # Validate page number
490
+ if page < 1:
491
+ page = 1
492
+ elif page > total_pages and total_pages > 0:
493
+ page = total_pages
494
+
495
+ # Get the specified page of results
478
496
  issue_list = []
479
- for issue in filtered_issues[:limit]:
480
- issue_info = {
481
- "number": issue.number,
482
- "title": issue.title,
483
- "user": issue.user.login,
484
- "created_at": issue.created_at.isoformat(),
485
- "state": issue.state,
486
- "url": issue.html_url,
487
- }
488
- issue_list.append(issue_info)
489
- return json.dumps(issue_list, indent=2)
497
+ page_start = (page - 1) * per_page
498
+ page_end = page_start + per_page
499
+
500
+ for i in range(page_start, min(page_end, total_issues)):
501
+ if i < len(all_issues):
502
+ issue = all_issues[i]
503
+ issue_info = {
504
+ "number": issue.number,
505
+ "title": issue.title,
506
+ "user": issue.user.login,
507
+ "created_at": issue.created_at.isoformat(),
508
+ "state": issue.state,
509
+ "url": issue.html_url,
510
+ }
511
+ issue_list.append(issue_info)
512
+
513
+ meta = {
514
+ "current_page": page,
515
+ "per_page": per_page,
516
+ "total_items": total_issues,
517
+ "total_pages": total_pages
518
+ }
519
+
520
+ response = {
521
+ "data": issue_list,
522
+ "meta": meta
523
+ }
524
+
525
+ return json.dumps(response, indent=2)
490
526
  except GithubException as e:
491
527
  logger.error(f"Error listing issues: {e}")
492
528
  return json.dumps({"error": str(e)})
@@ -1,5 +1,6 @@
1
1
  import json
2
2
  from hashlib import md5
3
+ from os import getenv
3
4
  from typing import Any, Dict, List, Optional
4
5
 
5
6
  try:
@@ -74,9 +75,12 @@ class LanceDb(VectorDb):
74
75
  # Distance metric
75
76
  self.distance: Distance = distance
76
77
 
78
+ # Remote LanceDB connection details
79
+ self.api_key: Optional[str] = api_key
80
+
77
81
  # LanceDB connection details
78
82
  self.uri: lancedb.URI = uri
79
- self.connection: lancedb.LanceDBConnection = connection or lancedb.connect(uri=self.uri, api_key=api_key)
83
+ self.connection: lancedb.DBConnection = connection or lancedb.connect(uri=self.uri, api_key=api_key)
80
84
  self.table: Optional[lancedb.db.LanceTable] = table
81
85
 
82
86
  self.async_connection: Optional[lancedb.AsyncConnection] = async_connection
@@ -168,7 +172,11 @@ class LanceDb(VectorDb):
168
172
  schema = self._base_schema()
169
173
 
170
174
  log_info(f"Creating table: {self.table_name}")
171
- tbl = self.connection.create_table(self.table_name, schema=schema, mode="overwrite", exist_ok=True) # type: ignore
175
+ if self.api_key or getenv("LANCEDB_API_KEY"):
176
+ log_info("API key found, creating table in remote LanceDB")
177
+ tbl = self.connection.create_table(name=self.table_name, schema=schema, mode="overwrite") # type: ignore
178
+ else:
179
+ tbl = self.connection.create_table(name=self.table_name, schema=schema, mode="overwrite", exist_ok=True) # type: ignore
172
180
  return tbl # type: ignore
173
181
 
174
182
  def doc_exists(self, document: Document) -> bool:
@@ -766,6 +766,9 @@ class PgVector(VectorDb):
766
766
  )
767
767
  )
768
768
 
769
+ if self.reranker:
770
+ search_results = self.reranker.rerank(query=query, documents=search_results)
771
+
769
772
  log_info(f"Found {len(search_results)} documents")
770
773
  return search_results
771
774
  except Exception as e:
@@ -2,7 +2,7 @@ import json
2
2
  import uuid
3
3
  from hashlib import md5
4
4
  from os import getenv
5
- from typing import Any, Dict, List, Optional
5
+ from typing import Any, Dict, List, Optional, Tuple
6
6
 
7
7
  try:
8
8
  from warnings import filterwarnings
@@ -73,6 +73,13 @@ class Weaviate(VectorDb):
73
73
  self.reranker: Optional[Reranker] = reranker
74
74
  self.hybrid_search_alpha = hybrid_search_alpha
75
75
 
76
+ @staticmethod
77
+ def _get_doc_uuid(document: Document) -> Tuple[uuid.UUID, str]:
78
+ cleaned_content = document.content.replace("\x00", "\ufffd")
79
+ content_hash = md5(cleaned_content.encode()).hexdigest()
80
+ doc_uuid = uuid.UUID(hex=content_hash[:32])
81
+ return doc_uuid, cleaned_content
82
+
76
83
  def get_client(self) -> weaviate.WeaviateClient:
77
84
  """Initialize and return a Weaviate client instance.
78
85
 
@@ -118,7 +125,7 @@ class Weaviate(VectorDb):
118
125
  await self.async_client.connect() # type: ignore
119
126
 
120
127
  if not await self.async_client.is_ready(): # type: ignore
121
- raise Exception("Weaviate async client is not ready")
128
+ raise ConnectionError("Weaviate async client is not ready")
122
129
 
123
130
  return self.async_client # type: ignore
124
131
 
@@ -155,6 +162,54 @@ class Weaviate(VectorDb):
155
162
  finally:
156
163
  await client.close()
157
164
 
165
+ def doc_content_changed(self, document: Document, check_existing: Optional[bool] = True) -> Optional[bool]:
166
+ """
167
+ Check if the content of the document has changed by comparing its UUID.
168
+
169
+ Args:
170
+ document (Document): Document to check
171
+
172
+ Returns:
173
+ bool: True if the document content has changed, False otherwise. None on wrong input.
174
+ check_existing (bool): If True, check if the document exists before checking if the content changed.
175
+ """
176
+ if not document or not document.content:
177
+ logger.warning("Invalid document: Missing content.")
178
+ return None
179
+
180
+ if check_existing and document.name and not self.name_exists(document.name):
181
+ logger.warning(f"A document by this name does not exist: {document.name}")
182
+ return None
183
+
184
+ doc_uuid, _ = self._get_doc_uuid(document)
185
+
186
+ collection = self.get_client().collections.get(self.collection)
187
+ existing_doc = collection.query.fetch_object_by_id(doc_uuid)
188
+
189
+ if not existing_doc:
190
+ return True
191
+ else:
192
+ return False
193
+
194
+ def doc_delete(self, name: str) -> None:
195
+ """
196
+ Delete all documents from Weaviate with a specific 'name' property.
197
+
198
+ Args:
199
+ name (str): Document name to delete.
200
+ """
201
+ collection = self.get_client().collections.get(self.collection)
202
+ filter_expr = Filter.by_property("name").equal(name)
203
+
204
+ result = collection.data.delete_many(where=filter_expr)
205
+
206
+ log_debug(f"Deleted document by name: '{name}' - {result.successful} documents deleted.")
207
+ if result.failed > 0:
208
+ logger.warning(
209
+ f"Failed to delete (some chunks of) document with name: '{name}' - "
210
+ f"Failed {result.failed} out of {result.matches} times. {result.successful} successful deletions."
211
+ )
212
+
158
213
  def doc_exists(self, document: Document) -> bool:
159
214
  """
160
215
  Validate if the document exists using consistent UUID generation.
@@ -169,9 +224,7 @@ class Weaviate(VectorDb):
169
224
  logger.warning("Invalid document: Missing content.")
170
225
  return False # Early exit for invalid input
171
226
 
172
- cleaned_content = document.content.replace("\x00", "\ufffd")
173
- content_hash = md5(cleaned_content.encode()).hexdigest()
174
- doc_uuid = uuid.UUID(hex=content_hash[:32])
227
+ doc_uuid, _ = self._get_doc_uuid(document)
175
228
 
176
229
  collection = self.get_client().collections.get(self.collection)
177
230
  return collection.data.exists(doc_uuid)
@@ -190,9 +243,7 @@ class Weaviate(VectorDb):
190
243
  logger.warning("Invalid document: Missing content.")
191
244
  return False # Early exit for invalid input
192
245
 
193
- cleaned_content = document.content.replace("\x00", "\ufffd")
194
- content_hash = md5(cleaned_content.encode()).hexdigest()
195
- doc_uuid = uuid.UUID(hex=content_hash[:32])
246
+ doc_uuid, _ = self._get_doc_uuid(document)
196
247
 
197
248
  client = await self.get_async_client()
198
249
  try:
@@ -256,9 +307,7 @@ class Weaviate(VectorDb):
256
307
  logger.error(f"Document embedding is None: {document.name}")
257
308
  continue
258
309
 
259
- cleaned_content = document.content.replace("\x00", "\ufffd")
260
- content_hash = md5(cleaned_content.encode()).hexdigest()
261
- doc_uuid = uuid.UUID(hex=content_hash[:32])
310
+ doc_uuid, cleaned_content = self._get_doc_uuid(document)
262
311
 
263
312
  # Merge filters with metadata
264
313
  meta_data = document.meta_data or {}
@@ -305,9 +354,7 @@ class Weaviate(VectorDb):
305
354
  continue
306
355
 
307
356
  # Clean content and generate UUID
308
- cleaned_content = document.content.replace("\x00", "\ufffd")
309
- content_hash = md5(cleaned_content.encode()).hexdigest()
310
- doc_uuid = uuid.UUID(hex=content_hash[:32])
357
+ doc_uuid, cleaned_content = self._get_doc_uuid(document)
311
358
 
312
359
  # Serialize meta_data to JSON string
313
360
  meta_data_str = json.dumps(document.meta_data) if document.meta_data else None
@@ -338,7 +385,28 @@ class Weaviate(VectorDb):
338
385
  filters (Optional[Dict[str, Any]]): Filters to apply while upserting
339
386
  """
340
387
  log_debug(f"Upserting {len(documents)} documents into Weaviate.")
341
- self.insert(documents)
388
+
389
+ _docs_to_insert = []
390
+ for document in documents:
391
+ assert document.name is not None, "Document name must be set for upsert operation."
392
+
393
+ if self.name_exists(document.name):
394
+ if self.doc_content_changed(document, check_existing=False):
395
+ log_debug(
396
+ f"Document already exists, but content changed. Document will be deleted and added again: {document.name}"
397
+ )
398
+
399
+ is_first_or_only_chunk = ("chunk" in document.meta_data and document.meta_data["chunk"] == 1) or (
400
+ "chunk" not in document.meta_data
401
+ )
402
+ if is_first_or_only_chunk:
403
+ self.doc_delete(document.name)
404
+ _docs_to_insert.append(document)
405
+ else:
406
+ log_debug(f"Document skipped, content is unchanged: {document.name}")
407
+ else:
408
+ _docs_to_insert.append(document)
409
+ self.insert(_docs_to_insert)
342
410
 
343
411
  async def async_upsert(self, documents: List[Document], filters: Optional[Dict[str, Any]] = None) -> None:
344
412
  """
@@ -365,9 +433,7 @@ class Weaviate(VectorDb):
365
433
  logger.error(f"Document embedding is None: {document.name}")
366
434
  continue
367
435
 
368
- cleaned_content = document.content.replace("\x00", "\ufffd")
369
- content_hash = md5(cleaned_content.encode()).hexdigest()
370
- doc_uuid = uuid.UUID(hex=content_hash[:32])
436
+ doc_uuid, cleaned_content = self._get_doc_uuid(document)
371
437
 
372
438
  # Serialize meta_data to JSON string
373
439
  meta_data_str = json.dumps(document.meta_data) if document.meta_data else None
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: agno
3
- Version: 1.7.8
3
+ Version: 1.7.10
4
4
  Summary: Agno: a lightweight library for building Multi-Agent Systems
5
5
  Author-email: Ashpreet Bedi <ashpreet@agno.com>
6
6
  License: Copyright (c) Agno, Inc.
@@ -400,6 +400,7 @@ License-File: LICENSE
400
400
  Requires-Dist: docstring-parser
401
401
  Requires-Dist: gitpython
402
402
  Requires-Dist: httpx
403
+ Requires-Dist: packaging
403
404
  Requires-Dist: pydantic-settings
404
405
  Requires-Dist: pydantic
405
406
  Requires-Dist: python-dotenv
@@ -5,7 +5,7 @@ agno/exceptions.py,sha256=HWuuNFS5J0l1RYJsdUrSx51M22aFEoh9ltoeonXBoBw,2891
5
5
  agno/media.py,sha256=lXJuylmhuIEWThKZkQ9pUZPp8Kms7EdT4N_U4YN9I00,12656
6
6
  agno/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
7
  agno/agent/__init__.py,sha256=Ai6GVyw-0rkA2eYAfoEQIvbi_mrWQUxuPFaFbSDJYCQ,1306
8
- agno/agent/agent.py,sha256=pvXeME41lUvYBALizxWnawLcIhBwKG33fYJbw-MNY8s,381013
8
+ agno/agent/agent.py,sha256=9qp01o6lX72-fflCY74J7XIeFpz4jm7mnvpvF6m7n_0,381409
9
9
  agno/agent/metrics.py,sha256=Lf7JYgPPdqRCyPfCDVUjnmUZ1SkWXrJClL80aW2ffEw,4379
10
10
  agno/api/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
11
11
  agno/api/agent.py,sha256=J-Y4HI-J0Bu6r9gxRYCM3U7SnVBGwLIouDy806KSIIw,2821
@@ -92,7 +92,7 @@ agno/document/reader/docx_reader.py,sha256=fNSZNzBlROQow7nagouEfN8E4KgVp3hTcSj3d
92
92
  agno/document/reader/firecrawl_reader.py,sha256=4CFACPA22t0gI1YgYL1mZLZQN_T6LrLj8V9mAmU2In8,5748
93
93
  agno/document/reader/json_reader.py,sha256=TrE14YAPkEd3q1e1dFf1ZX-GJPlXadsbeCzNh6EGpgg,2189
94
94
  agno/document/reader/markdown_reader.py,sha256=SX0Zydj_0AmBr8Grk8z9jDiNmebU7rnPg2aAJoFEHAk,3546
95
- agno/document/reader/pdf_reader.py,sha256=UQpKO41JtmA1lZaVe4gyZERsxglcZWK2qlnpYNp1_fI,11253
95
+ agno/document/reader/pdf_reader.py,sha256=CGh2aYSJb7dAu-blSDz8ZkjiyU3U5-F_Foag7Eebnko,19584
96
96
  agno/document/reader/text_reader.py,sha256=jtCuhWHkC5QNPmRF3DyXcXVKHM1jnqqxXVxHKZIpkfQ,3315
97
97
  agno/document/reader/url_reader.py,sha256=dQmuO1NkJg9A9m2YeiVMuR7GikLl_K1FudE0UO62Um4,1988
98
98
  agno/document/reader/website_reader.py,sha256=Ei-FIsdw0FWhGOBVge24JcNMfiAHL8nUA1tawrfBZPM,17307
@@ -138,7 +138,7 @@ agno/infra/db_app.py,sha256=W_XeDK0FhIkc--kfB0Jd34MJmgOfFQeT9M2y5840vlA,1794
138
138
  agno/infra/resource.py,sha256=yPRZI4uprQtaugLD6x8_WAmFTPNPy5rlLvT1-bNIa5c,8491
139
139
  agno/infra/resources.py,sha256=FKmDaDFup4cDiSA_y8eZRxpXEAmlEPxWzXKcY8xqF5w,1681
140
140
  agno/knowledge/__init__.py,sha256=H1opQqY6oTPYJiLAiaIHtPuaVCry5GAhPoyT1ojdJwg,85
141
- agno/knowledge/agent.py,sha256=KnWZFwKS7ihqZcf9Psx1kUMkCSSQslxQ-xfeHopKdQ4,29730
141
+ agno/knowledge/agent.py,sha256=udSFrUyHAwUA4RWT6iLR_hzYKh4-TnbKkQg_4xfksJk,29773
142
142
  agno/knowledge/arxiv.py,sha256=0q1teC40wmau50ZTmdbvewCNxgxF_92QtfhJ87Evagk,1140
143
143
  agno/knowledge/combined.py,sha256=6aHPfbjdKSfkE0D-vt8CocU3WOVAQaPWhuNjKBVLrv4,1262
144
144
  agno/knowledge/csv.py,sha256=uUusY3Gf2HrYDtAOxoXsWfw11z95NEE9x71YNDqoK6g,5732
@@ -151,9 +151,9 @@ agno/knowledge/langchain.py,sha256=nHk4ohORSRwEY00DcdgXSwMewcv-caKMG24wghnUXaM,2
151
151
  agno/knowledge/light_rag.py,sha256=8grl8nRirgqUyaoExNNJ1MwEiqqyRXdtM7hQw7w5z3s,11516
152
152
  agno/knowledge/llamaindex.py,sha256=Lclu1rA0XMf4Y1xuupwUrtPvTi75gj9XvJ-so6oWxfw,2332
153
153
  agno/knowledge/markdown.py,sha256=4DS3nb25ZP-Gld-H0TMijUIsqq2D8E2BVgfZzXKI0A8,5639
154
- agno/knowledge/pdf.py,sha256=O8hrW_rmQQgP7w0GlU1uSCR-crLRmHF8E3AZmNRFTuk,5561
154
+ agno/knowledge/pdf.py,sha256=ioV5szNDIVR1kzG3gZPwrM9FJprLSY0YzSP3VC9xpHo,6366
155
155
  agno/knowledge/pdf_bytes.py,sha256=VmLuWO-UCJQ9CCXuWfYB0nG3W90_69g1xCoFxiKbaEM,1399
156
- agno/knowledge/pdf_url.py,sha256=XMNKi1w_clr1SFl1-Pb1OJV2xegH_sLHcZcayAI83B8,5689
156
+ agno/knowledge/pdf_url.py,sha256=gXskDyRbWqRK1mtBH6OfujlCy7OTQLOZY1LlqGfh84g,6119
157
157
  agno/knowledge/text.py,sha256=SHVnvEF6Qa2yksuXY0tpdEvP8Y4cbFneKzyUi1V3tNw,5620
158
158
  agno/knowledge/url.py,sha256=OTy-4BFP32Hg8N3IRvb-7LaoAlKAW61iewhkAASDL84,1488
159
159
  agno/knowledge/website.py,sha256=W_vnFKAYteuNwnoNVnESEw55q-o3C9JHpfDyDxcnZNA,6556
@@ -252,7 +252,7 @@ agno/models/ollama/tools.py,sha256=PLYT9VSCGSwKAHNDEgOtyKg0HuUlYUxzGzvhoK19Vr0,1
252
252
  agno/models/openai/__init__.py,sha256=OssVgQRpsriU6aJZ3lIp_jFuqvX6y78L4Fd3uTlmI3E,225
253
253
  agno/models/openai/chat.py,sha256=PQ8GfVNZxM17rvLtY5UqeOPo4faGmX-1H_hx8BSLphI,30033
254
254
  agno/models/openai/like.py,sha256=wmw9PfAVqluBs4MMY73dgjelKn1yl5JDKyCRvaNFjFw,745
255
- agno/models/openai/responses.py,sha256=dH-wyL7KMLg12GcBfSK6-9e7iX_VB4tR73-d9orR9d0,36448
255
+ agno/models/openai/responses.py,sha256=CxNS39S2O6eiXCY540ls2pJDu5m8XmYWvT_jvyEhDTQ,37951
256
256
  agno/models/openrouter/__init__.py,sha256=ZpZhNyy_EGSXp58uC9e2iyjnxBctql7GaY8rUG-599I,90
257
257
  agno/models/openrouter/openrouter.py,sha256=Ng-_ztpq_lghGI3tM94nsC8minKhiZ6d265c6IYXtg4,869
258
258
  agno/models/perplexity/__init__.py,sha256=JNmOElDLwcZ9_Lk5owkEdgwmAhaH3YJ-VJqOI8rgp5c,90
@@ -291,8 +291,8 @@ agno/reranker/sentence_transformer.py,sha256=Pqv38uZ5MhwYPQkei8ixs3jANoBOIKqVwI3
291
291
  agno/run/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
292
292
  agno/run/base.py,sha256=cueGFKz_TOCNO9aMe8IBFwohax4z6IgL0e3HAK7XqRQ,7546
293
293
  agno/run/messages.py,sha256=rAC4CLW-xBA6qFS1BOvcjJ9j_qYf0a7sX1mcdY04zMU,1126
294
- agno/run/response.py,sha256=4Y1VPfRVIQdhacqW_N41RaM_y0RoDvJ-D32cACv2Tvo,15348
295
- agno/run/team.py,sha256=3VSdOrlGhRu_zJ9pE623eSqb0MDZiYSZ43GBAl0juQw,16075
294
+ agno/run/response.py,sha256=CafLgeLszVbdre7jm1A5TNG4WMpN0OiPMPk6ioeN-cg,15766
295
+ agno/run/team.py,sha256=WT5HbqVA1fvKPQg8gr2tpdeaNq2aM3WoWpas93P07ck,16504
296
296
  agno/run/workflow.py,sha256=2eBvNXbGini3-cWwl3dOf-o-VgGq51ZEl4GCbQFblaw,1581
297
297
  agno/run/v2/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
298
298
  agno/run/v2/workflow.py,sha256=FiZY5eWl6oEJCEfBUIX2q1WDHLI8mqVmaWWwKBA1PL8,18903
@@ -328,14 +328,14 @@ agno/storage/workflow/mongodb.py,sha256=x-0Jl2WovupTfwuVNOSndE9-7V4U7BBIjejtJ1Wa
328
328
  agno/storage/workflow/postgres.py,sha256=66bvx6eT7PtFvd4EtTCfI2smynAyvpjvAPYtPo-PCNg,91
329
329
  agno/storage/workflow/sqlite.py,sha256=PLqEA1YC8AtIklINr6wy8lzK6KABEqvlJW-nz5KacWM,85
330
330
  agno/team/__init__.py,sha256=OSkwJhm4uSoOwpHLeDdcH4q2R_BmfS-7a9_aPxB-Skw,967
331
- agno/team/team.py,sha256=XmA2r9LAqgYVGINIj0hanfJH-iFtfY4Bn4pRl7TK82s,376693
331
+ agno/team/team.py,sha256=bWK4aaNyipoN0BbqaKkqWWocH8yflXQFLJo3eESTvo8,377734
332
332
  agno/tools/__init__.py,sha256=jNll2sELhPPbqm5nPeT4_uyzRO2_KRTW-8Or60kioS0,210
333
333
  agno/tools/agentql.py,sha256=w6FlCfhuS0cc2BHa9K6dZjqO1ycA66fSZbR_nvXiVSo,3813
334
334
  agno/tools/airflow.py,sha256=2ZCwx65w_tSXm4xEzZQR_teOiXJlnEgIqU9AgQTQemI,2493
335
335
  agno/tools/api.py,sha256=gd86Fvk_3kHcaNWepTQ_Bmzs9RwajwiwcsEHJKdngB8,4238
336
336
  agno/tools/apify.py,sha256=WWs9NWiiyMW5jKRRYLDHBoPPX4ScGMMt87VCXHowTy0,13555
337
337
  agno/tools/arxiv.py,sha256=xnfbzOBDuHRj5SHImlz_q-pdRT9o_Vnna-VtDt1JuDU,5202
338
- agno/tools/aws_lambda.py,sha256=GL4McjdbzveteVzeYHKHcwTCLA_B6DJmK4J5tLSNfFk,1459
338
+ agno/tools/aws_lambda.py,sha256=CbVQpoLudpmle1KkgecuVDqE_JdapBBf26OdIj8fUsY,1831
339
339
  agno/tools/aws_ses.py,sha256=fl5NTRWcljzxp4WxTg2gIAjLMNcuEWs_vnjeRtEKRHY,2090
340
340
  agno/tools/baidusearch.py,sha256=HBdhLz1HUtKXJjIQru21jKiSonG9jEjNB_W6FPjklew,2883
341
341
  agno/tools/bitbucket.py,sha256=CLhYdB_HTriy44VHtsRtqCY-BhnHpZMBHQ9vgL4vpWg,11207
@@ -368,7 +368,7 @@ agno/tools/financial_datasets.py,sha256=rvGSjz7gRdouB0PRJGngRSlO0wOwQE7cnrI8YaNI
368
368
  agno/tools/firecrawl.py,sha256=0jeJlupLXCJTf2tDckEXlCV6EpLeDEO_G27-w4EWDL0,4985
369
369
  agno/tools/function.py,sha256=VWgQAjIqxJl7MJrrMmMr7tNNvz3L3m7jXaUoIqxdlKY,36119
370
370
  agno/tools/giphy.py,sha256=HKzTHEmiUdrkJsguG0qkpnsmXPikbrQyCoAHvAzI6XU,2422
371
- agno/tools/github.py,sha256=5G3UAocmrrizElrIA8i9_YH0AcGZ63flW9nF3QU3y9A,72026
371
+ agno/tools/github.py,sha256=GMKuULX_9bzJY3PVocJsUVJITMR7g0hsjxY4gquL7wg,73271
372
372
  agno/tools/gmail.py,sha256=p7zKW2NLuRIYsZZ6ru4WMdwMPQpoBt4JbuCwfMI3YTs,28845
373
373
  agno/tools/google_bigquery.py,sha256=i93QJLJCH39sZDMPWYmie_A_ElBxVC6D36TVDcSaplo,4423
374
374
  agno/tools/google_maps.py,sha256=iZa6FgjNID_G6T96ZXUOe5JnXIWn0c3AgzFU7O6S2WE,10123
@@ -511,14 +511,14 @@ agno/vectordb/clickhouse/index.py,sha256=_YW-8AuEYy5kzOHi0zIzjngpQPgJOBdSrn9BfEL
511
511
  agno/vectordb/couchbase/__init__.py,sha256=dKZkcQLFN4r2_NIdXby4inzAAn4BDMlb9T2BW_i0_gQ,93
512
512
  agno/vectordb/couchbase/couchbase.py,sha256=I-nWRPAEyEoww-1FpQJLM6CyxWXWPtR9dRjpAyzLWyo,48814
513
513
  agno/vectordb/lancedb/__init__.py,sha256=tb9qvinKyWMTLjJYMwW_lhYHFvrfWTfHODtBfMj-NLE,111
514
- agno/vectordb/lancedb/lance_db.py,sha256=0zKFBJ-RNx-BBxmHfKxzeird6JrYxM2beJd5ySOqmpg,22511
514
+ agno/vectordb/lancedb/lance_db.py,sha256=PBLtn0AkAVEEYJywYKzdf5gWbQWvka6yJXeAfsJQdtI,22886
515
515
  agno/vectordb/milvus/__init__.py,sha256=I9V-Rm-rIYxWdRVIs6bKI-6JSJsyOd1-vvasvVpYHuE,127
516
516
  agno/vectordb/milvus/milvus.py,sha256=SwLPmgP80dPWFeN9ehj3D1yseyVXbHJDIBNCu-NPs9s,30002
517
517
  agno/vectordb/mongodb/__init__.py,sha256=yYwaWdxZRnFTd87Hfgs8_DO4QxcJxy1iL3__bnxP71I,73
518
518
  agno/vectordb/mongodb/mongodb.py,sha256=yG_bs7iJrXatrmI2BMLALxkVT1qVx4BYoiUcXWXlSsg,48537
519
519
  agno/vectordb/pgvector/__init__.py,sha256=Lui0HBzoHPIsKh5QuiT0eyTvYW88nQPfd_723jjHFCk,288
520
520
  agno/vectordb/pgvector/index.py,sha256=qfGgPP33SwZkXLfUcAC_XgQsyZIyggpGS2bfIkjjs-E,495
521
- agno/vectordb/pgvector/pgvector.py,sha256=IRtsuHknq5OyHK81QRXl_LMJsBmfbPS2cWob6jRkvrU,44181
521
+ agno/vectordb/pgvector/pgvector.py,sha256=JE52MgXSXRqbySPMzgy1DcvJxZhabiw1ufFHf6QImWA,44305
522
522
  agno/vectordb/pineconedb/__init__.py,sha256=D7iThXtUCxNO0Nyjunv5Z91Jc1vHG1pgAFXthqD1I_w,92
523
523
  agno/vectordb/pineconedb/pineconedb.py,sha256=NaYmkskY1eLAWIM-HSBa-DVHEMQ6ZuZDqqUmmHZhlro,18399
524
524
  agno/vectordb/qdrant/__init__.py,sha256=x1ReQt79f9aI_T4JUWb36KNFnvdd-kVwZ1sLsU4sW7Q,76
@@ -532,7 +532,7 @@ agno/vectordb/upstashdb/__init__.py,sha256=set3Sx1F3ZCw0--0AeC036EAS0cC1xKsvQUK5
532
532
  agno/vectordb/upstashdb/upstashdb.py,sha256=PNV_Wt0LTszwt-jzn2E87y_6aulCr8BaeA2YlJrkTtQ,13088
533
533
  agno/vectordb/weaviate/__init__.py,sha256=FIoFJgqSmGuFgpvmsg8EjAn8FDAhuqAXed7fjaW4exY,182
534
534
  agno/vectordb/weaviate/index.py,sha256=y4XYPRZFksMfrrF85B4hn5AtmXM4SH--4CyLo27EHgM,253
535
- agno/vectordb/weaviate/weaviate.py,sha256=yO46pOOXblZUb75XyLV3pjw-2zvXU-Rzs-yjHwzuktM,30683
535
+ agno/vectordb/weaviate/weaviate.py,sha256=ZOHCHIuenpBcSx--jIA8l8nvUzZ-DzER2ISSfdGHtSc,33253
536
536
  agno/workflow/__init__.py,sha256=jPTHCWpHZbfR34-KqIX-SLA7tO7VdZqgZ8C2I0Nhbps,407
537
537
  agno/workflow/workflow.py,sha256=iHWjowKjw_gKE-JTigHseY9DDL1rpqQrP6ihBUO9d-A,35227
538
538
  agno/workflow/v2/__init__.py,sha256=tACFZfj7OqbmjOtyZ8nllYnsal3w8xN2SHrIXXmA6Ys,566
@@ -550,9 +550,9 @@ agno/workspace/enums.py,sha256=MxF1CUMXBaZMTKLEfiR-7kEhTki2Gfz6W7u49RdYYaE,123
550
550
  agno/workspace/helpers.py,sha256=Mp-VlRsPVhW10CfDWYVhc9ANLk9RjNurDfCgXmycZCg,2066
551
551
  agno/workspace/operator.py,sha256=CNLwVR45eE5dSRjto2o0c9NgCi2xD-JZR5uLt9kfIt8,30758
552
552
  agno/workspace/settings.py,sha256=bcyHHN7lH1LPSMt4i_20XpTjZLoNXdzwyW-G9nHYV40,5703
553
- agno-1.7.8.dist-info/licenses/LICENSE,sha256=m2rfTWFUfIwCaQqgT2WeBjuKzMKEJRwnaiofg9n8MsQ,16751
554
- agno-1.7.8.dist-info/METADATA,sha256=Y5HQs_UEHkulA08VeiMi7w6cTig4B-C2DykiMQETwb4,44277
555
- agno-1.7.8.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
556
- agno-1.7.8.dist-info/entry_points.txt,sha256=Be-iPnPVabMohESsuUdV5w6IAYEIlpc2emJZbyNnfGI,88
557
- agno-1.7.8.dist-info/top_level.txt,sha256=MKyeuVesTyOKIXUhc-d_tPa2Hrh0oTA4LM0izowpx70,5
558
- agno-1.7.8.dist-info/RECORD,,
553
+ agno-1.7.10.dist-info/licenses/LICENSE,sha256=m2rfTWFUfIwCaQqgT2WeBjuKzMKEJRwnaiofg9n8MsQ,16751
554
+ agno-1.7.10.dist-info/METADATA,sha256=39SoZig58R20Lust76guW14N2t8HpMHYRa-zAgXLVIU,44303
555
+ agno-1.7.10.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
556
+ agno-1.7.10.dist-info/entry_points.txt,sha256=Be-iPnPVabMohESsuUdV5w6IAYEIlpc2emJZbyNnfGI,88
557
+ agno-1.7.10.dist-info/top_level.txt,sha256=MKyeuVesTyOKIXUhc-d_tPa2Hrh0oTA4LM0izowpx70,5
558
+ agno-1.7.10.dist-info/RECORD,,
File without changes