Summary
MapAGUI in Microsoft.Agents.AI.Hosting.AGUI.AspNetCore passes thread: null to AIAgent.RunStreamingAsync(), which means the agent's ChatMessageStoreFactory configuration is not properly utilized for thread persistence across requests.
Current Behavior
Looking at AGUIEndpointRouteBuilderExtensions.cs:
var events = aiAgent.RunStreamingAsync(
messages,
options: runOptions, // <-- No thread parameter passed (defaults to null)
cancellationToken: cancellationToken)
When thread is null, ChatClientAgent calls GetNewThread() which creates a new ChatClientAgentThread with a new ChatMessageStore instance for every single request.
The AG-UI thread ID is passed via ChatOptions.AdditionalProperties[\"ag_ui_thread_id\"], but since no AgentThread is passed, each request:
- Creates a brand new thread
- Creates a brand new
ChatMessageStore via ChatMessageStoreFactory
- The
ChatMessageStore has no way to correlate with the AG-UI thread ID until AddMessagesAsync is called (after the factory)
Expected Behavior
MapAGUI should support server-side thread persistence so that:
- If an agent has a
ChatMessageStoreFactory configured, it should be used to restore/persist conversation history per AG-UI thread ID
- The
ChatMessageStore should be created with knowledge of the AG-UI thread ID upfront
- On subsequent requests with the same
ag_ui_thread_id, the same logical thread/store should be used
Workaround
Currently, developers must use ambient context (AsyncLocal) to pass the AG-UI thread ID from middleware to the ChatMessageStore, and manually manage thread storage outside of the Agent Framework's normal patterns:
// In middleware before agent runs:
CurrentThreadContext.ThreadId = ExtractThreadIdFromOptions(options);
// In ChatMessageStoreFactory:
ChatMessageStoreFactory = ctx => new CustomChatMessageStore(
threadStore,
CurrentThreadContext.ThreadId, // Read from ambient context
ctx.SerializedState
)
This is fragile and requires duplicating message storage logic outside of the normal Agent Framework patterns.
Related Issues
Environment
- Package:
Microsoft.Agents.AI.Hosting.AGUI.AspNetCore
Summary
MapAGUIinMicrosoft.Agents.AI.Hosting.AGUI.AspNetCorepassesthread: nulltoAIAgent.RunStreamingAsync(), which means the agent'sChatMessageStoreFactoryconfiguration is not properly utilized for thread persistence across requests.Current Behavior
Looking at
AGUIEndpointRouteBuilderExtensions.cs:When
threadisnull,ChatClientAgentcallsGetNewThread()which creates a newChatClientAgentThreadwith a newChatMessageStoreinstance for every single request.The AG-UI thread ID is passed via
ChatOptions.AdditionalProperties[\"ag_ui_thread_id\"], but since noAgentThreadis passed, each request:ChatMessageStoreviaChatMessageStoreFactoryChatMessageStorehas no way to correlate with the AG-UI thread ID untilAddMessagesAsyncis called (after the factory)Expected Behavior
MapAGUIshould support server-side thread persistence so that:ChatMessageStoreFactoryconfigured, it should be used to restore/persist conversation history per AG-UI thread IDChatMessageStoreshould be created with knowledge of the AG-UI thread ID upfrontag_ui_thread_id, the same logical thread/store should be usedWorkaround
Currently, developers must use ambient context (
AsyncLocal) to pass the AG-UI thread ID from middleware to theChatMessageStore, and manually manage thread storage outside of the Agent Framework's normal patterns:This is fragile and requires duplicating message storage logic outside of the normal Agent Framework patterns.
Related Issues
Environment
Microsoft.Agents.AI.Hosting.AGUI.AspNetCore