diff --git a/.gitignore b/.gitignore index aa973201fd15..16ce2f0b08ed 100644 --- a/.gitignore +++ b/.gitignore @@ -100,3 +100,10 @@ update_model_cost_map.py tests/test_litellm/proxy/_experimental/mcp_server/test_mcp_server_manager.py litellm/proxy/_experimental/out/guardrails/index.html scripts/test_vertex_ai_search.py +.claude +*claude-flow +.hive-mind +.swarm +/memory +.mcp.json +prompt*.md diff --git a/litellm/llms/bedrock/chat/agentcore/transformation.py b/litellm/llms/bedrock/chat/agentcore/transformation.py index 7c65cad94df0..f18fa4924422 100644 --- a/litellm/llms/bedrock/chat/agentcore/transformation.py +++ b/litellm/llms/bedrock/chat/agentcore/transformation.py @@ -116,8 +116,13 @@ def sign_request( fake_stream: Optional[bool] = None, ) -> Tuple[dict, Optional[bytes]]: # Check if api_key (bearer token) is provided for Cognito authentication - jwt_token = optional_params.get("api_key") + # Priority: api_key parameter first, then optional_params + print(f"[DEBUG sign_request] api_key parameter: {api_key[:50] if api_key else 'NONE'}...") + print(f"[DEBUG sign_request] optional_params.get('api_key'): {optional_params.get('api_key', 'NONE')[:50] if optional_params.get('api_key') else 'NONE'}...") + + jwt_token = api_key or optional_params.get("api_key") if jwt_token: + print(f"[DEBUG sign_request] ✅ USING JWT BEARER TOKEN (NOT AWS SigV4)") verbose_logger.debug( f"AgentCore: Using Bearer token authentication (Cognito/JWT) - token: {jwt_token[:50]}..." ) @@ -127,6 +132,7 @@ def sign_request( return headers, json.dumps(request_data).encode() # Otherwise, use AWS SigV4 authentication + print("[DEBUG sign_request] ❌ NO JWT TOKEN - Falling back to AWS SigV4") verbose_logger.debug("AgentCore: Using AWS SigV4 authentication (IAM)") return self._sign_request( service_name="bedrock-agentcore", diff --git a/pyproject.toml b/pyproject.toml index f32a2d4d28f9..42f6a43bdabe 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -5,10 +5,7 @@ description = "Library to easily interface with LLM API providers" authors = ["BerriAI"] license = "MIT" readme = "README.md" -packages = [ - { include = "litellm" }, - { include = "litellm/py.typed"}, -] +packages = [{ include = "litellm" }, { include = "litellm/py.typed" }] [tool.poetry.urls] homepage = "https://litellm.ai" @@ -56,7 +53,7 @@ google-cloud-iam = {version = "^2.19.1", optional = true} resend = {version = ">=0.8.0", optional = true} pynacl = {version = "^1.5.0", optional = true} websockets = {version = "^13.1.0", optional = true} -boto3 = {version = "1.36.0", optional = true} +boto3 = { version = "1.40.76", optional = true } redisvl = {version = "^0.4.1", optional = true, markers = "python_version >= '3.9' and python_version < '3.14'"} mcp = {version = "^1.21.2", optional = true, python = ">=3.10"} litellm-proxy-extras = {version = "0.4.6", optional = true} @@ -71,45 +68,43 @@ grpcio = ">=1.62.3,<1.68.0" # Constrain to < 1.68.0 to avoid resource exhausted [tool.poetry.extras] proxy = [ - "gunicorn", - "uvicorn", - "uvloop", - "fastapi", - "backoff", - "pyyaml", - "rq", - "orjson", - "apscheduler", - "fastapi-sso", - "PyJWT", - "python-multipart", - "cryptography", - "pynacl", - "websockets", - "boto3", - "azure-identity", - "azure-storage-blob", - "mcp", - "litellm-proxy-extras", - "litellm-enterprise", - "rich", - "polars", - "soundfile", + "gunicorn", + "uvicorn", + "uvloop", + "fastapi", + "backoff", + "pyyaml", + "rq", + "orjson", + "apscheduler", + "fastapi-sso", + "PyJWT", + "python-multipart", + "cryptography", + "pynacl", + "websockets", + "boto3", + "azure-identity", + "azure-storage-blob", + "mcp", + "litellm-proxy-extras", + "litellm-enterprise", + "rich", + "polars", + "soundfile", ] extra_proxy = [ - "prisma", - "azure-identity", - "azure-keyvault-secrets", - "google-cloud-kms", - "google-cloud-iam", - "resend", - "redisvl" + "prisma", + "azure-identity", + "azure-keyvault-secrets", + "google-cloud-kms", + "google-cloud-iam", + "resend", + "redisvl", ] -utils = [ - "numpydoc", -] +utils = ["numpydoc"] caching = ["diskcache"] @@ -170,6 +165,4 @@ plugins = "pydantic.mypy" [tool.pytest.ini_options] asyncio_mode = "auto" -markers = [ - "asyncio: mark test as an asyncio test", -] +markers = ["asyncio: mark test as an asyncio test"] diff --git a/requirements.txt b/requirements.txt index 08129155d7fa..b658e320b5e5 100644 --- a/requirements.txt +++ b/requirements.txt @@ -10,7 +10,7 @@ uvicorn==0.31.1 # server dep gunicorn==23.0.0 # server dep fastuuid==0.13.5 # for uuid4 uvloop==0.21.0 # uvicorn dep, gives us much better performance under load -boto3==1.36.0 # aws bedrock/sagemaker calls +boto3==1.40.53 # aws bedrock/sagemaker calls (has bedrock-agentcore-control, compatible with aioboto3) redis==5.2.1 # redis caching prisma==0.11.0 # for db mangum==0.17.0 # for aws lambda functions @@ -54,7 +54,7 @@ click==8.1.7 # for proxy cli rich==13.7.1 # for litellm proxy cli jinja2==3.1.6 # for prompt templates aiohttp==3.12.14 # for network calls -aioboto3==13.4.0 # for async sagemaker calls +aioboto3==15.5.0 # for async sagemaker calls (updated to match boto3 1.40.73) tenacity==8.5.0 # for retrying requests, when litellm.num_retries set pydantic>=2.11,<3 # proxy + openai req. + mcp jsonschema==4.22.0 # validating json schema diff --git a/taplo.toml b/taplo.toml new file mode 100644 index 000000000000..720888bfc2f2 --- /dev/null +++ b/taplo.toml @@ -0,0 +1,26 @@ +"$schema" = "https://taplo.tamasfe.dev/schema/config.json" + +[format] +# 4-space indentation to match your existing pyproject.toml +indent_string = " " + +# Long enough to avoid wrapping Poetry dependency blocks +column_width = 120 + +# Keep keys exactly in the order you wrote them +reorder_keys = false + +# Do NOT rewrite arrays (your style mixes inline + multiline arrays) +array_auto_expand = false +array_auto_collapse = false + +# Keep existing style for inline tables (don’t collapse them) +compact_inline_tables = false +compact_arrays = false + +# Ensure newline at EOF +trailing_newline = true + +[format.keys] +# Do not align or normalize keys — keeps Homepage/homepage, Repository/repository as-is +align = false