![[Update] IAM authentication is now available for MCP Server targets in Amazon Bedrock AgentCore Gateway](https://images.ctfassets.net/ct0aopd36mqt/7M0d5bjsd0K4Et30cVFvB6/5b2095750cc8bf73f04f63ed0d4b3546/AgentCore2.png?w=3840&fm=webp)
[Update] IAM authentication is now available for MCP Server targets in Amazon Bedrock AgentCore Gateway
This page has been translated by machine translation. View original
Introduction
Hello, I'm Jinno from the Consulting Department, and I'm a big fan of cheese naan.
Previously, I introduced a configuration where AgentCore Gateway's Target is set to an MCP Server deployed on AgentCore Runtime.
In that article, I used Cognito M2M (Client Credentials) for Gateway→Runtime (MCP Server) Outbound authentication.
While it worked perfectly fine, I felt it was a bit cumbersome to use Cognito for communication between AWS resources.
Recently, GATEWAY_IAM_ROLE has been added as an Outbound authentication option for Gateway Target with MCP Server targets!
Now we can directly call Runtime with SigV4 signatures using the Gateway's IAM role, making integration much easier! That's great!
In this article, I'll test whether we can directly call MCP tools on AgentCore Runtime from Claude Code using this configuration!
Prerequisites
- AWS account (verified in us-east-1 region)
- Terraform v1.14.4 + AWS Provider v6.39.0
- Python 3.13 (for MCP Server code)
- Docker v29.1.5 (for ARM64 image building)
- Claude Code v2.1.84
- uv v0.9.26 (used to run mcp-proxy-for-aws v1.1.6)
Architecture
The overall architecture is as follows:

It's nicely simple with just IAM. (Previously, we had to use Cognito as an intermediary...)
From the client's Claude Code, we connect to the Gateway as an MCP Server using MCP Proxy for AWS.
Implementation
MCP Server Implementation
The MCP Server code is the same as in the previous article. Using FastMCP 3.2.3, I implemented three tools: addition, multiplication, and greeting.
from fastmcp import FastMCP
mcp = FastMCP("sample-tools")
@mcp.tool()
def add_numbers(a: int, b: int) -> int:
"""2つの数字を足し算します"""
return a + b
@mcp.tool()
def multiply_numbers(a: int, b: int) -> int:
"""2つの数字を掛け算します"""
return a * b
@mcp.tool()
def greet_user(name: str) -> str:
"""ユーザーに挨拶します"""
return f"Hello, {name}! Welcome to AgentCore Runtime."
if __name__ == "__main__":
mcp.run()
Functions with the @mcp.tool() decorator are published as MCP tools. The docstring becomes the tool's description, which helps the agent decide which tool to call.
Next is the Dockerfile for the container image. Since AgentCore Runtime runs on ARM64 architecture, we specify --platform linux/arm64 during the build (this is done in Terraform).
FROM public.ecr.aws/docker/library/python:3.12-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
COPY mcp_server.py .
CMD ["python", "mcp_server.py"]
This is a simple configuration that uses Python 3.12 slim image as the base, installs dependency packages, and starts the MCP Server.
The only dependency package is fastmcp.
fastmcp
Deploying Runtime + Gateway with Terraform
Using Terraform, we'll create Runtime, ECR, IAM roles, and Gateway. We'll set up the Gateway Target in the console.
For the complete Terraform code, please refer to the GitHub repository.
Here, I'll focus on explaining the important points from an IAM authentication perspective.
IAM Role Design
In this IAM configuration, three permissions appear.
| Permission | Who | To What | Purpose |
|---|---|---|---|
bedrock-agentcore:InvokeGateway |
Caller (Claude Code user) | Gateway | Inbound: To pass Gateway IAM authentication |
bedrock-agentcore:InvokeAgentRuntime |
Gateway IAM role | Runtime | Outbound: For Gateway to call Runtime |
ecr:BatchGetImage etc. |
Runtime IAM role | ECR repository | For Runtime to pull container images |
In Terraform, they're defined as follows:
# Policy for Gateway to call Runtime
resource "aws_iam_role_policy" "gateway_invoke_runtime" {
name = "${var.project_name}-gateway-invoke-runtime-policy"
role = aws_iam_role.gateway.id
policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Sid = "InvokeAgentRuntime"
Effect = "Allow"
Action = "bedrock-agentcore:InvokeAgentRuntime"
Resource = "${aws_bedrockagentcore_agent_runtime.mcp_server.agent_runtime_arn}*"
}]
})
}
The only permission needed for the Gateway role is InvokeAgentRuntime. We add * at the end of Resource because the actual access destination is a subresource like runtime/xxx/runtime-endpoint/DEFAULT.
Gateway Configuration
The Gateway definition is simple. We specify AWS_IAM for authorizer_type.
resource "aws_bedrockagentcore_gateway" "main" {
name = "${var.project_name}-gateway-${random_string.suffix.result}"
description = "AgentCore Gateway with IAM inbound authentication"
role_arn = aws_iam_role.gateway.arn
authorizer_type = "AWS_IAM"
protocol_type = "MCP"
}
Deployment
Run the terraform apply command to deploy.
terraform init
terraform apply
# When asked if you want to apply, select yes
After apply completes, the following Output is displayed.
gateway_id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
gateway_url = "https://xxxxxxxx.gateway.bedrock-agentcore.us-east-1.amazonaws.com"
runtime_arn_url_encoded = "https://bedrock-agentcore.us-east-1.amazonaws.com/runtimes/arn%3Aaws%3A.../invocations"
gateway_url will be used in the Gateway Target configuration and .mcp.json. runtime_arn_url_encoded will be used as the Endpoint for Gateway Target.
Creating a Gateway Target in the Console (IAM Authentication)
Once the Gateway is created, add Runtime as a Target.
Opening the Gateway details screen confirms that the Inbound Auth type is "IAM permissions". Click "Add" for targets.

Enter the following and click "Add target":
- Target type:
MCP server - MCP endpoint: Enter the
runtime_arn_url_encodedfrom Terraform output - Outbound authentication configuration: Select
IAM role - Service:
bedrock-agentcore

When the Target status becomes Ready, it's complete. You can also confirm that the Outbound Auth configurations is "IAM roles".

Note that Outbound IAM authentication (SigV4) is only available with MCP servers behind AWS services that can verify SigV4 signatures. These include AgentCore Runtime, AgentCore Gateway, API Gateway, and Lambda Function URLs. It cannot be used with MCP servers on ALB or EC2, so be aware of this limitation.
Setting Caller IAM Permissions
Since Gateway Inbound authentication is AWS_IAM, we need to grant InvokeGateway permission to the IAM entity used by Claude Code (mcp-proxy-for-aws). Without this permission, access to the Gateway will be denied.
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "AllowGatewayInvocation",
"Effect": "Allow",
"Action": "bedrock-agentcore:InvokeGateway",
"Resource": "arn:aws:bedrock-agentcore:us-east-1:<ACCOUNT_ID>:gateway/<GATEWAY_ID>"
}
]
}
Attach this policy to the IAM user or role linked to your local AWS profile. You can confirm <GATEWAY_ID> from the Terraform output gateway_id. While it's possible to use wildcards for Resource, it's recommended to narrow it down to specific Gateway ARNs for security reasons.
Connection Settings from Claude Code
What is MCP Proxy for AWS?
MCP Proxy for AWS is an official AWS open-source tool. MCP clients like Claude Code don't natively support SigV4 signatures. This proxy automatically adds SigV4 signatures to MCP requests using local AWS credentials (~/.aws/credentials or environment variables) and forwards them to the Gateway.
It can be directly configured in Claude Code's .mcp.json.
.mcp.json Configuration
Create a .mcp.json file in the project root.
{
"mcpServers": {
"agentcore-gateway": {
"command": "uvx",
"args": [
"mcp-proxy-for-aws@latest",
"https://<GATEWAY_ID>.gateway.bedrock-agentcore.us-east-1.amazonaws.com/mcp",
"--service", "bedrock-agentcore",
"--region", "us-east-1"
]
}
}
}
Replace <GATEWAY_ID> with the value of gateway_id from the Terraform output. --service bedrock-agentcore is the service name for SigV4 signature, and --region is the region for signing.
If you want to add it directly from Claude Code, you can use the following command:
claude mcp add --transport stdio agentcore-gateway -- \
uvx mcp-proxy-for-aws@latest \
"https://<GATEWAY_ID>.gateway.bedrock-agentcore.us-east-1.amazonaws.com/mcp" \
--service bedrock-agentcore \
--region us-east-1
Operation Check
When you start Claude Code, mcp-proxy-for-aws starts as a stdio process, establishing a SigV4-signed connection to the Gateway. MCP Server tools are automatically loaded.
First, to check if the connection is established, run /mcp.
When the connection to the MCP Server is established, you'll see connected.

Checking the tool list shows that the three tools on Runtime are recognized.

Let's try calling a tool. When I enter "Use the addition tool to add 3123 + 31341234", Claude Code calls the add_numbers tool.

And the result comes back!

We successfully called an MCP tool on Runtime from Claude Code via AgentCore Gateway. That was easy!
Conclusion
I tried out an IAM authentication configuration combining AgentCore Gateway's Outbound IAM authentication support with MCP Proxy for AWS!
I think this is a good approach for use cases where you want to unify with IAM authentication, such as for internal tools or within AWS accounts. It's a good update since I previously found it cumbersome to call an MCP Server deployed on Runtime via Gateway!
I used to avoid deploying MCP Servers on Runtime and linking them to Gateway because I didn't want to add Cognito in between, but now I'd like to actively use this approach.
I hope this article has been helpful. Thank you for reading to the end!