The agent is not the user: Using Amazon Bedrock AgentCore with Okta to secure AI agent identity

Modeling the identity boundary correctly helps verify that every tool call carries the identity of the person who initiated it.

About the Author

02 octubre 2026 Time to read: ~

Executive summary

Amazon Bedrock AgentCore validates inbound user authentication but defaults outbound tool calls to the agent's own principal. Integrating Okta Cross-App Access (XAA) and the Identity Assertion Authorization Grant (ID-JAG) bridges this gap by exchanging the user's OIDC token for a short-lived, scoped OAuth 2.0 access token that carries both user attribution and agent identity across tool hops.

Amazon Bedrock AgentCore is an agentic platform for building, deploying, and operating AI agents securely at scale. It works with any framework and foundation model. Its modular services cover the runtime, memory, tool connectivity, identity, policy, and observability, so you can move agents into production without managing infrastructure.

AgentCore helps you move agents from prototype to production quickly, but the harder question comes next: When this agent queries the HR system, whose authority is it using?

The honest answer, for most first deployments, is the agent's own. And that answer does not survive a security review because of how agent runtimes handle identity. AgentCore will authenticate the inbound user. It will not, on its own, carry that user's authority outbound to the tools the agent decides to call.

This article explains how Okta for AI Agents closes the gap using a brand-new authorization framework designed to handle multiple trust domains an agent will travel through. We will look at two patterns, both grounded in Cross-App Access and the Identity Assertion Authorization Grant, and perform a quick walkthrough of what actually lands in the token at each hop.

The identity gap in agent runtimes

Architecture diagram titled "System architecture diagram for agent runtime" illustrating an identity gap between Okta user authorization and MCP authorization across an AgentCore runtime.

AgentCore helps developers build and deploy agents quickly, however a critical identity gap occurs during outbound tool execution: 

  • Inbound authentication: AgentCore accepts an inbound JSON Web Token (JWT) issued by an OpenID Connect (OIDC) identity provider. Configure AgentCore to validate the incoming user token from Okta. AgentCore validates the token, and the agent starts working. The gap is on the way out when the agent attempts to access a downstream resource. 
  • Outbound authorization gap: When the agent invokes an MCP tool exposed by the Agentcore gateway, it does so in the context of its own principal and ignores the incoming upstream user authentication context. You can pass the user's token through to the downstream resource, but that isn't the same as presenting a scoped token with proper user attribution to a specific target resource. The identity story disconnects at exactly the hop where least privilege matters most.

Why simple token forwarding fails

Forwarding a user’s original OIDC token downstream breaks security boundaries and introduces major authorization gaps:

  • AgentCore attribution: Inbound authentication and outbound authorization are separate problems, and the runtime solves only the first one. Outbound calls carry the agent's principal unless you configure deliberate delegation.
  • Runtime boundaries: AgentCore Runtime hands your agent an invocation payload and forwards it to the entry point. It does not perform an Okta token exchange. That's your application code’s job.
  • Protected MCP server expectations: An MCP server that mirrors an internal API expects a modern authorization assertion—such as an OAuth 2.0 bearer token issued for a defined audience by an authorization server it trusts, validated at the resource. 
  • User token limitations: This one is often overlooked. The user's OIDC token was issued in the context of the web application's client. It is a statement to the application about who signed in, not a bearer credential for a separate resource server. Forwarding it downstream means the MCP server accepts a token minted for a different audience. A user token alone cannot grant access to a protected MCP resource, and a resource server that accepts one has stopped enforcing a boundary.

So the agent needs a token it doesn't have and can't mint. The MCP server trusts a different authorization server. Okta bridges these two trust domains (the user authorization server and the MCP authorization server) while preserving user attribution in the request.

How Cross-App Access and ID-JAG solve agent delegation

Okta Cross-App Access (XAA) lets an AI agent exchange a subject token for an ID-JAG token (identity assertion authorization grant, per the IETF Identity Assertion Authorization Grant draft). The grant serves as the bridge. It carries the user's identity across an authorization server boundary without handing the agent user credentials or a broadly scoped token.

Diagram illustrating the Okta identity provider access flow for cross-app agent delegation.

Rather than impersonating the user, the agent uses a two-step delegation process:

  1. The ID-JAG step: The agent presents the user's authentication token as the subject token and authenticates itself using its own credentials. Okta binds the user's identity to the agent's workload context, scoped to the target resource authorization server's audience. This produces a short-lived, one-time-use ID-JAG token.
  2. The token exchange step: The ID-JAG token is exchanged at the target authorization server for an access token, which the MCP server validates against the issuer, audience, and scopes.

Two steps, two distinct claims: The first proves the user authorized the agent to act toward the resource. The second provides a narrow credential valid only for that audience and scope. Neither step allows the agent to widen its reach, because the agent doesn’t mint its own authority. Instead, it asks Okta, and Okta responds based on the defined policy.

This marks the critical difference between impersonation and delegation. An impersonating agent presents the user's token and disappears from audit logs. A delegated agent presents a token naming both parties: the user and the agent. Moreover, it carries the complete delegation chain within the ID-JAG token. When audit questions arise regarding who acted and under whose authority, the token answers directly without requiring manual log reconstruction.

The agent as a first-class identity in Okta

Before either pattern works, the agent must exist in Okta as a governable identity. Okta models an agent as an identity with an owner, credentials, and resource access policies.

Okta can import agents automatically from AgentCore using an AWS application configured from the Okta Integration Network. From there, each agent is configured as a governed principal. By positioning Okta as the corporate identity registry for lifecycle governance and accountability alongside AgentCore for runtime authentication to AWS services, organizations can respect technical boundaries while establishing a unified security model.

An agent whose authority is solely a set of AWS credentials in a container image has no off-switch short of redeployment. An agent registered in Okta with declared resource connections can be revoked instantly without searching for copied keys.

On the resource side, the target MCP server sits behind a custom authorization server with preconfigured scopes and an access policy permitting the configured agent access.

Dashboard screenshot showing Resource Connections settings for an AI agent in Okta.

Pattern A: Running XAA directly inside the agent

This is the simplest topology where the pro-code agent performs the exchange itself. It leverages the Okta SDK to issue tokens from Okta during a tool call.

Sequence diagram showing the Okta user authentication flow with AWS Bedrock AgentCore and downstream Resource Applications.
  1. Inbound request: The web application handles OIDC sign-in, gets the id_token, and invokes AgentCore Runtime with the prompt and the token in the invocation payload. The runtime forwards that payload to the agent's entry point. 
  2. Token exchange: The agent extracts the id_token, runs Cross-App Access against the resource authorization server, and receives an access token.
  3. Tool execution: The agent then calls the MCP server that’s supplying the resource access token. The MCP server validates the token against its authorization server and returns results.

The advantage: Fewer moving parts. The agent controls the flow inside its own container.

See our technical guide on how to secure an Amazon Bedrock AgentCore agent. You can also explore the Okta XAA + AgentCore sample on GitHub for a complete reference implementation.

Pattern B: Enforcing XAA using a AWS Lambda interceptor at AgentCore Gateway

The second pattern moves the exchange outside the agent. The AgentCore Gateway with a AWS Lambda interceptor provides a centralized control point for securing AI agent access to MCP servers and other OAuth-enabled resources. 

  1. Tool invocation request: MCP tools are exposed through the AgentCore Gateway, which acts as the entry point for agent requests and enforces security controls before requests reach the protected resources.
  2. Identity interception: The AWS Lambda interceptor processes incoming requests and validates the identity context. 
  3. Token exchange logic: The interceptor applies the required XAA authorization logic and transforms the agent identity context and request metadata into the required OAuth 2.0 bearer token format. 
  4. Upstream forwarding: The interceptor forwards authenticated requests to the target MCP server through the AgentCore Gateway.

This pattern enables centralized authorization enforcement and consistent identity propagation across agent-to-resource interactions while maintaining secure access controls throughout the request lifecycle.

The high-level flow for this pattern is shown below. To see this workflow in action, explore Okta XAA delegation chain + AgentCore sample on GitHub.

Architecture diagram showing the OAuth2 cross-app access token exchange flow for AWS Bedrock AgentCore using a Lambda Interceptor and Okta AuthZ Server.

Here, the agent does not implement XAA logic directly. Its only requirement is a header contract: send the user's token in an allowlisted header on the MCP request to the AgentCore Gateway. 

The AWS Lambda interceptor attached to the gateway reads the header, executes the XAA (ID-JAG) exchange on behalf of the calling agent, and forwards the request to the target MCP resource with a scoped, short-lived access token that carries the delegation chain with both user and agent attribution.

The advantage: The agent container image holds no agent credentials or key material. Token exchange policies live in one auditable location without requiring agent redeployments.

API gateway sequence diagram showing token exchange between a Web App, Okta, AgentCore, Interceptor Lambda, and Target Resource.

Architecture comparison: Pattern A vs. Pattern B

Pattern A: Direct MCP, in-agent XAA

Pattern B: Gateway + interceptor

Network path

Agent → MCP over HTTPS

Agent → Gateway → Lambda → MCP

XAA execution location

Inside the AgentCore agent

Inside the AWS Lambda interceptor

Bearer token presenter

The agent

The AWS Lambda interceptor

Okta SDK in the agent?

Yes

No

Gateway/Lambda required?

No

Yes

Key material storage

In the agent runtime

In AWS Secrets Manager, accessible only to the AWS Lambda function

Typical use case

Minimal AWS footprint, few agents

Centralized authorization control, many agents

Network path

Agent → MCP over HTTPS

XAA execution location

Inside the AgentCore agent

Bearer token presenter

The agent

Okta SDK in the agent?

Yes

Gateway/Lambda required?

No

Key material storage

In the agent runtime

Typical use case

Minimal AWS footprint, few agents

The trade-off is between centralization and deployment simplicity. For one or two agents owned by the team that wrote them, Pattern A is simple and quick. For a growing agent fleet where security teams need centralized authorization control, Pattern B provides unified management that scales; the extra components pay for themselves as you onboard more agents.

Both patterns land in the same place at the resource. The MCP server validates a token from an authorization server it trusts, scoped to its own audience, that carries the user and agent contexts and an associated chain of custody. What differs is who performs the exchange, not what authorization control is in place for the resource.

Token payload breakdown: What claims does the resource see?

The ultimate outcome is the token payload delivered to the MCP server. Consider an HR business partner asking an agent to list employee records, and follow the claims:

  1. Initial user token from the Okta authorization server after sign-in

{
  "iss": "https://acme.okta.com",        
  "aud": "0oa4h9...",                    
  "sub": "priya@acme.com",               
  "exp": 1789231200
}

Status: This authenticates the user to the application, but is insufficient for the MCP server: wrong audience, wrong issuer, and no scopes.

  1. ID-JAG assertion token issued with XAA

{
   "iss": "https://acme.okta.com",                         
   "aud": "https://acme.okta.com/oauth2/aus7k2...",      
   "sub": "00uun....",                    // user id   
   "client_id": "wlpoa8x...",           // agent workload principal
   "scope": "mcp:read",
   "act": { "sub": "wlpoa8x..." }                                   
}

Status: Both the user and the agent are named, and the assertion is addressed specifically to the target authorization server. It is not a bearer token for the MCP server—it's the grant used to retrieve one.

  1. After the token exchange, the agent or adapter presents the final MCP access token to the MCP resource

{
  "iss": "https://acme.okta.com/oauth2/aus7k2...", // issuer the MCP server trusts
  "aud": "api://agentcore-hr-mcp",             // resource audience
  "sub": "priya@acme.com",                     // user identity
  "cid": "wlpoa8x...",                         // agent identity
  "act": { "sub": "wlpoa8x..." },              // delegation chain
  "scp": ["mcp:read"],                                 
  "exp": 1789227900                          // configurable expiry          
}

Status: Now the resource can validate everything directly from the token: which agent called (cid), on whose authority (sub), with a detailed delegation chain (act), and what it’s permitted to do (scp).

If a malicious prompt convinces the agent to update salary records, the request remains constrained by a token scoped to read operation. The model may attempt the request, but it cannot hold a credential it was never issued.

Securing the future of agentic scale

As AI agents become part of core enterprise infrastructure, identity is no longer an afterthought—it’s the foundational boundary for security and compliance. By leveraging Okta for AI Agents integrated with Amazon Bedrock AgentCore, you eliminate the risks of agent sprawl and over-privileged credentials without sacrificing velocity. The XAA and ID-JAG framework ensures that every downstream tool invocation carries verified human intent, strict audience scoping, and complete auditability. Okta writes the identity authorization decision to its own audit logs, while AgentCore writes the tool-call execution decision to Amazon CloudWatch, providing a queryable audit record across both the corporate and runtime layers.

Implementing this identity-first architecture with Okta for AI Agents enables your team to safely deploy autonomous workflows at scale, giving you the control to innovate quickly while remaining compliant. 

Ready to bring runtime governance to your AI workforce? Download our solution brief to learn how Okta for AI Agents and Amazon Bedrock eliminate identity sprawl and enforce agent lifecycle governance across your enterprise.

About the Author

Continue your Identity journey