@case-framework/survey-assistant 0.7.0 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +58 -3
- package/dist/{attachments-B0hg3vpT.mjs → attachments-BuNni5vB.mjs} +1 -1
- package/dist/{attachments-B0hg3vpT.mjs.map → attachments-BuNni5vB.mjs.map} +1 -1
- package/dist/{authoring-references-BJQ_1nMX.mjs → authoring-references-DbuOKerg.mjs} +12 -3
- package/dist/authoring-references-DbuOKerg.mjs.map +1 -0
- package/dist/{capabilities-DVTfogjv.d.mts → capabilities-CmeeAjEc.d.mts} +3 -4
- package/dist/capabilities-CmeeAjEc.d.mts.map +1 -0
- package/dist/{capabilities-1KNnNO1_.mjs → capabilities-DCMA71PP.mjs} +4 -19
- package/dist/capabilities-DCMA71PP.mjs.map +1 -0
- package/dist/capabilities-default.d.mts +13 -12
- package/dist/capabilities-default.d.mts.map +1 -1
- package/dist/capabilities-default.mjs +2 -411
- package/dist/{constants-Be91Gay9.d.mts → constants-B6HzpEsx.d.mts} +7 -28
- package/dist/constants-B6HzpEsx.d.mts.map +1 -0
- package/dist/{constants-0UHGFcRJ.mjs → constants-Ct-vv9cu.mjs} +1 -1
- package/dist/{constants-0UHGFcRJ.mjs.map → constants-Ct-vv9cu.mjs.map} +1 -1
- package/dist/controller-proxy-D7uQfm5f.d.mts +65 -0
- package/dist/controller-proxy-D7uQfm5f.d.mts.map +1 -0
- package/dist/{controller-proxy-BH05e-C2.mjs → controller-proxy-DEeFl9IA.mjs} +10 -20
- package/dist/controller-proxy-DEeFl9IA.mjs.map +1 -0
- package/dist/default-fhSon2RM.mjs +760 -0
- package/dist/default-fhSon2RM.mjs.map +1 -0
- package/dist/{digest-SJmoYVaK.d.mts → digest-C39WyAWG.d.mts} +2 -3
- package/dist/digest-C39WyAWG.d.mts.map +1 -0
- package/dist/digest.d.mts +1 -1
- package/dist/digest.mjs.map +1 -1
- package/dist/{engine-Bo85Oyj0.mjs → engine-nXoCWYpQ.mjs} +755 -590
- package/dist/engine-nXoCWYpQ.mjs.map +1 -0
- package/dist/engine.d.mts +3 -3
- package/dist/engine.mjs +3 -3
- package/dist/{fair-guidance-CRYCRxQm.mjs → fair-guidance-BmO4PswW.mjs} +1 -1
- package/dist/{fair-guidance-CRYCRxQm.mjs.map → fair-guidance-BmO4PswW.mjs.map} +1 -1
- package/dist/{index-Tnqv-yKW.d.mts → index-Ciq7vHIs.d.mts} +80 -141
- package/dist/index-Ciq7vHIs.d.mts.map +1 -0
- package/dist/{index-nhrgbgO5.d.mts → index-D7wT6P3t.d.mts} +277 -60
- package/dist/index-D7wT6P3t.d.mts.map +1 -0
- package/dist/{index-l_EK4yK7.d.mts → index-WB5kfnz0.d.mts} +15 -71
- package/dist/index-WB5kfnz0.d.mts.map +1 -0
- package/dist/{index-x0qprHgK.d.mts → index-r5riv4md.d.mts} +33 -24
- package/dist/index-r5riv4md.d.mts.map +1 -0
- package/dist/{lifecycle-Bx0aq_4S.d.mts → lifecycle-Dm8u7QFh.d.mts} +34 -18
- package/dist/lifecycle-Dm8u7QFh.d.mts.map +1 -0
- package/dist/{memory-thread-repository-KWHQWFEW.mjs → memory-thread-repository-DAnOGIB3.mjs} +51 -27
- package/dist/memory-thread-repository-DAnOGIB3.mjs.map +1 -0
- package/dist/{protocol-BhzQbx81.mjs → protocol-CF4Bh_Ch.mjs} +118 -36
- package/dist/protocol-CF4Bh_Ch.mjs.map +1 -0
- package/dist/protocol.d.mts +4 -4
- package/dist/protocol.mjs +3 -3
- package/dist/{react-B3ybjJ-X.mjs → react-C_GY-Fsc.mjs} +146 -39
- package/dist/react-C_GY-Fsc.mjs.map +1 -0
- package/dist/react-integration.d.mts +2 -2
- package/dist/react-integration.mjs +2 -2
- package/dist/react.d.mts +3 -3
- package/dist/react.mjs +3 -3
- package/dist/references/assistant-operations.md +100 -31
- package/dist/references/core-rules.md +6 -3
- package/dist/references/embedded-forms.md +34 -14
- package/dist/references/expressions.md +220 -58
- package/dist/references/fair-by-design.md +9 -9
- package/dist/references/item-types.md +305 -71
- package/dist/references/response-variables.md +38 -0
- package/dist/references/source-material-surveys.md +4 -3
- package/dist/references/survey-data-model.md +23 -8
- package/dist/{request-context-CG4SWijt.mjs → request-context-Dg4jSwN1.mjs} +4 -10
- package/dist/request-context-Dg4jSwN1.mjs.map +1 -0
- package/dist/{request-guardrails-TmgQtqp4.mjs → request-guardrails-C0ugBOp0.mjs} +6 -5
- package/dist/request-guardrails-C0ugBOp0.mjs.map +1 -0
- package/dist/server-agent.d.mts +37 -39
- package/dist/server-agent.d.mts.map +1 -1
- package/dist/server-agent.mjs +45 -20
- package/dist/server-agent.mjs.map +1 -1
- package/dist/server-runtime.d.mts +23 -42
- package/dist/server-runtime.d.mts.map +1 -1
- package/dist/server-runtime.mjs +12 -12
- package/dist/server-runtime.mjs.map +1 -1
- package/dist/server-tasks.d.mts +2 -2
- package/dist/server-tasks.mjs +2 -313
- package/dist/server-tools.d.mts +1 -1
- package/dist/server-tools.mjs +1 -1
- package/dist/server.d.mts +13 -36
- package/dist/server.d.mts.map +1 -1
- package/dist/server.mjs +5 -5
- package/dist/server.mjs.map +1 -1
- package/dist/storage-postgres.d.mts +9 -25
- package/dist/storage-postgres.d.mts.map +1 -1
- package/dist/storage-postgres.mjs +5 -4
- package/dist/storage-postgres.mjs.map +1 -1
- package/dist/{tasks-CYqrcaRO.d.mts → tasks-B9h3LPam.d.mts} +18 -34
- package/dist/tasks-B9h3LPam.d.mts.map +1 -0
- package/dist/tasks-BZEiwgxA.mjs +396 -0
- package/dist/tasks-BZEiwgxA.mjs.map +1 -0
- package/dist/thread-documents-DrHbaXqP.d.mts +119 -0
- package/dist/thread-documents-DrHbaXqP.d.mts.map +1 -0
- package/dist/{thread-handlers-DBAaU7BA.d.mts → thread-handlers-Bef0td9N.d.mts} +8 -40
- package/dist/thread-handlers-Bef0td9N.d.mts.map +1 -0
- package/dist/{tools-BvSovehT.mjs → tools-CEsv-WoO.mjs} +296 -105
- package/dist/tools-CEsv-WoO.mjs.map +1 -0
- package/dist/ui.css +1 -1
- package/dist/ui.d.mts +15 -54
- package/dist/ui.d.mts.map +1 -1
- package/dist/ui.mjs +172 -137
- package/dist/ui.mjs.map +1 -1
- package/docs/integration.md +11 -1
- package/package.json +40 -35
- package/dist/authoring-references-BJQ_1nMX.mjs.map +0 -1
- package/dist/capabilities-1KNnNO1_.mjs.map +0 -1
- package/dist/capabilities-DVTfogjv.d.mts.map +0 -1
- package/dist/capabilities-default.mjs.map +0 -1
- package/dist/constants-Be91Gay9.d.mts.map +0 -1
- package/dist/controller-proxy-BH05e-C2.mjs.map +0 -1
- package/dist/controller-proxy-Bd0ZHBPF.d.mts +0 -85
- package/dist/controller-proxy-Bd0ZHBPF.d.mts.map +0 -1
- package/dist/digest-SJmoYVaK.d.mts.map +0 -1
- package/dist/engine-Bo85Oyj0.mjs.map +0 -1
- package/dist/index-Tnqv-yKW.d.mts.map +0 -1
- package/dist/index-l_EK4yK7.d.mts.map +0 -1
- package/dist/index-nhrgbgO5.d.mts.map +0 -1
- package/dist/index-x0qprHgK.d.mts.map +0 -1
- package/dist/lifecycle-Bx0aq_4S.d.mts.map +0 -1
- package/dist/memory-thread-repository-KWHQWFEW.mjs.map +0 -1
- package/dist/protocol-BhzQbx81.mjs.map +0 -1
- package/dist/react-B3ybjJ-X.mjs.map +0 -1
- package/dist/request-context-CG4SWijt.mjs.map +0 -1
- package/dist/request-guardrails-TmgQtqp4.mjs.map +0 -1
- package/dist/server-tasks.mjs.map +0 -1
- package/dist/tasks-CYqrcaRO.d.mts.map +0 -1
- package/dist/thread-documents-rmd6nyX9.d.mts +0 -107
- package/dist/thread-documents-rmd6nyX9.d.mts.map +0 -1
- package/dist/thread-handlers-DBAaU7BA.d.mts.map +0 -1
- package/dist/tools-BvSovehT.mjs.map +0 -1
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"react-B3ybjJ-X.mjs","names":["findLastUserMessageIndex","surveyAssistantPackageVersion"],"sources":["../src/react/session-state.ts","../src/react/turn-authorization.ts","../src/react/transport.ts","../src/react/thread-client.ts","../src/react/support-bundle-limits.ts","../src/react/diagnostic-store.ts","../package.json","../src/react/support-bundle.ts","../src/react/model-catalog.ts","../src/react/document-baseline.ts","../src/react/use-survey-assistant-session.ts"],"sourcesContent":["export type SurveyAssistantSessionState =\n | \"idle\"\n | \"submitting\"\n | \"streaming\"\n | \"completed\"\n | \"failed\"\n | \"aborted\"\n | \"applying\"\n | \"applied\";\n\nexport type SurveyAssistantSessionEvent =\n | { type: \"submit\" }\n | { type: \"stream-started\" }\n | { type: \"completed\" }\n | { type: \"apply-started\" }\n | { type: \"applied\" }\n | { type: \"failed\" }\n | { type: \"aborted\" }\n | { type: \"reset\"; hasTranscript: boolean };\n\nexport const isSurveyAssistantTurnActive = ({\n isStreaming,\n state,\n}: {\n isStreaming: boolean;\n state: SurveyAssistantSessionState;\n}): boolean =>\n state !== \"aborted\" &&\n (isStreaming || state === \"submitting\" || state === \"streaming\" || state === \"applying\");\n\nexport const reduceSurveyAssistantSessionState = (\n _state: SurveyAssistantSessionState,\n event: SurveyAssistantSessionEvent,\n): SurveyAssistantSessionState => {\n switch (event.type) {\n case \"submit\":\n return \"submitting\";\n case \"stream-started\":\n return \"streaming\";\n case \"completed\":\n return \"completed\";\n case \"apply-started\":\n return \"applying\";\n case \"applied\":\n return \"applied\";\n case \"failed\":\n return \"failed\";\n case \"aborted\":\n return \"aborted\";\n case \"reset\":\n return event.hasTranscript ? \"completed\" : \"idle\";\n }\n};\n","import {\n SURVEY_ASSISTANT_PROTOCOL_VERSION,\n SURVEY_ASSISTANT_TURN_FINAL_PART_TYPE,\n applyReceiptSchema,\n surveyAssistantTurnFinalSchema,\n surveyChangeSetSchema,\n type ApplyReceipt,\n type SurveyAssistantSnapshot,\n type SurveyAssistantTurnFinal,\n type SurveyApplyResult,\n type SurveyChangeSet,\n type SurveyDocumentVersion,\n} from \"../protocol\";\nimport type { UIMessage } from \"ai\";\n\nconst isRecord = (value: unknown): value is Record<string, unknown> =>\n typeof value === \"object\" && value !== null && !Array.isArray(value);\n\nconst isCompletedToolPart = (\n part: UIMessage[\"parts\"][number],\n): part is UIMessage[\"parts\"][number] & { state: \"output-available\"; output: unknown } =>\n (part.type === \"dynamic-tool\" || part.type.startsWith(\"tool-\")) &&\n \"state\" in part &&\n part.state === \"output-available\" &&\n \"output\" in part;\n\nexport const unwrapSurveyAssistantToolOutput = (output: unknown) => {\n if (isRecord(output) && \"output\" in output && output.output !== undefined) {\n return output.output;\n }\n return output;\n};\n\nexport const parseSurveyChangeSet = (output: unknown): SurveyChangeSet | null => {\n const parsed = surveyChangeSetSchema.safeParse(unwrapSurveyAssistantToolOutput(output));\n return parsed.success ? parsed.data : null;\n};\n\nexport const collectSurveyChangeSets = (messages: UIMessage[]): SurveyChangeSet[] => {\n const changes: SurveyChangeSet[] = [];\n for (const message of messages) {\n for (const part of message.parts) {\n if (!isCompletedToolPart(part)) {\n continue;\n }\n const change = parseSurveyChangeSet(part.output);\n if (change) {\n changes.push(change);\n }\n }\n }\n return changes;\n};\n\nconst findLastUserMessageIndex = (messages: UIMessage[]) => {\n for (let index = messages.length - 1; index >= 0; index -= 1) {\n if (messages[index]?.role === \"user\") return index;\n }\n return -1;\n};\n\nexport type SurveyTurnAuthorization =\n | { status: \"pending\" }\n | { status: \"invalid\"; reason: string; turnId?: string }\n | {\n status: \"failed\" | \"aborted\";\n turnFinal: SurveyAssistantTurnFinal;\n changeSets: [];\n }\n | {\n status: \"completed\";\n turnFinal: SurveyAssistantTurnFinal;\n changeSets: SurveyChangeSet[];\n };\n\nexport type SurveyTurnOutcome =\n | {\n status: \"failed\";\n terminationReason?: SurveyAssistantTurnFinal[\"terminationReason\"];\n }\n | {\n status: \"aborted\";\n terminationReason?: SurveyAssistantTurnFinal[\"terminationReason\"];\n }\n | {\n status: \"blocked\";\n blockedChangeSetCount: number;\n }\n | {\n status: \"apply-failed\";\n appliedChangeSetCount: number;\n failedChangeSetCount: number;\n };\n\nexport const resolveLatestSurveyTurnAuthorization = (\n messages: UIMessage[],\n): SurveyTurnAuthorization => {\n const lastUserIndex = findLastUserMessageIndex(messages);\n if (lastUserIndex < 0) {\n return { status: \"pending\" };\n }\n\n const turnMessages = messages.slice(lastUserIndex + 1);\n const finalParts = turnMessages\n .flatMap((message) => message.parts)\n .filter((part) => part.type === SURVEY_ASSISTANT_TURN_FINAL_PART_TYPE);\n if (finalParts.length === 0) {\n return { status: \"pending\" };\n }\n if (finalParts.length !== 1) {\n return { status: \"invalid\", reason: \"The assistant returned multiple turn finals.\" };\n }\n\n const finalPart = finalParts[0];\n const finalParse = surveyAssistantTurnFinalSchema.safeParse(\n finalPart && \"data\" in finalPart ? finalPart.data : undefined,\n );\n if (!finalParse.success) {\n return { status: \"invalid\", reason: \"The assistant returned an invalid turn final.\" };\n }\n const turnFinal = finalParse.data;\n if (turnFinal.status !== \"completed\") {\n return { status: turnFinal.status, turnFinal, changeSets: [] };\n }\n\n const candidates = collectSurveyChangeSets(turnMessages).filter(\n (change) => change.turnId === turnFinal.turnId,\n );\n const candidatesById = new Map<string, SurveyChangeSet>();\n for (const candidate of candidates) {\n if (candidatesById.has(candidate.id)) {\n return {\n status: \"invalid\",\n turnId: turnFinal.turnId,\n reason: `The assistant returned duplicate change set \"${candidate.id}\".`,\n };\n }\n candidatesById.set(candidate.id, candidate);\n }\n\n for (const blockedChangeSetId of turnFinal.blockedChangeSetIds ?? []) {\n const candidate = candidatesById.get(blockedChangeSetId);\n if (!candidate || candidate.status !== \"rejected\" || candidate.validation.valid) {\n return {\n status: \"invalid\",\n turnId: turnFinal.turnId,\n reason: `The assistant did not provide blocked change set \"${blockedChangeSetId}\".`,\n };\n }\n }\n\n const changeSets: SurveyChangeSet[] = [];\n for (const changeSetId of turnFinal.executableChangeSetIds) {\n const candidate = candidatesById.get(changeSetId);\n if (!candidate || candidate.status !== \"validated\" || !candidate.validation.valid) {\n return {\n status: \"invalid\",\n turnId: turnFinal.turnId,\n reason: `The assistant did not provide authorized change set \"${changeSetId}\".`,\n };\n }\n changeSets.push(candidate);\n }\n\n return { status: \"completed\", turnFinal, changeSets };\n};\n\nexport const resolveSurveyTurnOutcome = ({\n applyResultsByChangeId,\n authorization,\n}: {\n applyResultsByChangeId: Record<string, SurveyApplyResult>;\n authorization: SurveyTurnAuthorization;\n}): SurveyTurnOutcome | null => {\n if (authorization.status === \"failed\" || authorization.status === \"aborted\") {\n return {\n status: authorization.status,\n terminationReason: authorization.turnFinal.terminationReason,\n };\n }\n if (authorization.status !== \"completed\") {\n return null;\n }\n\n const blockedChangeSetCount = authorization.turnFinal.blockedChangeSetIds?.length ?? 0;\n if (blockedChangeSetCount > 0) {\n return { status: \"blocked\", blockedChangeSetCount };\n }\n\n if (authorization.changeSets.length === 0) {\n return null;\n }\n\n const results = authorization.changeSets.map((change) => applyResultsByChangeId[change.id]);\n if (results.some((result) => result === undefined)) {\n return null;\n }\n\n const failedChangeSetCount = results.filter((result) => result.status !== \"applied\").length;\n if (failedChangeSetCount === 0) {\n return null;\n }\n\n return {\n status: \"apply-failed\",\n appliedChangeSetCount: results.length - failedChangeSetCount,\n failedChangeSetCount,\n };\n};\n\nexport const getSurveyDocumentVersionFromSnapshot = (\n snapshot: SurveyAssistantSnapshot,\n): SurveyDocumentVersion => ({ ...snapshot.version });\n\nexport const createApplyReceipts = ({\n afterSnapshot,\n beforeSnapshot,\n changeSets,\n results,\n turnFinal,\n createdAt = new Date().toISOString(),\n}: {\n afterSnapshot: SurveyAssistantSnapshot | null;\n beforeSnapshot: SurveyAssistantSnapshot;\n changeSets: SurveyChangeSet[];\n results: SurveyApplyResult[];\n turnFinal: SurveyAssistantTurnFinal;\n createdAt?: string;\n}): ApplyReceipt[] => {\n const beforeVersion = getSurveyDocumentVersionFromSnapshot(beforeSnapshot);\n const afterVersion = afterSnapshot\n ? getSurveyDocumentVersionFromSnapshot(afterSnapshot)\n : undefined;\n const resultsByChangeId = new Map(results.map((result) => [result.changeId, result]));\n\n return changeSets.map((changeSet) => {\n const result = resultsByChangeId.get(changeSet.id);\n const status = result?.status ?? \"failed\";\n return applyReceiptSchema.parse({\n protocolVersion: SURVEY_ASSISTANT_PROTOCOL_VERSION,\n turnId: turnFinal.turnId,\n changeSetId: changeSet.id,\n beforeVersion,\n ...(status === \"applied\" && afterVersion ? { afterVersion } : {}),\n status,\n operationCount: changeSet.operations.length,\n ...(status === \"applied\" && afterVersion?.historyIndex !== undefined\n ? { commit: { index: afterVersion.historyIndex } }\n : {}),\n ...(result?.issues ? { issues: result.issues } : {}),\n createdAt,\n });\n });\n};\n","import { DefaultChatTransport, type UIMessage } from \"ai\";\nimport { readSurveyAssistantJson } from \"./client-error\";\n\nconst findLastUserMessage = (messages: UIMessage[]): UIMessage | undefined => {\n for (let index = messages.length - 1; index >= 0; index -= 1) {\n if (messages[index]?.role === \"user\") return messages[index];\n }\n return undefined;\n};\n\nconst fetchSurveyAssistantChat: typeof fetch = async (input, init) => {\n const response = await globalThis.fetch(input, init);\n if (!response.ok) await readSurveyAssistantJson(response);\n return response;\n};\n\nexport const createSurveyAssistantTransport = ({\n api = \"/api/survey-assistant/chat\",\n resourceId,\n surveyId,\n threadId,\n}: {\n api?: string;\n resourceId: string;\n surveyId?: string;\n threadId: string;\n}) =>\n new DefaultChatTransport({\n api,\n body: { resourceId, ...(surveyId ? { surveyId } : {}), threadId },\n fetch: fetchSurveyAssistantChat,\n prepareSendMessagesRequest: ({\n api,\n body,\n credentials,\n headers,\n id,\n messageId,\n messages,\n trigger,\n }) => {\n const latestUserMessage = findLastUserMessage(messages);\n return {\n api,\n credentials,\n headers,\n body: {\n ...body,\n id,\n messages: latestUserMessage ? [latestUserMessage] : [],\n trigger,\n messageId,\n },\n };\n },\n });\n","import {\n surveyAssistantThreadListSchema,\n surveyAssistantThreadSchema,\n surveyAssistantThreadTranscriptSchema,\n type SurveyAssistantThread,\n type SurveyAssistantThreadList,\n type SurveyAssistantThreadTranscript,\n} from \"../protocol\";\nimport { readSurveyAssistantJson } from \"./client-error\";\n\nexport interface SurveyAssistantThreadClient {\n delete(threadId: string): Promise<void>;\n create(title?: string): Promise<SurveyAssistantThread>;\n list(): Promise<SurveyAssistantThread[]>;\n /** Paged history capability. Older custom clients may omit this method. */\n listPage?(options?: { cursor?: string }): Promise<SurveyAssistantThreadList>;\n read(\n threadId: string,\n cursor?: string,\n options?: { signal?: AbortSignal },\n ): Promise<SurveyAssistantThreadTranscript>;\n rename(threadId: string, title: string): Promise<SurveyAssistantThread>;\n setAutomaticTitle(threadId: string, title?: string): Promise<SurveyAssistantThread>;\n}\n\nexport const createSurveyAssistantThreadClient = (\n api = \"/api/survey-assistant/threads\",\n): SurveyAssistantThreadClient => ({\n async delete(threadId) {\n const response = await fetch(`${api}/${encodeURIComponent(threadId)}`, { method: \"DELETE\" });\n if (!response.ok) await readSurveyAssistantJson(response);\n },\n async create(title) {\n const body = await readSurveyAssistantJson(\n await fetch(api, {\n body: JSON.stringify(title ? { title } : {}),\n headers: { \"content-type\": \"application/json\" },\n method: \"POST\",\n }),\n );\n return surveyAssistantThreadSchema.parse(body.thread);\n },\n async list() {\n const body = await readSurveyAssistantJson(await fetch(api, { cache: \"no-store\" }));\n return surveyAssistantThreadListSchema.parse(body).threads;\n },\n async listPage(options) {\n const search = new URLSearchParams();\n if (options?.cursor) search.set(\"cursor\", options.cursor);\n const body = await readSurveyAssistantJson(\n await fetch(`${api}${search.size ? `?${search}` : \"\"}`, { cache: \"no-store\" }),\n );\n return surveyAssistantThreadListSchema.parse(body);\n },\n async read(threadId, cursor, options) {\n const search = cursor ? `?cursor=${encodeURIComponent(cursor)}` : \"\";\n const body = await readSurveyAssistantJson(\n await fetch(`${api}/${encodeURIComponent(threadId)}${search}`, {\n cache: \"no-store\",\n signal: options?.signal,\n }),\n );\n return surveyAssistantThreadTranscriptSchema.parse(body);\n },\n async rename(threadId, title) {\n const body = await readSurveyAssistantJson(\n await fetch(`${api}/${encodeURIComponent(threadId)}`, {\n body: JSON.stringify({ mode: \"manual\", title }),\n headers: { \"content-type\": \"application/json\" },\n method: \"PATCH\",\n }),\n );\n return surveyAssistantThreadSchema.parse(body.thread);\n },\n async setAutomaticTitle(threadId, title) {\n const body = await readSurveyAssistantJson(\n await fetch(`${api}/${encodeURIComponent(threadId)}`, {\n body: JSON.stringify({ mode: \"automatic\", ...(title ? { title } : {}) }),\n headers: { \"content-type\": \"application/json\" },\n method: \"PATCH\",\n }),\n );\n return surveyAssistantThreadSchema.parse(body.thread);\n },\n});\n","export interface SurveyAssistantSupportBundleLimits {\n attemptEvents: number;\n attemptStoreBytes: number;\n bundleBytes: number;\n emailWarningBytes: number;\n retainedAttempts: number;\n transcriptBytes: number;\n transcriptMessages: number;\n transcriptPages: number;\n zipEntryBytes: number;\n}\n\nconst MEBIBYTE = 1024 * 1024;\n\nexport const SURVEY_ASSISTANT_DEFAULT_SUPPORT_BUNDLE_LIMITS = {\n attemptEvents: 200,\n attemptStoreBytes: 48 * MEBIBYTE,\n bundleBytes: 64 * MEBIBYTE,\n emailWarningBytes: 15 * MEBIBYTE,\n retainedAttempts: 5,\n transcriptBytes: 24 * MEBIBYTE,\n transcriptMessages: 2_000,\n transcriptPages: 20,\n zipEntryBytes: 32 * MEBIBYTE,\n} as const satisfies SurveyAssistantSupportBundleLimits;\n\nexport const resolveSurveyAssistantSupportBundleLimits = (\n overrides?: Partial<SurveyAssistantSupportBundleLimits>,\n): SurveyAssistantSupportBundleLimits => {\n const limits = { ...SURVEY_ASSISTANT_DEFAULT_SUPPORT_BUNDLE_LIMITS, ...overrides };\n for (const [name, value] of Object.entries(limits)) {\n if (!Number.isSafeInteger(value) || value <= 0) {\n throw new Error(\n `Survey assistant support-bundle limit \"${name}\" must be a positive integer.`,\n );\n }\n }\n if (limits.transcriptBytes > limits.zipEntryBytes) {\n throw new Error(\"The transcript limit cannot exceed the individual ZIP-entry limit.\");\n }\n if (limits.zipEntryBytes > limits.bundleBytes) {\n throw new Error(\"The individual ZIP-entry limit cannot exceed the complete bundle limit.\");\n }\n return limits;\n};\n","import { hashString } from \"../protocol/digest\";\nimport type {\n ApplyReceipt,\n SurveyAssistantApplyOutcome,\n SurveyAssistantAttachmentReference,\n SurveyAssistantErrorInfo,\n SurveyAssistantSnapshot,\n SurveyAssistantTurnFinal,\n} from \"../protocol\";\nimport type { FileUIPart } from \"ai\";\nimport {\n resolveSurveyAssistantSupportBundleLimits,\n type SurveyAssistantSupportBundleLimits,\n} from \"./support-bundle-limits\";\n\nexport type SurveyAssistantDiagnosticEventFields = Record<\n string,\n boolean | number | string | null | undefined\n>;\n\nexport interface SurveyAssistantDiagnosticEvent {\n at: string;\n event: string;\n fields?: SurveyAssistantDiagnosticEventFields;\n}\n\nexport interface SurveyAssistantDiagnosticAttachmentReference {\n bytes: number;\n filename: string;\n mediaType: string;\n sessionContentDigest: string;\n storeKey: string;\n}\n\nexport interface SurveyAssistantDiagnosticAttempt {\n applyOutcome?: SurveyAssistantApplyOutcome;\n applyReceipts?: ApplyReceipt[];\n attachments: SurveyAssistantDiagnosticAttachmentReference[];\n captureFailure?: string;\n error?: SurveyAssistantErrorInfo;\n events: SurveyAssistantDiagnosticEvent[];\n messages?: unknown[];\n modelId?: string;\n requestId: string;\n resourceId: string;\n submittedAt: string;\n submittedSurvey?: SurveyAssistantSnapshot | null;\n threadId: string;\n turnFinal?: SurveyAssistantTurnFinal;\n}\n\ninterface StoredAttachment extends SurveyAssistantDiagnosticAttachmentReference {\n dataUrl?: string;\n retainedBytes: number;\n}\n\ninterface StoredAttempt extends SurveyAssistantDiagnosticAttempt {\n retainedBytes: number;\n}\n\nexport interface SurveyAssistantDiagnosticStore {\n beginAttempt(input: {\n attachmentReferences?: SurveyAssistantAttachmentReference[];\n files: FileUIPart[];\n modelId?: string;\n requestId?: string;\n resourceId: string;\n submittedSurvey: SurveyAssistantSnapshot | null;\n threadId: string;\n }): string;\n deleteThread(threadId: string): void;\n getAttachment(storeKey: string): StoredAttachment | undefined;\n getExportAttempt(threadId: string): SurveyAssistantDiagnosticAttempt | undefined;\n recordApplyOutcome(threadId: string, outcome: SurveyAssistantApplyOutcome): void;\n recordApplyReceipts(threadId: string, receipts: ApplyReceipt[]): void;\n recordEvent(threadId: string, event: string, fields?: SurveyAssistantDiagnosticEventFields): void;\n recordFailure(threadId: string, messages: unknown[], error: SurveyAssistantErrorInfo): void;\n recordTurnFinal(threadId: string, turnFinal: SurveyAssistantTurnFinal): void;\n}\n\nexport const createSurveyAssistantDiagnosticId = (prefix = \"attempt\"): string => {\n const randomId = globalThis.crypto?.randomUUID?.();\n if (randomId) return `${prefix}-${randomId}`.slice(0, 64);\n const segment = () => Math.random().toString(36).slice(2).padEnd(12, \"0\");\n return `${prefix}-${segment()}${segment()}`.slice(0, 64);\n};\n\nconst cloneDiagnosticValue = <T>(value: T): T => {\n if (typeof structuredClone === \"function\") return structuredClone(value);\n return JSON.parse(JSON.stringify(value)) as T;\n};\n\nconst getDataUrlBytes = (value: string): number => {\n const comma = value.indexOf(\",\");\n if (comma < 0) return new TextEncoder().encode(value).byteLength;\n const payload = value.slice(comma + 1).replace(/\\s/g, \"\");\n if (!/;base64,/i.test(value.slice(0, comma + 1))) {\n try {\n return new TextEncoder().encode(decodeURIComponent(payload)).byteLength;\n } catch {\n return new TextEncoder().encode(payload).byteLength;\n }\n }\n const padding = payload.endsWith(\"==\") ? 2 : payload.endsWith(\"=\") ? 1 : 0;\n return Math.max(0, Math.floor((payload.length * 3) / 4) - padding);\n};\n\nconst stripMessageAttachmentBytes = (messages: unknown[]): unknown[] => {\n const cloned = cloneDiagnosticValue(messages);\n if (!Array.isArray(cloned)) return [];\n for (const message of cloned) {\n if (!message || typeof message !== \"object\" || !(\"parts\" in message)) continue;\n const parts = (message as { parts?: unknown }).parts;\n if (!Array.isArray(parts)) continue;\n for (const part of parts) {\n if (\n part &&\n typeof part === \"object\" &&\n \"type\" in part &&\n part.type === \"file\" &&\n \"url\" in part &&\n typeof part.url === \"string\" &&\n part.url.startsWith(\"data:\")\n ) {\n part.url = \"[attachment bytes retained separately when available]\";\n }\n }\n }\n return cloned;\n};\n\nconst getApproximateBytes = (value: unknown): number => {\n try {\n return new TextEncoder().encode(JSON.stringify(value)).byteLength;\n } catch {\n return 0;\n }\n};\n\nconst toAttachmentReference = (\n attachment: StoredAttachment,\n): SurveyAssistantDiagnosticAttachmentReference => ({\n bytes: attachment.bytes,\n filename: attachment.filename,\n mediaType: attachment.mediaType,\n sessionContentDigest: attachment.sessionContentDigest,\n storeKey: attachment.storeKey,\n});\n\nconst toPublicAttempt = ({ retainedBytes: _retainedBytes, ...attempt }: StoredAttempt) =>\n cloneDiagnosticValue(attempt);\n\nconst safeEventFields = (\n fields: SurveyAssistantDiagnosticEventFields | undefined,\n): SurveyAssistantDiagnosticEventFields | undefined => {\n if (!fields) return undefined;\n const allowed: SurveyAssistantDiagnosticEventFields = {};\n for (const [key, value] of Object.entries(fields)) {\n if (\n !/^(?:aborted|applied|changeSetId|code|count|durationMs|httpStatus|operationCount|retryable|status|turnId)$/.test(\n key,\n )\n )\n continue;\n if (\n value === null ||\n value === undefined ||\n typeof value === \"boolean\" ||\n typeof value === \"number\" ||\n typeof value === \"string\"\n ) {\n allowed[key] = typeof value === \"string\" ? value.slice(0, 240) : value;\n }\n }\n return Object.keys(allowed).length > 0 ? allowed : undefined;\n};\n\nexport const createSurveyAssistantDiagnosticStore = (\n overrides?: Partial<SurveyAssistantSupportBundleLimits>,\n): SurveyAssistantDiagnosticStore => {\n const limits = resolveSurveyAssistantSupportBundleLimits(overrides);\n const attempts: StoredAttempt[] = [];\n const attachments = new Map<string, StoredAttachment>();\n let attachmentSequence = 0;\n\n const latest = (threadId: string) =>\n [...attempts].reverse().find((attempt) => attempt.threadId === threadId);\n\n const exportAttempt = (threadId: string) => latest(threadId);\n\n const updateAttemptBytes = (attempt: StoredAttempt) => {\n const { retainedBytes: _retainedBytes, ...value } = attempt;\n attempt.retainedBytes = getApproximateBytes(value);\n };\n\n const retainedBytes = () =>\n attempts.reduce((total, attempt) => total + attempt.retainedBytes, 0) +\n [...attachments.values()].reduce((total, attachment) => total + attachment.retainedBytes, 0);\n\n const removeUnreferencedAttachments = () => {\n const retainedKeys = new Set(\n attempts.flatMap((attempt) => attempt.attachments.map((item) => item.storeKey)),\n );\n for (const key of attachments.keys()) if (!retainedKeys.has(key)) attachments.delete(key);\n };\n\n const enforceLimits = () => {\n if (attempts.length > limits.retainedAttempts) {\n const newest = attempts.at(-1)!;\n const newestFirst = [...attempts].reverse();\n const retained = new Set(\n [\n newest,\n ...newestFirst.filter(\n (attempt) =>\n attempt !== newest &&\n (attempt.error !== undefined || attempt.captureFailure !== undefined),\n ),\n ...newestFirst.filter(\n (attempt) =>\n attempt !== newest &&\n attempt.error === undefined &&\n attempt.captureFailure === undefined,\n ),\n ].slice(0, limits.retainedAttempts),\n );\n for (let index = attempts.length - 1; index >= 0; index -= 1) {\n if (!retained.has(attempts[index]!)) attempts.splice(index, 1);\n }\n }\n removeUnreferencedAttachments();\n if (retainedBytes() <= limits.attemptStoreBytes) return;\n\n const protectedAttempts = new Set(\n [...new Set(attempts.map((attempt) => attempt.threadId))]\n .map(exportAttempt)\n .filter((attempt): attempt is StoredAttempt => attempt !== undefined),\n );\n for (const attempt of attempts) {\n if (protectedAttempts.has(attempt)) continue;\n attempt.messages = undefined;\n attempt.submittedSurvey = undefined;\n updateAttemptBytes(attempt);\n if (retainedBytes() <= limits.attemptStoreBytes) return;\n }\n const protectedAttachmentKeys = new Set(\n [...protectedAttempts].flatMap((attempt) =>\n attempt.attachments.map((attachment) => attachment.storeKey),\n ),\n );\n for (const attachment of attachments.values()) {\n if (protectedAttachmentKeys.has(attachment.storeKey)) continue;\n attachment.dataUrl = undefined;\n attachment.retainedBytes = 0;\n if (retainedBytes() <= limits.attemptStoreBytes) return;\n }\n for (const attachment of attachments.values()) {\n attachment.dataUrl = undefined;\n attachment.retainedBytes = 0;\n if (retainedBytes() <= limits.attemptStoreBytes) return;\n }\n for (const protectedAttempt of protectedAttempts) {\n protectedAttempt.messages = undefined;\n protectedAttempt.submittedSurvey = undefined;\n protectedAttempt.captureFailure ??=\n \"Diagnostic content was evicted because the browser limit was reached.\";\n updateAttemptBytes(protectedAttempt);\n if (retainedBytes() <= limits.attemptStoreBytes) return;\n }\n };\n\n const retainAttachment = (file: FileUIPart): SurveyAssistantDiagnosticAttachmentReference => {\n const dataUrl =\n typeof file.url === \"string\" && file.url.startsWith(\"data:\") ? file.url : undefined;\n const mediaType = file.mediaType || \"application/octet-stream\";\n const filename = file.filename?.trim() || \"Attached document\";\n const bytes = dataUrl ? getDataUrlBytes(dataUrl) : 0;\n const sessionContentDigest = hashString(\n dataUrl ?? `${mediaType}\\u0000${filename}\\u0000${bytes}`,\n );\n if (dataUrl) {\n for (const candidate of attachments.values()) {\n if (\n candidate.sessionContentDigest === sessionContentDigest &&\n candidate.mediaType === mediaType &&\n candidate.bytes === bytes &&\n candidate.dataUrl === dataUrl\n ) {\n return toAttachmentReference(candidate);\n }\n }\n }\n attachmentSequence += 1;\n const stored: StoredAttachment = {\n bytes,\n filename,\n mediaType,\n sessionContentDigest,\n storeKey: `${sessionContentDigest}-${attachmentSequence}`,\n retainedBytes: dataUrl?.length ?? 0,\n ...(dataUrl ? { dataUrl } : {}),\n };\n attachments.set(stored.storeKey, stored);\n return toAttachmentReference(stored);\n };\n\n const retainAttachmentReference = (\n reference: SurveyAssistantAttachmentReference,\n ): SurveyAssistantDiagnosticAttachmentReference => {\n const filename = reference.filename.trim() || \"Attached document\";\n const mediaType = reference.mediaType || \"application/octet-stream\";\n const sessionContentDigest = hashString(\n `${reference.documentId ?? \"restored\"}\\u0000${mediaType}\\u0000${filename}\\u0000${reference.bytes}`,\n );\n attachmentSequence += 1;\n const stored: StoredAttachment = {\n bytes: reference.bytes,\n filename,\n mediaType,\n retainedBytes: 0,\n sessionContentDigest,\n storeKey: `${sessionContentDigest}-${attachmentSequence}`,\n };\n attachments.set(stored.storeKey, stored);\n return toAttachmentReference(stored);\n };\n\n const recordEvent = (\n threadId: string,\n event: string,\n fields?: SurveyAssistantDiagnosticEventFields,\n ) => {\n const attempt = latest(threadId);\n if (!attempt) return;\n attempt.events.push({\n at: new Date().toISOString(),\n event: event.slice(0, 80),\n ...(safeEventFields(fields) ? { fields: safeEventFields(fields) } : {}),\n });\n if (attempt.events.length > limits.attemptEvents) {\n attempt.events.splice(0, attempt.events.length - limits.attemptEvents);\n }\n updateAttemptBytes(attempt);\n };\n\n return {\n beginAttempt(input) {\n const requestId = input.requestId ?? createSurveyAssistantDiagnosticId();\n const attempt: StoredAttempt = {\n attachments: [\n ...input.files.map(retainAttachment),\n ...(input.attachmentReferences ?? []).map(retainAttachmentReference),\n ],\n events: [],\n ...(input.modelId ? { modelId: input.modelId } : {}),\n requestId,\n resourceId: input.resourceId,\n submittedAt: new Date().toISOString(),\n submittedSurvey: cloneDiagnosticValue(input.submittedSurvey),\n threadId: input.threadId,\n retainedBytes: 0,\n };\n updateAttemptBytes(attempt);\n attempts.push(attempt);\n recordEvent(input.threadId, \"submission\");\n enforceLimits();\n return requestId;\n },\n deleteThread(threadId) {\n for (let index = attempts.length - 1; index >= 0; index -= 1) {\n if (attempts[index]?.threadId === threadId) attempts.splice(index, 1);\n }\n removeUnreferencedAttachments();\n },\n getAttachment(storeKey) {\n return attachments.get(storeKey);\n },\n getExportAttempt(threadId) {\n const attempt = exportAttempt(threadId);\n return attempt ? toPublicAttempt(attempt) : undefined;\n },\n recordApplyOutcome(threadId, outcome) {\n const attempt = latest(threadId);\n if (!attempt) return;\n attempt.applyOutcome = cloneDiagnosticValue(outcome);\n recordEvent(threadId, \"apply-result\", { status: outcome.status });\n enforceLimits();\n },\n recordApplyReceipts(threadId, receipts) {\n const attempt = latest(threadId);\n if (!attempt) return;\n attempt.applyReceipts = cloneDiagnosticValue(receipts);\n recordEvent(threadId, \"apply-receipts\", {\n count: receipts.length,\n operationCount: receipts.reduce((sum, receipt) => sum + receipt.operationCount, 0),\n });\n enforceLimits();\n },\n recordEvent,\n recordFailure(threadId, messages, error) {\n const attempt = latest(threadId);\n if (!attempt) return;\n try {\n attempt.messages = stripMessageAttachmentBytes(messages);\n attempt.error = cloneDiagnosticValue(error);\n recordEvent(threadId, \"failure\", {\n code: error.code,\n httpStatus: error.upstreamStatus,\n retryable: error.retryable,\n });\n enforceLimits();\n } catch {\n attempt.messages = undefined;\n attempt.captureFailure = \"The failed assistant messages could not be captured.\";\n recordEvent(threadId, \"capture-failed\");\n }\n },\n recordTurnFinal(threadId, turnFinal) {\n const attempt = latest(threadId);\n if (!attempt) return;\n attempt.turnFinal = cloneDiagnosticValue(turnFinal);\n recordEvent(threadId, \"turn-final\", {\n durationMs: turnFinal.durationMs,\n status: turnFinal.status,\n turnId: turnFinal.turnId,\n });\n enforceLimits();\n },\n };\n};\n","","import {\n getSurveyAssistantEmbeddedBinaryMarker,\n isSurveyAssistantSensitiveMetadataKey,\n redactSurveyAssistantDiagnosticSecrets,\n type SurveyAssistantSnapshot,\n} from \"../protocol\";\nimport { Zip, ZipPassThrough } from \"fflate\";\nimport type { SurveyAssistantController } from \"./controller\";\nimport type {\n SurveyAssistantDiagnosticAttempt,\n SurveyAssistantDiagnosticStore,\n} from \"./diagnostic-store\";\nimport {\n resolveSurveyAssistantSupportBundleLimits,\n type SurveyAssistantSupportBundleLimits,\n} from \"./support-bundle-limits\";\nimport type { SurveyAssistantThreadClient } from \"./thread-client\";\nimport { version as surveyAssistantPackageVersion } from \"../../package.json\";\n\nexport type SurveyAssistantSupportBundleCategory = \"attachments\" | \"conversation\" | \"survey\";\n\nexport type SurveyAssistantSupportBundleSelection = Record<\n SurveyAssistantSupportBundleCategory,\n boolean\n>;\n\nexport const SURVEY_ASSISTANT_DEFAULT_SUPPORT_BUNDLE_SELECTION = {\n attachments: true,\n conversation: true,\n survey: true,\n} as const satisfies SurveyAssistantSupportBundleSelection;\n\nexport interface SurveyAssistantSupportBundleConfig {\n /** Set to false to disable support-bundle preparation and generation. Defaults to true. */\n enabled?: boolean;\n hostBuildVersion?: string;\n limits?: Partial<SurveyAssistantSupportBundleLimits>;\n packageVersion?: string;\n subjectPrefix?: string;\n supportEmail?: string;\n}\n\nexport const isSurveyAssistantSupportBundleEnabled = (\n config?: SurveyAssistantSupportBundleConfig,\n): boolean => config?.enabled !== false;\n\nconst assertSurveyAssistantSupportBundleEnabled = (config?: SurveyAssistantSupportBundleConfig) => {\n if (!isSurveyAssistantSupportBundleEnabled(config)) {\n throw new Error(\"Support bundle export is disabled by host configuration.\");\n }\n};\n\ninterface PreparedEntry {\n bytes: Uint8Array;\n category: SurveyAssistantSupportBundleCategory;\n path: string;\n source: \"authorized-transcript\" | \"browser-session\";\n}\n\ninterface UnavailableComponent {\n bytes?: number;\n category: SurveyAssistantSupportBundleCategory;\n filename?: string;\n mediaType?: string;\n reason: \"capture-failed\" | \"no-attempt-retained\" | \"not-retained\" | \"too-large\" | \"unavailable\";\n path?: string;\n}\n\ninterface DeclinedUnavailableComponents {\n category: SurveyAssistantSupportBundleCategory;\n itemCount: number;\n totalBytes: number;\n}\n\nexport interface PreparedSurveyAssistantSupportBundle {\n attempt?: SurveyAssistantDiagnosticAttempt;\n categoryBytes: Record<SurveyAssistantSupportBundleCategory, number>;\n currentSurveyCapturedAt: string;\n entries: PreparedEntry[];\n limits: SurveyAssistantSupportBundleLimits;\n resourceId: string;\n threadId: string;\n unavailable: UnavailableComponent[];\n}\n\nexport interface GeneratedSurveyAssistantSupportBundle {\n blob: Blob;\n filename: string;\n generatedAt: string;\n includedCategories: SurveyAssistantSupportBundleCategory[];\n size: number;\n}\n\nconst encoder = new TextEncoder();\n\nconst encodeJson = (value: unknown): Uint8Array => encoder.encode(JSON.stringify(value));\n\nconst abortIfNeeded = (signal?: AbortSignal) => {\n if (signal?.aborted)\n throw new DOMException(\"Support bundle preparation was cancelled.\", \"AbortError\");\n};\n\ninterface SanitizationState {\n nodes: number;\n redactions: number;\n truncated: boolean;\n}\n\nconst sanitizeValue = (\n value: unknown,\n state: SanitizationState,\n parent?: Record<string, unknown>,\n key?: string,\n depth = 0,\n): unknown => {\n state.nodes += 1;\n if (state.nodes > 100_000) {\n state.redactions += 1;\n state.truncated = true;\n return { redacted: \"node-limit\" };\n }\n if (depth > 32) {\n state.redactions += 1;\n state.truncated = true;\n return { redacted: \"depth-limit\" };\n }\n\n const binaryMarker = getSurveyAssistantEmbeddedBinaryMarker(value, parent, key);\n if (binaryMarker) {\n state.redactions += 1;\n return binaryMarker;\n }\n if (key && isSurveyAssistantSensitiveMetadataKey(key)) {\n state.redactions += 1;\n return { redacted: \"sensitive-field\" };\n }\n if (typeof value === \"string\") {\n const redacted = redactSurveyAssistantDiagnosticSecrets(value);\n if (redacted !== value) state.redactions += 1;\n return redacted.length > 200_000 ? `${redacted.slice(0, 199_999)}…` : redacted;\n }\n if (value === null || typeof value === \"number\" || typeof value === \"boolean\") return value;\n if (value === undefined) return undefined;\n if (Array.isArray(value)) {\n if (value.length > 20_000) state.truncated = true;\n return value\n .slice(0, 20_000)\n .map((item) => sanitizeValue(item, state, undefined, undefined, depth + 1));\n }\n if (typeof value !== \"object\") return String(value);\n\n const record = value as Record<string, unknown>;\n const sanitized: Record<string, unknown> = {};\n const entries = Object.entries(record);\n if (entries.length > 20_000) state.truncated = true;\n for (const [childKey, childValue] of entries.slice(0, 20_000)) {\n sanitized[childKey] = sanitizeValue(childValue, state, record, childKey, depth + 1);\n }\n return sanitized;\n};\n\nexport const sanitizeSurveyAssistantSupportValue = (value: unknown) => {\n const state: SanitizationState = { nodes: 0, redactions: 0, truncated: false };\n const sanitized = sanitizeValue(value, state);\n return { redactions: state.redactions, truncated: state.truncated, value: sanitized };\n};\n\nconst createJsonEntry = (\n path: string,\n category: SurveyAssistantSupportBundleCategory,\n source: PreparedEntry[\"source\"],\n value: unknown,\n): PreparedEntry => {\n const state: SanitizationState = { nodes: 0, redactions: 0, truncated: false };\n const sanitized = sanitizeValue(value, state);\n return {\n bytes: encodeJson({\n redactions: state.redactions,\n truncated: state.truncated,\n value: sanitized,\n }),\n category,\n path,\n source,\n };\n};\n\nconst snapshotVersion = (snapshot: SurveyAssistantSnapshot | null | undefined) => snapshot?.version;\n\nconst extensionForMediaType = (mediaType: string): string => {\n switch (mediaType.toLocaleLowerCase()) {\n case \"application/pdf\":\n return \".pdf\";\n case \"image/jpeg\":\n return \".jpg\";\n case \"image/png\":\n return \".png\";\n default:\n return \".bin\";\n }\n};\n\nconst sanitizeFilename = (filename: string, mediaType: string): string => {\n const extension = extensionForMediaType(mediaType);\n const withoutExtension = filename.replace(/\\.[a-z0-9]{1,10}$/i, \"\");\n const stem = withoutExtension\n .normalize(\"NFKD\")\n .replace(/[^A-Za-z0-9._-]+/g, \"-\")\n .replace(/^[._-]+|[._-]+$/g, \"\")\n .slice(0, 100);\n return `${stem || \"attachment\"}${extension}`;\n};\n\nconst disambiguateFilenames = (files: Array<{ filename: string; mediaType: string }>): string[] => {\n const used = new Set<string>();\n return files.map((file) => {\n const sanitized = sanitizeFilename(file.filename, file.mediaType);\n const dot = sanitized.lastIndexOf(\".\");\n const stem = dot > 0 ? sanitized.slice(0, dot) : sanitized;\n const extension = dot > 0 ? sanitized.slice(dot) : \"\";\n let candidate = sanitized;\n let index = 2;\n while (used.has(candidate.toLocaleLowerCase())) {\n candidate = `${stem}-${index}${extension}`;\n index += 1;\n }\n used.add(candidate.toLocaleLowerCase());\n return candidate;\n });\n};\n\nconst dataUrlToBytes = (dataUrl: string): Uint8Array => {\n const comma = dataUrl.indexOf(\",\");\n if (comma < 0) return encoder.encode(dataUrl);\n const metadata = dataUrl.slice(0, comma);\n const payload = dataUrl.slice(comma + 1);\n if (!/;base64$/i.test(metadata)) return encoder.encode(decodeURIComponent(payload));\n const decoded = globalThis.atob(payload);\n const bytes = new Uint8Array(decoded.length);\n for (let index = 0; index < decoded.length; index += 1) bytes[index] = decoded.charCodeAt(index);\n return bytes;\n};\n\nconst pushPreparedEntry = (\n entries: PreparedEntry[],\n unavailable: UnavailableComponent[],\n entry: PreparedEntry,\n limits: SurveyAssistantSupportBundleLimits,\n) => {\n if (entry.bytes.byteLength > limits.zipEntryBytes) {\n unavailable.push({\n bytes: entry.bytes.byteLength,\n category: entry.category,\n path: entry.path,\n reason: \"too-large\",\n });\n return;\n }\n entries.push(entry);\n};\n\nexport const prepareSurveyAssistantSupportBundle = async ({\n config,\n controller,\n diagnosticStore,\n resourceId,\n signal,\n threadClient,\n threadId,\n}: {\n config?: SurveyAssistantSupportBundleConfig;\n controller?: SurveyAssistantController | null;\n diagnosticStore: SurveyAssistantDiagnosticStore;\n resourceId: string;\n signal?: AbortSignal;\n threadClient: SurveyAssistantThreadClient;\n threadId: string;\n}): Promise<PreparedSurveyAssistantSupportBundle> => {\n assertSurveyAssistantSupportBundleEnabled(config);\n const limits = resolveSurveyAssistantSupportBundleLimits(config?.limits);\n const entries: PreparedEntry[] = [];\n const unavailable: UnavailableComponent[] = [];\n const attempt = diagnosticStore.getExportAttempt(threadId);\n const currentSurveyCapturedAt = new Date().toISOString();\n let currentSurvey: SurveyAssistantSnapshot | null = null;\n try {\n currentSurvey = controller?.getSnapshot() ?? null;\n if (currentSurvey) {\n currentSurvey =\n typeof structuredClone === \"function\"\n ? structuredClone(currentSurvey)\n : (JSON.parse(JSON.stringify(currentSurvey)) as SurveyAssistantSnapshot);\n }\n } catch {\n unavailable.push({\n category: \"survey\",\n reason: \"capture-failed\",\n path: \"survey/current-survey.json\",\n });\n }\n\n abortIfNeeded(signal);\n if (!attempt) {\n unavailable.push(\n {\n category: \"conversation\",\n path: \"conversation/attempt-messages.json\",\n reason: \"no-attempt-retained\",\n },\n {\n category: \"conversation\",\n path: \"diagnostics/client-apply-outcome.json\",\n reason: \"no-attempt-retained\",\n },\n {\n category: \"conversation\",\n path: \"diagnostics/client-apply-receipts.json\",\n reason: \"no-attempt-retained\",\n },\n { category: \"attachments\", reason: \"no-attempt-retained\" },\n );\n }\n if (attempt?.messages) {\n pushPreparedEntry(\n entries,\n unavailable,\n createJsonEntry(\n \"conversation/attempt-messages.json\",\n \"conversation\",\n \"browser-session\",\n attempt.messages,\n ),\n limits,\n );\n } else if (attempt?.captureFailure) {\n unavailable.push({\n category: \"conversation\",\n reason: \"capture-failed\",\n path: \"conversation/attempt-messages.json\",\n });\n } else if (attempt) {\n unavailable.push({\n category: \"conversation\",\n reason: \"not-retained\",\n path: \"conversation/attempt-messages.json\",\n });\n }\n if (attempt?.applyOutcome) {\n pushPreparedEntry(\n entries,\n unavailable,\n createJsonEntry(\n \"diagnostics/client-apply-outcome.json\",\n \"conversation\",\n \"browser-session\",\n attempt.applyOutcome,\n ),\n limits,\n );\n }\n if (attempt?.applyReceipts) {\n pushPreparedEntry(\n entries,\n unavailable,\n createJsonEntry(\n \"diagnostics/client-apply-receipts.json\",\n \"conversation\",\n \"browser-session\",\n attempt.applyReceipts,\n ),\n limits,\n );\n }\n\n const transcriptMessages: unknown[] = [];\n let transcriptBytes = 0;\n let transcriptCursor: string | undefined;\n let transcriptRedactions = 0;\n let transcriptTruncated = false;\n try {\n for (let page = 0; page < limits.transcriptPages; page += 1) {\n abortIfNeeded(signal);\n const transcript = await threadClient.read(threadId, transcriptCursor, { signal });\n abortIfNeeded(signal);\n const pageState: SanitizationState = { nodes: 0, redactions: 0, truncated: false };\n const sanitizedPage = sanitizeValue(transcript.messages, pageState);\n transcriptRedactions += pageState.redactions;\n transcriptTruncated ||= pageState.truncated;\n const pageMessages = Array.isArray(sanitizedPage) ? sanitizedPage : [];\n const pageBytes = encodeJson(pageMessages).byteLength;\n if (\n transcriptMessages.length + pageMessages.length > limits.transcriptMessages ||\n transcriptBytes + pageBytes > limits.transcriptBytes\n ) {\n transcriptTruncated = true;\n break;\n }\n transcriptMessages.unshift(...pageMessages);\n transcriptBytes += pageBytes;\n transcriptCursor = transcript.nextCursor;\n if (!transcriptCursor) break;\n if (page === limits.transcriptPages - 1) transcriptTruncated = true;\n }\n pushPreparedEntry(\n entries,\n unavailable,\n {\n bytes: encodeJson({\n messages: transcriptMessages,\n redactions: transcriptRedactions,\n truncated: transcriptTruncated,\n }),\n category: \"conversation\",\n path: \"conversation/transcript.json\",\n source: \"authorized-transcript\",\n },\n limits,\n );\n } catch (error) {\n if (signal?.aborted) throw error;\n unavailable.push({\n category: \"conversation\",\n reason: \"unavailable\",\n path: \"conversation/transcript.json\",\n });\n }\n\n if (attempt?.submittedSurvey !== undefined) {\n pushPreparedEntry(\n entries,\n unavailable,\n createJsonEntry(\"survey/submitted-survey.json\", \"survey\", \"browser-session\", {\n snapshot: attempt.submittedSurvey,\n version: snapshotVersion(attempt.submittedSurvey),\n }),\n limits,\n );\n } else {\n unavailable.push({\n category: \"survey\",\n reason: attempt ? \"not-retained\" : \"no-attempt-retained\",\n path: \"survey/submitted-survey.json\",\n });\n }\n if (currentSurvey) {\n pushPreparedEntry(\n entries,\n unavailable,\n createJsonEntry(\"survey/current-survey.json\", \"survey\", \"browser-session\", {\n capturedAt: currentSurveyCapturedAt,\n snapshot: currentSurvey,\n version: snapshotVersion(currentSurvey),\n }),\n limits,\n );\n }\n\n if (attempt) {\n const availableAttachments = attempt.attachments\n .map((reference) => ({\n reference,\n stored: diagnosticStore.getAttachment(reference.storeKey),\n }))\n .filter((item) => Boolean(item.stored?.dataUrl));\n const filenames = disambiguateFilenames(availableAttachments.map(({ reference }) => reference));\n for (const [index, { reference, stored }] of availableAttachments.entries()) {\n abortIfNeeded(signal);\n const bytes = dataUrlToBytes(stored!.dataUrl!);\n pushPreparedEntry(\n entries,\n unavailable,\n {\n bytes,\n category: \"attachments\",\n path: `attachments/${filenames[index]}`,\n source: \"browser-session\",\n },\n limits,\n );\n }\n for (const reference of attempt.attachments) {\n if (!diagnosticStore.getAttachment(reference.storeKey)?.dataUrl) {\n unavailable.push({\n bytes: reference.bytes,\n category: \"attachments\",\n filename: reference.filename,\n mediaType: reference.mediaType,\n reason: \"not-retained\",\n });\n }\n }\n }\n\n const categoryBytes = {\n attachments: 0,\n conversation: 0,\n survey: 0,\n } satisfies Record<SurveyAssistantSupportBundleCategory, number>;\n for (const entry of entries) categoryBytes[entry.category] += entry.bytes.byteLength;\n\n return {\n attempt,\n categoryBytes,\n currentSurveyCapturedAt,\n entries,\n limits,\n resourceId,\n threadId,\n unavailable,\n };\n};\n\nconst validateZipPath = (path: string) => {\n if (!path || path.startsWith(\"/\") || path.includes(\"\\\\\") || path.split(\"/\").includes(\"..\")) {\n throw new Error(`Unsafe support-bundle ZIP path: ${path}`);\n }\n};\n\nconst toBlobPart = (bytes: Uint8Array): ArrayBuffer => {\n if (\n bytes.buffer instanceof ArrayBuffer &&\n bytes.byteOffset === 0 &&\n bytes.byteLength === bytes.buffer.byteLength\n ) {\n return bytes.buffer;\n }\n return bytes.slice().buffer as ArrayBuffer;\n};\n\nconst createZipBlob = (entries: Array<{ bytes: Uint8Array; path: string }>): Promise<Blob> => {\n const paths = new Set<string>();\n for (const entry of entries) {\n validateZipPath(entry.path);\n if (paths.has(entry.path)) throw new Error(`Duplicate support-bundle ZIP path: ${entry.path}`);\n paths.add(entry.path);\n }\n return new Promise((resolve, reject) => {\n const chunks: BlobPart[] = [];\n const zip = new Zip((error, data, final) => {\n if (error) {\n reject(error);\n return;\n }\n chunks.push(toBlobPart(data));\n if (final) resolve(new Blob(chunks, { type: \"application/zip\" }));\n });\n try {\n for (const entry of entries) {\n const file = new ZipPassThrough(entry.path);\n zip.add(file);\n file.push(entry.bytes, true);\n }\n zip.end();\n } catch (error) {\n zip.terminate();\n reject(error);\n }\n });\n};\n\nconst categoryDescriptors = (\n prepared: PreparedSurveyAssistantSupportBundle,\n selection: SurveyAssistantSupportBundleSelection,\n) =>\n (Object.keys(selection) as SurveyAssistantSupportBundleCategory[]).map((category) => {\n const entries = prepared.entries.filter((entry) => entry.category === category);\n return selection[category]\n ? {\n category,\n included: true,\n itemCount: entries.length,\n totalBytes: entries.reduce((total, entry) => total + entry.bytes.byteLength, 0),\n entries: entries.map((entry) => ({\n bytes: entry.bytes.byteLength,\n path: entry.path,\n source: entry.source,\n })),\n }\n : {\n category,\n included: false,\n itemCount: entries.length,\n totalBytes: entries.reduce((total, entry) => total + entry.bytes.byteLength, 0),\n };\n });\n\nconst createAttemptMetadata = (\n prepared: PreparedSurveyAssistantSupportBundle,\n selection: SurveyAssistantSupportBundleSelection,\n) => {\n const attempt = prepared.attempt;\n return {\n attemptAvailable: Boolean(attempt),\n ...(attempt\n ? {\n captureFailure: attempt.captureFailure,\n error: attempt.error,\n events: attempt.events,\n modelId: attempt.modelId,\n requestId: attempt.requestId,\n resourceId: attempt.resourceId,\n submittedAt: attempt.submittedAt,\n threadId: attempt.threadId,\n turnFinal: attempt.turnFinal,\n }\n : { threadId: prepared.threadId }),\n categories: categoryDescriptors(prepared, selection),\n };\n};\n\nconst encodeSanitizedJson = (value: unknown): Uint8Array =>\n encodeJson(sanitizeSurveyAssistantSupportValue(value).value);\n\nconst createRequiredEntries = (\n prepared: PreparedSurveyAssistantSupportBundle,\n selection: SurveyAssistantSupportBundleSelection,\n config: SurveyAssistantSupportBundleConfig | undefined,\n generatedAt: string,\n) => {\n const descriptors = categoryDescriptors(prepared, selection);\n const unavailable = (Object.keys(selection) as SurveyAssistantSupportBundleCategory[]).flatMap<\n UnavailableComponent | DeclinedUnavailableComponents\n >((category) => {\n const categoryUnavailable = prepared.unavailable.filter((item) => item.category === category);\n if (categoryUnavailable.length === 0) return [];\n if (selection[category]) return categoryUnavailable;\n return [\n {\n category,\n itemCount: categoryUnavailable.length,\n totalBytes: categoryUnavailable.reduce((total, item) => total + (item.bytes ?? 0), 0),\n },\n ];\n });\n const manifest = {\n schemaVersion: 1,\n generatedAt,\n packageVersion: config?.packageVersion ?? surveyAssistantPackageVersion,\n hostBuildVersion: config?.hostBuildVersion,\n resourceId: prepared.resourceId,\n threadId: prepared.threadId,\n requestId: prepared.attempt?.requestId,\n turnId: prepared.attempt?.turnFinal?.turnId,\n modelId: prepared.attempt?.modelId,\n categories: descriptors,\n unavailable,\n currentSurveyCapturedAt: prepared.currentSurveyCapturedAt,\n };\n const readme = [\n \"CASE Survey Assistant support bundle\",\n \"\",\n `Generated: ${generatedAt}`,\n \"This archive contains diagnostic data selected by the user, including visible model reasoning when conversation data is included.\",\n \"Nothing was uploaded or emailed automatically.\",\n \"See manifest.json for the authoritative inventory and availability information.\",\n \"Treat the archive as potentially sensitive.\",\n ].join(\"\\n\");\n return [\n { bytes: encodeSanitizedJson(manifest), path: \"manifest.json\" },\n { bytes: encoder.encode(readme), path: \"README.txt\" },\n {\n bytes: encodeSanitizedJson(createAttemptMetadata(prepared, selection)),\n path: \"diagnostics/client-attempt.json\",\n },\n ];\n};\n\nconst estimateArchiveBytes = (entries: Array<{ bytes: Uint8Array; path: string }>) =>\n entries.reduce(\n (total, entry) =>\n total + entry.bytes.byteLength + encoder.encode(entry.path).byteLength * 2 + 110,\n 22,\n );\n\nexport const estimateSurveyAssistantSupportBundleBytes = (\n prepared: PreparedSurveyAssistantSupportBundle,\n selection: SurveyAssistantSupportBundleSelection,\n config?: SurveyAssistantSupportBundleConfig,\n): number => {\n if (!isSurveyAssistantSupportBundleEnabled(config)) return 0;\n const entries = [\n ...createRequiredEntries(prepared, selection, config, new Date().toISOString()),\n ...prepared.entries\n .filter((entry) => selection[entry.category])\n .map(({ bytes, path }) => ({ bytes, path })),\n ];\n return estimateArchiveBytes(entries);\n};\n\nexport const generateSurveyAssistantSupportBundle = async (\n prepared: PreparedSurveyAssistantSupportBundle,\n selection: SurveyAssistantSupportBundleSelection,\n config?: SurveyAssistantSupportBundleConfig,\n): Promise<GeneratedSurveyAssistantSupportBundle> => {\n assertSurveyAssistantSupportBundleEnabled(config);\n const generatedAt = new Date().toISOString();\n const selectedEntries = prepared.entries.filter((entry) => selection[entry.category]);\n const allEntries = [\n ...createRequiredEntries(prepared, selection, config, generatedAt),\n ...selectedEntries.map(({ bytes, path }) => ({ bytes, path })),\n ];\n const estimatedBytes = estimateArchiveBytes(allEntries);\n if (estimatedBytes > prepared.limits.bundleBytes) {\n throw new Error(\"The selected support-bundle data exceeds the configured bundle limit.\");\n }\n const blob = await createZipBlob(allEntries);\n if (blob.size > prepared.limits.bundleBytes) {\n throw new Error(\"The selected support-bundle data exceeds the configured bundle limit.\");\n }\n const safeToken =\n (prepared.attempt?.requestId ?? prepared.attempt?.turnFinal?.turnId ?? \"unidentified\")\n .replace(/[^A-Za-z0-9_-]/g, \"-\")\n .slice(0, 64) || \"unidentified\";\n const timestamp = generatedAt.replace(/[-:]/g, \"\").replace(/\\.\\d{3}Z$/, \"Z\");\n return {\n blob,\n filename: `case-survey-assistant-support-${safeToken}-${timestamp}.zip`,\n generatedAt,\n includedCategories: (Object.keys(selection) as SurveyAssistantSupportBundleCategory[]).filter(\n (category) => selection[category],\n ),\n size: blob.size,\n };\n};\n\nexport const downloadSurveyAssistantSupportBundle = (\n bundle: GeneratedSurveyAssistantSupportBundle,\n) => {\n const url = URL.createObjectURL(bundle.blob);\n const anchor = document.createElement(\"a\");\n anchor.href = url;\n anchor.download = bundle.filename;\n anchor.style.display = \"none\";\n document.body.append(anchor);\n anchor.click();\n anchor.remove();\n window.setTimeout(() => URL.revokeObjectURL(url), 0);\n};\n\nexport const createSurveyAssistantSupportDetails = ({\n bundle,\n prepared,\n}: {\n bundle: GeneratedSurveyAssistantSupportBundle;\n prepared: PreparedSurveyAssistantSupportBundle;\n}): string =>\n [\n `File: ${bundle.filename}`,\n `Request: ${prepared.attempt?.requestId ?? \"unavailable\"}`,\n `Model: ${prepared.attempt?.modelId ?? \"unavailable\"}`,\n `Error category: ${prepared.attempt?.error?.code ?? \"unavailable\"}`,\n `Generated: ${bundle.generatedAt}`,\n ].join(\"\\n\");\n\nexport const createSurveyAssistantSupportMailto = ({\n bundle,\n config,\n prepared,\n}: {\n bundle: GeneratedSurveyAssistantSupportBundle;\n config: SurveyAssistantSupportBundleConfig;\n prepared: PreparedSurveyAssistantSupportBundle;\n}): string | undefined => {\n if (!isSurveyAssistantSupportBundleEnabled(config)) return undefined;\n if (!config.supportEmail?.trim()) return undefined;\n const subject =\n `${config.subjectPrefix?.trim() || \"CASE Survey Assistant support\"} ${prepared.attempt?.requestId ?? \"\"}`.trim();\n const body = [\n \"IMPORTANT: ATTACH THE DOWNLOADED ZIP FILE TO THIS EMAIL BEFORE SENDING.\",\n \"\",\n \"A Survey Assistant support bundle has been downloaded for this issue.\",\n \"\",\n createSurveyAssistantSupportDetails({ bundle, prepared }),\n ].join(\"\\n\");\n return `mailto:${encodeURIComponent(config.supportEmail.trim())}?subject=${encodeURIComponent(subject)}&body=${encodeURIComponent(body)}`;\n};\n","import { useCallback, useEffect, useState } from \"react\";\nimport {\n surveyAssistantModelCatalogSchema,\n type SurveyAssistantModelCatalog,\n type SurveyAssistantModelOption,\n} from \"../protocol\";\nimport { readSurveyAssistantJson } from \"./client-error\";\n\nconst DEFAULT_MODEL_STORAGE_KEY = \"survey-assistant-selected-model\";\n\nexport interface SurveyAssistantModelCatalogClient {\n get(): Promise<SurveyAssistantModelCatalog>;\n}\n\nexport const createSurveyAssistantModelCatalogClient = (\n api = \"/api/survey-assistant/models\",\n): SurveyAssistantModelCatalogClient => ({\n async get() {\n const body = await readSurveyAssistantJson(\n await fetch(api, { cache: \"no-store\" }),\n \"The assistant model catalog could not be loaded.\",\n );\n return surveyAssistantModelCatalogSchema.parse(body);\n },\n});\n\nexport interface UseSurveyAssistantModelCatalogOptions {\n api?: string;\n client?: SurveyAssistantModelCatalogClient;\n onModelChange?(modelId: string): void;\n storageKey?: string | false;\n}\n\nexport interface SurveyAssistantModelCatalogState {\n error: Error | null;\n loading: boolean;\n modelId?: string;\n models: SurveyAssistantModelOption[];\n reload(): void;\n selectModel(modelId: string): void;\n}\n\nexport const useSurveyAssistantModelCatalog = ({\n api,\n client: providedClient,\n onModelChange,\n storageKey = DEFAULT_MODEL_STORAGE_KEY,\n}: UseSurveyAssistantModelCatalogOptions = {}): SurveyAssistantModelCatalogState => {\n const [models, setModels] = useState<SurveyAssistantModelOption[]>([]);\n const [modelId, setModelId] = useState<string>();\n const [error, setError] = useState<Error | null>(null);\n const [loading, setLoading] = useState(true);\n const [reloadToken, setReloadToken] = useState(0);\n\n useEffect(() => {\n let cancelled = false;\n const client = providedClient ?? createSurveyAssistantModelCatalogClient(api);\n setLoading(true);\n setError(null);\n void client\n .get()\n .then((catalog) => {\n if (cancelled) return;\n const rememberedId =\n storageKey && typeof window !== \"undefined\"\n ? (window.localStorage.getItem(storageKey) ?? undefined)\n : undefined;\n const selectedId =\n rememberedId && catalog.models.some((model) => model.id === rememberedId)\n ? rememberedId\n : catalog.defaultModelId;\n setModels(catalog.models);\n setModelId(selectedId);\n onModelChange?.(selectedId);\n })\n .catch((reason: unknown) => {\n if (!cancelled) setError(reason instanceof Error ? reason : new Error(String(reason)));\n })\n .finally(() => {\n if (!cancelled) setLoading(false);\n });\n return () => {\n cancelled = true;\n };\n }, [api, onModelChange, providedClient, reloadToken, storageKey]);\n\n const selectModel = useCallback(\n (nextModelId: string) => {\n if (!models.some((model) => model.id === nextModelId)) return;\n setModelId(nextModelId);\n if (storageKey && typeof window !== \"undefined\") {\n window.localStorage.setItem(storageKey, nextModelId);\n }\n onModelChange?.(nextModelId);\n },\n [models, onModelChange, storageKey],\n );\n\n const reload = useCallback(() => setReloadToken((current) => current + 1), []);\n\n return { error, loading, modelId, models, reload, selectModel };\n};\n","\"use client\";\n\nimport {\n surveyDocumentVersionSchema,\n type SurveyAssistantSnapshot,\n type SurveyDocumentVersion,\n} from \"../protocol\";\n\nconst STORAGE_PREFIX = \"case-survey-assistant:settled-document:\";\nconst memoryBaselines = new Map<string, SurveyDocumentVersion>();\n\nconst getStorageKey = (resourceId: string, threadId: string) =>\n `${STORAGE_PREFIX}${encodeURIComponent(resourceId)}:${encodeURIComponent(threadId)}`;\n\nconst getSessionStorage = (): Storage | undefined => {\n if (typeof document === \"undefined\") return undefined;\n\n try {\n return window.sessionStorage;\n } catch {\n return undefined;\n }\n};\n\nexport const readSettledDocumentVersion = ({\n resourceId,\n threadId,\n}: {\n resourceId: string;\n threadId: string;\n}): SurveyDocumentVersion | undefined => {\n const storageKey = getStorageKey(resourceId, threadId);\n const storedInMemory = memoryBaselines.get(storageKey);\n if (storedInMemory) return { ...storedInMemory };\n\n const serialized = getSessionStorage()?.getItem(storageKey);\n if (!serialized) return undefined;\n\n try {\n const parsed = surveyDocumentVersionSchema.safeParse(JSON.parse(serialized));\n if (!parsed.success) return undefined;\n memoryBaselines.set(storageKey, parsed.data);\n return { ...parsed.data };\n } catch {\n return undefined;\n }\n};\n\nexport const writeSettledDocumentVersion = ({\n resourceId,\n snapshot,\n threadId,\n}: {\n resourceId: string;\n snapshot: SurveyAssistantSnapshot;\n threadId: string;\n}): void => {\n const storageKey = getStorageKey(resourceId, threadId);\n const version = surveyDocumentVersionSchema.parse(snapshot.version);\n memoryBaselines.set(storageKey, version);\n\n try {\n getSessionStorage()?.setItem(storageKey, JSON.stringify(version));\n } catch {\n // In-memory continuity still works when browser storage is disabled or full.\n }\n};\n","\"use client\";\n\nimport { useChat } from \"@ai-sdk/react\";\nimport {\n SURVEY_ASSISTANT_ATTACHMENT_PART_TYPE,\n SURVEY_ASSISTANT_PROTOCOL_VERSION,\n parseSurveyAssistantError,\n surveyAssistantApplyOutcomeSchema,\n type ApplyReceipt,\n type SurveyAssistantApplyOutcome,\n type SurveyAssistantAttachmentReference,\n type SurveyApplyResult,\n type SurveyAssistantApplyPolicy,\n type SurveyAssistantTurnFinal,\n type SurveyChangeSet,\n} from \"../protocol\";\nimport type { ChatStatus, FileUIPart, UIMessage } from \"ai\";\nimport {\n useCallback,\n useEffect,\n useEffectEvent,\n useMemo,\n useReducer,\n useRef,\n useState,\n} from \"react\";\nimport {\n collectSurveyChangeSets,\n createApplyReceipts,\n resolveLatestSurveyTurnAuthorization,\n resolveSurveyTurnOutcome,\n} from \"./turn-authorization\";\nimport { isSurveyAssistantTurnActive, reduceSurveyAssistantSessionState } from \"./session-state\";\nimport type { SurveyAssistantSessionState } from \"./session-state\";\nimport type { SurveyTurnOutcome } from \"./turn-authorization\";\nimport { createSurveyAssistantTransport } from \"./transport\";\nimport type { SurveyAssistantController } from \"./controller\";\nimport { readSettledDocumentVersion, writeSettledDocumentVersion } from \"./document-baseline\";\nimport {\n applySurveyAssistantLaunchUIContext,\n type SurveyAssistantLaunchUIContext,\n} from \"./thread-launcher\";\nimport {\n createSurveyAssistantDiagnosticId,\n type SurveyAssistantDiagnosticStore,\n} from \"./diagnostic-store\";\n\nconst createLocalId = (prefix: string) => {\n return createSurveyAssistantDiagnosticId(prefix);\n};\n\nconst compactOutcomeText = (value: string, maximum: number, fallback: string) => {\n const normalized = value.trim() || fallback;\n return normalized.length > maximum ? `${normalized.slice(0, maximum - 1)}…` : normalized;\n};\n\nconst createApplyOutcome = ({\n message,\n preparedChanges,\n results,\n status,\n turnId,\n}: {\n message: string;\n preparedChanges?: SurveyChangeSet[];\n results?: SurveyApplyResult[];\n status: SurveyAssistantApplyOutcome[\"status\"];\n turnId: string;\n}): SurveyAssistantApplyOutcome =>\n surveyAssistantApplyOutcomeSchema.parse({\n protocolVersion: SURVEY_ASSISTANT_PROTOCOL_VERSION,\n turnId,\n status,\n message: compactOutcomeText(message, 2_000, \"No lifecycle detail was reported.\"),\n ...(results && results.length > 0\n ? {\n results: results.slice(0, 100).map((result) => ({\n status: result.status,\n changeId: compactOutcomeText(result.changeId, 240, \"unknown-change\"),\n summary: compactOutcomeText(result.summary, 500, \"Survey change\"),\n message: compactOutcomeText(result.message, 2_000, \"No apply detail was reported.\"),\n appliedOperations: result.appliedOperations,\n })),\n }\n : {}),\n ...(preparedChanges && preparedChanges.length > 0\n ? {\n preparedChanges: preparedChanges.slice(-24).map((change) => ({\n changeId: compactOutcomeText(change.id, 240, \"unknown-change\"),\n status: change.status,\n summary: compactOutcomeText(change.summary, 500, \"Survey change\"),\n operationCount: change.operations.length,\n })),\n }\n : {}),\n createdAt: new Date().toISOString(),\n });\n\ntype AssistantTextPart = Extract<UIMessage[\"parts\"][number], { type: \"text\" }>;\n\nconst getAssistantTextParts = (message: UIMessage) =>\n message.parts.filter(\n (part): part is AssistantTextPart => part.type === \"text\" && part.text.trim().length > 0,\n );\n\nconst findLastAssistantTextMessageIndex = (\n messages: UIMessage[],\n endExclusive = messages.length,\n) => {\n for (let index = Math.min(messages.length, endExclusive) - 1; index >= 0; index -= 1) {\n const message = messages[index];\n if (message?.role === \"assistant\" && getAssistantTextParts(message).length > 0) return index;\n }\n return -1;\n};\n\nconst findLastUserMessageIndex = (messages: UIMessage[]) => {\n for (let index = messages.length - 1; index >= 0; index -= 1) {\n if (messages[index]?.role === \"user\") return index;\n }\n return -1;\n};\n\nconst pruneFailedMessagesForDisplay = (messages: UIMessage[]): UIMessage[] => {\n const lastUserIndex = findLastUserMessageIndex(messages);\n const lastCompletedAssistantIndex = findLastAssistantTextMessageIndex(messages);\n\n if (lastUserIndex > lastCompletedAssistantIndex) return messages.slice(0, lastUserIndex + 1);\n return lastCompletedAssistantIndex >= 0 ? messages.slice(0, lastCompletedAssistantIndex + 1) : [];\n};\n\nconst hasCompletedAssistantResponseAfterLastUser = (messages: UIMessage[]) => {\n const lastUserIndex = findLastUserMessageIndex(messages);\n return lastUserIndex >= 0 && findLastAssistantTextMessageIndex(messages) > lastUserIndex;\n};\n\nconst collectChangeSetsAfterLastUser = (messages: UIMessage[]) => {\n const lastUserIndex = findLastUserMessageIndex(messages);\n return lastUserIndex < 0 ? [] : collectSurveyChangeSets(messages.slice(lastUserIndex + 1));\n};\n\nconst getInitialSessionState = (messages: UIMessage[]): SurveyAssistantSessionState => {\n if (messages.length === 0) return \"idle\";\n const authorization = resolveLatestSurveyTurnAuthorization(messages);\n if (authorization.status === \"failed\") return \"failed\";\n if (authorization.status === \"aborted\") return \"aborted\";\n return \"completed\";\n};\n\nexport interface SurveyAssistantSessionOptions {\n api?: string;\n /** Explicit host decision: apply immediately, present for review, or deny mutations. */\n applyPolicy: SurveyAssistantApplyPolicy;\n controller?: SurveyAssistantController | null;\n /** Optional browser-session diagnostics sink used by the support-bundle UI. */\n diagnosticStore?: SurveyAssistantDiagnosticStore;\n initialMessages?: UIMessage[];\n modelId?: string;\n onApplyReceipts?: (receipts: ApplyReceipt[]) => void;\n /**\n * Production persistence/audit barrier. The turn remains active until this\n * resolves; rejection leaves the settled baseline unchanged.\n */\n onSettleApply?: (input: {\n changeSets: SurveyChangeSet[];\n receipts: ApplyReceipt[];\n turnFinal: SurveyAssistantTurnFinal;\n }) => void | Promise<void>;\n /**\n * Required for `review`. Resolve true to apply the authorized change sets,\n * or false to leave the editor unchanged.\n */\n onReviewChangeSets?: (\n changeSets: SurveyChangeSet[],\n turnFinal: SurveyAssistantTurnFinal,\n ) => boolean | Promise<boolean>;\n /** Reports when a turn owns the editor state, including submission, streaming, and apply. */\n onTurnActiveChange?: (active: boolean) => void;\n resourceId?: string;\n /** Host survey id sent as untrusted request context for server-side authorization. */\n surveyId?: string;\n threadId?: string;\n}\n\nexport const resolveSurveyAssistantReviewDecision = async ({\n changeSets,\n onReviewChangeSets,\n turnFinal,\n}: {\n changeSets: SurveyChangeSet[];\n onReviewChangeSets?: SurveyAssistantSessionOptions[\"onReviewChangeSets\"];\n turnFinal: SurveyAssistantTurnFinal;\n}) => {\n if (!onReviewChangeSets) {\n throw new Error(\"No survey assistant review adapter is available.\");\n }\n return onReviewChangeSets(changeSets, turnFinal);\n};\n\nexport interface SurveyAssistantSubmitMessage {\n text: string;\n files: FileUIPart[];\n /** Optional model used for this turn instead of the session's selected model. */\n modelId?: string;\n /** Turn-local UI context layered over the controller snapshot for this submission. */\n uiContext?: SurveyAssistantLaunchUIContext;\n}\n\nexport interface SurveyAssistantSession {\n applyResultsByChangeId: Record<string, SurveyApplyResult>;\n authorizationError: string | null;\n dismissError(): void;\n error: Error | undefined;\n isStreaming: boolean;\n latestTurnOutcome: SurveyTurnOutcome | null;\n messages: UIMessage[];\n prependMessages(messages: UIMessage[]): void;\n state: SurveyAssistantSessionState;\n status: ChatStatus;\n stop(): void;\n submit(message: SurveyAssistantSubmitMessage): boolean;\n retry(): void;\n}\n\nexport const useSurveyAssistantSession = ({\n api,\n applyPolicy,\n controller,\n diagnosticStore,\n initialMessages = [],\n modelId,\n onApplyReceipts,\n onSettleApply,\n onReviewChangeSets,\n onTurnActiveChange,\n resourceId: controlledResourceId,\n surveyId,\n threadId: controlledThreadId,\n}: SurveyAssistantSessionOptions): SurveyAssistantSession => {\n const [localResourceId] = useState(() => createLocalId(\"survey-assistant-local-user\"));\n const [localThreadId] = useState(() => createLocalId(\"survey-assistant-local-thread\"));\n const resourceId = controlledResourceId ?? localResourceId;\n const threadId = controlledThreadId ?? localThreadId;\n const applyOutcomeScopeKey = `${resourceId}\\u0000${threadId}`;\n const [state, dispatch] = useReducer(\n reduceSurveyAssistantSessionState,\n initialMessages,\n getInitialSessionState,\n );\n const [applyResultsByChangeId, setApplyResultsByChangeId] = useState<\n Record<string, SurveyApplyResult>\n >({});\n const [authorizationError, setAuthorizationError] = useState<string | null>(null);\n const handledTurnIdsRef = useRef<Set<string>>(new Set());\n const localTurnAwaitingApplyRef = useRef(false);\n const localTurnStreamStartedRef = useRef(false);\n const captureSettledVersionRef = useRef(false);\n const lastSubmittedUIContextRef = useRef<SurveyAssistantLaunchUIContext | undefined>(undefined);\n const lastSubmittedModelIdRef = useRef<string | undefined>(undefined);\n const previousApplyOutcomesRef = useRef<Map<string, SurveyAssistantApplyOutcome>>(new Map());\n const capturedChatErrorRef = useRef<Error | undefined>(undefined);\n\n const transport = useMemo(\n () => createSurveyAssistantTransport({ api, resourceId, surveyId, threadId }),\n [api, resourceId, surveyId, threadId],\n );\n const {\n messages,\n setMessages,\n sendMessage,\n status,\n stop: stopChat,\n error,\n clearError,\n regenerate,\n } = useChat({ id: threadId, messages: initialMessages, transport });\n const isStreaming = status === \"submitted\" || status === \"streaming\";\n const messagesRef = useRef(messages);\n messagesRef.current = messages;\n const isTurnActive = isSurveyAssistantTurnActive({ isStreaming, state });\n const notifyTurnActiveChange = useEffectEvent((active: boolean) => {\n onTurnActiveChange?.(active);\n });\n const prependMessages = useCallback(\n (olderMessages: UIMessage[]) => {\n setMessages((current) => {\n const currentIds = new Set(current.map((message) => message.id));\n return [...olderMessages.filter((message) => !currentIds.has(message.id)), ...current];\n });\n },\n [setMessages],\n );\n const turnAuthorization = useMemo(\n () => resolveLatestSurveyTurnAuthorization(messages),\n [messages],\n );\n const latestTurnOutcome = useMemo(\n () => resolveSurveyTurnOutcome({ applyResultsByChangeId, authorization: turnAuthorization }),\n [applyResultsByChangeId, turnAuthorization],\n );\n const hasUsefulLatestAssistantResponse = useMemo(\n () =>\n hasCompletedAssistantResponseAfterLastUser(messages) ||\n collectChangeSetsAfterLastUser(messages).length > 0,\n [messages],\n );\n\n const reportAuthorizationError = useCallback(\n (message: string) => {\n try {\n diagnosticStore?.recordFailure(threadId, messagesRef.current, {\n code: \"request_failed\",\n detail: message,\n retryable: false,\n });\n } catch {\n // Diagnostic capture must never replace the actual assistant error.\n }\n queueMicrotask(() => {\n setAuthorizationError(message);\n dispatch({ type: \"failed\" });\n });\n },\n [diagnosticStore, threadId],\n );\n\n const rememberApplyOutcome = useCallback(\n (outcome: SurveyAssistantApplyOutcome) => {\n previousApplyOutcomesRef.current.set(applyOutcomeScopeKey, outcome);\n try {\n diagnosticStore?.recordApplyOutcome(threadId, outcome);\n } catch {\n // Diagnostics are best-effort and cannot affect editor lifecycle.\n }\n },\n [applyOutcomeScopeKey, diagnosticStore, threadId],\n );\n\n useEffect(() => {\n if (status === \"submitted\") dispatch({ type: \"submit\" });\n if (status === \"streaming\") dispatch({ type: \"stream-started\" });\n }, [status]);\n\n useEffect(() => {\n notifyTurnActiveChange(isTurnActive);\n\n return () => {\n if (isTurnActive) notifyTurnActiveChange(false);\n };\n }, [isTurnActive]);\n\n useEffect(() => {\n if (\n !captureSettledVersionRef.current ||\n isStreaming ||\n (state !== \"completed\" && state !== \"failed\" && state !== \"aborted\" && state !== \"applied\")\n ) {\n return;\n }\n\n captureSettledVersionRef.current = false;\n try {\n const snapshot = controller?.getSnapshot();\n if (snapshot) {\n writeSettledDocumentVersion({ resourceId, snapshot, threadId });\n }\n } catch {\n // A failed host snapshot must not crash failure settlement or advance the baseline.\n }\n }, [controller, isStreaming, resourceId, state, threadId]);\n\n useEffect(() => {\n if (isStreaming) {\n localTurnStreamStartedRef.current = true;\n return;\n }\n if (!localTurnAwaitingApplyRef.current) return;\n\n if (turnAuthorization.status === \"pending\") {\n if (!localTurnStreamStartedRef.current) return;\n const timeoutId = window.setTimeout(() => {\n if (capturedChatErrorRef.current) return;\n localTurnAwaitingApplyRef.current = false;\n localTurnStreamStartedRef.current = false;\n reportAuthorizationError(\"The assistant response ended without a valid turn final.\");\n }, 100);\n return () => window.clearTimeout(timeoutId);\n }\n\n localTurnAwaitingApplyRef.current = false;\n localTurnStreamStartedRef.current = false;\n if (turnAuthorization.status === \"invalid\") {\n reportAuthorizationError(turnAuthorization.reason);\n return;\n }\n\n const { turnFinal } = turnAuthorization;\n try {\n diagnosticStore?.recordTurnFinal(threadId, turnFinal);\n } catch {\n // Diagnostics are best-effort and cannot affect turn settlement.\n }\n if (handledTurnIdsRef.current.has(turnFinal.turnId)) return;\n handledTurnIdsRef.current.add(turnFinal.turnId);\n const preparedChanges = collectChangeSetsAfterLastUser(messages).filter(\n (change) => change.turnId === turnFinal.turnId,\n );\n\n if (turnAuthorization.status === \"failed\") {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message:\n \"The previous assistant turn failed before editor authorization. Every request-scoped draft change from that turn was discarded and was not applied.\",\n preparedChanges,\n }),\n );\n dispatch({ type: \"failed\" });\n return;\n }\n if (turnAuthorization.status === \"aborted\") {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message:\n \"The previous assistant turn was interrupted before editor authorization. Every request-scoped draft change from that turn was discarded and was not applied.\",\n preparedChanges,\n }),\n );\n dispatch({ type: \"aborted\" });\n return;\n }\n if (turnAuthorization.changeSets.length === 0) {\n if ((turnFinal.blockedChangeSetIds?.length ?? 0) > 0) {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message:\n \"The previous assistant turn ended with unresolved rejected changes. No request-scoped draft change from that turn was authorized or applied.\",\n preparedChanges,\n }),\n );\n }\n dispatch({ type: \"completed\" });\n return;\n }\n if (applyPolicy === \"deny\") {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message: \"The host apply policy did not authorize editor mutations for this turn.\",\n preparedChanges,\n }),\n );\n dispatch({ type: \"completed\" });\n return;\n }\n dispatch({ type: \"apply-started\" });\n void (async () => {\n if (applyPolicy === \"review\") {\n let approved: boolean;\n try {\n approved = await resolveSurveyAssistantReviewDecision({\n changeSets: turnAuthorization.changeSets,\n onReviewChangeSets,\n turnFinal,\n });\n } catch (error) {\n const message =\n error instanceof Error &&\n error.message === \"No survey assistant review adapter is available.\"\n ? error.message\n : \"The survey assistant review could not be completed.\";\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message,\n preparedChanges,\n }),\n );\n reportAuthorizationError(message);\n return;\n }\n if (!approved) {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"not-applied\",\n message: \"The proposed editor changes were not approved during review.\",\n preparedChanges,\n }),\n );\n dispatch({ type: \"completed\" });\n return;\n }\n }\n\n if (!controller?.applyAssistantChanges) {\n const message = \"No survey editor apply adapter is available.\";\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"apply-failed\",\n message,\n preparedChanges,\n }),\n );\n reportAuthorizationError(message);\n return;\n }\n const results: SurveyApplyResult[] = [];\n let applyStarted = false;\n const hasCompleteApplyResults = () => {\n const ids = new Set(results.map((result) => result.changeId));\n return (\n results.length === turnAuthorization.changeSets.length &&\n ids.size === results.length &&\n turnAuthorization.changeSets.every((change) => ids.has(change.id))\n );\n };\n const allChangesApplied = () =>\n hasCompleteApplyResults() && results.every((result) => result.status === \"applied\");\n const retainApplyResults = () => {\n const entries = results.map((result) => [result.changeId, result]);\n queueMicrotask(() =>\n setApplyResultsByChangeId((current) => ({ ...current, ...Object.fromEntries(entries) })),\n );\n };\n\n try {\n const beforeSnapshot = controller.getSnapshot();\n if (!beforeSnapshot) throw new Error(\"Editor snapshot unavailable.\");\n applyStarted = true;\n results.push(...controller.applyAssistantChanges(turnAuthorization.changeSets).results);\n retainApplyResults();\n const receipts = createApplyReceipts({\n beforeSnapshot,\n afterSnapshot: controller.getSnapshot(),\n changeSets: turnAuthorization.changeSets,\n results,\n turnFinal,\n });\n try {\n diagnosticStore?.recordApplyReceipts(threadId, receipts);\n } catch {\n // Diagnostics are best-effort and cannot affect host receipt delivery.\n }\n onApplyReceipts?.(receipts);\n if (!hasCompleteApplyResults())\n throw new Error(\"The host returned mismatched apply results.\");\n if (!allChangesApplied()) {\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: \"apply-failed\",\n message: \"One or more authorized survey changes could not be applied to the editor.\",\n preparedChanges,\n results,\n }),\n );\n dispatch({ type: \"completed\" });\n return;\n }\n await onSettleApply?.({\n changeSets: turnAuthorization.changeSets,\n receipts,\n turnFinal,\n });\n previousApplyOutcomesRef.current.delete(applyOutcomeScopeKey);\n dispatch({ type: \"applied\" });\n } catch {\n // Preserve returned batch results if receipt delivery or host settlement throws.\n retainApplyResults();\n const applied = allChangesApplied();\n const message = applied\n ? \"The assistant changes were applied locally but could not be settled by the host.\"\n : applyStarted\n ? \"The host could not complete the assistant apply lifecycle. Some changes may already have been applied.\"\n : \"The editor state was unavailable before applying the assistant changes. No changes were applied.\";\n rememberApplyOutcome(\n createApplyOutcome({\n turnId: turnFinal.turnId,\n status: applied ? \"settle-failed\" : \"apply-failed\",\n message,\n preparedChanges,\n results,\n }),\n );\n reportAuthorizationError(message);\n }\n })();\n }, [\n applyPolicy,\n applyOutcomeScopeKey,\n controller,\n diagnosticStore,\n isStreaming,\n onApplyReceipts,\n onReviewChangeSets,\n onSettleApply,\n reportAuthorizationError,\n rememberApplyOutcome,\n messages,\n threadId,\n turnAuthorization,\n ]);\n\n useEffect(() => {\n if (!error) {\n capturedChatErrorRef.current = undefined;\n return;\n }\n if (capturedChatErrorRef.current === error) return;\n capturedChatErrorRef.current = error;\n localTurnAwaitingApplyRef.current = false;\n localTurnStreamStartedRef.current = false;\n dispatch({ type: \"failed\" });\n try {\n diagnosticStore?.recordFailure(\n threadId,\n messagesRef.current,\n parseSurveyAssistantError(error),\n );\n } catch {\n // Diagnostic capture must never replace the actual assistant error.\n }\n if (!hasUsefulLatestAssistantResponse) setMessages(pruneFailedMessagesForDisplay);\n }, [diagnosticStore, error, hasUsefulLatestAssistantResponse, setMessages, threadId]);\n\n const submit = useCallback(\n ({\n files,\n modelId: submittedModelId,\n text: rawText,\n uiContext,\n }: SurveyAssistantSubmitMessage) => {\n const text = rawText.trim();\n if (!text && files.length === 0) return false;\n if (isStreaming || localTurnAwaitingApplyRef.current) return false;\n\n let snapshot;\n try {\n snapshot = applySurveyAssistantLaunchUIContext(\n controller?.getSnapshot() ?? null,\n uiContext,\n );\n } catch {\n reportAuthorizationError(\n \"The editor state was unavailable before sending the assistant request. No request was sent.\",\n );\n return false;\n }\n\n localTurnAwaitingApplyRef.current = true;\n localTurnStreamStartedRef.current = false;\n setAuthorizationError(null);\n if ((authorizationError || error) && !hasUsefulLatestAssistantResponse) {\n setMessages(pruneFailedMessagesForDisplay);\n }\n clearError();\n dispatch({ type: \"submit\" });\n captureSettledVersionRef.current = true;\n lastSubmittedUIContextRef.current = uiContext;\n lastSubmittedModelIdRef.current = submittedModelId ?? modelId;\n\n const requestId = createSurveyAssistantDiagnosticId();\n try {\n diagnosticStore?.beginAttempt({\n files,\n modelId: lastSubmittedModelIdRef.current,\n requestId,\n resourceId,\n submittedSurvey: snapshot,\n threadId,\n });\n } catch {\n // Diagnostic capture is optional; the assistant request must continue.\n }\n void sendMessage(files.length > 0 ? (text ? { text, files } : { files }) : { text }, {\n body: {\n requestId,\n snapshot,\n previousSettledVersion: readSettledDocumentVersion({ resourceId, threadId }),\n previousApplyOutcome: previousApplyOutcomesRef.current.get(applyOutcomeScopeKey),\n ...(lastSubmittedModelIdRef.current ? { modelId: lastSubmittedModelIdRef.current } : {}),\n },\n });\n return true;\n },\n [\n authorizationError,\n applyOutcomeScopeKey,\n clearError,\n controller,\n diagnosticStore,\n error,\n hasUsefulLatestAssistantResponse,\n isStreaming,\n modelId,\n resourceId,\n reportAuthorizationError,\n sendMessage,\n setMessages,\n threadId,\n ],\n );\n\n const stop = useCallback(() => {\n localTurnAwaitingApplyRef.current = false;\n localTurnStreamStartedRef.current = false;\n dispatch({ type: \"aborted\" });\n void stopChat();\n }, [stopChat]);\n\n const retry = useCallback(() => {\n let snapshot;\n try {\n snapshot = applySurveyAssistantLaunchUIContext(\n controller?.getSnapshot() ?? null,\n lastSubmittedUIContextRef.current,\n );\n } catch {\n reportAuthorizationError(\n \"The editor state was unavailable before retrying the assistant request. No request was sent.\",\n );\n return;\n }\n localTurnAwaitingApplyRef.current = true;\n localTurnStreamStartedRef.current = false;\n setAuthorizationError(null);\n clearError();\n dispatch({ type: \"submit\" });\n captureSettledVersionRef.current = true;\n const latestUserMessage = [...messagesRef.current]\n .reverse()\n .find((message) => message.role === \"user\");\n const files = (latestUserMessage?.parts ?? []).filter(\n (part): part is FileUIPart => part.type === \"file\",\n );\n const attachmentReferences = (latestUserMessage?.parts ?? []).flatMap((part) =>\n part.type === SURVEY_ASSISTANT_ATTACHMENT_PART_TYPE &&\n typeof part.data === \"object\" &&\n part.data !== null\n ? [part.data as SurveyAssistantAttachmentReference]\n : [],\n );\n const requestId = createSurveyAssistantDiagnosticId();\n try {\n diagnosticStore?.beginAttempt({\n attachmentReferences,\n files,\n modelId: lastSubmittedModelIdRef.current ?? modelId,\n requestId,\n resourceId,\n submittedSurvey: snapshot,\n threadId,\n });\n diagnosticStore?.recordEvent(threadId, \"retry\");\n } catch {\n // Diagnostic capture is optional; retry must continue.\n }\n void regenerate({\n body: {\n requestId,\n snapshot,\n previousSettledVersion: readSettledDocumentVersion({ resourceId, threadId }),\n previousApplyOutcome: previousApplyOutcomesRef.current.get(applyOutcomeScopeKey),\n ...(lastSubmittedModelIdRef.current ? { modelId: lastSubmittedModelIdRef.current } : {}),\n },\n });\n }, [\n applyOutcomeScopeKey,\n clearError,\n controller,\n diagnosticStore,\n modelId,\n regenerate,\n resourceId,\n reportAuthorizationError,\n threadId,\n ]);\n\n const dismissError = useCallback(() => {\n localTurnAwaitingApplyRef.current = false;\n localTurnStreamStartedRef.current = false;\n if (!hasUsefulLatestAssistantResponse) setMessages(pruneFailedMessagesForDisplay);\n setAuthorizationError(null);\n clearError();\n dispatch({ type: \"reset\", hasTranscript: messages.length > 0 });\n try {\n diagnosticStore?.recordEvent(threadId, \"dismiss\");\n } catch {\n // Diagnostic capture is optional.\n }\n }, [\n clearError,\n diagnosticStore,\n hasUsefulLatestAssistantResponse,\n messages.length,\n setMessages,\n threadId,\n ]);\n\n return {\n applyResultsByChangeId,\n authorizationError,\n dismissError,\n error,\n isStreaming,\n latestTurnOutcome,\n messages,\n prependMessages,\n state,\n status,\n stop,\n submit,\n retry,\n };\n};\n"],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"request-context-CG4SWijt.mjs","names":[],"sources":["../src/server/request-context.ts"],"sourcesContent":["import {\n MASTRA_RESOURCE_ID_KEY,\n MASTRA_THREAD_ID_KEY,\n RequestContext,\n} from \"@mastra/core/request-context\";\nimport type { OpenAICompatibleConfig } from \"@mastra/core/llm\";\nimport type { AgentExecutionOptions } from \"@mastra/core/agent\";\nimport {\n surveyAssistantSnapshotPayloadSchema,\n surveyAssistantApplyOutcomeSchema,\n surveyDocumentVersionSchema,\n type SurveyAssistantApplyOutcome,\n type SurveyDocumentSnapshot,\n type SurveyDocumentVersion,\n} from \"../protocol\";\nimport {\n createSurveyAssistantEngineContext,\n TurnSurveyDraft,\n type SurveyAssistantCapabilitySet,\n type SurveyAssistantEngineContext,\n} from \"../engine\";\nimport { defaultSurveyAssistantCapabilitySet } from \"../capabilities/default\";\nimport type {\n SurveyAssistantAttachmentAccess,\n SurveyAssistantModelAttachment,\n} from \"./thread-documents\";\n\nexport interface SurveyAssistantInvocationContext {\n kind: \"chat\";\n}\n\nexport interface SurveyAssistantIdentityContext {\n authority: \"experimental-client-request\" | \"authenticated-host\";\n resourceId: string;\n surveyId?: string;\n threadId: string;\n}\n\nexport interface SurveyAssistantModelSelection {\n id: string;\n model: string | OpenAICompatibleConfig;\n providerName?: string;\n providerOptions?: AgentExecutionOptions[\"providerOptions\"];\n}\n\nexport type SurveyAssistantDocumentTransition =\n | { status: \"no-baseline\" }\n | {\n status: \"session-changed\";\n previousHistoryIndex: number;\n currentHistoryIndex: number;\n }\n | {\n status: \"unchanged\";\n previousHistoryIndex: number;\n currentHistoryIndex: number;\n capabilitiesChanged: boolean;\n }\n | {\n status: \"changed\";\n previousHistoryIndex: number;\n currentHistoryIndex: number;\n historyDirection: \"backward\" | \"forward\" | \"same-index\";\n recordedSources: Array<\"user\" | \"system\" | \"assistant\">;\n capabilitiesChanged: boolean;\n };\n\nexport interface SurveyAssistantRequestContext {\n invocation: SurveyAssistantInvocationContext;\n turnId: string;\n turnDraft: TurnSurveyDraft;\n identity: SurveyAssistantIdentityContext;\n authenticatedResourceId?: string;\n authorizedThreadId?: string;\n applyPolicy?: \"auto\" | \"review\" | \"deny\";\n mastra__resourceId?: string;\n mastra__threadId?: string;\n documentTransition?: SurveyAssistantDocumentTransition;\n engineContext?: SurveyAssistantEngineContext;\n documentSnapshot?: SurveyDocumentSnapshot;\n modelAttachments?: SurveyAssistantModelAttachment[];\n attachmentAccess?: SurveyAssistantAttachmentAccess;\n modelSelection?: SurveyAssistantModelSelection;\n previousApplyOutcome?: SurveyAssistantApplyOutcome;\n}\n\nexport const parseSurveyAssistantSnapshot = (value: unknown): SurveyDocumentSnapshot | null => {\n if (value === undefined || value === null) {\n return null;\n }\n\n return surveyAssistantSnapshotPayloadSchema.parse(value);\n};\n\nexport const parseSurveyAssistantPreviousSettledVersion = (\n value: unknown,\n): SurveyDocumentVersion | null => {\n if (value === undefined || value === null) {\n return null;\n }\n\n return surveyDocumentVersionSchema.parse(value);\n};\n\nexport const parseSurveyAssistantPreviousApplyOutcome = (\n value: unknown,\n): SurveyAssistantApplyOutcome | null => {\n if (value === undefined || value === null) {\n return null;\n }\n\n return surveyAssistantApplyOutcomeSchema.parse(value);\n};\n\nexport const deriveSurveyAssistantDocumentTransition = ({\n current,\n previous,\n}: {\n current: SurveyDocumentSnapshot | null;\n previous: SurveyDocumentVersion | null;\n}): SurveyAssistantDocumentTransition | undefined => {\n if (!current) return undefined;\n if (!previous) return { status: \"no-baseline\" };\n\n const previousHistoryIndex = previous.historyIndex;\n const currentHistoryIndex = current.version.historyIndex;\n if (previous.sessionId !== current.version.sessionId) {\n return {\n status: \"session-changed\",\n previousHistoryIndex,\n currentHistoryIndex,\n };\n }\n\n const capabilitiesChanged = previous.capabilityDigest !== current.version.capabilityDigest;\n if (previous.contentHash === current.version.contentHash) {\n return {\n status: \"unchanged\",\n previousHistoryIndex,\n currentHistoryIndex,\n capabilitiesChanged,\n };\n }\n\n const historyDirection =\n currentHistoryIndex > previousHistoryIndex\n ? \"forward\"\n : currentHistoryIndex < previousHistoryIndex\n ? \"backward\"\n : \"same-index\";\n const recordedSources =\n historyDirection === \"forward\"\n ? [\n ...new Set(\n (current.ui.history?.recent ?? [])\n .filter(\n (entry) => entry.index > previousHistoryIndex && entry.index <= currentHistoryIndex,\n )\n .flatMap((entry) => (entry.source ? [entry.source] : [])),\n ),\n ]\n : [];\n\n return {\n status: \"changed\",\n previousHistoryIndex,\n currentHistoryIndex,\n historyDirection,\n recordedSources,\n capabilitiesChanged,\n };\n};\n\nexport const buildSurveyAssistantRequestContext = ({\n turnDraft,\n identity,\n snapshot,\n previousSettledVersion = null,\n trustedCapabilities = defaultSurveyAssistantCapabilitySet,\n attachmentAccess,\n modelAttachments = [],\n modelSelection,\n previousApplyOutcome,\n}: {\n turnDraft: TurnSurveyDraft;\n identity: SurveyAssistantIdentityContext;\n snapshot: SurveyDocumentSnapshot | null;\n previousSettledVersion?: SurveyDocumentVersion | null;\n trustedCapabilities?: SurveyAssistantCapabilitySet;\n attachmentAccess?: SurveyAssistantAttachmentAccess;\n modelAttachments?: SurveyAssistantModelAttachment[];\n modelSelection?: SurveyAssistantModelSelection;\n previousApplyOutcome?: SurveyAssistantApplyOutcome | null;\n}): RequestContext<SurveyAssistantRequestContext> => {\n const requestContext = new RequestContext<SurveyAssistantRequestContext>();\n\n requestContext.set(\"invocation\", { kind: \"chat\" });\n requestContext.set(\"turnId\", turnDraft.turnId);\n requestContext.set(\"turnDraft\", turnDraft);\n requestContext.set(\"identity\", identity);\n if (identity.authority === \"authenticated-host\") {\n requestContext.set(\"authenticatedResourceId\", identity.resourceId);\n requestContext.set(\"authorizedThreadId\", identity.threadId);\n }\n requestContext.set(MASTRA_RESOURCE_ID_KEY, identity.resourceId);\n requestContext.set(MASTRA_THREAD_ID_KEY, identity.threadId);\n const documentTransition = deriveSurveyAssistantDocumentTransition({\n current: snapshot,\n previous: previousSettledVersion,\n });\n if (documentTransition) {\n requestContext.set(\"documentTransition\", documentTransition);\n }\n if (attachmentAccess && attachmentAccess.documents.length > 0) {\n requestContext.set(\"attachmentAccess\", attachmentAccess);\n }\n if (modelAttachments.length > 0) {\n requestContext.set(\"modelAttachments\", modelAttachments);\n }\n if (modelSelection) {\n requestContext.set(\"modelSelection\", modelSelection);\n }\n if (previousApplyOutcome) {\n requestContext.set(\"previousApplyOutcome\", previousApplyOutcome);\n }\n\n if (!snapshot) {\n return requestContext;\n }\n\n const engineContext = createSurveyAssistantEngineContext(snapshot, trustedCapabilities);\n turnDraft.initialize(engineContext);\n requestContext.set(\"documentSnapshot\", snapshot);\n requestContext.set(\"engineContext\", engineContext);\n\n return requestContext;\n};\n\n/**\n * Returns the materialized request-local survey state. The immutable\n * engineContext remains available as the turn baseline, while every tool uses\n * this accessor so successful same-turn mutations are immediately visible.\n */\nexport const getSurveyAssistantEngineContext = (\n requestContext: RequestContext<SurveyAssistantRequestContext> | undefined,\n): SurveyAssistantEngineContext | undefined =>\n requestContext?.get(\"turnDraft\")?.context ?? requestContext?.get(\"engineContext\");\n\nexport const requireSurveyAssistantTurnState = (\n requestContext: RequestContext<SurveyAssistantRequestContext> | undefined,\n) => {\n const turnId = requestContext?.get(\"turnId\");\n const turnDraft = requestContext?.get(\"turnDraft\");\n if (!turnId || !turnDraft || turnDraft.turnId !== turnId) {\n throw new Error(\"Survey assistant turn context is unavailable or inconsistent.\");\n }\n\n return { turnId, turnDraft };\n};\n"],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"request-guardrails-TmgQtqp4.mjs","names":[],"sources":["../src/server/request-guardrails.ts"],"sourcesContent":["import type { UIMessage } from \"ai\";\nimport { SURVEY_ASSISTANT_ATTACHMENT_MEDIA_TYPES } from \"../protocol/attachments\";\n\nexport const SURVEY_ASSISTANT_MAX_REQUEST_BYTES = 20 * 1024 * 1024;\nexport const SURVEY_ASSISTANT_MAX_MESSAGES = 32;\nexport const SURVEY_ASSISTANT_MAX_ATTACHMENTS = 4;\nexport const SURVEY_ASSISTANT_MAX_ATTACHMENT_BYTES = 5 * 1024 * 1024;\nexport const SURVEY_ASSISTANT_MAX_TOTAL_ATTACHMENT_BYTES = 12 * 1024 * 1024;\nexport const SURVEY_ASSISTANT_MAX_TEXT_PART_CHARS = 64_000;\nexport const SURVEY_ASSISTANT_MAX_ATTACHMENT_NAME_CHARS = 255;\n\nexport const SURVEY_ASSISTANT_ACCEPTED_ATTACHMENT_TYPES = new Set<string>(\n SURVEY_ASSISTANT_ATTACHMENT_MEDIA_TYPES,\n);\n\nexport interface SurveyAssistantRequestLimits {\n acceptedAttachmentTypes: ReadonlySet<string>;\n maxAttachmentBytes: number;\n maxAttachmentNameChars: number;\n maxAttachments: number;\n maxMessages: number;\n maxRequestBytes: number;\n maxTextPartChars: number;\n maxTotalAttachmentBytes: number;\n}\n\nexport const SURVEY_ASSISTANT_DEFAULT_REQUEST_LIMITS: SurveyAssistantRequestLimits = Object.freeze({\n acceptedAttachmentTypes: SURVEY_ASSISTANT_ACCEPTED_ATTACHMENT_TYPES,\n maxAttachmentBytes: SURVEY_ASSISTANT_MAX_ATTACHMENT_BYTES,\n maxAttachmentNameChars: SURVEY_ASSISTANT_MAX_ATTACHMENT_NAME_CHARS,\n maxAttachments: SURVEY_ASSISTANT_MAX_ATTACHMENTS,\n maxMessages: SURVEY_ASSISTANT_MAX_MESSAGES,\n maxRequestBytes: SURVEY_ASSISTANT_MAX_REQUEST_BYTES,\n maxTextPartChars: SURVEY_ASSISTANT_MAX_TEXT_PART_CHARS,\n maxTotalAttachmentBytes: SURVEY_ASSISTANT_MAX_TOTAL_ATTACHMENT_BYTES,\n});\n\nexport class SurveyAssistantRequestError extends Error {\n readonly status: number;\n\n constructor(message: string, status = 400) {\n super(message);\n this.name = \"SurveyAssistantRequestError\";\n this.status = status;\n }\n}\n\nconst attachmentSignatures: Record<string, (bytes: Uint8Array) => boolean> = {\n \"application/pdf\": (bytes) =>\n bytes[0] === 0x25 && bytes[1] === 0x50 && bytes[2] === 0x44 && bytes[3] === 0x46,\n \"image/jpeg\": (bytes) => bytes[0] === 0xff && bytes[1] === 0xd8 && bytes[2] === 0xff,\n \"image/png\": (bytes) =>\n [0x89, 0x50, 0x4e, 0x47, 0x0d, 0x0a, 0x1a, 0x0a].every(\n (value, index) => bytes[index] === value,\n ),\n};\n\nconst decodeBase64Prefix = (payload: string) => {\n try {\n const binary = atob(payload.slice(0, 24));\n return Uint8Array.from(binary, (character) => character.charCodeAt(0));\n } catch {\n throw new SurveyAssistantRequestError(\"The survey assistant attachment is malformed.\");\n }\n};\n\nconst getDataUrlBytes = (url: string, expectedMediaType: string): number => {\n const match = /^data:([^;,]+);base64,([A-Za-z0-9+/]*={0,2})$/.exec(url);\n if (!match) {\n throw new SurveyAssistantRequestError(\"Attachments must be base64 data URLs.\");\n }\n if (match[1]?.toLowerCase() !== expectedMediaType.toLowerCase()) {\n throw new SurveyAssistantRequestError(\"Attachment media type does not match its data URL.\");\n }\n\n const payload = match[2] ?? \"\";\n const signatureMatches = attachmentSignatures[expectedMediaType.toLowerCase()];\n if (signatureMatches && !signatureMatches(decodeBase64Prefix(payload))) {\n throw new SurveyAssistantRequestError(\n \"Attachment content does not match its declared media type.\",\n );\n }\n const padding = payload.endsWith(\"==\") ? 2 : payload.endsWith(\"=\") ? 1 : 0;\n return Math.max(0, Math.floor((payload.length * 3) / 4) - padding);\n};\n\nexport const validateSurveyAssistantMessages = (\n value: unknown,\n limits: SurveyAssistantRequestLimits = SURVEY_ASSISTANT_DEFAULT_REQUEST_LIMITS,\n): UIMessage[] => {\n if (!Array.isArray(value) || value.length === 0) {\n throw new SurveyAssistantRequestError(\"A survey assistant message is required.\");\n }\n if (value.length > limits.maxMessages) {\n throw new SurveyAssistantRequestError(\n \"The survey assistant request contains too many messages.\",\n );\n }\n if (value.length !== 1 || value[0]?.role !== \"user\") {\n throw new SurveyAssistantRequestError(\n \"The survey assistant request must contain only the current user message.\",\n );\n }\n\n let attachmentCount = 0;\n let totalAttachmentBytes = 0;\n for (const message of value) {\n if (!message || typeof message !== \"object\" || !Array.isArray(message.parts)) {\n throw new SurveyAssistantRequestError(\"The survey assistant messages are malformed.\");\n }\n\n for (const part of message.parts) {\n if (!part || typeof part !== \"object\" || typeof part.type !== \"string\") {\n throw new SurveyAssistantRequestError(\"A survey assistant message part is malformed.\");\n }\n if (part.type === \"text\") {\n if (typeof part.text !== \"string\") {\n throw new SurveyAssistantRequestError(\"A survey assistant text part is malformed.\");\n }\n if (part.text.length > limits.maxTextPartChars) {\n throw new SurveyAssistantRequestError(\"A survey assistant message is too long.\");\n }\n continue;\n }\n if (part.type !== \"file\") {\n throw new SurveyAssistantRequestError(\n \"The survey assistant message part is not supported.\",\n );\n }\n\n attachmentCount += 1;\n if (attachmentCount > limits.maxAttachments) {\n throw new SurveyAssistantRequestError(\n \"The survey assistant request has too many attachments.\",\n );\n }\n if (\n typeof part.mediaType !== \"string\" ||\n !limits.acceptedAttachmentTypes.has(part.mediaType.toLowerCase())\n ) {\n throw new SurveyAssistantRequestError(\n \"The survey assistant attachment type is not supported. Upload a PDF, PNG, or JPEG file.\",\n );\n }\n if (typeof part.url !== \"string\") {\n throw new SurveyAssistantRequestError(\"The survey assistant attachment is malformed.\");\n }\n if (\n part.filename !== undefined &&\n (typeof part.filename !== \"string\" ||\n part.filename.length > limits.maxAttachmentNameChars ||\n /[\\u0000-\\u001f\\u007f]/.test(part.filename))\n ) {\n throw new SurveyAssistantRequestError(\"The survey assistant attachment name is invalid.\");\n }\n\n const bytes = getDataUrlBytes(part.url, part.mediaType);\n if (bytes > limits.maxAttachmentBytes) {\n throw new SurveyAssistantRequestError(\"A survey assistant attachment is too large.\");\n }\n totalAttachmentBytes += bytes;\n if (totalAttachmentBytes > limits.maxTotalAttachmentBytes) {\n throw new SurveyAssistantRequestError(\n \"The survey assistant attachments are too large in total.\",\n );\n }\n }\n }\n\n return value as UIMessage[];\n};\n\nexport const readSurveyAssistantRequestJson = async (\n request: Request,\n maxRequestBytes = SURVEY_ASSISTANT_MAX_REQUEST_BYTES,\n): Promise<unknown> => {\n const declaredLength = Number(request.headers.get(\"content-length\"));\n if (Number.isFinite(declaredLength) && declaredLength > maxRequestBytes) {\n throw new SurveyAssistantRequestError(\"The survey assistant request is too large.\", 413);\n }\n\n const reader = request.body?.getReader();\n const chunks: Uint8Array[] = [];\n let totalBytes = 0;\n if (reader) {\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n totalBytes += value.byteLength;\n if (totalBytes > maxRequestBytes) {\n await reader.cancel();\n throw new SurveyAssistantRequestError(\"The survey assistant request is too large.\", 413);\n }\n chunks.push(value);\n }\n }\n const bytes = new Uint8Array(totalBytes);\n let offset = 0;\n for (const chunk of chunks) {\n bytes.set(chunk, offset);\n offset += chunk.byteLength;\n }\n const text = new TextDecoder().decode(bytes);\n\n try {\n return JSON.parse(text) as unknown;\n } catch {\n throw new SurveyAssistantRequestError(\"The survey assistant request is not valid JSON.\");\n }\n};\n"],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"server-tasks.mjs","names":[],"sources":["../src/server/tasks.ts"],"sourcesContent":["import { Agent, type AgentConfig, type AgentExecutionOptions } from \"@mastra/core/agent\";\nimport { RequestContext } from \"@mastra/core/request-context\";\nimport { z } from \"zod\";\nimport { surveyAssistantTaskRequestSchema } from \"../protocol\";\nimport type {\n SurveyAssistantSuggestItemKeyInput,\n SurveyAssistantSuggestItemKeyResult,\n SurveyAssistantKeySuggestionCategory,\n SurveyAssistantSuggestItemLabelInput,\n SurveyAssistantSuggestItemLabelResult,\n SurveyAssistantTaskInvocationMode,\n SurveyAssistantTaskContext,\n SurveyAssistantTranslateContentInput,\n SurveyAssistantTranslateContentResult,\n} from \"../protocol\";\nimport {\n surveyAuthoringReferences,\n type SurveyAuthoringReferenceTopic,\n} from \"./authoring-references\";\nimport type {\n SurveyAssistantModelSelection,\n SurveyAssistantRequestContext,\n} from \"./request-context\";\nimport { SURVEY_ASSISTANT_TASK_AGENT_ID } from \"./constants\";\nimport { FAIR_ITEM_KEY_RULES_TEXT } from \"./fair-guidance\";\nimport { readSurveyAssistantRequestJson, SurveyAssistantRequestError } from \"./request-guardrails\";\n\ntype SurveyAssistantTaskAgentConfig = AgentConfig<\n typeof SURVEY_ASSISTANT_TASK_AGENT_ID,\n Record<string, never>,\n undefined,\n SurveyAssistantRequestContext\n>;\n\nexport interface CreateSurveyAssistantTaskAgentOptions {\n model: SurveyAssistantTaskAgentConfig[\"model\"];\n}\n\nexport const createSurveyAssistantTaskAgent = ({ model }: CreateSurveyAssistantTaskAgentOptions) =>\n new Agent<\n typeof SURVEY_ASSISTANT_TASK_AGENT_ID,\n Record<string, never>,\n undefined,\n SurveyAssistantRequestContext\n >({\n id: SURVEY_ASSISTANT_TASK_AGENT_ID,\n name: \"Survey Assistant Tasks\",\n instructions:\n \"Perform the supplied bounded survey-authoring task and return only its requested structured output.\",\n model,\n });\n\nexport interface RunSurveyAssistantTaskOptions<TSchema extends z.ZodType> {\n agent: Pick<Agent, \"generate\">;\n taskId: string;\n input: unknown;\n context: SurveyAssistantTaskContext;\n schema: TSchema;\n instructions: readonly string[];\n referenceTopics?: readonly SurveyAuthoringReferenceTopic[];\n requestContext?: RequestContext<SurveyAssistantRequestContext>;\n providerOptions?: AgentExecutionOptions[\"providerOptions\"];\n abortSignal?: AbortSignal;\n}\n\nconst BASE_TASK_INSTRUCTIONS = [\n \"You perform one bounded CASE Survey Editor AI task and return only the requested structured result.\",\n \"The supplied task context was derived from the current canonical survey document snapshot. Use it as current survey context, but do not mutate it and do not claim that any editor change was applied.\",\n \"Follow the supplied CASE authoring references where relevant. Do not invent item types, locales, ids, or capabilities that are absent from the task input and context.\",\n \"Keep generated respondent-facing wording neutral, concise, and consistent with the requested locale and surrounding survey content.\",\n \"Be fast, don't think.\",\n] as const;\n\nexport const runSurveyAssistantTask = async <TSchema extends z.ZodType>({\n agent,\n taskId,\n input,\n context,\n schema,\n instructions,\n referenceTopics = [],\n requestContext,\n providerOptions,\n abortSignal,\n}: RunSurveyAssistantTaskOptions<TSchema>): Promise<z.output<TSchema>> => {\n const references = referenceTopics.map((topic) => ({\n topic,\n title: surveyAuthoringReferences[topic].title,\n content: surveyAuthoringReferences[topic].content,\n }));\n const response = await agent.generate(\n JSON.stringify({ taskId, input, currentSurveyContext: context }),\n {\n instructions: [\n ...BASE_TASK_INSTRUCTIONS,\n ...instructions,\n ...references.map((entry) => `Reference: ${entry.title}\\n${entry.content}`),\n ],\n activeTools: [],\n inputProcessors: [],\n maxSteps: 1,\n structuredOutput: {\n schema,\n errorStrategy: \"strict\",\n },\n ...(requestContext ? { requestContext } : {}),\n ...(providerOptions ? { providerOptions } : {}),\n ...(abortSignal ? { abortSignal } : {}),\n },\n );\n\n return schema.parse(response.object);\n};\n\nconst keySuggestionValueSchema = z.object({\n text: z.string().min(1),\n rationale: z.string().optional(),\n});\n\nconst keySuggestionCategorySchema = z.enum([\"survey-pattern\", \"compact\", \"preferred\", \"fair\"]);\n\nconst keySuggestionSchema = z.object({\n surveyPattern: keySuggestionValueSchema.describe(\n \"A key that follows the strongest naming and numbering pattern in the current survey.\",\n ),\n compact: keySuggestionValueSchema.extend({\n text: z\n .string()\n .min(2)\n .max(5)\n .regex(/^[A-Z][A-Z0-9]{1,4}$/)\n .describe(\"A recognizable 2-5 character uppercase abbreviation.\"),\n }),\n preferred: keySuggestionValueSchema.describe(\n \"The key the model considers clearest without a category-specific naming constraint.\",\n ),\n fair: keySuggestionValueSchema.extend({\n text: z\n .string()\n .min(1)\n .max(32)\n .regex(/^[a-z][a-z0-9]*(?:_[a-z0-9]+)*$/)\n .describe(\"A FAIR-by-design lowercase snake_case variable name.\"),\n }),\n alternatives: z\n .array(\n keySuggestionValueSchema.extend({\n category: keySuggestionCategorySchema,\n }),\n )\n .max(2),\n});\n\nconst labelSuggestionSchema = z.object({\n suggestions: z.array(\n z.object({\n text: z.string().min(1),\n }),\n ),\n});\n\nconst translationsSchema = z.object({\n translations: z.record(z.string(), z.record(z.string(), z.string())),\n});\n\nexport interface RunSurveyAssistantBuiltInTaskOptions {\n agent: Pick<Agent, \"generate\">;\n context: SurveyAssistantTaskContext;\n mode?: SurveyAssistantTaskInvocationMode;\n requestContext?: RequestContext<SurveyAssistantRequestContext>;\n providerOptions?: AgentExecutionOptions[\"providerOptions\"];\n abortSignal?: AbortSignal;\n}\n\nconst clampLimit = (value: number | undefined, fallback: number, maximum: number) =>\n Math.min(Math.max(1, value ?? fallback), maximum);\n\nconst sanitizeCodingKey = (value: string) =>\n value\n .trim()\n .replace(/[.\\s-]+/g, \"_\")\n .replace(/[^A-Za-z0-9_]+/g, \"_\")\n .replace(/_+/g, \"_\")\n .replace(/^_+|_+$/g, \"\");\n\nconst getCodingKeyIdentity = (value: string) => sanitizeCodingKey(value).toLocaleLowerCase();\n\nconst getNumberedKeyParts = (value: string) => {\n const match = /^(.+?)_(\\d+)$/.exec(getCodingKeyIdentity(value));\n return match ? { stem: match[1], number: Number(match[2]) } : undefined;\n};\n\nconst isUnsupportedFocusedItemSequence = (\n candidate: string,\n input: SurveyAssistantSuggestItemKeyInput,\n context: SurveyAssistantTaskContext,\n) => {\n const candidateParts = getNumberedKeyParts(candidate);\n const focusItem = context.focus?.item;\n if (!candidateParts || !focusItem) return false;\n\n const focusedKeyParts = [input.currentKey, input.draftKey, focusItem.key]\n .map(getNumberedKeyParts)\n .find((parts) => parts?.stem === candidateParts.stem && parts.number < candidateParts.number);\n if (!focusedKeyParts) return false;\n\n return !context.naming?.keyExamples.some((example) => {\n const exampleParts = getNumberedKeyParts(example.key);\n return example.itemType === focusItem.itemType && exampleParts?.stem === candidateParts.stem;\n });\n};\n\nconst invocationInstruction = (mode: SurveyAssistantTaskInvocationMode | undefined) =>\n mode === \"background\"\n ? \"This is a background invocation. Be efficient, but do not relax task conventions, completeness, or output quality.\"\n : \"This is an explicit user invocation. Prioritize quality and useful variation.\";\n\nexport const runSurveyAssistantSuggestItemKeyTask = async (\n input: SurveyAssistantSuggestItemKeyInput,\n options: RunSurveyAssistantBuiltInTaskOptions,\n): Promise<SurveyAssistantSuggestItemKeyResult> => {\n const maxSuggestions = Math.min(Math.max(4, input.maxSuggestions ?? 6), 6);\n const result = await runSurveyAssistantTask({\n ...options,\n taskId: \"suggest-item-key\",\n input,\n schema: keySuggestionSchema,\n instructions: [\n \"Generate coding keys for the focused survey item, not editor labels or respondent-facing text.\",\n \"Infer the dominant topic from the focused item's visible text, descendants, hierarchy, and draft key.\",\n \"For a group or other container, treat its own descendants as the primary evidence for what the container represents. Derive a descriptive group key from those children before considering generic default container names.\",\n \"The input currentKey and draftKey, plus the focused item's key and fullKey in currentSurveyContext, identify the value being replaced. They may provide topic hints, but they are not evidence of an established naming or numbering pattern.\",\n \"Use only currentSurveyContext.naming.keyExamples and sibling keys from other items to infer the survey's established naming pattern. Pay particular attention to prefixes, casing, separators, numeric sequences, and zero padding.\",\n \"Treat a numeric pattern as established only when at least one other survey item supports it. For example, another item Q1_APPLES can support a topic-appropriate Q2_... key, while Q1_APPLES and Q2_ORANGES support Q3_.... The focused item's current key choice_1 by itself does not support choice_2 or a numeric suffix in other suggestions.\",\n \"In particular, a focused group named group_1 is a default placeholder, not a group-numbering pattern. Do not propose group_2 (or another group_N key) from it unless another group/container in currentSurveyContext.naming.keyExamples independently uses the same group_N pattern. The group's children provide semantic context, not evidence of a group-numbering pattern.\",\n \"Return one surveyPattern key that follows the strongest detected local pattern. Preserve that pattern's casing and increment a clear sequence rather than copying an existing number. If no meaningful pattern exists, use a consistent descriptive key.\",\n \"Return one compact key: a recognizable 2-5 character uppercase abbreviation using only A-Z and digits.\",\n \"Return one preferred key: the key you consider clearest and most useful without category-specific naming constraints, while still using only letters, digits, and underscores.\",\n `Return one fair key following these FAIR-by-design rules: ${FAIR_ITEM_KEY_RULES_TEXT}. Meaning belongs in metadata, so do not turn it into a sentence.`,\n `You may return up to ${Math.max(0, maxSuggestions - 4)} genuinely useful alternatives when another category has more than one strong candidate. Tag each alternative with its category.`,\n \"Never repeat the same suggestion, including case-only or punctuation-only variations.\",\n \"Do not return the current key, a sibling key, or a semantically unrelated abbreviation.\",\n `Return between 4 and ${maxSuggestions} distinct suggestions in total.`,\n invocationInstruction(options.mode),\n ],\n });\n\n const excluded = new Set(\n [input.currentKey, ...input.siblingKeys].map(getCodingKeyIdentity).filter(Boolean),\n );\n const seen = new Set<string>();\n const categorizedSuggestions: Array<{\n text: string;\n rationale?: string;\n category: SurveyAssistantKeySuggestionCategory;\n }> = [\n { ...result.surveyPattern, category: \"survey-pattern\" },\n { ...result.compact, category: \"compact\" },\n { ...result.preferred, category: \"preferred\" },\n { ...result.fair, category: \"fair\" },\n ...result.alternatives,\n ];\n const suggestions = categorizedSuggestions\n .flatMap((suggestion) => {\n const text = sanitizeCodingKey(suggestion.text);\n const identity = getCodingKeyIdentity(text);\n if (\n !text ||\n excluded.has(identity) ||\n seen.has(identity) ||\n isUnsupportedFocusedItemSequence(text, input, options.context)\n ) {\n return [];\n }\n seen.add(identity);\n return [{ ...suggestion, text }];\n })\n .slice(0, maxSuggestions);\n return { suggestions };\n};\n\nexport const runSurveyAssistantSuggestItemLabelTask = async (\n input: SurveyAssistantSuggestItemLabelInput,\n options: RunSurveyAssistantBuiltInTaskOptions,\n): Promise<SurveyAssistantSuggestItemLabelResult> => {\n const maxSuggestions = clampLimit(input.maxSuggestions, 3, 10);\n const locale = input.locale ?? options.context.survey.selectedLocale;\n const result = await runSurveyAssistantTask({\n ...options,\n taskId: \"suggest-item-label\",\n input,\n schema: labelSuggestionSchema,\n instructions: [\n \"Suggest concise editor-only item labels, not coding keys and not respondent-facing question text.\",\n \"Infer the item's purpose from its type, draft label, visible content, hierarchy, siblings, and descendants.\",\n \"Use currentSurveyContext.naming.labelExamples to infer established capitalization, prefixes, abbreviations, delimiters, and typical length.\",\n \"If existing label examples are available, the first suggestion must follow their dominant pattern while still describing the focused item accurately. Other suggestions may offer useful concise alternatives.\",\n \"Do not copy the subject matter of an unrelated example merely to imitate its style, and do not return an existing unrelated label verbatim.\",\n `Write labels in locale ${locale}.`,\n `Return at most ${maxSuggestions} distinct, specific, human-readable suggestions.`,\n invocationInstruction(options.mode),\n ],\n referenceTopics: [\"core-rules\"],\n });\n\n const normalizeLabel = (value: string) => value.trim().toLocaleLowerCase();\n const excludedLabels = new Set([\n normalizeLabel(input.draftLabel),\n ...(options.context.naming?.labelExamples ?? []).map((example) =>\n normalizeLabel(example.label),\n ),\n ]);\n const seen = new Set<string>();\n return {\n suggestions: result.suggestions\n .flatMap((suggestion) => {\n const text = suggestion.text.trim();\n const normalizedText = normalizeLabel(text);\n if (!text || excludedLabels.has(normalizedText) || seen.has(normalizedText)) return [];\n seen.add(normalizedText);\n return [{ ...suggestion, text }];\n })\n .slice(0, maxSuggestions),\n };\n};\n\nconst getProtectedTokens = (value: string) =>\n value.match(/\\{\\{[^{}]+\\}\\}|\\{[^{}]+\\}|\\$\\{[^{}]+\\}|%\\d*\\$?[a-z]/gi) ?? [];\n\nexport const runSurveyAssistantTranslateContentTask = async (\n input: SurveyAssistantTranslateContentInput,\n options: RunSurveyAssistantBuiltInTaskOptions,\n): Promise<SurveyAssistantTranslateContentResult> => {\n const result = await runSurveyAssistantTask({\n ...options,\n taskId: \"translate-content\",\n input,\n schema: translationsSchema,\n instructions: [\n \"Translate every supplied survey-content entry faithfully without adding explanations or omitting content.\",\n `Translate from ${input.sourceLocale} into exactly these target locales: ${input.targetLocales.join(\", \")}.`,\n \"Use currentSurveyContext.translation.examples as a terminology and style reference when relevant. The supplied source entries remain authoritative.\",\n \"Preserve meaning, register, survey terminology, punctuation, line breaks, response semantics, placeholders, interpolation tokens, URLs, and identifiers that should not be translated.\",\n \"Keep repeated terminology consistent across all entries and target locales. Do not use a neighboring translation when its meaning differs.\",\n \"Return plain strings keyed first by target locale and then by the original entry id. Return every requested locale and entry exactly once.\",\n invocationInstruction(options.mode),\n ],\n referenceTopics: [\"localization\"],\n });\n\n const translations: SurveyAssistantTranslateContentResult[\"translations\"] = {};\n for (const locale of input.targetLocales) {\n const entries = result.translations[locale];\n if (!entries) throw new Error(`Translation result is missing locale ${locale}.`);\n const translatedEntries: Record<string, string> = {};\n for (const entry of input.entries) {\n const translation = entries[entry.id];\n if (typeof translation !== \"string\" || translation.trim().length === 0) {\n throw new Error(`Translation result is missing entry ${entry.id} for locale ${locale}.`);\n }\n const sourceTokens = getProtectedTokens(entry.text).sort();\n const translatedTokens = getProtectedTokens(translation).sort();\n if (sourceTokens.join(\"\\u0000\") !== translatedTokens.join(\"\\u0000\")) {\n throw new Error(\n `Translation result changed protected tokens in entry ${entry.id} for locale ${locale}.`,\n );\n }\n translatedEntries[entry.id] = translation;\n }\n translations[locale] = translatedEntries;\n }\n return { translations };\n};\n\nconst MAX_TASK_REQUEST_BYTES = 512 * 1024;\nconst DEFAULT_MAX_TASK_CONCURRENT_REQUESTS = 4;\nconst DEFAULT_MAX_TASK_DURATION_MS = 60_000;\n\nexport interface SurveyAssistantTaskAuthorizedIdentity {\n resourceId: string;\n surveyId?: string;\n}\n\nexport interface SurveyAssistantTaskAuthorizationInput {\n request: Request;\n requestedResourceId?: string;\n requestedSurveyId?: string;\n}\n\nexport interface SurveyAssistantTaskModelResolutionInput {\n identity: SurveyAssistantTaskAuthorizedIdentity;\n request: Request;\n requestedModelId?: string;\n}\n\nexport interface CreateSurveyAssistantTaskHandlerOptions {\n agent:\n | Pick<Agent, \"generate\">\n | (() => Pick<Agent, \"generate\"> | Promise<Pick<Agent, \"generate\">>);\n authorize(\n input: SurveyAssistantTaskAuthorizationInput,\n ): SurveyAssistantTaskAuthorizedIdentity | Promise<SurveyAssistantTaskAuthorizedIdentity>;\n getReadinessError?(request: Request): string | null | Promise<string | null>;\n isEnabled?(request: Request): boolean | Promise<boolean>;\n maxConcurrentRequests?: number;\n maxDurationMs?: number;\n onTaskMetrics?(input: {\n durationMs: number;\n identity: SurveyAssistantTaskAuthorizedIdentity;\n status: \"completed\" | \"failed\";\n taskId: string;\n }): void;\n providerOptions?: AgentExecutionOptions[\"providerOptions\"];\n resolveModel?(\n input: SurveyAssistantTaskModelResolutionInput,\n ):\n | SurveyAssistantModelSelection\n | null\n | undefined\n | Promise<SurveyAssistantModelSelection | null | undefined>;\n}\n\nconst taskErrorResponse = (error: unknown) => {\n const status =\n typeof error === \"object\" &&\n error !== null &&\n \"status\" in error &&\n typeof error.status === \"number\"\n ? error.status\n : error instanceof SyntaxError || (error instanceof Error && error.name === \"ZodError\")\n ? 400\n : 500;\n const message =\n error instanceof SurveyAssistantRequestError\n ? error.message\n : status === 401 || status === 403 || status === 404\n ? status === 404\n ? \"Survey assistant task not found.\"\n : \"The survey assistant task is not authorized.\"\n : status >= 500\n ? \"The survey assistant task could not be completed.\"\n : \"The survey assistant task request is invalid.\";\n return Response.json(\n {\n code:\n status === 401 || status === 403 || status === 404\n ? \"authorization_failed\"\n : \"request_failed\",\n error: message,\n },\n { status },\n );\n};\n\nexport const createSurveyAssistantTaskHandler = ({\n agent,\n authorize,\n getReadinessError,\n isEnabled,\n maxConcurrentRequests = DEFAULT_MAX_TASK_CONCURRENT_REQUESTS,\n maxDurationMs = DEFAULT_MAX_TASK_DURATION_MS,\n onTaskMetrics,\n providerOptions,\n resolveModel,\n}: CreateSurveyAssistantTaskHandlerOptions) => {\n const concurrency =\n Number.isInteger(maxConcurrentRequests) && maxConcurrentRequests > 0\n ? maxConcurrentRequests\n : DEFAULT_MAX_TASK_CONCURRENT_REQUESTS;\n const duration =\n Number.isFinite(maxDurationMs) && maxDurationMs > 0\n ? maxDurationMs\n : DEFAULT_MAX_TASK_DURATION_MS;\n let activeRequests = 0;\n\n return async (request: Request): Promise<Response> => {\n if (activeRequests >= concurrency) {\n return Response.json(\n {\n code: \"rate_limited\",\n error: \"The survey assistant is handling too many tasks. Try again shortly.\",\n },\n { status: 429 },\n );\n }\n activeRequests += 1;\n const startedAt = Date.now();\n let metricsIdentity: SurveyAssistantTaskAuthorizedIdentity | undefined;\n let metricsTaskId = \"unknown\";\n let completed = false;\n try {\n if (isEnabled && !(await isEnabled(request))) {\n return Response.json(\n { code: \"request_failed\", error: \"Survey assistant is disabled.\" },\n { status: 404 },\n );\n }\n const task = surveyAssistantTaskRequestSchema.parse(\n await readSurveyAssistantRequestJson(request, MAX_TASK_REQUEST_BYTES),\n );\n metricsTaskId = task.taskId;\n const identity = await authorize({\n request,\n requestedResourceId: task.resourceId,\n requestedSurveyId: task.surveyId,\n });\n if (\n !identity?.resourceId?.trim() ||\n identity.resourceId.trim().length > 240 ||\n (identity.surveyId !== undefined &&\n (!identity.surveyId.trim() || identity.surveyId.trim().length > 240))\n ) {\n throw Object.assign(new Error(\"The host returned an invalid task identity.\"), {\n status: 500,\n });\n }\n metricsIdentity = {\n resourceId: identity.resourceId.trim(),\n ...(identity.surveyId?.trim() ? { surveyId: identity.surveyId.trim() } : {}),\n };\n\n const readinessError = await getReadinessError?.(request);\n if (readinessError) {\n return Response.json({ code: \"request_failed\", error: readinessError }, { status: 503 });\n }\n\n const requestContext = new RequestContext<SurveyAssistantRequestContext>();\n let modelSelection: SurveyAssistantModelSelection | undefined;\n if (resolveModel) {\n modelSelection =\n (await resolveModel({\n identity: metricsIdentity,\n request,\n requestedModelId: task.modelId,\n })) ?? undefined;\n if (!modelSelection) {\n return Response.json(\n {\n code: \"request_failed\",\n error: \"The selected survey assistant model is unavailable.\",\n },\n { status: 400 },\n );\n }\n requestContext.set(\"modelSelection\", modelSelection);\n }\n\n const resolvedAgent = typeof agent === \"function\" ? await agent() : agent;\n const runtime: RunSurveyAssistantBuiltInTaskOptions = {\n abortSignal: AbortSignal.any([request.signal, AbortSignal.timeout(duration)]),\n agent: resolvedAgent,\n context: task.context,\n mode: task.mode,\n requestContext,\n providerOptions: modelSelection?.providerOptions ?? providerOptions,\n };\n const result =\n task.taskId === \"suggest-item-key\"\n ? await runSurveyAssistantSuggestItemKeyTask(task.input, runtime)\n : task.taskId === \"suggest-item-label\"\n ? await runSurveyAssistantSuggestItemLabelTask(task.input, runtime)\n : await runSurveyAssistantTranslateContentTask(task.input, runtime);\n completed = true;\n return Response.json(result);\n } catch (error) {\n return taskErrorResponse(error);\n } finally {\n activeRequests = Math.max(0, activeRequests - 1);\n if (metricsIdentity) {\n try {\n onTaskMetrics?.({\n durationMs: Date.now() - startedAt,\n identity: metricsIdentity,\n status: completed ? \"completed\" : \"failed\",\n taskId: metricsTaskId,\n });\n } catch {\n // Host metrics must not change the task response.\n }\n }\n }\n };\n};\n"],"mappings":"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"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"tasks-CYqrcaRO.d.mts","names":[],"sources":["../src/server/authoring-references.ts","../src/server/tasks.ts"],"mappings":";;;;;;;;cAMa,8BAAA;AAAA,KAcD,6BAAA,WAAwC,8BAAA;AAAA,cAmCvC,yBAAA;EAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAqEA,iDAAA;;;KCjGR,8BAAA,GAAiC,WAAA,QAC7B,8BAAA,EACP,MAAA,4BAEA,6BAAA;AAAA,UAGe,qCAAA;EACf,KAAA,EAAO,8BAAA;AAAA;AAAA,cAGI,8BAAA;EAAkC;AAAA,GAAW,qCAAA,KAAqC,KAAA,gCAAA,MAAA,4BAAA,6BAAA,EAAA,qBAAA,CAAA,iBAAA;AAAA,UAc9E,6BAAA,iBAA8C,CAAA,CAAE,OAAA;EAC/D,KAAA,EAAO,IAAA,CAAK,KAAA;EACZ,MAAA;EACA,KAAA;EACA,OAAA,EAAS,0BAAA;EACT,MAAA,EAAQ,OAAA;EACR,YAAA;EACA,eAAA,YAA2B,6BAAA;EAC3B,cAAA,GAAiB,cAAA,CAAe,6BAAA;EAChC,eAAA,GAAkB,qBAAA;EAClB,WAAA,GAAc,WAAA;AAAA;AAAA,cAWH,sBAAA,mBAAgD,CAAA,CAAE,OAAA;EAAS,KAAA;EAAA,MAAA;EAAA,KAAA;EAAA,OAAA;EAAA,MAAA;EAAA,YAAA;EAAA,eAAA;EAAA,cAAA;EAAA,eAAA;EAAA;AAAA,GAWrE,6BAAA,CAA8B,OAAA,MAAW,OAAA,CAAQ,CAAA,CAAE,MAAA,CAAO,OAAA;AAAA,UAiF5C,oCAAA;EACf,KAAA,EAAO,IAAA,CAAK,KAAA;EACZ,OAAA,EAAS,0BAAA;EACT,IAAA,GAAO,iCAAA;EACP,cAAA,GAAiB,cAAA,CAAe,6BAAA;EAChC,eAAA,GAAkB,qBAAA;EAClB,WAAA,GAAc,WAAA;AAAA;AAAA,cA8CH,oCAAA,GACX,KAAA,EAAO,kCAAA,EACP,OAAA,EAAS,oCAAA,KACR,OAAA,CAAQ,mCAAA;AAAA,cA6DE,sCAAA,GACX,KAAA,EAAO,oCAAA,EACP,OAAA,EAAS,oCAAA,KACR,OAAA,CAAQ,qCAAA;AAAA,cA6CE,sCAAA,GACX,KAAA,EAAO,oCAAA,EACP,OAAA,EAAS,oCAAA,KACR,OAAA,CAAQ,qCAAA;AAAA,UA8CM,qCAAA;EACf,UAAA;EACA,QAAA;AAAA;AAAA,UAGe,qCAAA;EACf,OAAA,EAAS,OAAA;EACT,mBAAA;EACA,iBAAA;AAAA;AAAA,UAGe,uCAAA;EACf,QAAA,EAAU,qCAAA;EACV,OAAA,EAAS,OAAA;EACT,gBAAA;AAAA;AAAA,UAGe,uCAAA;EACf,KAAA,EACI,IAAA,CAAK,KAAA,uBACE,IAAA,CAAK,KAAA,gBAAqB,OAAA,CAAQ,IAAA,CAAK,KAAA;EAClD,SAAA,CACE,KAAA,EAAO,qCAAA,GACN,qCAAA,GAAwC,OAAA,CAAQ,qCAAA;EACnD,iBAAA,EAAmB,OAAA,EAAS,OAAA,mBAA0B,OAAA;EACtD,SAAA,EAAW,OAAA,EAAS,OAAA,aAAoB,OAAA;EACxC,qBAAA;EACA,aAAA;EACA,aAAA,EAAe,KAAA;IACb,UAAA;IACA,QAAA,EAAU,qCAAA;IACV,MAAA;IACA,MAAA;EAAA;EAEF,eAAA,GAAkB,qBAAA;EAClB,YAAA,EACE,KAAA,EAAO,uCAAA,GAEL,6BAAA,sBAGA,OAAA,CAAQ,6BAAA;AAAA;AAAA,cAmCD,gCAAA;EAAoC,KAAA;EAAA,SAAA;EAAA,iBAAA;EAAA,SAAA;EAAA,qBAAA;EAAA,aAAA;EAAA,aAAA;EAAA,eAAA;EAAA;AAAA,GAU9C,uCAAA,MAWa,OAAA,EAAS,OAAA,KAAU,OAAA,CAAQ,QAAA"}
|
|
@@ -1,107 +0,0 @@
|
|
|
1
|
-
import * as _$ai from "ai";
|
|
2
|
-
import { UIMessage } from "ai";
|
|
3
|
-
|
|
4
|
-
//#region src/server/thread-documents.d.ts
|
|
5
|
-
interface SurveyAssistantThreadDocument {
|
|
6
|
-
id: string;
|
|
7
|
-
name: string;
|
|
8
|
-
mediaType: string;
|
|
9
|
-
bytes: number;
|
|
10
|
-
contentHash: string;
|
|
11
|
-
createdAt: string;
|
|
12
|
-
}
|
|
13
|
-
interface SurveyAssistantThreadDocumentContent extends SurveyAssistantThreadDocument {
|
|
14
|
-
data: string;
|
|
15
|
-
}
|
|
16
|
-
interface SurveyAssistantModelAttachment {
|
|
17
|
-
filename: string;
|
|
18
|
-
mediaType: string;
|
|
19
|
-
data: string;
|
|
20
|
-
contentHash: string;
|
|
21
|
-
}
|
|
22
|
-
interface SurveyAssistantAttachmentAccess {
|
|
23
|
-
documents: SurveyAssistantThreadDocument[];
|
|
24
|
-
/** Attachments submitted in the current user message; already present as model context. */
|
|
25
|
-
currentDocumentIds?: string[];
|
|
26
|
-
selectedAttachments: SurveyAssistantModelAttachment[];
|
|
27
|
-
load(documentIds: string[]): Promise<SurveyAssistantModelAttachment[]>;
|
|
28
|
-
}
|
|
29
|
-
interface SurveyAssistantThreadDocumentRepository {
|
|
30
|
-
put(input: {
|
|
31
|
-
resourceId: string;
|
|
32
|
-
threadId: string;
|
|
33
|
-
name: string;
|
|
34
|
-
mediaType: string;
|
|
35
|
-
data: string;
|
|
36
|
-
bytes: number;
|
|
37
|
-
}): Promise<SurveyAssistantThreadDocument>;
|
|
38
|
-
list(input: {
|
|
39
|
-
resourceId: string;
|
|
40
|
-
threadId: string;
|
|
41
|
-
}): Promise<SurveyAssistantThreadDocument[]>;
|
|
42
|
-
read(input: {
|
|
43
|
-
resourceId: string;
|
|
44
|
-
threadId: string;
|
|
45
|
-
documentId: string;
|
|
46
|
-
}): Promise<SurveyAssistantThreadDocumentContent | null>;
|
|
47
|
-
deleteThread(input: {
|
|
48
|
-
resourceId: string;
|
|
49
|
-
threadId: string;
|
|
50
|
-
}): Promise<void>;
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* Replaces current-turn file data with small repository references before the
|
|
54
|
-
* message is handed to Mastra for persistence. The provider-bound attachment
|
|
55
|
-
* processor re-injects the authorized repository copy transiently.
|
|
56
|
-
*/
|
|
57
|
-
declare const replaceCurrentSurveyAssistantAttachmentsWithReferences: ({
|
|
58
|
-
documents,
|
|
59
|
-
messages
|
|
60
|
-
}: {
|
|
61
|
-
documents: SurveyAssistantThreadDocument[];
|
|
62
|
-
messages: UIMessage[];
|
|
63
|
-
}) => UIMessage[];
|
|
64
|
-
declare const registerSurveyAssistantThreadAttachments: ({
|
|
65
|
-
messages,
|
|
66
|
-
repository,
|
|
67
|
-
resourceId,
|
|
68
|
-
threadId
|
|
69
|
-
}: {
|
|
70
|
-
messages: UIMessage[];
|
|
71
|
-
repository: SurveyAssistantThreadDocumentRepository;
|
|
72
|
-
resourceId: string;
|
|
73
|
-
threadId: string;
|
|
74
|
-
}) => Promise<SurveyAssistantThreadDocument[]>;
|
|
75
|
-
declare const removeHistoricalSurveyAssistantAttachments: (messages: UIMessage[]) => UIMessage<unknown, _$ai.UIDataTypes, _$ai.UITools>[];
|
|
76
|
-
/**
|
|
77
|
-
* Excludes the exact repository documents already loaded for the current turn.
|
|
78
|
-
* Message parts are references by this stage and are not a deduplication source.
|
|
79
|
-
*/
|
|
80
|
-
declare const getSurveyAssistantReplayableDocuments: (documents: SurveyAssistantThreadDocument[], currentDocumentIds: ReadonlySet<string>) => SurveyAssistantThreadDocument[];
|
|
81
|
-
declare const loadSurveyAssistantThreadAttachments: ({
|
|
82
|
-
currentDocumentIds,
|
|
83
|
-
documents,
|
|
84
|
-
repository,
|
|
85
|
-
resourceId,
|
|
86
|
-
threadId
|
|
87
|
-
}: {
|
|
88
|
-
currentDocumentIds?: ReadonlySet<string>;
|
|
89
|
-
documents: SurveyAssistantThreadDocument[];
|
|
90
|
-
repository: SurveyAssistantThreadDocumentRepository;
|
|
91
|
-
resourceId: string;
|
|
92
|
-
threadId: string;
|
|
93
|
-
}) => Promise<SurveyAssistantModelAttachment[]>;
|
|
94
|
-
declare const loadSurveyAssistantDocuments: ({
|
|
95
|
-
documents,
|
|
96
|
-
repository,
|
|
97
|
-
resourceId,
|
|
98
|
-
threadId
|
|
99
|
-
}: {
|
|
100
|
-
documents: SurveyAssistantThreadDocument[];
|
|
101
|
-
repository: SurveyAssistantThreadDocumentRepository;
|
|
102
|
-
resourceId: string;
|
|
103
|
-
threadId: string;
|
|
104
|
-
}) => Promise<SurveyAssistantModelAttachment[]>;
|
|
105
|
-
//#endregion
|
|
106
|
-
export { SurveyAssistantThreadDocumentRepository as a, loadSurveyAssistantThreadAttachments as c, replaceCurrentSurveyAssistantAttachmentsWithReferences as d, SurveyAssistantThreadDocumentContent as i, registerSurveyAssistantThreadAttachments as l, SurveyAssistantModelAttachment as n, getSurveyAssistantReplayableDocuments as o, SurveyAssistantThreadDocument as r, loadSurveyAssistantDocuments as s, SurveyAssistantAttachmentAccess as t, removeHistoricalSurveyAssistantAttachments as u };
|
|
107
|
-
//# sourceMappingURL=thread-documents-rmd6nyX9.d.mts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"thread-documents-rmd6nyX9.d.mts","names":[],"sources":["../src/server/thread-documents.ts"],"mappings":";;;;UAOiB,6BAAA;EACf,EAAA;EACA,IAAA;EACA,SAAA;EACA,KAAA;EACA,WAAA;EACA,SAAA;AAAA;AAAA,UAGe,oCAAA,SAA6C,6BAAA;EAC5D,IAAA;AAAA;AAAA,UAGe,8BAAA;EACf,QAAA;EACA,SAAA;EACA,IAAA;EACA,WAAA;AAAA;AAAA,UAGe,+BAAA;EACf,SAAA,EAAW,6BAAA;EAXP;EAaJ,kBAAA;EACA,mBAAA,EAAqB,8BAAA;EACrB,IAAA,CAAK,WAAA,aAAwB,OAAA,CAAQ,8BAAA;AAAA;AAAA,UAGtB,uCAAA;EACf,GAAA,CAAI,KAAA;IACF,UAAA;IACA,QAAA;IACA,IAAA;IACA,SAAA;IACA,IAAA;IACA,KAAA;EAAA,IACE,OAAA,CAAQ,6BAAA;EACZ,IAAA,CAAK,KAAA;IAAS,UAAA;IAAoB,QAAA;EAAA,IAAqB,OAAA,CAAQ,6BAAA;EAC/D,IAAA,CAAK,KAAA;IACH,UAAA;IACA,QAAA;IACA,UAAA;EAAA,IACE,OAAA,CAAQ,oCAAA;EACZ,YAAA,CAAa,KAAA;IAAS,UAAA;IAAoB,QAAA;EAAA,IAAqB,OAAA;AAAA;;;;AAfjE;;cA4Da,sDAAA;EAA0D,SAAA;EAAA;AAAA;EAIrE,SAAA,EAAW,6BAAA;EACX,QAAA,EAAU,SAAA;AAAA,MACR,SAAA;AAAA,cA2BS,wCAAA;EAAkD,QAAA;EAAA,UAAA;EAAA,UAAA;EAAA;AAAA;EAM7D,QAAA,EAAU,SAAA;EACV,UAAA,EAAY,uCAAA;EACZ,UAAA;EACA,QAAA;AAAA,MACD,OAAA,CAAA,6BAAA;AAAA,cAkCY,0CAAA,GAA8C,QAAA,EAAU,SAAA,OAAW,SAAA,UAAF,IAAA,CAAE,WAAA,EAAA,IAAA,CAAA,OAAA;;;;;cAanE,qCAAA,GACX,SAAA,EAAW,6BAAA,IACX,kBAAA,EAAoB,WAAA,aAAmB,6BAAA;AAAA,cAG5B,oCAAA;EAA8C,kBAAA;EAAA,SAAA;EAAA,UAAA;EAAA,UAAA;EAAA;AAAA;EAOzD,kBAAA,GAAqB,WAAA;EACrB,SAAA,EAAW,6BAAA;EACX,UAAA,EAAY,uCAAA;EACZ,UAAA;EACA,QAAA;AAAA,MACE,OAAA,CAAQ,8BAAA;AAAA,cAWC,4BAAA;EAAsC,SAAA;EAAA,UAAA;EAAA,UAAA;EAAA;AAAA;EAMjD,SAAA,EAAW,6BAAA;EACX,UAAA,EAAY,uCAAA;EACZ,UAAA;EACA,QAAA;AAAA,MACE,OAAA,CAAQ,8BAAA"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"thread-handlers-DBAaU7BA.d.mts","names":[],"sources":["../src/server/request-guardrails.ts","../src/server/handler.ts","../src/server/thread-handlers.ts"],"mappings":"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"}
|