Fix draft agent handoff continuity

Move optimistic user message reconciliation into the stream reducers and keep draft-created agents in a handoff lifecycle until authoritative history lands.
This commit is contained in:
Mohamed Boudra
2026-05-25 20:53:49 +07:00
parent e5658654c0
commit 53faba64ca
21 changed files with 677 additions and 458 deletions
+14 -1
View File
@@ -4,7 +4,7 @@ import type { AgentAttachment } from "@server/shared/messages";
export type CreateFlowLifecycleState = "active" | "abandoned" | "sent";
interface PendingCreateAttempt {
export interface PendingCreateAttempt {
draftId: string;
serverId: string;
agentId: string | null;
@@ -23,6 +23,7 @@ interface CreateFlowState {
markLifecycle: (input: { draftId: string; lifecycle: CreateFlowLifecycleState }) => void;
rekeyDraft: (input: { fromDraftId: string; toDraftId: string }) => void;
clear: (input: { draftId: string }) => void;
clearByAgent: (input: { serverId: string; agentId: string }) => void;
clearAll: () => void;
}
@@ -89,5 +90,17 @@ export const useCreateFlowStore = create<CreateFlowState>((set) => ({
const { [draftId]: _removed, ...rest } = state.pendingByDraftId;
return { pendingByDraftId: rest };
}),
clearByAgent: ({ serverId, agentId }) =>
set((state) => {
const next = Object.fromEntries(
Object.entries(state.pendingByDraftId).filter(
([, pending]) => pending.serverId !== serverId || pending.agentId !== agentId,
),
);
if (Object.keys(next).length === Object.keys(state.pendingByDraftId).length) {
return state;
}
return { pendingByDraftId: next };
}),
clearAll: () => set({ pendingByDraftId: {} }),
}));