


























@@ -11,6 +11,7 @@ type CapturedReplyPayload = {
1111isError?: boolean;
1212mediaUrl?: string;
1313mediaUrls?: string[];
14+replyToId?: string | null;
1415};
15161617type CapturedDispatchParams = {
@@ -720,6 +721,7 @@ describe("whatsapp inbound dispatch", () => {
720721agentId: "main",
721722to: "+1000",
722723info: { kind: "final" },
724+replyToId: null,
723725});
724726expectRecordFields(requireRecord(durableParams.payload, "durable payload"), {
725727text: "final payload",
@@ -734,6 +736,64 @@ describe("whatsapp inbound dispatch", () => {
734736});
735737});
736738739+it.each([
740+{
741+name: "uses resolved final payload reply targets",
742+payload: { text: "final payload", replyToId: "trigger-message" },
743+expectedReplyToId: "trigger-message",
744+},
745+{
746+name: "blocks durable fallback without a final payload reply target",
747+payload: { text: "final payload" },
748+expectedReplyToId: null,
749+},
750+] satisfies Array<{
751+name: string;
752+payload: CapturedReplyPayload;
753+expectedReplyToId: string | null;
754+}>)("$name while preserving quoted WhatsApp context", async ({ payload, expectedReplyToId }) => {
755+deliverInboundReplyWithMessageSendContextMock.mockResolvedValueOnce({
756+status: "handled_visible",
757+delivery: {
758+messageIds: ["wa-1"],
759+visibleReplySent: true,
760+},
761+});
762+const deliverReply = vi.fn(async () => acceptedDeliveryResult());
763+764+await dispatchBufferedReply({
765+context: {
766+Body: "incoming",
767+ReplyToId: "quoted-bot-message",
768+ReplyToBody: "Earlier bot reply",
769+ReplyToSender: "OpenClaw",
770+},
771+ deliverReply,
772+msg: makeMsg({
773+event: { id: "trigger-message" },
774+}),
775+});
776+777+const deliver = getCapturedDeliver();
778+await deliver?.(payload, { kind: "final" });
779+780+const durableParams = requireMockArg(
781+deliverInboundReplyWithMessageSendContextMock,
782+0,
783+0,
784+"durable delivery params",
785+);
786+expectRecordFields(durableParams, {
787+replyToId: expectedReplyToId,
788+});
789+expectRecordFields(requireRecord(durableParams.ctxPayload, "durable context"), {
790+ReplyToId: "quoted-bot-message",
791+ReplyToBody: "Earlier bot reply",
792+ReplyToSender: "OpenClaw",
793+});
794+expect(deliverReply).not.toHaveBeenCalled();
795+});
796+737797it("does not fall back when durable WhatsApp delivery suppresses a send", async () => {
738798deliverInboundReplyWithMessageSendContextMock.mockResolvedValueOnce({
739799status: "handled_no_send",
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。