agno 2.0.1__py3-none-any.whl → 2.3.0__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 +6015 -2823
- agno/api/api.py +2 -0
- agno/api/os.py +1 -1
- agno/culture/__init__.py +3 -0
- agno/culture/manager.py +956 -0
- agno/db/async_postgres/__init__.py +3 -0
- agno/db/base.py +385 -6
- agno/db/dynamo/dynamo.py +388 -81
- agno/db/dynamo/schemas.py +47 -10
- agno/db/dynamo/utils.py +63 -4
- agno/db/firestore/firestore.py +435 -64
- agno/db/firestore/schemas.py +11 -0
- agno/db/firestore/utils.py +102 -4
- agno/db/gcs_json/gcs_json_db.py +384 -42
- agno/db/gcs_json/utils.py +60 -26
- agno/db/in_memory/in_memory_db.py +351 -66
- agno/db/in_memory/utils.py +60 -2
- agno/db/json/json_db.py +339 -48
- agno/db/json/utils.py +60 -26
- agno/db/migrations/manager.py +199 -0
- agno/db/migrations/v1_to_v2.py +510 -37
- agno/db/migrations/versions/__init__.py +0 -0
- agno/db/migrations/versions/v2_3_0.py +938 -0
- agno/db/mongo/__init__.py +15 -1
- agno/db/mongo/async_mongo.py +2036 -0
- agno/db/mongo/mongo.py +653 -76
- agno/db/mongo/schemas.py +13 -0
- agno/db/mongo/utils.py +80 -8
- agno/db/mysql/mysql.py +687 -25
- agno/db/mysql/schemas.py +61 -37
- agno/db/mysql/utils.py +60 -2
- agno/db/postgres/__init__.py +2 -1
- agno/db/postgres/async_postgres.py +2001 -0
- agno/db/postgres/postgres.py +676 -57
- agno/db/postgres/schemas.py +43 -18
- agno/db/postgres/utils.py +164 -2
- agno/db/redis/redis.py +344 -38
- agno/db/redis/schemas.py +18 -0
- agno/db/redis/utils.py +60 -2
- agno/db/schemas/__init__.py +2 -1
- agno/db/schemas/culture.py +120 -0
- agno/db/schemas/memory.py +13 -0
- agno/db/singlestore/schemas.py +26 -1
- agno/db/singlestore/singlestore.py +687 -53
- agno/db/singlestore/utils.py +60 -2
- agno/db/sqlite/__init__.py +2 -1
- agno/db/sqlite/async_sqlite.py +2371 -0
- agno/db/sqlite/schemas.py +24 -0
- agno/db/sqlite/sqlite.py +774 -85
- agno/db/sqlite/utils.py +168 -5
- agno/db/surrealdb/__init__.py +3 -0
- agno/db/surrealdb/metrics.py +292 -0
- agno/db/surrealdb/models.py +309 -0
- agno/db/surrealdb/queries.py +71 -0
- agno/db/surrealdb/surrealdb.py +1361 -0
- agno/db/surrealdb/utils.py +147 -0
- agno/db/utils.py +50 -22
- agno/eval/accuracy.py +50 -43
- agno/eval/performance.py +6 -3
- agno/eval/reliability.py +6 -3
- agno/eval/utils.py +33 -16
- agno/exceptions.py +68 -1
- agno/filters.py +354 -0
- agno/guardrails/__init__.py +6 -0
- agno/guardrails/base.py +19 -0
- agno/guardrails/openai.py +144 -0
- agno/guardrails/pii.py +94 -0
- agno/guardrails/prompt_injection.py +52 -0
- agno/integrations/discord/client.py +1 -0
- agno/knowledge/chunking/agentic.py +13 -10
- agno/knowledge/chunking/fixed.py +1 -1
- agno/knowledge/chunking/semantic.py +40 -8
- agno/knowledge/chunking/strategy.py +59 -15
- agno/knowledge/embedder/aws_bedrock.py +9 -4
- agno/knowledge/embedder/azure_openai.py +54 -0
- agno/knowledge/embedder/base.py +2 -0
- agno/knowledge/embedder/cohere.py +184 -5
- agno/knowledge/embedder/fastembed.py +1 -1
- agno/knowledge/embedder/google.py +79 -1
- agno/knowledge/embedder/huggingface.py +9 -4
- agno/knowledge/embedder/jina.py +63 -0
- agno/knowledge/embedder/mistral.py +78 -11
- agno/knowledge/embedder/nebius.py +1 -1
- agno/knowledge/embedder/ollama.py +13 -0
- agno/knowledge/embedder/openai.py +37 -65
- agno/knowledge/embedder/sentence_transformer.py +8 -4
- agno/knowledge/embedder/vllm.py +262 -0
- agno/knowledge/embedder/voyageai.py +69 -16
- agno/knowledge/knowledge.py +594 -186
- agno/knowledge/reader/base.py +9 -2
- agno/knowledge/reader/csv_reader.py +8 -10
- agno/knowledge/reader/docx_reader.py +5 -6
- agno/knowledge/reader/field_labeled_csv_reader.py +290 -0
- agno/knowledge/reader/json_reader.py +6 -5
- agno/knowledge/reader/markdown_reader.py +13 -13
- agno/knowledge/reader/pdf_reader.py +43 -68
- agno/knowledge/reader/pptx_reader.py +101 -0
- agno/knowledge/reader/reader_factory.py +51 -6
- agno/knowledge/reader/s3_reader.py +3 -15
- agno/knowledge/reader/tavily_reader.py +194 -0
- agno/knowledge/reader/text_reader.py +13 -13
- agno/knowledge/reader/web_search_reader.py +2 -43
- agno/knowledge/reader/website_reader.py +43 -25
- agno/knowledge/reranker/__init__.py +2 -8
- agno/knowledge/types.py +9 -0
- agno/knowledge/utils.py +20 -0
- agno/media.py +72 -0
- agno/memory/manager.py +336 -82
- agno/models/aimlapi/aimlapi.py +2 -2
- agno/models/anthropic/claude.py +183 -37
- agno/models/aws/bedrock.py +52 -112
- agno/models/aws/claude.py +33 -1
- agno/models/azure/ai_foundry.py +33 -15
- agno/models/azure/openai_chat.py +25 -8
- agno/models/base.py +999 -519
- agno/models/cerebras/cerebras.py +19 -13
- agno/models/cerebras/cerebras_openai.py +8 -5
- agno/models/cohere/chat.py +27 -1
- agno/models/cometapi/__init__.py +5 -0
- agno/models/cometapi/cometapi.py +57 -0
- agno/models/dashscope/dashscope.py +1 -0
- agno/models/deepinfra/deepinfra.py +2 -2
- agno/models/deepseek/deepseek.py +2 -2
- agno/models/fireworks/fireworks.py +2 -2
- agno/models/google/gemini.py +103 -31
- agno/models/groq/groq.py +28 -11
- agno/models/huggingface/huggingface.py +2 -1
- agno/models/internlm/internlm.py +2 -2
- agno/models/langdb/langdb.py +4 -4
- agno/models/litellm/chat.py +18 -1
- agno/models/litellm/litellm_openai.py +2 -2
- agno/models/llama_cpp/__init__.py +5 -0
- agno/models/llama_cpp/llama_cpp.py +22 -0
- agno/models/message.py +139 -0
- agno/models/meta/llama.py +27 -10
- agno/models/meta/llama_openai.py +5 -17
- agno/models/nebius/nebius.py +6 -6
- agno/models/nexus/__init__.py +3 -0
- agno/models/nexus/nexus.py +22 -0
- agno/models/nvidia/nvidia.py +2 -2
- agno/models/ollama/chat.py +59 -5
- agno/models/openai/chat.py +69 -29
- agno/models/openai/responses.py +103 -106
- agno/models/openrouter/openrouter.py +41 -3
- agno/models/perplexity/perplexity.py +4 -5
- agno/models/portkey/portkey.py +3 -3
- agno/models/requesty/__init__.py +5 -0
- agno/models/requesty/requesty.py +52 -0
- agno/models/response.py +77 -1
- agno/models/sambanova/sambanova.py +2 -2
- agno/models/siliconflow/__init__.py +5 -0
- agno/models/siliconflow/siliconflow.py +25 -0
- agno/models/together/together.py +2 -2
- agno/models/utils.py +254 -8
- agno/models/vercel/v0.py +2 -2
- agno/models/vertexai/__init__.py +0 -0
- agno/models/vertexai/claude.py +96 -0
- agno/models/vllm/vllm.py +1 -0
- agno/models/xai/xai.py +3 -2
- agno/os/app.py +543 -178
- agno/os/auth.py +24 -14
- agno/os/config.py +1 -0
- agno/os/interfaces/__init__.py +1 -0
- agno/os/interfaces/a2a/__init__.py +3 -0
- agno/os/interfaces/a2a/a2a.py +42 -0
- agno/os/interfaces/a2a/router.py +250 -0
- agno/os/interfaces/a2a/utils.py +924 -0
- agno/os/interfaces/agui/agui.py +23 -7
- agno/os/interfaces/agui/router.py +27 -3
- agno/os/interfaces/agui/utils.py +242 -142
- agno/os/interfaces/base.py +6 -2
- agno/os/interfaces/slack/router.py +81 -23
- agno/os/interfaces/slack/slack.py +29 -14
- agno/os/interfaces/whatsapp/router.py +11 -4
- agno/os/interfaces/whatsapp/whatsapp.py +14 -7
- agno/os/mcp.py +111 -54
- agno/os/middleware/__init__.py +7 -0
- agno/os/middleware/jwt.py +233 -0
- agno/os/router.py +556 -139
- agno/os/routers/evals/evals.py +71 -34
- agno/os/routers/evals/schemas.py +31 -31
- agno/os/routers/evals/utils.py +6 -5
- agno/os/routers/health.py +31 -0
- agno/os/routers/home.py +52 -0
- agno/os/routers/knowledge/knowledge.py +185 -38
- agno/os/routers/knowledge/schemas.py +82 -22
- agno/os/routers/memory/memory.py +158 -53
- agno/os/routers/memory/schemas.py +20 -16
- agno/os/routers/metrics/metrics.py +20 -8
- agno/os/routers/metrics/schemas.py +16 -16
- agno/os/routers/session/session.py +499 -38
- agno/os/schema.py +308 -198
- agno/os/utils.py +401 -41
- agno/reasoning/anthropic.py +80 -0
- agno/reasoning/azure_ai_foundry.py +2 -2
- agno/reasoning/deepseek.py +2 -2
- agno/reasoning/default.py +3 -1
- agno/reasoning/gemini.py +73 -0
- agno/reasoning/groq.py +2 -2
- agno/reasoning/ollama.py +2 -2
- agno/reasoning/openai.py +7 -2
- agno/reasoning/vertexai.py +76 -0
- agno/run/__init__.py +6 -0
- agno/run/agent.py +248 -94
- agno/run/base.py +44 -5
- agno/run/team.py +238 -97
- agno/run/workflow.py +144 -33
- agno/session/agent.py +105 -89
- agno/session/summary.py +65 -25
- agno/session/team.py +176 -96
- agno/session/workflow.py +406 -40
- agno/team/team.py +3854 -1610
- agno/tools/dalle.py +2 -4
- agno/tools/decorator.py +4 -2
- agno/tools/duckduckgo.py +15 -11
- agno/tools/e2b.py +14 -7
- agno/tools/eleven_labs.py +23 -25
- agno/tools/exa.py +21 -16
- agno/tools/file.py +153 -23
- agno/tools/file_generation.py +350 -0
- agno/tools/firecrawl.py +4 -4
- agno/tools/function.py +250 -30
- agno/tools/gmail.py +238 -14
- agno/tools/google_drive.py +270 -0
- agno/tools/googlecalendar.py +36 -8
- agno/tools/googlesheets.py +20 -5
- agno/tools/jira.py +20 -0
- agno/tools/knowledge.py +3 -3
- agno/tools/mcp/__init__.py +10 -0
- agno/tools/mcp/mcp.py +331 -0
- agno/tools/mcp/multi_mcp.py +347 -0
- agno/tools/mcp/params.py +24 -0
- agno/tools/mcp_toolbox.py +284 -0
- agno/tools/mem0.py +11 -17
- agno/tools/memori.py +1 -53
- agno/tools/memory.py +419 -0
- agno/tools/models/nebius.py +5 -5
- agno/tools/models_labs.py +20 -10
- agno/tools/notion.py +204 -0
- agno/tools/parallel.py +314 -0
- agno/tools/scrapegraph.py +58 -31
- agno/tools/searxng.py +2 -2
- agno/tools/serper.py +2 -2
- agno/tools/slack.py +18 -3
- agno/tools/spider.py +2 -2
- agno/tools/tavily.py +146 -0
- agno/tools/whatsapp.py +1 -1
- agno/tools/workflow.py +278 -0
- agno/tools/yfinance.py +12 -11
- agno/utils/agent.py +820 -0
- agno/utils/audio.py +27 -0
- agno/utils/common.py +90 -1
- agno/utils/events.py +217 -2
- agno/utils/gemini.py +180 -22
- agno/utils/hooks.py +57 -0
- agno/utils/http.py +111 -0
- agno/utils/knowledge.py +12 -5
- agno/utils/log.py +1 -0
- agno/utils/mcp.py +92 -2
- agno/utils/media.py +188 -10
- agno/utils/merge_dict.py +22 -1
- agno/utils/message.py +60 -0
- agno/utils/models/claude.py +40 -11
- agno/utils/print_response/agent.py +105 -21
- agno/utils/print_response/team.py +103 -38
- agno/utils/print_response/workflow.py +251 -34
- agno/utils/reasoning.py +22 -1
- agno/utils/serialize.py +32 -0
- agno/utils/streamlit.py +16 -10
- agno/utils/string.py +41 -0
- agno/utils/team.py +98 -9
- agno/utils/tools.py +1 -1
- agno/vectordb/base.py +23 -4
- agno/vectordb/cassandra/cassandra.py +65 -9
- agno/vectordb/chroma/chromadb.py +182 -38
- agno/vectordb/clickhouse/clickhousedb.py +64 -11
- agno/vectordb/couchbase/couchbase.py +105 -10
- agno/vectordb/lancedb/lance_db.py +124 -133
- agno/vectordb/langchaindb/langchaindb.py +25 -7
- agno/vectordb/lightrag/lightrag.py +17 -3
- agno/vectordb/llamaindex/__init__.py +3 -0
- agno/vectordb/llamaindex/llamaindexdb.py +46 -7
- agno/vectordb/milvus/milvus.py +126 -9
- agno/vectordb/mongodb/__init__.py +7 -1
- agno/vectordb/mongodb/mongodb.py +112 -7
- agno/vectordb/pgvector/pgvector.py +142 -21
- agno/vectordb/pineconedb/pineconedb.py +80 -8
- agno/vectordb/qdrant/qdrant.py +125 -39
- agno/vectordb/redis/__init__.py +9 -0
- agno/vectordb/redis/redisdb.py +694 -0
- agno/vectordb/singlestore/singlestore.py +111 -25
- agno/vectordb/surrealdb/surrealdb.py +31 -5
- agno/vectordb/upstashdb/upstashdb.py +76 -8
- agno/vectordb/weaviate/weaviate.py +86 -15
- agno/workflow/__init__.py +2 -0
- agno/workflow/agent.py +299 -0
- agno/workflow/condition.py +112 -18
- agno/workflow/loop.py +69 -10
- agno/workflow/parallel.py +266 -118
- agno/workflow/router.py +110 -17
- agno/workflow/step.py +638 -129
- agno/workflow/steps.py +65 -6
- agno/workflow/types.py +61 -23
- agno/workflow/workflow.py +2085 -272
- {agno-2.0.1.dist-info → agno-2.3.0.dist-info}/METADATA +182 -58
- agno-2.3.0.dist-info/RECORD +577 -0
- agno/knowledge/reader/url_reader.py +0 -128
- agno/tools/googlesearch.py +0 -98
- agno/tools/mcp.py +0 -610
- agno/utils/models/aws_claude.py +0 -170
- agno-2.0.1.dist-info/RECORD +0 -515
- {agno-2.0.1.dist-info → agno-2.3.0.dist-info}/WHEEL +0 -0
- {agno-2.0.1.dist-info → agno-2.3.0.dist-info}/licenses/LICENSE +0 -0
- {agno-2.0.1.dist-info → agno-2.3.0.dist-info}/top_level.txt +0 -0
|
@@ -1,128 +0,0 @@
|
|
|
1
|
-
from io import BytesIO
|
|
2
|
-
from os.path import basename
|
|
3
|
-
from pathlib import Path
|
|
4
|
-
from typing import List, Optional
|
|
5
|
-
from urllib.parse import urlparse
|
|
6
|
-
|
|
7
|
-
import httpx
|
|
8
|
-
|
|
9
|
-
from agno.knowledge.chunking.fixed import FixedSizeChunking
|
|
10
|
-
from agno.knowledge.chunking.strategy import ChunkingStrategy, ChunkingStrategyType
|
|
11
|
-
from agno.knowledge.document.base import Document
|
|
12
|
-
from agno.knowledge.reader.base import Reader
|
|
13
|
-
from agno.knowledge.reader.csv_reader import CSVReader
|
|
14
|
-
from agno.knowledge.reader.pdf_reader import PDFReader
|
|
15
|
-
from agno.knowledge.types import ContentType
|
|
16
|
-
from agno.utils.http import async_fetch_with_retry, fetch_with_retry
|
|
17
|
-
from agno.utils.log import log_debug
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
class URLReader(Reader):
|
|
21
|
-
"""Reader for general URL content"""
|
|
22
|
-
|
|
23
|
-
def __init__(
|
|
24
|
-
self, chunking_strategy: Optional[ChunkingStrategy] = FixedSizeChunking(), proxy: Optional[str] = None, **kwargs
|
|
25
|
-
):
|
|
26
|
-
super().__init__(chunking_strategy=chunking_strategy, **kwargs)
|
|
27
|
-
self.proxy = proxy
|
|
28
|
-
|
|
29
|
-
@classmethod
|
|
30
|
-
def get_supported_chunking_strategies(self) -> List[ChunkingStrategyType]:
|
|
31
|
-
"""Get the list of supported chunking strategies for URL readers."""
|
|
32
|
-
return [
|
|
33
|
-
ChunkingStrategyType.FIXED_SIZE_CHUNKER,
|
|
34
|
-
ChunkingStrategyType.AGENTIC_CHUNKER,
|
|
35
|
-
ChunkingStrategyType.DOCUMENT_CHUNKER,
|
|
36
|
-
ChunkingStrategyType.RECURSIVE_CHUNKER,
|
|
37
|
-
ChunkingStrategyType.SEMANTIC_CHUNKER,
|
|
38
|
-
]
|
|
39
|
-
|
|
40
|
-
@classmethod
|
|
41
|
-
def get_supported_content_types(self) -> List[ContentType]:
|
|
42
|
-
return [ContentType.URL]
|
|
43
|
-
|
|
44
|
-
def read(
|
|
45
|
-
self, url: str, id: Optional[str] = None, name: Optional[str] = None, password: Optional[str] = None
|
|
46
|
-
) -> List[Document]:
|
|
47
|
-
if not url:
|
|
48
|
-
raise ValueError("No url provided")
|
|
49
|
-
|
|
50
|
-
log_debug(f"Reading: {url}")
|
|
51
|
-
|
|
52
|
-
# Retry the request up to 3 times with exponential backoff
|
|
53
|
-
response = fetch_with_retry(url, proxy=self.proxy)
|
|
54
|
-
|
|
55
|
-
documents = self._create_documents(
|
|
56
|
-
url=url, text=response.text, content=response.content, id=id, name=name, password=password
|
|
57
|
-
)
|
|
58
|
-
|
|
59
|
-
if not self.chunk:
|
|
60
|
-
return documents
|
|
61
|
-
|
|
62
|
-
chunked_documents = []
|
|
63
|
-
for document in documents:
|
|
64
|
-
chunked_documents.append(self.chunk_document(document))
|
|
65
|
-
return [doc for sublist in chunked_documents for doc in sublist]
|
|
66
|
-
|
|
67
|
-
async def async_read(
|
|
68
|
-
self, url: str, id: Optional[str] = None, name: Optional[str] = None, password: Optional[str] = None
|
|
69
|
-
) -> List[Document]:
|
|
70
|
-
"""Async version of read method"""
|
|
71
|
-
if not url:
|
|
72
|
-
raise ValueError("No url provided")
|
|
73
|
-
|
|
74
|
-
log_debug(f"Reading async: {url}")
|
|
75
|
-
client_args = {"proxy": self.proxy} if self.proxy else {}
|
|
76
|
-
async with httpx.AsyncClient(**client_args) as client: # type: ignore
|
|
77
|
-
response = await async_fetch_with_retry(url, client=client)
|
|
78
|
-
|
|
79
|
-
documents = self._create_documents(
|
|
80
|
-
url=url, text=response.text, content=response.content, id=id, name=name, password=password
|
|
81
|
-
)
|
|
82
|
-
|
|
83
|
-
if not self.chunk:
|
|
84
|
-
return documents
|
|
85
|
-
|
|
86
|
-
return await self.chunk_documents_async(documents)
|
|
87
|
-
|
|
88
|
-
def _create_documents(
|
|
89
|
-
self,
|
|
90
|
-
url: str,
|
|
91
|
-
text: str,
|
|
92
|
-
content: bytes,
|
|
93
|
-
id: Optional[str] = None,
|
|
94
|
-
name: Optional[str] = None,
|
|
95
|
-
password: Optional[str] = None,
|
|
96
|
-
) -> List[Document]:
|
|
97
|
-
"""Helper method to create a document from URL content"""
|
|
98
|
-
|
|
99
|
-
# Determine file extension from URL
|
|
100
|
-
parsed_url = urlparse(url)
|
|
101
|
-
url_path = Path(parsed_url.path) # type: ignore
|
|
102
|
-
file_extension = url_path.suffix.lower()
|
|
103
|
-
|
|
104
|
-
# Read the document using the appropriate reader
|
|
105
|
-
if file_extension == ".csv":
|
|
106
|
-
filename = basename(parsed_url.path) or "data.csv"
|
|
107
|
-
return CSVReader().read(file=BytesIO(content), name=filename)
|
|
108
|
-
elif file_extension == ".pdf":
|
|
109
|
-
if password:
|
|
110
|
-
return PDFReader().read(pdf=BytesIO(content), name=name, password=password)
|
|
111
|
-
else:
|
|
112
|
-
return PDFReader().read(pdf=BytesIO(content), name=name)
|
|
113
|
-
else:
|
|
114
|
-
doc_name = name or parsed_url.path.strip("/").replace("/", "_").replace(" ", "_")
|
|
115
|
-
if not doc_name:
|
|
116
|
-
doc_name = parsed_url.netloc
|
|
117
|
-
if not doc_name:
|
|
118
|
-
doc_name = url
|
|
119
|
-
|
|
120
|
-
return [
|
|
121
|
-
Document(
|
|
122
|
-
name=doc_name,
|
|
123
|
-
id=id or doc_name,
|
|
124
|
-
meta_data={"url": url},
|
|
125
|
-
content=text,
|
|
126
|
-
size=len(text),
|
|
127
|
-
)
|
|
128
|
-
]
|
agno/tools/googlesearch.py
DELETED
|
@@ -1,98 +0,0 @@
|
|
|
1
|
-
import json
|
|
2
|
-
from typing import Any, Dict, List, Optional
|
|
3
|
-
|
|
4
|
-
from agno.tools import Toolkit
|
|
5
|
-
from agno.utils.log import log_debug
|
|
6
|
-
|
|
7
|
-
try:
|
|
8
|
-
from googlesearch import search
|
|
9
|
-
except ImportError:
|
|
10
|
-
raise ImportError("`googlesearch-python` not installed. Please install using `pip install googlesearch-python`")
|
|
11
|
-
|
|
12
|
-
try:
|
|
13
|
-
from pycountry import pycountry
|
|
14
|
-
except ImportError:
|
|
15
|
-
raise ImportError("`pycountry` not installed. Please install using `pip install pycountry`")
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
class GoogleSearchTools(Toolkit):
|
|
19
|
-
"""
|
|
20
|
-
GoogleSearch is a Python library for searching Google easily.
|
|
21
|
-
It uses requests and BeautifulSoup4 to scrape Google.
|
|
22
|
-
|
|
23
|
-
Args:
|
|
24
|
-
fixed_max_results (Optional[int]): A fixed number of maximum results.
|
|
25
|
-
fixed_language (Optional[str]): Language of the search results.
|
|
26
|
-
headers (Optional[Any]): Custom headers for the request.
|
|
27
|
-
proxy (Optional[str]): Proxy settings for the request.
|
|
28
|
-
timeout (Optional[int]): Timeout for the request, default is 10 seconds.
|
|
29
|
-
cache_results (bool): Enable caching of search results.
|
|
30
|
-
cache_ttl (int): Time-to-live for cached results in seconds.
|
|
31
|
-
cache_dir (Optional[str]): Directory to store cache files.
|
|
32
|
-
enable_google_search (bool): Enable Google search.
|
|
33
|
-
all (bool): Enable all tools.
|
|
34
|
-
"""
|
|
35
|
-
|
|
36
|
-
def __init__(
|
|
37
|
-
self,
|
|
38
|
-
fixed_max_results: Optional[int] = None,
|
|
39
|
-
fixed_language: Optional[str] = None,
|
|
40
|
-
headers: Optional[Any] = None,
|
|
41
|
-
proxy: Optional[str] = None,
|
|
42
|
-
timeout: Optional[int] = 10,
|
|
43
|
-
enable_google_search: bool = True,
|
|
44
|
-
all: bool = False,
|
|
45
|
-
**kwargs,
|
|
46
|
-
):
|
|
47
|
-
self.fixed_max_results: Optional[int] = fixed_max_results
|
|
48
|
-
self.fixed_language: Optional[str] = fixed_language
|
|
49
|
-
self.headers: Optional[Any] = headers
|
|
50
|
-
self.proxy: Optional[str] = proxy
|
|
51
|
-
self.timeout: Optional[int] = timeout
|
|
52
|
-
|
|
53
|
-
tools = []
|
|
54
|
-
if all or enable_google_search:
|
|
55
|
-
tools.append(self.google_search)
|
|
56
|
-
|
|
57
|
-
super().__init__(name="google_search_tools", tools=tools, **kwargs)
|
|
58
|
-
|
|
59
|
-
def google_search(self, query: str, max_results: int = 5, language: str = "en") -> str:
|
|
60
|
-
"""
|
|
61
|
-
Use this function to search Google for a specified query.
|
|
62
|
-
|
|
63
|
-
Args:
|
|
64
|
-
query (str): The query to search for.
|
|
65
|
-
max_results (int, optional): The maximum number of results to return. Default is 5.
|
|
66
|
-
language (str, optional): The language of the search results. Default is "en".
|
|
67
|
-
|
|
68
|
-
Returns:
|
|
69
|
-
str: A JSON formatted string containing the search results.
|
|
70
|
-
"""
|
|
71
|
-
max_results = self.fixed_max_results or max_results
|
|
72
|
-
language = self.fixed_language or language
|
|
73
|
-
|
|
74
|
-
# Resolve language to ISO 639-1 code if needed
|
|
75
|
-
if len(language) != 2:
|
|
76
|
-
_language = pycountry.languages.lookup(language)
|
|
77
|
-
if _language:
|
|
78
|
-
language = _language.alpha_2
|
|
79
|
-
else:
|
|
80
|
-
language = "en"
|
|
81
|
-
|
|
82
|
-
log_debug(f"Searching Google [{language}] for: {query}")
|
|
83
|
-
|
|
84
|
-
# Perform Google search using the googlesearch-python package
|
|
85
|
-
results = list(search(query, num=max_results, lang=language))
|
|
86
|
-
|
|
87
|
-
# Collect the search results
|
|
88
|
-
res: List[Dict[str, str]] = []
|
|
89
|
-
for result in results:
|
|
90
|
-
res.append(
|
|
91
|
-
{
|
|
92
|
-
"title": result.title,
|
|
93
|
-
"url": result.url,
|
|
94
|
-
"description": result.description,
|
|
95
|
-
}
|
|
96
|
-
)
|
|
97
|
-
|
|
98
|
-
return json.dumps(res, indent=2)
|