What happened
For a new user with no existing memories, the first user-summary run can fail because it starts at the same time as fact extraction.
At the 20-turn threshold, the change-feed handler starts ExtractMemoriesOrchestrator and UserSummaryOrchestrator independently. The user-summary activity retries three times with a two-second initial interval. If extraction has not persisted any facts yet, all attempts fail with:
ValidationError: No memories found for user_id='repro-user'
Extraction can then complete successfully, but the failed user summary is not retried automatically.
Why this matters
The first consolidated user profile can be missing even though turn ingestion and fact extraction both succeed. It requires an operator retry or waiting until a later summary threshold.
Reproduction
Use a Function app and toolkit built from the same current source revision (the separate package-pin problem is tracked in #39), then use a new user and thread with no existing memory records.
Write 20 turns quickly to memories_turns. With a configured async client, the write portion is:
for index in range(20):
await client.upsert_memory(
user_id="repro-user",
thread_id="repro-thread",
role="user" if index % 2 == 0 else "agent",
content=f"Reproduction turn {index}",
memory_type="turn",
embed=False,
)
Run the client with MEMORY_PROCESSOR_OWNER=durable so the change-feed Function owns processing. Then inspect these two Durable instances:
extract:repro-user:repro-thread:20
user_summary:repro-user:20
In a live reproduction:
- Both orchestrations started in the same second.
UserSummaryOrchestrator failed after its short retry window with No memories found.
ExtractMemoriesOrchestrator completed about 21 seconds after it started and persisted facts.
- Starting
UserSummaryOrchestrator again after extraction completed succeeded immediately.
The current source still schedules the two orchestrations independently in function_app/triggers/change_feed.py. UserSummaryOrchestrator uses the shared retry policy of three attempts with a two-second initial interval.
Expected behavior
When the user-summary threshold is crossed, the summary should eventually be produced without manual intervention, even when extraction takes longer than the activity retry window.
Suggested resolution
Coordinate user-summary generation with successful memory persistence, or add a bounded Durable wait/retry specifically for the expected "no memories yet" condition. A regression test should delay extraction beyond the current retry window and confirm that the user summary still completes.
What happened
For a new user with no existing memories, the first user-summary run can fail because it starts at the same time as fact extraction.
At the 20-turn threshold, the change-feed handler starts
ExtractMemoriesOrchestratorandUserSummaryOrchestratorindependently. The user-summary activity retries three times with a two-second initial interval. If extraction has not persisted any facts yet, all attempts fail with:Extraction can then complete successfully, but the failed user summary is not retried automatically.
Why this matters
The first consolidated user profile can be missing even though turn ingestion and fact extraction both succeed. It requires an operator retry or waiting until a later summary threshold.
Reproduction
Use a Function app and toolkit built from the same current source revision (the separate package-pin problem is tracked in #39), then use a new user and thread with no existing memory records.
Write 20 turns quickly to
memories_turns. With a configured async client, the write portion is:Run the client with
MEMORY_PROCESSOR_OWNER=durableso the change-feed Function owns processing. Then inspect these two Durable instances:In a live reproduction:
UserSummaryOrchestratorfailed after its short retry window withNo memories found.ExtractMemoriesOrchestratorcompleted about 21 seconds after it started and persisted facts.UserSummaryOrchestratoragain after extraction completed succeeded immediately.The current source still schedules the two orchestrations independently in
function_app/triggers/change_feed.py.UserSummaryOrchestratoruses the shared retry policy of three attempts with a two-second initial interval.Expected behavior
When the user-summary threshold is crossed, the summary should eventually be produced without manual intervention, even when extraction takes longer than the activity retry window.
Suggested resolution
Coordinate user-summary generation with successful memory persistence, or add a bounded Durable wait/retry specifically for the expected "no memories yet" condition. A regression test should delay extraction beyond the current retry window and confirm that the user summary still completes.