





















@@ -1,6 +1,9 @@
11import fs from "node:fs";
22import { createSubsystemLogger } from "../../logging/subsystem.js";
3-import { normalizeSessionDeliveryFields } from "../../utils/delivery-context.shared.js";
3+import {
4+normalizeDeliveryContext,
5+normalizeSessionDeliveryFields,
6+} from "../../utils/delivery-context.shared.js";
47import { getFileStatSnapshot } from "../cache-utils.js";
58import {
69cloneSessionStoreRecord,
@@ -37,6 +40,104 @@ function isSessionEntryRecord(value: unknown): value is SessionEntry {
3740return !!value && typeof value === "object" && !Array.isArray(value);
3841}
394243+function isRecord(value: unknown): value is Record<string, unknown> {
44+return !!value && typeof value === "object" && !Array.isArray(value);
45+}
46+47+function normalizeOptionalFiniteNumber(value: unknown): number | undefined {
48+return typeof value === "number" && Number.isFinite(value) && value >= 0 ? value : undefined;
49+}
50+51+function normalizeOptionalAttemptCount(value: unknown): number | undefined {
52+return typeof value === "number" && Number.isInteger(value) && value >= 0 ? value : undefined;
53+}
54+55+function normalizeOptionalStringOrNull(value: unknown): string | null | undefined {
56+if (value === null || typeof value === "string") {
57+return value;
58+}
59+return undefined;
60+}
61+62+function normalizeOptionalDeliveryContext(
63+value: unknown,
64+): SessionEntry["pendingFinalDeliveryContext"] {
65+if (!isRecord(value)) {
66+return undefined;
67+}
68+const normalized = normalizeDeliveryContext({
69+channel: typeof value.channel === "string" ? value.channel : undefined,
70+to: typeof value.to === "string" ? value.to : undefined,
71+accountId: typeof value.accountId === "string" ? value.accountId : undefined,
72+threadId:
73+typeof value.threadId === "string" || typeof value.threadId === "number"
74+ ? value.threadId
75+ : undefined,
76+});
77+return normalized?.channel && normalized.to ? normalized : undefined;
78+}
79+80+function sameDeliveryContext(
81+left: SessionEntry["pendingFinalDeliveryContext"],
82+right: SessionEntry["pendingFinalDeliveryContext"],
83+): boolean {
84+return (
85+(left?.channel ?? undefined) === (right?.channel ?? undefined) &&
86+(left?.to ?? undefined) === (right?.to ?? undefined) &&
87+(left?.accountId ?? undefined) === (right?.accountId ?? undefined) &&
88+(left?.threadId ?? undefined) === (right?.threadId ?? undefined)
89+);
90+}
91+92+function normalizePendingFinalDeliveryFields(entry: SessionEntry): SessionEntry {
93+let next = entry;
94+95+const assign = <K extends keyof SessionEntry>(key: K, value: SessionEntry[K] | undefined) => {
96+if (entry[key] === value) {
97+return;
98+}
99+if (next === entry) {
100+next = { ...entry };
101+}
102+if (value === undefined) {
103+delete next[key];
104+} else {
105+next[key] = value;
106+}
107+};
108+109+assign("pendingFinalDelivery", entry.pendingFinalDelivery === true ? true : undefined);
110+assign("pendingFinalDeliveryText", normalizeOptionalStringOrNull(entry.pendingFinalDeliveryText));
111+assign(
112+"pendingFinalDeliveryCreatedAt",
113+normalizeOptionalFiniteNumber(entry.pendingFinalDeliveryCreatedAt),
114+);
115+assign(
116+"pendingFinalDeliveryLastAttemptAt",
117+normalizeOptionalFiniteNumber(entry.pendingFinalDeliveryLastAttemptAt),
118+);
119+assign(
120+"pendingFinalDeliveryAttemptCount",
121+normalizeOptionalAttemptCount(entry.pendingFinalDeliveryAttemptCount),
122+);
123+assign(
124+"pendingFinalDeliveryLastError",
125+normalizeOptionalStringOrNull(entry.pendingFinalDeliveryLastError),
126+);
127+const pendingFinalDeliveryContext = normalizeOptionalDeliveryContext(
128+entry.pendingFinalDeliveryContext,
129+);
130+if (!sameDeliveryContext(entry.pendingFinalDeliveryContext, pendingFinalDeliveryContext)) {
131+assign("pendingFinalDeliveryContext", pendingFinalDeliveryContext);
132+}
133+assign(
134+"pendingFinalDeliveryIntentId",
135+normalizeOptionalStringOrNull(entry.pendingFinalDeliveryIntentId),
136+);
137+138+return next;
139+}
140+40141function normalizeSessionEntryDelivery(entry: SessionEntry): SessionEntry {
41142const normalized = normalizeSessionDeliveryFields({
42143channel: entry.channel,
@@ -94,7 +195,9 @@ export function normalizeSessionStore(store: Record<string, SessionEntry>): bool
94195continue;
95196}
96197const normalized = stripPersistedSkillsCache(
97-normalizeSessionEntryDelivery(normalizeSessionRuntimeModelFields(entry)),
198+normalizePendingFinalDeliveryFields(
199+normalizeSessionEntryDelivery(normalizeSessionRuntimeModelFields(entry)),
200+),
98201);
99202if (normalized !== entry) {
100203store[key] = normalized;
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。