agno 1.8.1__py3-none-any.whl → 2.0.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/__init__.py +8 -0
- agno/agent/__init__.py +19 -27
- agno/agent/agent.py +3143 -4170
- agno/api/agent.py +11 -67
- agno/api/api.py +5 -46
- agno/api/evals.py +8 -19
- agno/api/os.py +17 -0
- agno/api/routes.py +6 -41
- agno/api/schemas/__init__.py +9 -0
- agno/api/schemas/agent.py +5 -21
- agno/api/schemas/evals.py +7 -16
- agno/api/schemas/os.py +14 -0
- agno/api/schemas/team.py +5 -21
- agno/api/schemas/utils.py +21 -0
- agno/api/schemas/workflows.py +11 -7
- agno/api/settings.py +53 -0
- agno/api/team.py +11 -66
- agno/api/workflow.py +28 -0
- agno/cloud/aws/base.py +214 -0
- agno/cloud/aws/s3/__init__.py +2 -0
- agno/cloud/aws/s3/api_client.py +43 -0
- agno/cloud/aws/s3/bucket.py +195 -0
- agno/cloud/aws/s3/object.py +57 -0
- agno/db/__init__.py +24 -0
- agno/db/base.py +245 -0
- agno/db/dynamo/__init__.py +3 -0
- agno/db/dynamo/dynamo.py +1743 -0
- agno/db/dynamo/schemas.py +278 -0
- agno/db/dynamo/utils.py +684 -0
- agno/db/firestore/__init__.py +3 -0
- agno/db/firestore/firestore.py +1432 -0
- agno/db/firestore/schemas.py +130 -0
- agno/db/firestore/utils.py +278 -0
- agno/db/gcs_json/__init__.py +3 -0
- agno/db/gcs_json/gcs_json_db.py +1001 -0
- agno/db/gcs_json/utils.py +194 -0
- agno/db/in_memory/__init__.py +3 -0
- agno/db/in_memory/in_memory_db.py +882 -0
- agno/db/in_memory/utils.py +172 -0
- agno/db/json/__init__.py +3 -0
- agno/db/json/json_db.py +1045 -0
- agno/db/json/utils.py +196 -0
- agno/db/migrations/v1_to_v2.py +162 -0
- agno/db/mongo/__init__.py +3 -0
- agno/db/mongo/mongo.py +1416 -0
- agno/db/mongo/schemas.py +77 -0
- agno/db/mongo/utils.py +204 -0
- agno/db/mysql/__init__.py +3 -0
- agno/db/mysql/mysql.py +1719 -0
- agno/db/mysql/schemas.py +124 -0
- agno/db/mysql/utils.py +297 -0
- agno/db/postgres/__init__.py +3 -0
- agno/db/postgres/postgres.py +1710 -0
- agno/db/postgres/schemas.py +124 -0
- agno/db/postgres/utils.py +280 -0
- agno/db/redis/__init__.py +3 -0
- agno/db/redis/redis.py +1367 -0
- agno/db/redis/schemas.py +109 -0
- agno/db/redis/utils.py +288 -0
- agno/db/schemas/__init__.py +3 -0
- agno/db/schemas/evals.py +33 -0
- agno/db/schemas/knowledge.py +40 -0
- agno/db/schemas/memory.py +46 -0
- agno/db/singlestore/__init__.py +3 -0
- agno/db/singlestore/schemas.py +116 -0
- agno/db/singlestore/singlestore.py +1712 -0
- agno/db/singlestore/utils.py +326 -0
- agno/db/sqlite/__init__.py +3 -0
- agno/db/sqlite/schemas.py +119 -0
- agno/db/sqlite/sqlite.py +1676 -0
- agno/db/sqlite/utils.py +268 -0
- agno/db/utils.py +88 -0
- agno/eval/__init__.py +14 -0
- agno/eval/accuracy.py +154 -48
- agno/eval/performance.py +88 -23
- agno/eval/reliability.py +73 -20
- agno/eval/utils.py +23 -13
- agno/integrations/discord/__init__.py +3 -0
- agno/{app → integrations}/discord/client.py +15 -11
- agno/knowledge/__init__.py +2 -2
- agno/{document → knowledge}/chunking/agentic.py +2 -2
- agno/{document → knowledge}/chunking/document.py +2 -2
- agno/{document → knowledge}/chunking/fixed.py +3 -3
- agno/{document → knowledge}/chunking/markdown.py +2 -2
- agno/{document → knowledge}/chunking/recursive.py +2 -2
- agno/{document → knowledge}/chunking/row.py +2 -2
- agno/knowledge/chunking/semantic.py +59 -0
- agno/knowledge/chunking/strategy.py +121 -0
- agno/knowledge/content.py +74 -0
- agno/knowledge/document/__init__.py +5 -0
- agno/{document → knowledge/document}/base.py +12 -2
- agno/knowledge/embedder/__init__.py +5 -0
- agno/{embedder → knowledge/embedder}/aws_bedrock.py +127 -1
- agno/{embedder → knowledge/embedder}/azure_openai.py +65 -1
- agno/{embedder → knowledge/embedder}/base.py +6 -0
- agno/{embedder → knowledge/embedder}/cohere.py +72 -1
- agno/{embedder → knowledge/embedder}/fastembed.py +17 -1
- agno/{embedder → knowledge/embedder}/fireworks.py +1 -1
- agno/{embedder → knowledge/embedder}/google.py +74 -1
- agno/{embedder → knowledge/embedder}/huggingface.py +36 -2
- agno/{embedder → knowledge/embedder}/jina.py +48 -2
- agno/knowledge/embedder/langdb.py +22 -0
- agno/knowledge/embedder/mistral.py +139 -0
- agno/{embedder → knowledge/embedder}/nebius.py +1 -1
- agno/{embedder → knowledge/embedder}/ollama.py +54 -3
- agno/knowledge/embedder/openai.py +223 -0
- agno/{embedder → knowledge/embedder}/sentence_transformer.py +16 -1
- agno/{embedder → knowledge/embedder}/together.py +1 -1
- agno/{embedder → knowledge/embedder}/voyageai.py +49 -1
- agno/knowledge/knowledge.py +1551 -0
- agno/knowledge/reader/__init__.py +7 -0
- agno/{document → knowledge}/reader/arxiv_reader.py +32 -4
- agno/knowledge/reader/base.py +88 -0
- agno/{document → knowledge}/reader/csv_reader.py +47 -65
- agno/knowledge/reader/docx_reader.py +83 -0
- agno/{document → knowledge}/reader/firecrawl_reader.py +42 -21
- agno/{document → knowledge}/reader/json_reader.py +30 -9
- agno/{document → knowledge}/reader/markdown_reader.py +58 -9
- agno/{document → knowledge}/reader/pdf_reader.py +71 -126
- agno/knowledge/reader/reader_factory.py +268 -0
- agno/knowledge/reader/s3_reader.py +101 -0
- agno/{document → knowledge}/reader/text_reader.py +31 -10
- agno/knowledge/reader/url_reader.py +128 -0
- agno/knowledge/reader/web_search_reader.py +366 -0
- agno/{document → knowledge}/reader/website_reader.py +37 -10
- agno/knowledge/reader/wikipedia_reader.py +59 -0
- agno/knowledge/reader/youtube_reader.py +78 -0
- agno/knowledge/remote_content/remote_content.py +88 -0
- agno/{reranker → knowledge/reranker}/base.py +1 -1
- agno/{reranker → knowledge/reranker}/cohere.py +2 -2
- agno/{reranker → knowledge/reranker}/infinity.py +2 -2
- agno/{reranker → knowledge/reranker}/sentence_transformer.py +2 -2
- agno/knowledge/types.py +30 -0
- agno/knowledge/utils.py +169 -0
- agno/media.py +269 -268
- agno/memory/__init__.py +2 -10
- agno/memory/manager.py +1003 -148
- agno/models/aimlapi/__init__.py +2 -2
- agno/models/aimlapi/aimlapi.py +6 -6
- agno/models/anthropic/claude.py +131 -131
- agno/models/aws/bedrock.py +110 -182
- agno/models/aws/claude.py +64 -18
- agno/models/azure/ai_foundry.py +73 -23
- agno/models/base.py +346 -290
- agno/models/cerebras/cerebras.py +84 -27
- agno/models/cohere/chat.py +106 -98
- agno/models/google/gemini.py +105 -46
- agno/models/groq/groq.py +97 -35
- agno/models/huggingface/huggingface.py +92 -27
- agno/models/ibm/watsonx.py +72 -13
- agno/models/litellm/chat.py +85 -13
- agno/models/message.py +46 -151
- agno/models/meta/llama.py +85 -49
- agno/models/metrics.py +120 -0
- agno/models/mistral/mistral.py +90 -21
- agno/models/ollama/__init__.py +0 -2
- agno/models/ollama/chat.py +85 -47
- agno/models/openai/chat.py +154 -37
- agno/models/openai/responses.py +178 -105
- agno/models/perplexity/perplexity.py +26 -2
- agno/models/portkey/portkey.py +0 -7
- agno/models/response.py +15 -9
- agno/models/utils.py +20 -0
- agno/models/vercel/__init__.py +2 -2
- agno/models/vercel/v0.py +1 -1
- agno/models/vllm/__init__.py +2 -2
- agno/models/vllm/vllm.py +3 -3
- agno/models/xai/xai.py +10 -10
- agno/os/__init__.py +3 -0
- agno/os/app.py +497 -0
- agno/os/auth.py +47 -0
- agno/os/config.py +103 -0
- agno/os/interfaces/agui/__init__.py +3 -0
- agno/os/interfaces/agui/agui.py +31 -0
- agno/{app/agui/async_router.py → os/interfaces/agui/router.py} +16 -16
- agno/{app → os/interfaces}/agui/utils.py +77 -33
- agno/os/interfaces/base.py +21 -0
- agno/os/interfaces/slack/__init__.py +3 -0
- agno/{app/slack/async_router.py → os/interfaces/slack/router.py} +3 -5
- agno/os/interfaces/slack/slack.py +32 -0
- agno/os/interfaces/whatsapp/__init__.py +3 -0
- agno/{app/whatsapp/async_router.py → os/interfaces/whatsapp/router.py} +4 -7
- agno/os/interfaces/whatsapp/whatsapp.py +29 -0
- agno/os/mcp.py +235 -0
- agno/os/router.py +1400 -0
- agno/os/routers/__init__.py +3 -0
- agno/os/routers/evals/__init__.py +3 -0
- agno/os/routers/evals/evals.py +393 -0
- agno/os/routers/evals/schemas.py +142 -0
- agno/os/routers/evals/utils.py +161 -0
- agno/os/routers/knowledge/__init__.py +3 -0
- agno/os/routers/knowledge/knowledge.py +850 -0
- agno/os/routers/knowledge/schemas.py +118 -0
- agno/os/routers/memory/__init__.py +3 -0
- agno/os/routers/memory/memory.py +410 -0
- agno/os/routers/memory/schemas.py +58 -0
- agno/os/routers/metrics/__init__.py +3 -0
- agno/os/routers/metrics/metrics.py +178 -0
- agno/os/routers/metrics/schemas.py +47 -0
- agno/os/routers/session/__init__.py +3 -0
- agno/os/routers/session/session.py +536 -0
- agno/os/schema.py +945 -0
- agno/{app/playground → os}/settings.py +7 -15
- agno/os/utils.py +270 -0
- agno/reasoning/azure_ai_foundry.py +4 -4
- agno/reasoning/deepseek.py +4 -4
- agno/reasoning/default.py +6 -11
- agno/reasoning/groq.py +4 -4
- agno/reasoning/helpers.py +4 -6
- agno/reasoning/ollama.py +4 -4
- agno/reasoning/openai.py +4 -4
- agno/run/agent.py +633 -0
- agno/run/base.py +53 -77
- agno/run/cancel.py +81 -0
- agno/run/team.py +243 -96
- agno/run/workflow.py +550 -12
- agno/session/__init__.py +10 -0
- agno/session/agent.py +244 -0
- agno/session/summary.py +225 -0
- agno/session/team.py +262 -0
- agno/{storage/session/v2 → session}/workflow.py +47 -24
- agno/team/__init__.py +15 -16
- agno/team/team.py +3260 -4824
- agno/tools/agentql.py +14 -5
- agno/tools/airflow.py +9 -4
- agno/tools/api.py +7 -3
- agno/tools/apify.py +2 -46
- agno/tools/arxiv.py +8 -3
- agno/tools/aws_lambda.py +7 -5
- agno/tools/aws_ses.py +7 -1
- agno/tools/baidusearch.py +4 -1
- agno/tools/bitbucket.py +4 -4
- agno/tools/brandfetch.py +14 -11
- agno/tools/bravesearch.py +4 -1
- agno/tools/brightdata.py +43 -23
- agno/tools/browserbase.py +13 -4
- agno/tools/calcom.py +12 -10
- agno/tools/calculator.py +10 -27
- agno/tools/cartesia.py +20 -17
- agno/tools/{clickup_tool.py → clickup.py} +12 -25
- agno/tools/confluence.py +8 -8
- agno/tools/crawl4ai.py +7 -1
- agno/tools/csv_toolkit.py +9 -8
- agno/tools/dalle.py +22 -12
- agno/tools/daytona.py +13 -16
- agno/tools/decorator.py +6 -3
- agno/tools/desi_vocal.py +17 -8
- agno/tools/discord.py +11 -8
- agno/tools/docker.py +30 -42
- agno/tools/duckdb.py +34 -53
- agno/tools/duckduckgo.py +8 -7
- agno/tools/e2b.py +62 -62
- agno/tools/eleven_labs.py +36 -29
- agno/tools/email.py +4 -1
- agno/tools/evm.py +7 -1
- agno/tools/exa.py +19 -14
- agno/tools/fal.py +30 -30
- agno/tools/file.py +9 -8
- agno/tools/financial_datasets.py +25 -44
- agno/tools/firecrawl.py +22 -22
- agno/tools/function.py +127 -18
- agno/tools/giphy.py +23 -11
- agno/tools/github.py +48 -126
- agno/tools/gmail.py +45 -61
- agno/tools/google_bigquery.py +7 -6
- agno/tools/google_maps.py +11 -26
- agno/tools/googlesearch.py +7 -2
- agno/tools/googlesheets.py +21 -17
- agno/tools/hackernews.py +9 -5
- agno/tools/jina.py +5 -4
- agno/tools/jira.py +18 -9
- agno/tools/knowledge.py +31 -32
- agno/tools/linear.py +19 -34
- agno/tools/linkup.py +5 -1
- agno/tools/local_file_system.py +8 -5
- agno/tools/lumalab.py +32 -20
- agno/tools/mcp.py +1 -2
- agno/tools/mem0.py +18 -12
- agno/tools/memori.py +14 -10
- agno/tools/mlx_transcribe.py +3 -2
- agno/tools/models/azure_openai.py +33 -15
- agno/tools/models/gemini.py +59 -32
- agno/tools/models/groq.py +30 -23
- agno/tools/models/nebius.py +28 -12
- agno/tools/models_labs.py +40 -16
- agno/tools/moviepy_video.py +7 -6
- agno/tools/neo4j.py +10 -8
- agno/tools/newspaper.py +7 -2
- agno/tools/newspaper4k.py +8 -3
- agno/tools/openai.py +58 -32
- agno/tools/openbb.py +12 -11
- agno/tools/opencv.py +63 -47
- agno/tools/openweather.py +14 -12
- agno/tools/pandas.py +11 -3
- agno/tools/postgres.py +4 -12
- agno/tools/pubmed.py +4 -1
- agno/tools/python.py +9 -22
- agno/tools/reasoning.py +35 -27
- agno/tools/reddit.py +11 -26
- agno/tools/replicate.py +55 -42
- agno/tools/resend.py +4 -1
- agno/tools/scrapegraph.py +15 -14
- agno/tools/searxng.py +10 -23
- agno/tools/serpapi.py +6 -3
- agno/tools/serper.py +13 -4
- agno/tools/shell.py +9 -2
- agno/tools/slack.py +12 -11
- agno/tools/sleep.py +3 -2
- agno/tools/spider.py +24 -4
- agno/tools/sql.py +7 -6
- agno/tools/tavily.py +6 -4
- agno/tools/telegram.py +12 -4
- agno/tools/todoist.py +11 -31
- agno/tools/toolkit.py +1 -1
- agno/tools/trafilatura.py +22 -6
- agno/tools/trello.py +9 -22
- agno/tools/twilio.py +10 -3
- agno/tools/user_control_flow.py +6 -1
- agno/tools/valyu.py +34 -5
- agno/tools/visualization.py +19 -28
- agno/tools/webbrowser.py +4 -3
- agno/tools/webex.py +11 -7
- agno/tools/website.py +15 -46
- agno/tools/webtools.py +12 -4
- agno/tools/whatsapp.py +5 -9
- agno/tools/wikipedia.py +20 -13
- agno/tools/x.py +14 -13
- agno/tools/yfinance.py +13 -40
- agno/tools/youtube.py +26 -20
- agno/tools/zendesk.py +7 -2
- agno/tools/zep.py +10 -7
- agno/tools/zoom.py +10 -9
- agno/utils/common.py +1 -19
- agno/utils/events.py +100 -123
- agno/utils/gemini.py +32 -2
- agno/utils/knowledge.py +29 -0
- agno/utils/log.py +54 -4
- agno/utils/mcp.py +68 -10
- agno/utils/media.py +39 -0
- agno/utils/message.py +12 -1
- agno/utils/models/aws_claude.py +1 -1
- agno/utils/models/claude.py +47 -4
- agno/utils/models/cohere.py +1 -1
- agno/utils/models/mistral.py +8 -7
- agno/utils/models/schema_utils.py +3 -3
- agno/utils/models/watsonx.py +1 -1
- agno/utils/openai.py +1 -1
- agno/utils/pprint.py +33 -32
- agno/utils/print_response/agent.py +779 -0
- agno/utils/print_response/team.py +1669 -0
- agno/utils/print_response/workflow.py +1451 -0
- agno/utils/prompts.py +14 -14
- agno/utils/reasoning.py +87 -0
- agno/utils/response.py +42 -42
- agno/utils/streamlit.py +481 -0
- agno/utils/string.py +8 -22
- agno/utils/team.py +50 -0
- agno/utils/timer.py +2 -2
- agno/vectordb/base.py +33 -21
- agno/vectordb/cassandra/cassandra.py +287 -23
- agno/vectordb/chroma/chromadb.py +482 -59
- agno/vectordb/clickhouse/clickhousedb.py +270 -63
- agno/vectordb/couchbase/couchbase.py +309 -29
- agno/vectordb/lancedb/lance_db.py +360 -21
- agno/vectordb/langchaindb/__init__.py +5 -0
- agno/vectordb/langchaindb/langchaindb.py +145 -0
- agno/vectordb/lightrag/__init__.py +5 -0
- agno/vectordb/lightrag/lightrag.py +374 -0
- agno/vectordb/llamaindex/llamaindexdb.py +127 -0
- agno/vectordb/milvus/milvus.py +242 -32
- agno/vectordb/mongodb/mongodb.py +200 -24
- agno/vectordb/pgvector/pgvector.py +319 -37
- agno/vectordb/pineconedb/pineconedb.py +221 -27
- agno/vectordb/qdrant/qdrant.py +334 -14
- agno/vectordb/singlestore/singlestore.py +286 -29
- agno/vectordb/surrealdb/surrealdb.py +187 -7
- agno/vectordb/upstashdb/upstashdb.py +342 -26
- agno/vectordb/weaviate/weaviate.py +227 -165
- agno/workflow/__init__.py +17 -13
- agno/workflow/{v2/condition.py → condition.py} +135 -32
- agno/workflow/{v2/loop.py → loop.py} +115 -28
- agno/workflow/{v2/parallel.py → parallel.py} +138 -108
- agno/workflow/{v2/router.py → router.py} +133 -32
- agno/workflow/{v2/step.py → step.py} +207 -49
- agno/workflow/{v2/steps.py → steps.py} +147 -66
- agno/workflow/types.py +482 -0
- agno/workflow/workflow.py +2410 -696
- agno-2.0.0.dist-info/METADATA +494 -0
- agno-2.0.0.dist-info/RECORD +515 -0
- agno-2.0.0.dist-info/licenses/LICENSE +201 -0
- agno/agent/metrics.py +0 -107
- agno/api/app.py +0 -35
- agno/api/playground.py +0 -92
- agno/api/schemas/app.py +0 -12
- agno/api/schemas/playground.py +0 -22
- agno/api/schemas/user.py +0 -35
- agno/api/schemas/workspace.py +0 -46
- agno/api/user.py +0 -160
- agno/api/workflows.py +0 -33
- agno/api/workspace.py +0 -175
- agno/app/agui/__init__.py +0 -3
- agno/app/agui/app.py +0 -17
- agno/app/agui/sync_router.py +0 -120
- agno/app/base.py +0 -186
- agno/app/discord/__init__.py +0 -3
- agno/app/fastapi/__init__.py +0 -3
- agno/app/fastapi/app.py +0 -107
- agno/app/fastapi/async_router.py +0 -457
- agno/app/fastapi/sync_router.py +0 -448
- agno/app/playground/app.py +0 -228
- agno/app/playground/async_router.py +0 -1050
- agno/app/playground/deploy.py +0 -249
- agno/app/playground/operator.py +0 -183
- agno/app/playground/schemas.py +0 -220
- agno/app/playground/serve.py +0 -55
- agno/app/playground/sync_router.py +0 -1042
- agno/app/playground/utils.py +0 -46
- agno/app/settings.py +0 -15
- agno/app/slack/__init__.py +0 -3
- agno/app/slack/app.py +0 -19
- agno/app/slack/sync_router.py +0 -92
- agno/app/utils.py +0 -54
- agno/app/whatsapp/__init__.py +0 -3
- agno/app/whatsapp/app.py +0 -15
- agno/app/whatsapp/sync_router.py +0 -197
- agno/cli/auth_server.py +0 -249
- agno/cli/config.py +0 -274
- agno/cli/console.py +0 -88
- agno/cli/credentials.py +0 -23
- agno/cli/entrypoint.py +0 -571
- agno/cli/operator.py +0 -357
- agno/cli/settings.py +0 -96
- agno/cli/ws/ws_cli.py +0 -817
- agno/constants.py +0 -13
- agno/document/__init__.py +0 -5
- agno/document/chunking/semantic.py +0 -45
- agno/document/chunking/strategy.py +0 -31
- agno/document/reader/__init__.py +0 -5
- agno/document/reader/base.py +0 -47
- agno/document/reader/docx_reader.py +0 -60
- agno/document/reader/gcs/pdf_reader.py +0 -44
- agno/document/reader/s3/pdf_reader.py +0 -59
- agno/document/reader/s3/text_reader.py +0 -63
- agno/document/reader/url_reader.py +0 -59
- agno/document/reader/youtube_reader.py +0 -58
- agno/embedder/__init__.py +0 -5
- agno/embedder/langdb.py +0 -80
- agno/embedder/mistral.py +0 -82
- agno/embedder/openai.py +0 -78
- agno/file/__init__.py +0 -5
- agno/file/file.py +0 -16
- agno/file/local/csv.py +0 -32
- agno/file/local/txt.py +0 -19
- agno/infra/app.py +0 -240
- agno/infra/base.py +0 -144
- agno/infra/context.py +0 -20
- agno/infra/db_app.py +0 -52
- agno/infra/resource.py +0 -205
- agno/infra/resources.py +0 -55
- agno/knowledge/agent.py +0 -702
- agno/knowledge/arxiv.py +0 -33
- agno/knowledge/combined.py +0 -36
- agno/knowledge/csv.py +0 -144
- agno/knowledge/csv_url.py +0 -124
- agno/knowledge/document.py +0 -223
- agno/knowledge/docx.py +0 -137
- agno/knowledge/firecrawl.py +0 -34
- agno/knowledge/gcs/__init__.py +0 -0
- agno/knowledge/gcs/base.py +0 -39
- agno/knowledge/gcs/pdf.py +0 -125
- agno/knowledge/json.py +0 -137
- agno/knowledge/langchain.py +0 -71
- agno/knowledge/light_rag.py +0 -273
- agno/knowledge/llamaindex.py +0 -66
- agno/knowledge/markdown.py +0 -154
- agno/knowledge/pdf.py +0 -164
- agno/knowledge/pdf_bytes.py +0 -42
- agno/knowledge/pdf_url.py +0 -148
- agno/knowledge/s3/__init__.py +0 -0
- agno/knowledge/s3/base.py +0 -64
- agno/knowledge/s3/pdf.py +0 -33
- agno/knowledge/s3/text.py +0 -34
- agno/knowledge/text.py +0 -141
- agno/knowledge/url.py +0 -46
- agno/knowledge/website.py +0 -179
- agno/knowledge/wikipedia.py +0 -32
- agno/knowledge/youtube.py +0 -35
- agno/memory/agent.py +0 -423
- agno/memory/classifier.py +0 -104
- agno/memory/db/__init__.py +0 -5
- agno/memory/db/base.py +0 -42
- agno/memory/db/mongodb.py +0 -189
- agno/memory/db/postgres.py +0 -203
- agno/memory/db/sqlite.py +0 -193
- agno/memory/memory.py +0 -22
- agno/memory/row.py +0 -36
- agno/memory/summarizer.py +0 -201
- agno/memory/summary.py +0 -19
- agno/memory/team.py +0 -415
- agno/memory/v2/__init__.py +0 -2
- agno/memory/v2/db/__init__.py +0 -1
- agno/memory/v2/db/base.py +0 -42
- agno/memory/v2/db/firestore.py +0 -339
- agno/memory/v2/db/mongodb.py +0 -196
- agno/memory/v2/db/postgres.py +0 -214
- agno/memory/v2/db/redis.py +0 -187
- agno/memory/v2/db/schema.py +0 -54
- agno/memory/v2/db/sqlite.py +0 -209
- agno/memory/v2/manager.py +0 -437
- agno/memory/v2/memory.py +0 -1097
- agno/memory/v2/schema.py +0 -55
- agno/memory/v2/summarizer.py +0 -215
- agno/memory/workflow.py +0 -38
- agno/models/ollama/tools.py +0 -430
- agno/models/qwen/__init__.py +0 -5
- agno/playground/__init__.py +0 -10
- agno/playground/deploy.py +0 -3
- agno/playground/playground.py +0 -3
- agno/playground/serve.py +0 -3
- agno/playground/settings.py +0 -3
- agno/reranker/__init__.py +0 -0
- agno/run/response.py +0 -467
- agno/run/v2/__init__.py +0 -0
- agno/run/v2/workflow.py +0 -567
- agno/storage/__init__.py +0 -0
- agno/storage/agent/__init__.py +0 -0
- agno/storage/agent/dynamodb.py +0 -1
- agno/storage/agent/json.py +0 -1
- agno/storage/agent/mongodb.py +0 -1
- agno/storage/agent/postgres.py +0 -1
- agno/storage/agent/singlestore.py +0 -1
- agno/storage/agent/sqlite.py +0 -1
- agno/storage/agent/yaml.py +0 -1
- agno/storage/base.py +0 -60
- agno/storage/dynamodb.py +0 -673
- agno/storage/firestore.py +0 -297
- agno/storage/gcs_json.py +0 -261
- agno/storage/in_memory.py +0 -234
- agno/storage/json.py +0 -237
- agno/storage/mongodb.py +0 -328
- agno/storage/mysql.py +0 -685
- agno/storage/postgres.py +0 -682
- agno/storage/redis.py +0 -336
- agno/storage/session/__init__.py +0 -16
- agno/storage/session/agent.py +0 -64
- agno/storage/session/team.py +0 -63
- agno/storage/session/v2/__init__.py +0 -5
- agno/storage/session/workflow.py +0 -61
- agno/storage/singlestore.py +0 -606
- agno/storage/sqlite.py +0 -646
- agno/storage/workflow/__init__.py +0 -0
- agno/storage/workflow/mongodb.py +0 -1
- agno/storage/workflow/postgres.py +0 -1
- agno/storage/workflow/sqlite.py +0 -1
- agno/storage/yaml.py +0 -241
- agno/tools/thinking.py +0 -73
- agno/utils/defaults.py +0 -57
- agno/utils/filesystem.py +0 -39
- agno/utils/git.py +0 -52
- agno/utils/json_io.py +0 -30
- agno/utils/load_env.py +0 -19
- agno/utils/py_io.py +0 -19
- agno/utils/pyproject.py +0 -18
- agno/utils/resource_filter.py +0 -31
- agno/workflow/v2/__init__.py +0 -21
- agno/workflow/v2/types.py +0 -357
- agno/workflow/v2/workflow.py +0 -3312
- agno/workspace/__init__.py +0 -0
- agno/workspace/config.py +0 -325
- agno/workspace/enums.py +0 -6
- agno/workspace/helpers.py +0 -52
- agno/workspace/operator.py +0 -757
- agno/workspace/settings.py +0 -158
- agno-1.8.1.dist-info/METADATA +0 -982
- agno-1.8.1.dist-info/RECORD +0 -566
- agno-1.8.1.dist-info/entry_points.txt +0 -3
- agno-1.8.1.dist-info/licenses/LICENSE +0 -375
- /agno/{app → db/migrations}/__init__.py +0 -0
- /agno/{app/playground/__init__.py → db/schemas/metrics.py} +0 -0
- /agno/{cli → integrations}/__init__.py +0 -0
- /agno/{cli/ws → knowledge/chunking}/__init__.py +0 -0
- /agno/{document/chunking → knowledge/remote_content}/__init__.py +0 -0
- /agno/{document/reader/gcs → knowledge/reranker}/__init__.py +0 -0
- /agno/{document/reader/s3 → os/interfaces}/__init__.py +0 -0
- /agno/{app → os/interfaces}/slack/security.py +0 -0
- /agno/{app → os/interfaces}/whatsapp/security.py +0 -0
- /agno/{file/local → utils/print_response}/__init__.py +0 -0
- /agno/{infra → vectordb/llamaindex}/__init__.py +0 -0
- {agno-1.8.1.dist-info → agno-2.0.0.dist-info}/WHEEL +0 -0
- {agno-1.8.1.dist-info → agno-2.0.0.dist-info}/top_level.txt +0 -0
agno/tools/linkup.py
CHANGED
|
@@ -16,6 +16,8 @@ class LinkupTools(Toolkit):
|
|
|
16
16
|
api_key: Optional[str] = None,
|
|
17
17
|
depth: Literal["standard", "deep"] = "standard",
|
|
18
18
|
output_type: Literal["sourcedAnswer", "searchResults"] = "searchResults",
|
|
19
|
+
enable_web_search_with_linkup: bool = True,
|
|
20
|
+
all: bool = False,
|
|
19
21
|
**kwargs,
|
|
20
22
|
):
|
|
21
23
|
self.api_key = api_key or getenv("LINKUP_API_KEY")
|
|
@@ -26,7 +28,9 @@ class LinkupTools(Toolkit):
|
|
|
26
28
|
self.depth = depth
|
|
27
29
|
self.output_type = output_type
|
|
28
30
|
|
|
29
|
-
tools: List[Any] = [
|
|
31
|
+
tools: List[Any] = []
|
|
32
|
+
if all or enable_web_search_with_linkup:
|
|
33
|
+
tools.append(self.web_search_with_linkup)
|
|
30
34
|
|
|
31
35
|
super().__init__(name="linkup_tools", tools=tools, **kwargs)
|
|
32
36
|
|
agno/tools/local_file_system.py
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import os
|
|
2
1
|
from pathlib import Path
|
|
3
2
|
from typing import Optional
|
|
4
3
|
from uuid import uuid4
|
|
@@ -12,6 +11,8 @@ class LocalFileSystemTools(Toolkit):
|
|
|
12
11
|
self,
|
|
13
12
|
target_directory: Optional[str] = None,
|
|
14
13
|
default_extension: str = "txt",
|
|
14
|
+
enable_write_file: bool = True,
|
|
15
|
+
all: bool = False,
|
|
15
16
|
**kwargs,
|
|
16
17
|
):
|
|
17
18
|
"""
|
|
@@ -21,14 +22,15 @@ class LocalFileSystemTools(Toolkit):
|
|
|
21
22
|
default_extension (str): Default file extension to use if none specified.
|
|
22
23
|
"""
|
|
23
24
|
|
|
24
|
-
self.target_directory = target_directory or
|
|
25
|
+
self.target_directory = target_directory or str(Path.cwd())
|
|
25
26
|
self.default_extension = default_extension.lstrip(".")
|
|
26
27
|
|
|
27
28
|
target_path = Path(self.target_directory)
|
|
28
29
|
target_path.mkdir(parents=True, exist_ok=True)
|
|
29
30
|
|
|
30
31
|
tools = []
|
|
31
|
-
|
|
32
|
+
if all or enable_write_file:
|
|
33
|
+
tools.append(self.write_file)
|
|
32
34
|
|
|
33
35
|
super().__init__(name="write_to_local", tools=tools, **kwargs)
|
|
34
36
|
|
|
@@ -53,8 +55,9 @@ class LocalFileSystemTools(Toolkit):
|
|
|
53
55
|
filename = filename or str(uuid4())
|
|
54
56
|
directory = directory or self.target_directory
|
|
55
57
|
if filename and "." in filename:
|
|
56
|
-
|
|
57
|
-
|
|
58
|
+
path_obj = Path(filename)
|
|
59
|
+
filename = path_obj.stem
|
|
60
|
+
extension = extension or path_obj.suffix.lstrip(".")
|
|
58
61
|
|
|
59
62
|
log_debug(f"Writing file to local system: {filename}")
|
|
60
63
|
|
agno/tools/lumalab.py
CHANGED
|
@@ -4,8 +4,9 @@ from os import getenv
|
|
|
4
4
|
from typing import Any, Dict, List, Literal, Optional, TypedDict
|
|
5
5
|
|
|
6
6
|
from agno.agent import Agent
|
|
7
|
-
from agno.media import
|
|
7
|
+
from agno.media import Video
|
|
8
8
|
from agno.tools import Toolkit
|
|
9
|
+
from agno.tools.function import ToolResult
|
|
9
10
|
from agno.utils.log import log_info, logger
|
|
10
11
|
|
|
11
12
|
try:
|
|
@@ -30,6 +31,9 @@ class LumaLabTools(Toolkit):
|
|
|
30
31
|
wait_for_completion: bool = True,
|
|
31
32
|
poll_interval: int = 3,
|
|
32
33
|
max_wait_time: int = 300, # 5 minutes
|
|
34
|
+
enable_generate_video: bool = True,
|
|
35
|
+
enable_image_to_video: bool = True,
|
|
36
|
+
all: bool = False,
|
|
33
37
|
**kwargs,
|
|
34
38
|
):
|
|
35
39
|
self.wait_for_completion = wait_for_completion
|
|
@@ -43,8 +47,10 @@ class LumaLabTools(Toolkit):
|
|
|
43
47
|
self.client = LumaAI(auth_token=self.api_key)
|
|
44
48
|
|
|
45
49
|
tools: List[Any] = []
|
|
46
|
-
|
|
47
|
-
|
|
50
|
+
if all or enable_generate_video:
|
|
51
|
+
tools.append(self.generate_video)
|
|
52
|
+
if all or enable_image_to_video:
|
|
53
|
+
tools.append(self.image_to_video)
|
|
48
54
|
|
|
49
55
|
super().__init__(name="luma_lab", tools=tools, **kwargs)
|
|
50
56
|
|
|
@@ -56,7 +62,7 @@ class LumaLabTools(Toolkit):
|
|
|
56
62
|
end_image_url: Optional[str] = None,
|
|
57
63
|
loop: bool = False,
|
|
58
64
|
aspect_ratio: Literal["1:1", "16:9", "9:16", "4:3", "3:4", "21:9", "9:21"] = "16:9",
|
|
59
|
-
) ->
|
|
65
|
+
) -> ToolResult:
|
|
60
66
|
"""Generate a video from one or two images with a prompt.
|
|
61
67
|
|
|
62
68
|
Args:
|
|
@@ -68,7 +74,7 @@ class LumaLabTools(Toolkit):
|
|
|
68
74
|
aspect_ratio: Aspect ratio of the output video
|
|
69
75
|
|
|
70
76
|
Returns:
|
|
71
|
-
|
|
77
|
+
ToolResult: A ToolResult containing the generated video or error message.
|
|
72
78
|
"""
|
|
73
79
|
|
|
74
80
|
try:
|
|
@@ -90,33 +96,36 @@ class LumaLabTools(Toolkit):
|
|
|
90
96
|
video_id = str(uuid.uuid4())
|
|
91
97
|
|
|
92
98
|
if not self.wait_for_completion:
|
|
93
|
-
return "Async generation unsupported"
|
|
99
|
+
return ToolResult(content="Async generation unsupported")
|
|
94
100
|
|
|
95
101
|
# Poll for completion
|
|
96
102
|
seconds_waited = 0
|
|
97
103
|
while seconds_waited < self.max_wait_time:
|
|
98
104
|
if not generation or not generation.id:
|
|
99
|
-
return "Failed to get generation ID"
|
|
105
|
+
return ToolResult(content="Failed to get generation ID")
|
|
100
106
|
|
|
101
107
|
generation = self.client.generations.get(generation.id)
|
|
102
108
|
|
|
103
109
|
if generation.state == "completed" and generation.assets:
|
|
104
110
|
video_url = generation.assets.video
|
|
105
111
|
if video_url:
|
|
106
|
-
|
|
107
|
-
return
|
|
112
|
+
video_artifact = Video(id=video_id, url=video_url, eta="completed")
|
|
113
|
+
return ToolResult(
|
|
114
|
+
content=f"Video generated successfully: {video_url}",
|
|
115
|
+
videos=[video_artifact],
|
|
116
|
+
)
|
|
108
117
|
elif generation.state == "failed":
|
|
109
|
-
return f"Generation failed: {generation.failure_reason}"
|
|
118
|
+
return ToolResult(content=f"Generation failed: {generation.failure_reason}")
|
|
110
119
|
|
|
111
120
|
log_info(f"Generation in progress... State: {generation.state}")
|
|
112
121
|
time.sleep(self.poll_interval)
|
|
113
122
|
seconds_waited += self.poll_interval
|
|
114
123
|
|
|
115
|
-
return f"Video generation timed out after {self.max_wait_time} seconds"
|
|
124
|
+
return ToolResult(content=f"Video generation timed out after {self.max_wait_time} seconds")
|
|
116
125
|
|
|
117
126
|
except Exception as e:
|
|
118
127
|
logger.error(f"Failed to generate video: {e}")
|
|
119
|
-
return f"Error: {e}"
|
|
128
|
+
return ToolResult(content=f"Error: {e}")
|
|
120
129
|
|
|
121
130
|
def generate_video(
|
|
122
131
|
self,
|
|
@@ -125,7 +134,7 @@ class LumaLabTools(Toolkit):
|
|
|
125
134
|
loop: bool = False,
|
|
126
135
|
aspect_ratio: Literal["1:1", "16:9", "9:16", "4:3", "3:4", "21:9", "9:21"] = "16:9",
|
|
127
136
|
keyframes: Optional[Dict[str, Dict[str, str]]] = None,
|
|
128
|
-
) ->
|
|
137
|
+
) -> ToolResult:
|
|
129
138
|
"""Use this function to generate a video given a prompt."""
|
|
130
139
|
|
|
131
140
|
try:
|
|
@@ -142,30 +151,33 @@ class LumaLabTools(Toolkit):
|
|
|
142
151
|
|
|
143
152
|
video_id = str(uuid.uuid4())
|
|
144
153
|
if not self.wait_for_completion:
|
|
145
|
-
return "Async generation unsupported"
|
|
154
|
+
return ToolResult(content="Async generation unsupported")
|
|
146
155
|
|
|
147
156
|
# Poll for completion
|
|
148
157
|
seconds_waited = 0
|
|
149
158
|
while seconds_waited < self.max_wait_time:
|
|
150
159
|
if not generation or not generation.id:
|
|
151
|
-
return "Failed to get generation ID"
|
|
160
|
+
return ToolResult(content="Failed to get generation ID")
|
|
152
161
|
|
|
153
162
|
generation = self.client.generations.get(generation.id)
|
|
154
163
|
|
|
155
164
|
if generation.state == "completed" and generation.assets:
|
|
156
165
|
video_url = generation.assets.video
|
|
157
166
|
if video_url:
|
|
158
|
-
|
|
159
|
-
return
|
|
167
|
+
video_artifact = Video(id=video_id, url=video_url, state="completed")
|
|
168
|
+
return ToolResult(
|
|
169
|
+
content=f"Video generated successfully: {video_url}",
|
|
170
|
+
videos=[video_artifact],
|
|
171
|
+
)
|
|
160
172
|
elif generation.state == "failed":
|
|
161
|
-
return f"Generation failed: {generation.failure_reason}"
|
|
173
|
+
return ToolResult(content=f"Generation failed: {generation.failure_reason}")
|
|
162
174
|
|
|
163
175
|
log_info(f"Generation in progress... State: {generation.state}")
|
|
164
176
|
time.sleep(self.poll_interval)
|
|
165
177
|
seconds_waited += self.poll_interval
|
|
166
178
|
|
|
167
|
-
return f"Video generation timed out after {self.max_wait_time} seconds"
|
|
179
|
+
return ToolResult(content=f"Video generation timed out after {self.max_wait_time} seconds")
|
|
168
180
|
|
|
169
181
|
except Exception as e:
|
|
170
182
|
logger.error(f"Failed to generate video: {e}")
|
|
171
|
-
return f"Error: {e}"
|
|
183
|
+
return ToolResult(content=f"Error: {e}")
|
agno/tools/mcp.py
CHANGED
|
@@ -365,7 +365,7 @@ class MultiMCPTools(Toolkit):
|
|
|
365
365
|
*,
|
|
366
366
|
env: Optional[dict[str, str]] = None,
|
|
367
367
|
server_params_list: Optional[
|
|
368
|
-
|
|
368
|
+
list[Union[SSEClientParams, StdioServerParameters, StreamableHTTPClientParams]]
|
|
369
369
|
] = None,
|
|
370
370
|
timeout_seconds: int = 5,
|
|
371
371
|
client=None,
|
|
@@ -531,7 +531,6 @@ class MultiMCPTools(Toolkit):
|
|
|
531
531
|
session = await self._async_exit_stack.enter_async_context(ClientSession(read, write))
|
|
532
532
|
self._active_contexts.append(session)
|
|
533
533
|
await self.initialize(session)
|
|
534
|
-
|
|
535
534
|
# Handle Streamable HTTP connections
|
|
536
535
|
elif isinstance(server_params, StreamableHTTPClientParams):
|
|
537
536
|
client_connection = await self._async_exit_stack.enter_async_context(
|
agno/tools/mem0.py
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import json
|
|
2
2
|
from os import getenv
|
|
3
|
-
from typing import Any, Dict, Optional, Union
|
|
3
|
+
from typing import Any, Dict, List, Optional, Union
|
|
4
4
|
|
|
5
5
|
from agno.agent import Agent
|
|
6
|
-
from agno.tools
|
|
6
|
+
from agno.tools import Toolkit
|
|
7
7
|
from agno.utils.log import log_debug, log_error, log_warning
|
|
8
8
|
|
|
9
9
|
try:
|
|
@@ -22,18 +22,24 @@ class Mem0Tools(Toolkit):
|
|
|
22
22
|
org_id: Optional[str] = None,
|
|
23
23
|
project_id: Optional[str] = None,
|
|
24
24
|
infer: bool = True,
|
|
25
|
+
enable_add_memory: bool = True,
|
|
26
|
+
enable_search_memory: bool = True,
|
|
27
|
+
enable_get_all_memories: bool = True,
|
|
28
|
+
enable_delete_all_memories: bool = True,
|
|
29
|
+
all: bool = False,
|
|
25
30
|
**kwargs,
|
|
26
31
|
):
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
tools
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
32
|
+
tools: List[Any] = []
|
|
33
|
+
if enable_add_memory or all:
|
|
34
|
+
tools.append(self.add_memory)
|
|
35
|
+
if enable_search_memory or all:
|
|
36
|
+
tools.append(self.search_memory)
|
|
37
|
+
if enable_get_all_memories or all:
|
|
38
|
+
tools.append(self.get_all_memories)
|
|
39
|
+
if enable_delete_all_memories or all:
|
|
40
|
+
tools.append(self.delete_all_memories)
|
|
41
|
+
|
|
42
|
+
super().__init__(name="mem0_tools", tools=tools, **kwargs)
|
|
37
43
|
self.api_key = api_key or getenv("MEM0_API_KEY")
|
|
38
44
|
self.user_id = user_id
|
|
39
45
|
self.org_id = org_id or getenv("MEM0_ORG_ID")
|
agno/tools/memori.py
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import json
|
|
2
|
-
from typing import Any, Dict, Optional
|
|
2
|
+
from typing import Any, Dict, List, Optional
|
|
3
3
|
|
|
4
4
|
from agno.agent import Agent
|
|
5
5
|
from agno.tools.toolkit import Toolkit
|
|
@@ -54,6 +54,10 @@ class MemoriTools(Toolkit):
|
|
|
54
54
|
verbose: bool = False,
|
|
55
55
|
config: Optional[Dict[str, Any]] = None,
|
|
56
56
|
auto_enable: bool = True,
|
|
57
|
+
enable_search_memory: bool = True,
|
|
58
|
+
enable_record_conversation: bool = True,
|
|
59
|
+
enable_get_memory_stats: bool = True,
|
|
60
|
+
all: bool = False,
|
|
57
61
|
**kwargs,
|
|
58
62
|
):
|
|
59
63
|
"""
|
|
@@ -69,15 +73,15 @@ class MemoriTools(Toolkit):
|
|
|
69
73
|
auto_enable: Automatically enable the memory system on initialization
|
|
70
74
|
**kwargs: Additional arguments passed to Toolkit base class
|
|
71
75
|
"""
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
tools
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
)
|
|
76
|
+
tools: List[Any] = []
|
|
77
|
+
if all or enable_search_memory:
|
|
78
|
+
tools.append(self.search_memory)
|
|
79
|
+
if all or enable_record_conversation:
|
|
80
|
+
tools.append(self.record_conversation)
|
|
81
|
+
if all or enable_get_memory_stats:
|
|
82
|
+
tools.append(self.get_memory_stats)
|
|
83
|
+
|
|
84
|
+
super().__init__(name="memori_tools", tools=tools, **kwargs)
|
|
81
85
|
|
|
82
86
|
# Set default database connection if not provided
|
|
83
87
|
if not database_connect:
|
agno/tools/mlx_transcribe.py
CHANGED
|
@@ -32,7 +32,7 @@ class MLXTranscribeTools(Toolkit):
|
|
|
32
32
|
def __init__(
|
|
33
33
|
self,
|
|
34
34
|
base_dir: Optional[Path] = None,
|
|
35
|
-
|
|
35
|
+
enable_read_files_in_base_dir: bool = True,
|
|
36
36
|
path_or_hf_repo: str = "mlx-community/whisper-large-v3-turbo",
|
|
37
37
|
verbose: Optional[bool] = None,
|
|
38
38
|
temperature: Optional[Union[float, Tuple[float, ...]]] = None,
|
|
@@ -47,6 +47,7 @@ class MLXTranscribeTools(Toolkit):
|
|
|
47
47
|
clip_timestamps: Optional[Union[str, List[float]]] = None,
|
|
48
48
|
hallucination_silence_threshold: Optional[float] = None,
|
|
49
49
|
decode_options: Optional[dict] = None,
|
|
50
|
+
all: bool = False,
|
|
50
51
|
**kwargs,
|
|
51
52
|
):
|
|
52
53
|
self.base_dir: Path = base_dir or Path.cwd()
|
|
@@ -66,7 +67,7 @@ class MLXTranscribeTools(Toolkit):
|
|
|
66
67
|
self.decode_options: Optional[dict] = decode_options
|
|
67
68
|
|
|
68
69
|
tools: List[Any] = [self.transcribe]
|
|
69
|
-
if
|
|
70
|
+
if enable_read_files_in_base_dir or all:
|
|
70
71
|
tools.append(self.read_files)
|
|
71
72
|
|
|
72
73
|
super().__init__(name="mlx_transcribe", tools=tools, **kwargs)
|
|
@@ -5,8 +5,9 @@ from uuid import uuid4
|
|
|
5
5
|
from requests import post
|
|
6
6
|
|
|
7
7
|
from agno.agent import Agent
|
|
8
|
-
from agno.media import
|
|
8
|
+
from agno.media import Image
|
|
9
9
|
from agno.tools import Toolkit
|
|
10
|
+
from agno.tools.function import ToolResult
|
|
10
11
|
from agno.utils.log import log_debug, logger
|
|
11
12
|
|
|
12
13
|
|
|
@@ -31,9 +32,9 @@ class AzureOpenAITools(Toolkit):
|
|
|
31
32
|
image_deployment: Optional[str] = None,
|
|
32
33
|
image_model: str = "dall-e-3",
|
|
33
34
|
image_quality: Literal["standard", "hd"] = "standard", # Note: "hd" quality is only available for dall-e-3.
|
|
35
|
+
enable_generate_image: bool = True,
|
|
36
|
+
all: bool = False,
|
|
34
37
|
):
|
|
35
|
-
super().__init__(name="azure_openai")
|
|
36
|
-
|
|
37
38
|
# Set credentials from parameters or environment variables
|
|
38
39
|
self.api_key = api_key or getenv("AZURE_OPENAI_API_KEY")
|
|
39
40
|
self.azure_endpoint = azure_endpoint or getenv("AZURE_OPENAI_ENDPOINT")
|
|
@@ -49,15 +50,20 @@ class AzureOpenAITools(Toolkit):
|
|
|
49
50
|
self.image_deployment = image_deployment or getenv("AZURE_OPENAI_IMAGE_DEPLOYMENT")
|
|
50
51
|
self.image_model = image_model
|
|
51
52
|
|
|
53
|
+
# Build tools list based on available services
|
|
54
|
+
tools = []
|
|
55
|
+
|
|
52
56
|
# Validate image generation parameters
|
|
53
57
|
if self.image_deployment and self.image_model in self.VALID_MODELS:
|
|
54
58
|
# Create and store the base URL
|
|
55
59
|
self.image_base_url = f"{self.azure_endpoint}/openai/deployments/{self.image_deployment}/images/generations?api-version={self.api_version}"
|
|
56
|
-
|
|
57
|
-
|
|
60
|
+
if all or enable_generate_image:
|
|
61
|
+
tools.append(self.generate_image)
|
|
58
62
|
else:
|
|
59
63
|
logger.error("Missing required image generation parameters or invalid model")
|
|
60
64
|
|
|
65
|
+
super().__init__(name="azure_openai_tools", tools=tools)
|
|
66
|
+
|
|
61
67
|
self.image_quality = image_quality
|
|
62
68
|
|
|
63
69
|
# Validate quality
|
|
@@ -98,7 +104,7 @@ class AzureOpenAITools(Toolkit):
|
|
|
98
104
|
n: int = 1,
|
|
99
105
|
size: Optional[Literal["256x256", "512x512", "1024x1024", "1792x1024", "1024x1792"]] = "1024x1024",
|
|
100
106
|
style: Literal["vivid", "natural"] = "vivid",
|
|
101
|
-
) ->
|
|
107
|
+
) -> ToolResult:
|
|
102
108
|
"""Generate an image using Azure OpenAI image generation.
|
|
103
109
|
|
|
104
110
|
Args:
|
|
@@ -114,7 +120,7 @@ class AzureOpenAITools(Toolkit):
|
|
|
114
120
|
Note: "vivid" produces more dramatic images, while "natural" produces more realistic ones.
|
|
115
121
|
|
|
116
122
|
Returns:
|
|
117
|
-
A
|
|
123
|
+
ToolResult: A ToolResult containing the generated images or error message.
|
|
118
124
|
|
|
119
125
|
Note:
|
|
120
126
|
Invalid parameters will be automatically corrected to valid values. For example:
|
|
@@ -125,7 +131,9 @@ class AzureOpenAITools(Toolkit):
|
|
|
125
131
|
"""
|
|
126
132
|
# Check if image generation is properly initialized
|
|
127
133
|
if not hasattr(self, "image_base_url"):
|
|
128
|
-
return
|
|
134
|
+
return ToolResult(
|
|
135
|
+
content="Image generation tool not properly initialized. Please check your configuration."
|
|
136
|
+
)
|
|
129
137
|
|
|
130
138
|
# Enforce valid parameters
|
|
131
139
|
params = self._enforce_valid_image_parameters(
|
|
@@ -147,26 +155,36 @@ class AzureOpenAITools(Toolkit):
|
|
|
147
155
|
response = post(self.image_base_url, headers=headers, json=params)
|
|
148
156
|
|
|
149
157
|
if response.status_code != 200:
|
|
150
|
-
return f"Error {response.status_code}: {response.text}"
|
|
158
|
+
return ToolResult(content=f"Error {response.status_code}: {response.text}")
|
|
151
159
|
|
|
152
160
|
# Process results
|
|
153
161
|
data = response.json()
|
|
154
162
|
log_debug("Image generated successfully")
|
|
155
163
|
|
|
156
|
-
#
|
|
164
|
+
# Create ImageArtifact objects for generated images
|
|
165
|
+
generated_images = []
|
|
157
166
|
response_str = ""
|
|
167
|
+
|
|
158
168
|
for img in data.get("data", []):
|
|
159
169
|
image_url = img.get("url")
|
|
160
170
|
revised_prompt = img.get("revised_prompt")
|
|
161
171
|
|
|
162
|
-
#
|
|
163
|
-
|
|
164
|
-
|
|
172
|
+
# Create ImageArtifact with URL
|
|
173
|
+
image_artifact = Image(
|
|
174
|
+
id=str(uuid4()), url=image_url, original_prompt=prompt, revised_prompt=revised_prompt
|
|
165
175
|
)
|
|
176
|
+
generated_images.append(image_artifact)
|
|
166
177
|
|
|
167
178
|
response_str += f"Image has been generated at the URL {image_url}\n"
|
|
168
|
-
|
|
179
|
+
|
|
180
|
+
if generated_images:
|
|
181
|
+
return ToolResult(
|
|
182
|
+
content=response_str.strip(),
|
|
183
|
+
images=generated_images,
|
|
184
|
+
)
|
|
185
|
+
else:
|
|
186
|
+
return ToolResult(content="No images were generated.")
|
|
169
187
|
|
|
170
188
|
except Exception as e:
|
|
171
189
|
logger.error(f"Failed to generate image: {e}")
|
|
172
|
-
return f"Error: {e}"
|
|
190
|
+
return ToolResult(content=f"Error: {e}")
|
agno/tools/models/gemini.py
CHANGED
|
@@ -5,8 +5,9 @@ from typing import Any, Optional
|
|
|
5
5
|
from uuid import uuid4
|
|
6
6
|
|
|
7
7
|
from agno.agent import Agent
|
|
8
|
-
from agno.media import
|
|
8
|
+
from agno.media import Image, Video
|
|
9
9
|
from agno.tools import Toolkit
|
|
10
|
+
from agno.tools.function import ToolResult
|
|
10
11
|
from agno.utils.log import log_debug, log_error, log_info
|
|
11
12
|
|
|
12
13
|
try:
|
|
@@ -27,9 +28,18 @@ class GeminiTools(Toolkit):
|
|
|
27
28
|
location: Optional[str] = None,
|
|
28
29
|
image_generation_model: str = "imagen-3.0-generate-002",
|
|
29
30
|
video_generation_model: str = "veo-2.0-generate-001",
|
|
31
|
+
enable_generate_image: bool = True,
|
|
32
|
+
enable_generate_video: bool = True,
|
|
33
|
+
all: bool = False,
|
|
30
34
|
**kwargs,
|
|
31
35
|
):
|
|
32
|
-
|
|
36
|
+
tools = []
|
|
37
|
+
if all or enable_generate_image:
|
|
38
|
+
tools.append(self.generate_image)
|
|
39
|
+
if all or enable_generate_video:
|
|
40
|
+
tools.append(self.generate_video)
|
|
41
|
+
|
|
42
|
+
super().__init__(name="gemini_tools", tools=tools, **kwargs)
|
|
33
43
|
|
|
34
44
|
# Set mode and credentials: use only provided vertexai parameter
|
|
35
45
|
self.vertexai = vertexai or getenv("GOOGLE_GENAI_USE_VERTEXAI") == "true"
|
|
@@ -67,13 +77,13 @@ class GeminiTools(Toolkit):
|
|
|
67
77
|
self,
|
|
68
78
|
agent: Agent,
|
|
69
79
|
prompt: str,
|
|
70
|
-
) ->
|
|
80
|
+
) -> ToolResult:
|
|
71
81
|
"""Generate images based on a text prompt using Google Imagen.
|
|
72
82
|
|
|
73
83
|
Args:
|
|
74
84
|
prompt (str): The text prompt to generate the image from.
|
|
75
85
|
Returns:
|
|
76
|
-
|
|
86
|
+
ToolResult: A ToolResult containing the generated images or error message.
|
|
77
87
|
"""
|
|
78
88
|
|
|
79
89
|
try:
|
|
@@ -87,47 +97,55 @@ class GeminiTools(Toolkit):
|
|
|
87
97
|
# Extract image bytes
|
|
88
98
|
if response.generated_images is None or not response.generated_images:
|
|
89
99
|
log_info("No images were generated.")
|
|
90
|
-
return "Failed to generate image: No images were generated."
|
|
100
|
+
return ToolResult(content="Failed to generate image: No images were generated.")
|
|
91
101
|
|
|
102
|
+
generated_images = []
|
|
92
103
|
for generated_image in response.generated_images:
|
|
93
104
|
if generated_image.image is None or not generated_image.image.image_bytes:
|
|
94
105
|
continue
|
|
106
|
+
|
|
95
107
|
image_bytes = generated_image.image.image_bytes
|
|
96
|
-
base64_encoded_image_bytes = base64.b64encode(image_bytes)
|
|
97
108
|
actual_mime_type = "image/png"
|
|
98
|
-
|
|
99
109
|
media_id = str(uuid4())
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
110
|
+
|
|
111
|
+
# Create ImageArtifact with raw bytes (not base64 encoded)
|
|
112
|
+
image_artifact = Image(
|
|
113
|
+
id=media_id,
|
|
114
|
+
content=image_bytes,
|
|
115
|
+
original_prompt=prompt,
|
|
116
|
+
mime_type=actual_mime_type,
|
|
107
117
|
)
|
|
118
|
+
generated_images.append(image_artifact)
|
|
108
119
|
log_debug(f"Successfully generated image {media_id} with model {self.image_model}")
|
|
109
|
-
|
|
120
|
+
|
|
121
|
+
if generated_images:
|
|
122
|
+
return ToolResult(
|
|
123
|
+
content="Image generated successfully",
|
|
124
|
+
images=generated_images,
|
|
125
|
+
)
|
|
126
|
+
else:
|
|
127
|
+
return ToolResult(content="Failed to generate image: No valid images were generated.")
|
|
110
128
|
|
|
111
129
|
except Exception as e:
|
|
112
130
|
log_error(f"Failed to generate image: Client or method not available ({e})")
|
|
113
|
-
return f"Failed to generate image: Client or method not available ({e})"
|
|
131
|
+
return ToolResult(content=f"Failed to generate image: Client or method not available ({e})")
|
|
114
132
|
|
|
115
133
|
def generate_video(
|
|
116
134
|
self,
|
|
117
135
|
agent: Agent,
|
|
118
136
|
prompt: str,
|
|
119
|
-
) ->
|
|
137
|
+
) -> ToolResult:
|
|
120
138
|
"""Generate a video based on a text prompt.
|
|
121
139
|
Args:
|
|
122
140
|
prompt (str): The text prompt to generate the video from.
|
|
123
141
|
Returns:
|
|
124
|
-
|
|
142
|
+
ToolResult: A ToolResult containing the generated video or error message.
|
|
125
143
|
"""
|
|
126
144
|
# Video generation requires Vertex AI mode.
|
|
127
145
|
if not self.vertexai:
|
|
128
146
|
log_error("Video generation requires Vertex AI mode. Please enable Vertex AI mode.")
|
|
129
|
-
return (
|
|
130
|
-
"Video generation requires Vertex AI mode. "
|
|
147
|
+
return ToolResult(
|
|
148
|
+
content="Video generation requires Vertex AI mode. "
|
|
131
149
|
"Please set `vertexai=True` or environment variable `GOOGLE_GENAI_USE_VERTEXAI=true`."
|
|
132
150
|
)
|
|
133
151
|
|
|
@@ -149,28 +167,37 @@ class GeminiTools(Toolkit):
|
|
|
149
167
|
result = operation.result
|
|
150
168
|
if result is None or result.generated_videos is None or not result.generated_videos:
|
|
151
169
|
log_error("No videos were generated.")
|
|
152
|
-
return "Failed to generate video: No videos were generated."
|
|
170
|
+
return ToolResult(content="Failed to generate video: No videos were generated.")
|
|
153
171
|
|
|
172
|
+
generated_videos = []
|
|
154
173
|
for video in result.generated_videos:
|
|
155
174
|
if video.video is None or not video.video.video_bytes:
|
|
156
175
|
continue
|
|
176
|
+
|
|
157
177
|
generated_video = video.video
|
|
158
178
|
if generated_video.video_bytes is None:
|
|
159
179
|
continue
|
|
160
180
|
|
|
161
181
|
media_id = str(uuid4())
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
mime_type=generated_video.mime_type or "video/mp4",
|
|
170
|
-
)
|
|
182
|
+
|
|
183
|
+
# Create VideoArtifact with base64 encoded content
|
|
184
|
+
video_artifact = Video(
|
|
185
|
+
id=media_id,
|
|
186
|
+
content=base64.b64encode(generated_video.video_bytes).decode("utf-8"),
|
|
187
|
+
original_prompt=prompt,
|
|
188
|
+
mime_type=generated_video.mime_type or "video/mp4",
|
|
171
189
|
)
|
|
190
|
+
generated_videos.append(video_artifact)
|
|
172
191
|
log_debug(f"Successfully generated video {media_id} with model {self.video_model}")
|
|
173
|
-
|
|
192
|
+
|
|
193
|
+
if generated_videos:
|
|
194
|
+
return ToolResult(
|
|
195
|
+
content="Video generated successfully",
|
|
196
|
+
videos=generated_videos,
|
|
197
|
+
)
|
|
198
|
+
else:
|
|
199
|
+
return ToolResult(content="Failed to generate video: No valid videos were generated.")
|
|
200
|
+
|
|
174
201
|
except Exception as e:
|
|
175
202
|
log_error(f"Failed to generate video: {e}")
|
|
176
|
-
return f"Failed to generate video: {e}"
|
|
203
|
+
return ToolResult(content=f"Failed to generate video: {e}")
|