@aws/agentcore 0.3.0-preview.2.0 → 0.3.0-preview.3.0
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.
- package/dist/assets/__tests__/__snapshots__/assets.snapshot.test.ts.snap +486 -133
- package/dist/assets/cdk/README.md +19 -7
- package/dist/assets/cdk/bin/cdk.ts +37 -2
- package/dist/assets/cdk/lib/cdk-stack.ts +25 -2
- package/dist/assets/cdk/package.json +1 -1
- package/dist/assets/cdk/test/cdk.test.ts +18 -14
- package/dist/assets/cdk/tsconfig.json +4 -4
- package/dist/assets/container/python/Dockerfile +19 -9
- package/dist/assets/container/python/dockerignore.template +7 -0
- package/dist/assets/python/autogen/base/README.md +9 -11
- package/dist/assets/python/autogen/base/mcp_client/__init__.py +1 -1
- package/dist/assets/python/autogen/base/model/__init__.py +1 -1
- package/dist/assets/python/crewai/base/README.md +9 -11
- package/dist/assets/python/crewai/base/model/__init__.py +1 -1
- package/dist/assets/python/googleadk/base/README.md +9 -9
- package/dist/assets/python/googleadk/base/main.py +10 -1
- package/dist/assets/python/googleadk/base/mcp_client/__init__.py +1 -1
- package/dist/assets/python/googleadk/base/mcp_client/client.py +54 -3
- package/dist/assets/python/googleadk/base/model/__init__.py +1 -1
- package/dist/assets/python/googleadk/base/pyproject.toml +2 -0
- package/dist/assets/python/langchain_langgraph/base/README.md +9 -11
- package/dist/assets/python/langchain_langgraph/base/main.py +11 -1
- package/dist/assets/python/langchain_langgraph/base/mcp_client/__init__.py +1 -1
- package/dist/assets/python/langchain_langgraph/base/mcp_client/client.py +52 -3
- package/dist/assets/python/langchain_langgraph/base/model/__init__.py +1 -1
- package/dist/assets/python/langchain_langgraph/base/pyproject.toml +2 -1
- package/dist/assets/python/openaiagents/base/README.md +9 -9
- package/dist/assets/python/openaiagents/base/main.py +43 -3
- package/dist/assets/python/openaiagents/base/mcp_client/__init__.py +1 -1
- package/dist/assets/python/openaiagents/base/mcp_client/client.py +54 -3
- package/dist/assets/python/openaiagents/base/model/__init__.py +1 -1
- package/dist/assets/python/openaiagents/base/pyproject.toml +2 -0
- package/dist/assets/python/strands/base/README.md +10 -12
- package/dist/assets/python/strands/base/main.py +16 -3
- package/dist/assets/python/strands/base/mcp_client/__init__.py +1 -1
- package/dist/assets/python/strands/base/mcp_client/client.py +56 -4
- package/dist/assets/python/strands/base/model/__init__.py +1 -1
- package/dist/assets/python/strands/base/pyproject.toml +4 -1
- package/dist/assets/python/strands/capabilities/memory/__init__.py +1 -0
- package/dist/cli/index.mjs +290 -286
- package/dist/lib/packaging/build-args.d.ts +6 -0
- package/dist/lib/packaging/build-args.d.ts.map +1 -0
- package/dist/lib/packaging/build-args.js +18 -0
- package/dist/lib/packaging/build-args.js.map +1 -0
- package/dist/lib/packaging/container.d.ts.map +1 -1
- package/dist/lib/packaging/container.js +2 -1
- package/dist/lib/packaging/container.js.map +1 -1
- package/dist/lib/schemas/io/cli-config.d.ts +10 -0
- package/dist/lib/schemas/io/cli-config.d.ts.map +1 -0
- package/dist/lib/schemas/io/cli-config.js +27 -0
- package/dist/lib/schemas/io/cli-config.js.map +1 -0
- package/dist/lib/schemas/io/index.d.ts +1 -0
- package/dist/lib/schemas/io/index.d.ts.map +1 -1
- package/dist/lib/schemas/io/index.js +3 -1
- package/dist/lib/schemas/io/index.js.map +1 -1
- package/dist/lib/utils/subprocess.d.ts.map +1 -1
- package/dist/lib/utils/subprocess.js +32 -10
- package/dist/lib/utils/subprocess.js.map +1 -1
- package/dist/schema/constants.d.ts.map +1 -1
- package/dist/schema/constants.js +0 -1
- package/dist/schema/constants.js.map +1 -1
- package/dist/schema/schemas/agentcore-project.d.ts +48 -5
- package/dist/schema/schemas/agentcore-project.d.ts.map +1 -1
- package/dist/schema/schemas/agentcore-project.js +19 -4
- package/dist/schema/schemas/agentcore-project.js.map +1 -1
- package/dist/schema/schemas/aws-targets.js +1 -1
- package/dist/schema/schemas/aws-targets.js.map +1 -1
- package/dist/schema/schemas/deployed-state.d.ts +32 -0
- package/dist/schema/schemas/deployed-state.d.ts.map +1 -1
- package/dist/schema/schemas/deployed-state.js +11 -1
- package/dist/schema/schemas/deployed-state.js.map +1 -1
- package/dist/schema/schemas/mcp-defs.d.ts +1 -1
- package/dist/schema/schemas/mcp-defs.js +1 -1
- package/dist/schema/schemas/mcp.d.ts +146 -6
- package/dist/schema/schemas/mcp.d.ts.map +1 -1
- package/dist/schema/schemas/mcp.js +49 -4
- package/dist/schema/schemas/mcp.js.map +1 -1
- package/package.json +8 -8
|
@@ -1,13 +1,61 @@
|
|
|
1
|
+
import os
|
|
2
|
+
import logging
|
|
1
3
|
from langchain_mcp_adapters.client import MultiServerMCPClient
|
|
2
4
|
|
|
5
|
+
logger = logging.getLogger(__name__)
|
|
6
|
+
|
|
7
|
+
{{#if hasGateway}}
|
|
8
|
+
{{#if (includes gatewayAuthTypes "AWS_IAM")}}
|
|
9
|
+
from mcp_proxy_for_aws.sigv4_helper import SigV4HTTPXAuth, create_aws_session
|
|
10
|
+
{{/if}}
|
|
11
|
+
{{#if (includes gatewayAuthTypes "CUSTOM_JWT")}}
|
|
12
|
+
from bedrock_agentcore.identity import requires_access_token
|
|
13
|
+
{{/if}}
|
|
14
|
+
|
|
15
|
+
{{#each gatewayProviders}}
|
|
16
|
+
{{#if (eq authType "CUSTOM_JWT")}}
|
|
17
|
+
@requires_access_token(
|
|
18
|
+
provider_name="{{credentialProviderName}}",
|
|
19
|
+
scopes=[{{#if scopes}}"{{scopes}}"{{/if}}],
|
|
20
|
+
auth_flow="M2M",
|
|
21
|
+
)
|
|
22
|
+
def _get_bearer_token_{{snakeCase name}}(*, access_token: str):
|
|
23
|
+
"""Obtain OAuth access token via AgentCore Identity for {{name}}."""
|
|
24
|
+
return access_token
|
|
25
|
+
|
|
26
|
+
{{/if}}
|
|
27
|
+
{{/each}}
|
|
28
|
+
|
|
29
|
+
def get_all_gateway_mcp_client() -> MultiServerMCPClient | None:
|
|
30
|
+
"""Returns an MCP Client connected to all configured gateways."""
|
|
31
|
+
servers = {}
|
|
32
|
+
{{#each gatewayProviders}}
|
|
33
|
+
url = os.environ.get("{{envVarName}}")
|
|
34
|
+
if url:
|
|
35
|
+
{{#if (eq authType "AWS_IAM")}}
|
|
36
|
+
session = create_aws_session()
|
|
37
|
+
auth = SigV4HTTPXAuth(session.get_credentials(), "bedrock-agentcore", session.region_name)
|
|
38
|
+
servers["{{name}}"] = {"transport": "streamable_http", "url": url, "auth": auth}
|
|
39
|
+
{{else if (eq authType "CUSTOM_JWT")}}
|
|
40
|
+
token = _get_bearer_token_{{snakeCase name}}()
|
|
41
|
+
headers = {"Authorization": f"Bearer {token}"} if token else None
|
|
42
|
+
servers["{{name}}"] = {"transport": "streamable_http", "url": url, "headers": headers}
|
|
43
|
+
{{else}}
|
|
44
|
+
servers["{{name}}"] = {"transport": "streamable_http", "url": url}
|
|
45
|
+
{{/if}}
|
|
46
|
+
else:
|
|
47
|
+
logger.warning("{{envVarName}} not set — {{name}} gateway tools unavailable")
|
|
48
|
+
{{/each}}
|
|
49
|
+
if not servers:
|
|
50
|
+
return None
|
|
51
|
+
return MultiServerMCPClient(servers)
|
|
52
|
+
{{else}}
|
|
3
53
|
# ExaAI provides information about code through web searches, crawling and code context searches through their platform. Requires no authentication
|
|
4
54
|
EXAMPLE_MCP_ENDPOINT = "https://mcp.exa.ai/mcp"
|
|
5
55
|
|
|
6
56
|
|
|
7
57
|
def get_streamable_http_mcp_client() -> MultiServerMCPClient:
|
|
8
|
-
"""
|
|
9
|
-
Returns an MCP Client compatible with LangChain/LangGraph.
|
|
10
|
-
"""
|
|
58
|
+
"""Returns an MCP Client compatible with LangChain/LangGraph."""
|
|
11
59
|
# to use an MCP server that supports bearer authentication, add headers={"Authorization": f"Bearer {access_token}"}
|
|
12
60
|
return MultiServerMCPClient(
|
|
13
61
|
{
|
|
@@ -17,3 +65,4 @@ def get_streamable_http_mcp_client() -> MultiServerMCPClient:
|
|
|
17
65
|
}
|
|
18
66
|
}
|
|
19
67
|
)
|
|
68
|
+
{{/if}}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
# Package marker
|
|
@@ -15,7 +15,6 @@ dependencies = [
|
|
|
15
15
|
"mcp >= 1.19.0",
|
|
16
16
|
"langchain-mcp-adapters >= 0.1.11",
|
|
17
17
|
"langchain >= 1.0.3",
|
|
18
|
-
"tiktoken == 0.11.0",
|
|
19
18
|
"bedrock-agentcore >= 1.0.3",
|
|
20
19
|
"botocore[crt] >= 1.35.0",
|
|
21
20
|
{{#if (eq modelProvider "Bedrock")}}
|
|
@@ -30,6 +29,8 @@ dependencies = [
|
|
|
30
29
|
{{#if (eq modelProvider "Gemini")}}
|
|
31
30
|
"langchain-google-genai >= 3.0.3",
|
|
32
31
|
{{/if}}
|
|
32
|
+
{{#if hasGateway}}{{#if (includes gatewayAuthTypes "AWS_IAM")}}"mcp-proxy-for-aws >= 1.1.0",
|
|
33
|
+
{{/if}}{{/if}}
|
|
33
34
|
]
|
|
34
35
|
|
|
35
36
|
[tool.hatch.build.targets.wheel]
|
|
@@ -2,23 +2,23 @@ This is a project generated by the agentcore create CLI tool!
|
|
|
2
2
|
|
|
3
3
|
# Layout
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
5
|
+
The generated application code lives at the agent root directory. At the root, there is a `.gitignore` file, an
|
|
6
|
+
`agentcore/` folder which represents the configurations and state associated with this project. Other `agentcore`
|
|
7
7
|
commands like `deploy`, `dev`, and `invoke` rely on the configuration stored here.
|
|
8
8
|
|
|
9
|
-
##
|
|
9
|
+
## Agent Root
|
|
10
10
|
|
|
11
|
-
The main entrypoint to your app is defined in `
|
|
11
|
+
The main entrypoint to your app is defined in `main.py`. Using the AgentCore SDK `@app.entrypoint` decorator, this
|
|
12
12
|
file defines a Starlette ASGI app with the OpenAI Agents SDK framework running within.
|
|
13
13
|
|
|
14
|
-
`
|
|
14
|
+
`model/load.py` instantiates your chosen model provider (OpenAI).
|
|
15
15
|
|
|
16
16
|
## Environment Variables
|
|
17
17
|
|
|
18
|
-
| Variable
|
|
19
|
-
|
|
|
20
|
-
| `
|
|
21
|
-
| `LOCAL_DEV`
|
|
18
|
+
| Variable | Required | Description |
|
|
19
|
+
| --- | --- | --- |
|
|
20
|
+
{{#if hasIdentity}}| `{{identityProviders.[0].envVarName}}` | Yes | {{modelProvider}} API key (local) or Identity provider name (deployed) |
|
|
21
|
+
{{/if}}| `LOCAL_DEV` | No | Set to `1` to use `.env.local` instead of AgentCore Identity |
|
|
22
22
|
|
|
23
23
|
# Developing locally
|
|
24
24
|
|
|
@@ -2,13 +2,22 @@ import os
|
|
|
2
2
|
from agents import Agent, Runner, function_tool
|
|
3
3
|
from bedrock_agentcore.runtime import BedrockAgentCoreApp
|
|
4
4
|
from model.load import load_model
|
|
5
|
+
{{#if hasGateway}}
|
|
6
|
+
from mcp_client.client import get_all_gateway_mcp_servers
|
|
7
|
+
{{else}}
|
|
5
8
|
from mcp_client.client import get_streamable_http_mcp_client
|
|
9
|
+
{{/if}}
|
|
6
10
|
|
|
7
11
|
app = BedrockAgentCoreApp()
|
|
8
12
|
log = app.logger
|
|
9
13
|
|
|
10
14
|
# Get MCP Server
|
|
15
|
+
{{#if hasGateway}}
|
|
16
|
+
mcp_servers = get_all_gateway_mcp_servers()
|
|
17
|
+
{{else}}
|
|
11
18
|
mcp_server = get_streamable_http_mcp_client()
|
|
19
|
+
mcp_servers = [mcp_server] if mcp_server else []
|
|
20
|
+
{{/if}}
|
|
12
21
|
|
|
13
22
|
_credentials_loaded = False
|
|
14
23
|
|
|
@@ -30,16 +39,47 @@ def add_numbers(a: int, b: int) -> int:
|
|
|
30
39
|
async def main(query):
|
|
31
40
|
ensure_credentials_loaded()
|
|
32
41
|
try:
|
|
33
|
-
|
|
34
|
-
|
|
42
|
+
{{#if hasGateway}}
|
|
43
|
+
if mcp_servers:
|
|
35
44
|
agent = Agent(
|
|
36
45
|
name="{{ name }}",
|
|
37
46
|
model="gpt-4.1",
|
|
38
|
-
mcp_servers=
|
|
47
|
+
mcp_servers=mcp_servers,
|
|
39
48
|
tools=[add_numbers]
|
|
40
49
|
)
|
|
41
50
|
result = await Runner.run(agent, query)
|
|
42
51
|
return result
|
|
52
|
+
else:
|
|
53
|
+
agent = Agent(
|
|
54
|
+
name="{{ name }}",
|
|
55
|
+
model="gpt-4.1",
|
|
56
|
+
mcp_servers=[],
|
|
57
|
+
tools=[add_numbers]
|
|
58
|
+
)
|
|
59
|
+
result = await Runner.run(agent, query)
|
|
60
|
+
return result
|
|
61
|
+
{{else}}
|
|
62
|
+
if mcp_servers:
|
|
63
|
+
async with mcp_servers[0] as server:
|
|
64
|
+
active_servers = [server]
|
|
65
|
+
agent = Agent(
|
|
66
|
+
name="{{ name }}",
|
|
67
|
+
model="gpt-4.1",
|
|
68
|
+
mcp_servers=active_servers,
|
|
69
|
+
tools=[add_numbers]
|
|
70
|
+
)
|
|
71
|
+
result = await Runner.run(agent, query)
|
|
72
|
+
return result
|
|
73
|
+
else:
|
|
74
|
+
agent = Agent(
|
|
75
|
+
name="{{ name }}",
|
|
76
|
+
model="gpt-4.1",
|
|
77
|
+
mcp_servers=[],
|
|
78
|
+
tools=[add_numbers]
|
|
79
|
+
)
|
|
80
|
+
result = await Runner.run(agent, query)
|
|
81
|
+
return result
|
|
82
|
+
{{/if}}
|
|
43
83
|
except Exception as e:
|
|
44
84
|
log.error(f"Error during agent execution: {e}", exc_info=True)
|
|
45
85
|
raise e
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
# Package marker
|
|
@@ -1,14 +1,65 @@
|
|
|
1
|
+
import os
|
|
2
|
+
import logging
|
|
1
3
|
from agents.mcp import MCPServerStreamableHttp
|
|
2
4
|
|
|
5
|
+
logger = logging.getLogger(__name__)
|
|
6
|
+
|
|
7
|
+
{{#if hasGateway}}
|
|
8
|
+
{{#if (includes gatewayAuthTypes "AWS_IAM")}}
|
|
9
|
+
import httpx
|
|
10
|
+
from mcp_proxy_for_aws.sigv4_helper import SigV4HTTPXAuth, create_aws_session
|
|
11
|
+
{{/if}}
|
|
12
|
+
{{#if (includes gatewayAuthTypes "CUSTOM_JWT")}}
|
|
13
|
+
from bedrock_agentcore.identity import requires_access_token
|
|
14
|
+
{{/if}}
|
|
15
|
+
|
|
16
|
+
{{#each gatewayProviders}}
|
|
17
|
+
{{#if (eq authType "CUSTOM_JWT")}}
|
|
18
|
+
@requires_access_token(
|
|
19
|
+
provider_name="{{credentialProviderName}}",
|
|
20
|
+
scopes=[{{#if scopes}}"{{scopes}}"{{/if}}],
|
|
21
|
+
auth_flow="M2M",
|
|
22
|
+
)
|
|
23
|
+
def _get_bearer_token_{{snakeCase name}}(*, access_token: str):
|
|
24
|
+
"""Obtain OAuth access token via AgentCore Identity for {{name}}."""
|
|
25
|
+
return access_token
|
|
26
|
+
|
|
27
|
+
{{/if}}
|
|
28
|
+
{{/each}}
|
|
29
|
+
|
|
30
|
+
def get_all_gateway_mcp_servers() -> list[MCPServerStreamableHttp]:
|
|
31
|
+
"""Returns MCP servers for all configured gateways."""
|
|
32
|
+
servers = []
|
|
33
|
+
{{#each gatewayProviders}}
|
|
34
|
+
url = os.environ.get("{{envVarName}}")
|
|
35
|
+
if url:
|
|
36
|
+
{{#if (eq authType "AWS_IAM")}}
|
|
37
|
+
session = create_aws_session()
|
|
38
|
+
auth = SigV4HTTPXAuth(session.get_credentials(), "bedrock-agentcore", session.region_name)
|
|
39
|
+
servers.append(MCPServerStreamableHttp(
|
|
40
|
+
name="{{name}}",
|
|
41
|
+
params={"url": url, "httpx_client_factory": lambda **kwargs: httpx.AsyncClient(auth=auth, **kwargs)}
|
|
42
|
+
))
|
|
43
|
+
{{else if (eq authType "CUSTOM_JWT")}}
|
|
44
|
+
token = _get_bearer_token_{{snakeCase name}}()
|
|
45
|
+
headers = {"Authorization": f"Bearer {token}"} if token else {}
|
|
46
|
+
servers.append(MCPServerStreamableHttp(name="{{name}}", params={"url": url, "headers": headers}))
|
|
47
|
+
{{else}}
|
|
48
|
+
servers.append(MCPServerStreamableHttp(name="{{name}}", params={"url": url}))
|
|
49
|
+
{{/if}}
|
|
50
|
+
else:
|
|
51
|
+
logger.warning("{{envVarName}} not set — {{name}} gateway tools unavailable")
|
|
52
|
+
{{/each}}
|
|
53
|
+
return servers
|
|
54
|
+
{{else}}
|
|
3
55
|
# ExaAI provides information about code through web searches, crawling and code context searches through their platform. Requires no authentication
|
|
4
56
|
EXAMPLE_MCP_ENDPOINT = "https://mcp.exa.ai/mcp"
|
|
5
57
|
|
|
6
58
|
|
|
7
59
|
def get_streamable_http_mcp_client() -> MCPServerStreamableHttp:
|
|
8
|
-
"""
|
|
9
|
-
Returns an MCP Client compatible with OpenAI Agents SDK.
|
|
10
|
-
"""
|
|
60
|
+
"""Returns an MCP Client compatible with OpenAI Agents SDK."""
|
|
11
61
|
# to use an MCP server that supports bearer authentication, add headers={"Authorization": f"Bearer {access_token}"}
|
|
12
62
|
return MCPServerStreamableHttp(
|
|
13
63
|
name="AgentCore Gateway MCP", params={"url": EXAMPLE_MCP_ENDPOINT}
|
|
14
64
|
)
|
|
65
|
+
{{/if}}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
# Package marker
|
|
@@ -13,6 +13,8 @@ dependencies = [
|
|
|
13
13
|
"openai-agents >= 0.4.2",
|
|
14
14
|
"bedrock-agentcore >= 1.0.3",
|
|
15
15
|
"botocore[crt] >= 1.35.0",
|
|
16
|
+
{{#if hasGateway}}{{#if (includes gatewayAuthTypes "AWS_IAM")}}"mcp-proxy-for-aws >= 1.1.0",
|
|
17
|
+
{{/if}}{{/if}}
|
|
16
18
|
]
|
|
17
19
|
|
|
18
20
|
[tool.hatch.build.targets.wheel]
|
|
@@ -1,26 +1,24 @@
|
|
|
1
|
-
This is a project generated by the
|
|
1
|
+
This is a project generated by the AgentCore CLI!
|
|
2
2
|
|
|
3
3
|
# Layout
|
|
4
4
|
|
|
5
|
-
|
|
6
|
-
|
|
5
|
+
The generated application code lives at the agent root directory. At the root, there is a `.gitignore` file, an
|
|
6
|
+
`agentcore/` folder which represents the configurations and state associated with this project. Other `agentcore`
|
|
7
7
|
commands like `deploy`, `dev`, and `invoke` rely on the configuration stored here.
|
|
8
8
|
|
|
9
|
-
##
|
|
9
|
+
## Agent Root
|
|
10
10
|
|
|
11
|
-
The main entrypoint to your app is defined in `
|
|
11
|
+
The main entrypoint to your app is defined in `main.py`. Using the AgentCore SDK `@app.entrypoint` decorator, this
|
|
12
12
|
file defines a Starlette ASGI app with the chosen Agent framework SDK running within.
|
|
13
13
|
|
|
14
|
-
`
|
|
14
|
+
`model/load.py` instantiates your chosen model provider.
|
|
15
15
|
|
|
16
16
|
## Environment Variables
|
|
17
17
|
|
|
18
|
-
| Variable
|
|
19
|
-
|
|
|
20
|
-
| `
|
|
21
|
-
| `
|
|
22
|
-
| `AGENTCORE_IDENTITY_GEMINI` | Yes (Gemini) | Gemini API key (local) or Identity provider name (deployed) |
|
|
23
|
-
| `LOCAL_DEV` | No | Set to `1` to use `agentcore/.env` instead of AgentCore Identity |
|
|
18
|
+
| Variable | Required | Description |
|
|
19
|
+
| --- | --- | --- |
|
|
20
|
+
{{#if hasIdentity}}| `{{identityProviders.[0].envVarName}}` | Yes | {{modelProvider}} API key (local) or Identity provider name (deployed) |
|
|
21
|
+
{{/if}}| `LOCAL_DEV` | No | Set to `1` to use `.env.local` instead of AgentCore Identity |
|
|
24
22
|
|
|
25
23
|
# Developing locally
|
|
26
24
|
|
|
@@ -1,7 +1,11 @@
|
|
|
1
1
|
from strands import Agent, tool
|
|
2
2
|
from bedrock_agentcore.runtime import BedrockAgentCoreApp
|
|
3
3
|
from model.load import load_model
|
|
4
|
+
{{#if hasGateway}}
|
|
5
|
+
from mcp_client.client import get_all_gateway_mcp_clients
|
|
6
|
+
{{else}}
|
|
4
7
|
from mcp_client.client import get_streamable_http_mcp_client
|
|
8
|
+
{{/if}}
|
|
5
9
|
{{#if hasMemory}}
|
|
6
10
|
from memory.session import get_memory_session_manager
|
|
7
11
|
{{/if}}
|
|
@@ -10,7 +14,11 @@ app = BedrockAgentCoreApp()
|
|
|
10
14
|
log = app.logger
|
|
11
15
|
|
|
12
16
|
# Define a Streamable HTTP MCP Client
|
|
13
|
-
|
|
17
|
+
{{#if hasGateway}}
|
|
18
|
+
mcp_clients = get_all_gateway_mcp_clients()
|
|
19
|
+
{{else}}
|
|
20
|
+
mcp_clients = [get_streamable_http_mcp_client()]
|
|
21
|
+
{{/if}}
|
|
14
22
|
|
|
15
23
|
# Define a collection of tools used by the model
|
|
16
24
|
tools = []
|
|
@@ -22,6 +30,11 @@ def add_numbers(a: int, b: int) -> int:
|
|
|
22
30
|
return a+b
|
|
23
31
|
tools.append(add_numbers)
|
|
24
32
|
|
|
33
|
+
# Add MCP client to tools if available
|
|
34
|
+
for mcp_client in mcp_clients:
|
|
35
|
+
if mcp_client:
|
|
36
|
+
tools.append(mcp_client)
|
|
37
|
+
|
|
25
38
|
|
|
26
39
|
{{#if hasMemory}}
|
|
27
40
|
def agent_factory():
|
|
@@ -36,7 +49,7 @@ def agent_factory():
|
|
|
36
49
|
system_prompt="""
|
|
37
50
|
You are a helpful assistant. Use tools when appropriate.
|
|
38
51
|
""",
|
|
39
|
-
tools=tools
|
|
52
|
+
tools=tools
|
|
40
53
|
)
|
|
41
54
|
return cache[key]
|
|
42
55
|
return get_or_create_agent
|
|
@@ -52,7 +65,7 @@ def get_or_create_agent():
|
|
|
52
65
|
system_prompt="""
|
|
53
66
|
You are a helpful assistant. Use tools when appropriate.
|
|
54
67
|
""",
|
|
55
|
-
tools=tools
|
|
68
|
+
tools=tools
|
|
56
69
|
)
|
|
57
70
|
return _agent
|
|
58
71
|
{{/if}}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
# Package marker
|
|
@@ -1,12 +1,64 @@
|
|
|
1
|
+
import os
|
|
2
|
+
import logging
|
|
1
3
|
from mcp.client.streamable_http import streamablehttp_client
|
|
2
4
|
from strands.tools.mcp.mcp_client import MCPClient
|
|
3
5
|
|
|
6
|
+
logger = logging.getLogger(__name__)
|
|
7
|
+
|
|
8
|
+
{{#if hasGateway}}
|
|
9
|
+
{{#if (includes gatewayAuthTypes "AWS_IAM")}}
|
|
10
|
+
from mcp_proxy_for_aws.client import aws_iam_streamablehttp_client
|
|
11
|
+
{{/if}}
|
|
12
|
+
{{#if (includes gatewayAuthTypes "CUSTOM_JWT")}}
|
|
13
|
+
from bedrock_agentcore.identity import requires_access_token
|
|
14
|
+
{{/if}}
|
|
15
|
+
|
|
16
|
+
{{#each gatewayProviders}}
|
|
17
|
+
{{#if (eq authType "CUSTOM_JWT")}}
|
|
18
|
+
@requires_access_token(
|
|
19
|
+
provider_name="{{credentialProviderName}}",
|
|
20
|
+
scopes=[{{#if scopes}}"{{scopes}}"{{/if}}],
|
|
21
|
+
auth_flow="M2M",
|
|
22
|
+
)
|
|
23
|
+
def _get_bearer_token_{{snakeCase name}}(*, access_token: str):
|
|
24
|
+
"""Obtain OAuth access token via AgentCore Identity for {{name}}."""
|
|
25
|
+
return access_token
|
|
26
|
+
|
|
27
|
+
{{/if}}
|
|
28
|
+
{{/each}}
|
|
29
|
+
{{#each gatewayProviders}}
|
|
30
|
+
def get_{{snakeCase name}}_mcp_client() -> MCPClient | None:
|
|
31
|
+
"""Returns an MCP Client connected to the {{name}} gateway."""
|
|
32
|
+
url = os.environ.get("{{envVarName}}")
|
|
33
|
+
if not url:
|
|
34
|
+
logger.warning("{{envVarName}} not set — {{name}} gateway tools unavailable")
|
|
35
|
+
return None
|
|
36
|
+
{{#if (eq authType "AWS_IAM")}}
|
|
37
|
+
return MCPClient(lambda: aws_iam_streamablehttp_client(url, aws_service="bedrock-agentcore", aws_region=os.environ.get("AWS_REGION", os.environ.get("AWS_DEFAULT_REGION"))))
|
|
38
|
+
{{else if (eq authType "CUSTOM_JWT")}}
|
|
39
|
+
token = _get_bearer_token_{{snakeCase name}}()
|
|
40
|
+
headers = {"Authorization": f"Bearer {token}"} if token else {}
|
|
41
|
+
return MCPClient(lambda: streamablehttp_client(url, headers=headers))
|
|
42
|
+
{{else}}
|
|
43
|
+
return MCPClient(lambda: streamablehttp_client(url))
|
|
44
|
+
{{/if}}
|
|
45
|
+
|
|
46
|
+
{{/each}}
|
|
47
|
+
def get_all_gateway_mcp_clients() -> list[MCPClient]:
|
|
48
|
+
"""Returns MCP clients for all configured gateways."""
|
|
49
|
+
clients = []
|
|
50
|
+
{{#each gatewayProviders}}
|
|
51
|
+
client = get_{{snakeCase name}}_mcp_client()
|
|
52
|
+
if client:
|
|
53
|
+
clients.append(client)
|
|
54
|
+
{{/each}}
|
|
55
|
+
return clients
|
|
56
|
+
{{else}}
|
|
4
57
|
# ExaAI provides information about code through web searches, crawling and code context searches through their platform. Requires no authentication
|
|
5
58
|
EXAMPLE_MCP_ENDPOINT = "https://mcp.exa.ai/mcp"
|
|
6
59
|
|
|
7
60
|
def get_streamable_http_mcp_client() -> MCPClient:
|
|
8
|
-
"""
|
|
9
|
-
Returns an MCP Client compatible with Strands
|
|
10
|
-
"""
|
|
61
|
+
"""Returns an MCP Client compatible with Strands"""
|
|
11
62
|
# to use an MCP server that supports bearer authentication, add headers={"Authorization": f"Bearer {access_token}"}
|
|
12
|
-
return MCPClient(lambda: streamablehttp_client(EXAMPLE_MCP_ENDPOINT))
|
|
63
|
+
return MCPClient(lambda: streamablehttp_client(EXAMPLE_MCP_ENDPOINT))
|
|
64
|
+
{{/if}}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
# Package marker
|
|
@@ -14,8 +14,11 @@ dependencies = [
|
|
|
14
14
|
"bedrock-agentcore >= 1.0.3",
|
|
15
15
|
"botocore[crt] >= 1.35.0",
|
|
16
16
|
{{#if (eq modelProvider "Gemini")}}"google-genai >= 1.0.0",
|
|
17
|
-
{{/if}}
|
|
17
|
+
{{/if}}"mcp >= 1.19.0",
|
|
18
|
+
{{#if (eq modelProvider "OpenAI")}}"openai >= 1.0.0",
|
|
18
19
|
{{/if}}"strands-agents >= 1.13.0",
|
|
20
|
+
{{#if hasGateway}}{{#if (includes gatewayAuthTypes "AWS_IAM")}}"mcp-proxy-for-aws >= 1.1.0",
|
|
21
|
+
{{/if}}{{/if}}
|
|
19
22
|
]
|
|
20
23
|
|
|
21
24
|
[tool.hatch.build.targets.wheel]
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
# Package marker
|