fix(chat): avoid overwriting user messages on unlock

This commit is contained in:
2026-07-01 10:22:11 +08:00
parent 5d9ed7e027
commit 9c45c7eb69
2 changed files with 77 additions and 1 deletions
@@ -529,6 +529,71 @@ describe("chatMachine transitions", () => {
actor.stop();
});
it("does not overwrite a user message when it shares the private message id", async () => {
const actor = createActor(
createTestChatMachine({
historyMessages: [
{
id: "msg-shared-id",
content: "User original question",
isFromAI: false,
date: "2026-06-29",
},
{
id: "msg-shared-id",
content: "",
isFromAI: true,
date: "2026-06-29",
locked: true,
lockReason: "private_message",
lockedPrivate: true,
privateMessageHint: "A private message is waiting.",
},
],
unlockMessageOutput: {
messageId: "msg-shared-id",
response: makeUnlockPrivateResponse({
content: "This is the unlocked private message.",
}),
},
}),
).start();
actor.send({ type: "ChatUserLogin", token: "token" });
await waitFor(actor, (snapshot) =>
snapshot.matches({ userSession: "ready" }),
);
actor.send({
type: "ChatUnlockMessageRequested",
messageId: "msg-shared-id",
kind: "private",
});
await waitFor(actor, (snapshot) =>
snapshot.matches({ userSession: "ready" }),
);
expect(actor.getSnapshot().context.messages).toMatchObject([
{
id: "msg-shared-id",
content: "User original question",
isFromAI: false,
},
{
id: "msg-shared-id",
content: "This is the unlocked private message.",
isFromAI: true,
locked: false,
lockReason: null,
lockedPrivate: false,
privateMessageHint: null,
},
]);
actor.stop();
});
it("requests payment when single message unlock lacks credits", async () => {
const actor = createActor(
createTestChatMachine({