Skip to content

.NET: [Bug]: Bearer token claims inaccessible inside DurableAIAgentProxy when using MapAGUI #6064

@kpobb1989

Description

@kpobb1989

Description

When using MapAGUI with DurableAIAgentProxy, there is no supported way to pass HttpContext claims (extracted from a Bearer token) into the durable agent entity. MapAGUI creates and runs the session internally with no hook to inject claims into StateBag before the DTS signal is sent. Inside AgentEntity.Run(), HttpContext is no longer available — the entity runs in a background DTS context with no HTTP request scope.

Expected: whoAmI tool returns "OID: a1b2c3-..., Full name: John Doe from Bearer token" — the sub/oid claim extracted server-side from the validated Bearer token.

Actual: whoAmI tool returns "OID: NULL, Full name: NULL from Bearer token". By the time AgentEntity.Run() executes inside DTS, HttpContext is gone and claims are inaccessible.

Root cause:
HTTP request (After Bearer token validated)
→ MapAGUI creates session internally — no hook to inject claims
→ DurableAIAgentProxy.RunCoreAsync() sends RunRequest to DTS
→ RunRequest carries no caller identity
→ AgentEntity.Run() — HttpContext = null, claims = lost

Code Sample

using Microsoft.Agents.AI;
using Microsoft.Agents.AI.DurableTask;
using Microsoft.Agents.AI.Hosting.AGUI.AspNetCore;
using Microsoft.Extensions.AI;
using OpenAI;
using System.ClientModel;
using System.Security.Claims;

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddAGUI();
builder.Services.AddHttpContextAccessor();

// JWT auth middleware
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
    .AddJwtBearer(options =>
    {
        options.Authority = "http://localhost:8090/default";
        options.Audience  = "my-app";
        options.RequireHttpsMetadata = false;
    });
builder.Services.AddAuthorization();

IChatClient chatClient = new OpenAIClient(
    new ApiKeyCredential("ollama"),
    new OpenAIClientOptions { Endpoint = new Uri("http://localhost:11434/v1") })
    .GetChatClient("llama3.2")
    .AsIChatClient();

// Server-side tool reading userId from Bearer token claims
// Server-side tool reading userId and full name from Bearer token claims
AITool whoAmITool = AIFunctionFactory.Create(
    () =>
    {
        var session  = DurableAgentContext.Current.CurrentSession;

        // ❌ Always null — HttpContext is gone by the time DTS entity runs
        var oid      = session.StateBag.GetValue<string>("oid");
        var fullName = session.StateBag.GetValue<string>("fullName");

        return $"OID: {oid ?? "NULL"}, Full name: {fullName ?? "NULL"}";
    },
    name: "whoAmI",
    description: "Returns the authenticated user's OID and full name from their Bearer token");

AIAgent agent = chatClient.AsAIAgent(
    name: "TestAgent",
    instructions: "Always call the whoAmI tool when the user asks who they are.",
    tools: [whoAmITool]);

builder.Services.ConfigureDurableAgents(
    options => options.AddAIAgent(agent),
    workerBuilder: b => b.UseDurableTaskScheduler(
        "Endpoint=http://localhost:8080;TaskHub=default;Authentication=None"),
    clientBuilder: b => b.UseDurableTaskScheduler(
        "Endpoint=http://localhost:8080;TaskHub=default;Authentication=None"));

var app = builder.Build();

app.UseAuthentication();
app.UseAuthorization();

AIAgent durableAgent = agent.AsDurableAgentProxy(app.Services);

// RequireAuthorization validates the Bearer token — claims ARE available here
// but MapAGUI gives no hook to pass them into the durable session
app.MapAGUI("/chat", durableAgent).RequireAuthorization();

await app.RunAsync();

Error Messages / Stack Traces

Package Versions

Microsoft.Agents.AI: 1.6.2, Microsoft.Agents.AI.Hosting.AGUI.AspNetCore: 1.6.2-preview.260521.1, Microsoft.Agents.AI.DurableTask: 1.6.2-preview.260521.1

.NET Version

.NET 10

Additional Context

Related bugs: #6061, #6063

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No fields configured for Bug.

    Projects

    Status

    No status

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions