@genesislcap/ai-assistant 15.27.0-agent-log-submit.3 → 15.27.1

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.
Files changed (36) hide show
  1. package/dist/ai-assistant.api.json +77 -838
  2. package/dist/ai-assistant.d.ts +23 -179
  3. package/dist/chat-driver.cjs +13 -14
  4. package/dist/chat-driver.cjs.map +2 -2
  5. package/dist/chat-driver.mjs +13 -14
  6. package/dist/chat-driver.mjs.map +2 -2
  7. package/dist/custom-elements.json +17 -454
  8. package/dist/dts/components/ai-driver/ai-driver.d.ts +11 -12
  9. package/dist/dts/components/ai-driver/ai-driver.d.ts.map +1 -1
  10. package/dist/dts/components/ai-driver/stub-driver.d.ts +17 -0
  11. package/dist/dts/components/ai-driver/stub-driver.d.ts.map +1 -0
  12. package/dist/dts/components/chat-driver/chat-driver.d.ts +10 -11
  13. package/dist/dts/components/chat-driver/chat-driver.d.ts.map +1 -1
  14. package/dist/dts/components/orchestrating-driver/orchestrating-driver.d.ts +2 -2
  15. package/dist/dts/components/orchestrating-driver/orchestrating-driver.d.ts.map +1 -1
  16. package/dist/dts/components/settings-modal/settings-modal.d.ts.map +1 -1
  17. package/dist/dts/components/settings-modal/settings-modal.styles.d.ts.map +1 -1
  18. package/dist/dts/components/settings-modal/settings-modal.template.d.ts +0 -8
  19. package/dist/dts/components/settings-modal/settings-modal.template.d.ts.map +1 -1
  20. package/dist/dts/index.d.ts +0 -1
  21. package/dist/dts/index.d.ts.map +1 -1
  22. package/dist/dts/main/main.d.ts +0 -148
  23. package/dist/dts/main/main.d.ts.map +1 -1
  24. package/dist/esm/components/ai-driver/stub-driver.js +16 -0
  25. package/dist/esm/components/chat-driver/chat-driver.js +11 -12
  26. package/dist/esm/components/orchestrating-driver/orchestrating-driver.js +5 -5
  27. package/dist/esm/components/settings-modal/settings-modal.js +0 -1
  28. package/dist/esm/components/settings-modal/settings-modal.styles.js +5 -85
  29. package/dist/esm/components/settings-modal/settings-modal.template.js +23 -167
  30. package/dist/esm/main/main.js +20 -444
  31. package/dist/esm/state/persistence/session-persister.js +20 -20
  32. package/docs/migration-GENC-1580.md +108 -58
  33. package/package.json +16 -16
  34. package/dist/dts/utils/resolve-debug-log-note.d.ts +0 -25
  35. package/dist/dts/utils/resolve-debug-log-note.d.ts.map +0 -1
  36. package/dist/esm/utils/resolve-debug-log-note.js +0 -37
@@ -58,7 +58,6 @@ import { deleteBankedBaseline } from '../utils/banked-usage-baselines';
58
58
  import { estimateContextTokens, isContextMeasurable, } from '../utils/context-tokens';
59
59
  import { logger } from '../utils/logger';
60
60
  import { filterVisibleMessages, trailingInteractionRow } from '../utils/message-partition';
61
- import { normalizeDebugLogNote, resolveDebugLogNoteConfig, } from '../utils/resolve-debug-log-note';
62
61
  import { DEFAULT_TIMESTAMP_DISPLAY, preferenceUnchanged, resolvePreferenceBaseline, } from '../utils/resolve-preference-baseline';
63
62
  import { stripAgentHandlers } from '../utils/strip-agent-handlers';
64
63
  import { emptyUsage, sumUsage, totalTokens } from '../utils/sum-usage';
@@ -93,33 +92,6 @@ export const genesisIconSvg = `<svg viewBox="-4 0 30 26" fill="none" xmlns="http
93
92
  function sanitizeIconMarkup(markup) {
94
93
  return DOMPurify.sanitize(markup, { USE_PROFILES: { svg: true, svgFilters: true } });
95
94
  }
96
- /**
97
- * Await `outcome` (a promise, or a sync return) but give up after `ms`, rejecting with a
98
- * named error. Used to bound a host callback we cannot otherwise trust to settle.
99
- */
100
- function settleWithin(outcome, ms, what) {
101
- return __awaiter(this, void 0, void 0, function* () {
102
- let timer;
103
- const timeout = new Promise((_, reject) => {
104
- timer = setTimeout(() => reject(new Error(`${what} did not settle within ${ms}ms`)), ms);
105
- });
106
- try {
107
- yield Promise.race([Promise.resolve(outcome), timeout]);
108
- }
109
- finally {
110
- clearTimeout(timer);
111
- }
112
- });
113
- }
114
- /**
115
- * How long the agent-log Send button shows its 'Sent'/'Failed' outcome before
116
- * returning to idle — long enough to read, short enough that a retry is never blocked.
117
- */
118
- const DEBUG_LOG_SUBMIT_RESULT_FLASH_MS = 4000;
119
- /** Default ceiling on the host's `debugLogSubmit.send` before the submission is failed. */
120
- const DEBUG_LOG_SUBMIT_TIMEOUT_MS = 30000;
121
- /** Announce the remaining note length once this few characters are left. */
122
- const DEBUG_LOG_NOTE_REMAINING_WARN = 20;
123
95
  /**
124
96
  * Reporter id for this element's OWN session persister in `brokenSources` (GENC-1511).
125
97
  *
@@ -334,34 +306,6 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
334
306
  * element has its own settings modal.
335
307
  */
336
308
  this.downloadingDebugLog = false;
337
- /**
338
- * True while `submitDebugLog` is building and handing off the log. Same role as
339
- * `downloadingDebugLog` for the Send button: the lifetime-stitch and the host's
340
- * `send` callback are async, so the button needs a visible in-flight state.
341
- */
342
- this.submittingDebugLog = false;
343
- /**
344
- * Outcome of the last log submission, shown briefly on the button ('Sent' /
345
- * 'Failed — retry') then cleared by `setDebugLogSubmitResult`'s timer. `null` when idle.
346
- */
347
- this.debugLogSubmitResult = null;
348
- /**
349
- * Whether the agent-log compose box (note + Send/Cancel) is open. Opened by the row's
350
- * Send button when `debugLogSubmit.note` is not `false`; closed by Cancel or a
351
- * successful send. Stays open after a failure so the typed note is not lost.
352
- */
353
- this.debugLogComposeOpen = false;
354
- /** The note typed in the compose box, raw (trimmed only at submit time). */
355
- this.debugLogNote = '';
356
- /** How long 'Sent' shows before idle. Overridable so tests need not wait 4 seconds. */
357
- this.debugLogSubmitResultFlashMs = DEBUG_LOG_SUBMIT_RESULT_FLASH_MS;
358
- /**
359
- * Bumped by `resetDebugLogSubmitState`. An in-flight `submitDebugLog` captures it and
360
- * drops its continuation when a reset (disconnect, session switch, Clear) happened
361
- * while it awaited — otherwise the stale submission would write state, arm a timer on
362
- * a torn-down element, or report 'Sent' into a session it never belonged to.
363
- */
364
- this.debugLogSubmitGeneration = 0;
365
309
  /**
366
310
  * GENC-1511 — persistence has failed repeatedly and it is no longer saving. Drives a BLOCKING
367
311
  * modal with a single Reload action: the whole failure class this ticket exists for is one the
@@ -1752,7 +1696,7 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
1752
1696
  if (agents.length === 1 && !agents[0].fallback) {
1753
1697
  // Preset for getters that read activeAgent before the first turn
1754
1698
  // (e.g. chatInputDuringExecution). The orchestrator will overwrite
1755
- // this via `agent-changed` once applyAgent fires on first sendMessage.
1699
+ // this via `agent-changed` once installAgent fires on first sendMessage.
1756
1700
  this.activeAgent = agents[0];
1757
1701
  }
1758
1702
  return new OrchestratingDriver(this.providerRegistry, agents, {
@@ -2204,9 +2148,6 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
2204
2148
  return;
2205
2149
  }
2206
2150
  this._deferredSwitchToKey = undefined;
2207
- // A note typed against the outgoing conversation must not caption the incoming one's
2208
- // log, and an outcome flash belongs to the session that produced it.
2209
- this.resetDebugLogSubmitState();
2210
2151
  // Cancel the outgoing session's debounced autosave FIRST, so it can't land in
2211
2152
  // the incoming session's file once `_sessionRef` swaps below.
2212
2153
  (_b = getPersister(oldKey)) === null || _b === void 0 ? void 0 : _b.cancelPendingSave();
@@ -2269,7 +2210,6 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
2269
2210
  // After `_sessionActive` is cleared, so the sync sees "disconnected" and stops.
2270
2211
  this.syncTimestampClock();
2271
2212
  this.stopLoadingTimer();
2272
- this.resetDebugLogSubmitState();
2273
2213
  this.state = 'idle';
2274
2214
  // Note: `compacting`/`restoring` are NOT cleared here. They're written through the
2275
2215
  // in-flight op's captured session store (see `initPersistenceForNewStore` /
@@ -2757,11 +2697,11 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
2757
2697
  * @internal
2758
2698
  */
2759
2699
  get contextReserve() {
2760
- var _a, _b, _c, _d;
2700
+ var _a, _b, _c;
2761
2701
  const resolved = (_b = (_a = this.driver) === null || _a === void 0 ? void 0 : _a.getContextReserve) === null || _b === void 0 ? void 0 : _b.call(_a);
2762
2702
  if (resolved)
2763
2703
  return resolved;
2764
- const active = (_d = (_c = this.driver) === null || _c === void 0 ? void 0 : _c.getActiveAgent) === null || _d === void 0 ? void 0 : _d.call(_c);
2704
+ const active = (_c = this.driver) === null || _c === void 0 ? void 0 : _c.getActiveAgent();
2765
2705
  const declared = active === null || active === void 0 ? void 0 : active.contextReserve;
2766
2706
  if (declared == null)
2767
2707
  return undefined;
@@ -3005,18 +2945,18 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3005
2945
  */
3006
2946
  clearSession() {
3007
2947
  return __awaiter(this, void 0, void 0, function* () {
3008
- var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k;
2948
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j;
3009
2949
  if ((_a = this.driver) === null || _a === void 0 ? void 0 : _a.isBusy())
3010
2950
  return; // the menu only opens when idle; defensive
3011
2951
  const key = this.getStateKey();
3012
2952
  // Capture the live agent + its serialized state BEFORE teardown — the
3013
2953
  // machine is stopped below, so this is the host's last chance to learn what
3014
2954
  // the agent was working on (so it can tidy up external state if it wants).
3015
- const liveActive = (_c = (_b = this.driver) === null || _b === void 0 ? void 0 : _b.getActiveAgent) === null || _c === void 0 ? void 0 : _c.call(_b);
3016
- const agentName = (_d = liveActive === null || liveActive === void 0 ? void 0 : liveActive.name) !== null && _d !== void 0 ? _d : (_e = this.activeAgent) === null || _e === void 0 ? void 0 : _e.name;
2955
+ const liveActive = (_b = this.driver) === null || _b === void 0 ? void 0 : _b.getActiveAgent();
2956
+ const agentName = (_c = liveActive === null || liveActive === void 0 ? void 0 : liveActive.name) !== null && _c !== void 0 ? _c : (_d = this.activeAgent) === null || _d === void 0 ? void 0 : _d.name;
3017
2957
  let agentSnapshot;
3018
2958
  try {
3019
- agentSnapshot = (_f = liveActive === null || liveActive === void 0 ? void 0 : liveActive.serialize) === null || _f === void 0 ? void 0 : _f.call(liveActive);
2959
+ agentSnapshot = (_e = liveActive === null || liveActive === void 0 ? void 0 : liveActive.serialize) === null || _e === void 0 ? void 0 : _e.call(liveActive);
3020
2960
  }
3021
2961
  catch (e) {
3022
2962
  logger.error('Session clear: agent serialize() failed:', e);
@@ -3027,10 +2967,7 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3027
2967
  const discarded = this.sessionUsage;
3028
2968
  if (this.driver)
3029
2969
  this.teardownDriver(key);
3030
- (_g = this._sessionRef) === null || _g === void 0 ? void 0 : _g.actions.aiAssistant.resetSession();
3031
- // Same reason as in `switchSession`: the compose box and its note were about the
3032
- // conversation just discarded.
3033
- this.resetDebugLogSubmitState();
2970
+ (_f = this._sessionRef) === null || _f === void 0 ? void 0 : _f.actions.aiAssistant.resetSession();
3034
2971
  // `resetSession` zeroes the store-backed `contextTokens`; the gate's held copy
3035
2972
  // is ours to drop. Leaving it would carry a block into a conversation that no
3036
2973
  // longer exists — the one thing `contextGate` must never do (GENC-1582).
@@ -3042,7 +2979,7 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3042
2979
  // Restore-core is owned by the shared per-session persister (GENC-1351 §5.10):
3043
2980
  // it drops the snapshot + resets the carry-forward cache. Diagnostics is
3044
2981
  // append-only and handled separately below.
3045
- yield ((_h = this.persister()) === null || _h === void 0 ? void 0 : _h.clearRestoreCore());
2982
+ yield ((_g = this.persister()) === null || _g === void 0 ? void 0 : _g.clearRestoreCore());
3046
2983
  this.confirmingClear = false;
3047
2984
  this.composerMenus.closeImmediate();
3048
2985
  this.logMeta('session.cleared', { agentName });
@@ -3051,8 +2988,8 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3051
2988
  // forward-capture cursors and flush, so the just-logged `session.cleared`
3052
2989
  // event becomes the stream's roll boundary: exactly like a page reload, the
3053
2990
  // new conversation begins a fresh section within the same lifetime log (§5.8).
3054
- resetDiagnosticsCursorsFor((_j = this.getStateKey()) !== null && _j !== void 0 ? _j : '');
3055
- (_k = this.persister()) === null || _k === void 0 ? void 0 : _k.scheduleDiagnostics();
2991
+ resetDiagnosticsCursorsFor((_h = this.getStateKey()) !== null && _h !== void 0 ? _h : '');
2992
+ (_j = this.persister()) === null || _j === void 0 ? void 0 : _j.scheduleDiagnostics();
3056
2993
  this.dispatchEvent(new CustomEvent(AiAssistantEvent.SessionCleared, {
3057
2994
  bubbles: true,
3058
2995
  composed: true,
@@ -3203,145 +3140,6 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3203
3140
  get settingsSessionTokensVisible() {
3204
3141
  return this.settings.sessionTokensVisible;
3205
3142
  }
3206
- /**
3207
- * Whether the settings "Agent log" section renders — shown when either action is
3208
- * enabled: the download button (`allowDebugDownload`) or the host-transport Send
3209
- * button (`debugLogSubmit`). Each button is additionally gated on its own flag
3210
- * inside the section, so a host can enable one without the other.
3211
- */
3212
- get settingsAgentLogSectionVisible() {
3213
- const ui = this.chatConfig.ui;
3214
- return (ui === null || ui === void 0 ? void 0 : ui.allowDebugDownload) === true || (ui === null || ui === void 0 ? void 0 : ui.debugLogSubmit) != null;
3215
- }
3216
- /**
3217
- * The resolved compose-box settings for the agent-log Send button, or `null` when the
3218
- * host opted out (`debugLogSubmit.note: false`) and the button sends on first click.
3219
- */
3220
- get debugLogNoteConfig() {
3221
- var _a;
3222
- return resolveDebugLogNoteConfig((_a = this.chatConfig.ui) === null || _a === void 0 ? void 0 : _a.debugLogSubmit);
3223
- }
3224
- /**
3225
- * Whether the typed note counts as empty — the ONE emptiness rule, shared by the
3226
- * compose box's disabled state and its "required" hint so the two cannot drift apart.
3227
- */
3228
- get debugLogNoteMissing() {
3229
- return normalizeDebugLogNote(this.debugLogNote) === undefined;
3230
- }
3231
- /** The Send button's idle label, as the host configured it. */
3232
- get debugLogSubmitLabel() {
3233
- var _a, _b, _c;
3234
- return (_c = (_b = (_a = this.chatConfig.ui) === null || _a === void 0 ? void 0 : _a.debugLogSubmit) === null || _b === void 0 ? void 0 : _b.label) !== null && _c !== void 0 ? _c : 'Send';
3235
- }
3236
- /**
3237
- * Label on the agent-log row's Send button. While the compose box is open the row
3238
- * button is just the (disabled) trigger, so it keeps its idle label; otherwise it
3239
- * reflects the in-flight / flashed outcome of the last submission.
3240
- */
3241
- get debugLogSubmitButtonLabel() {
3242
- if (this.debugLogComposeOpen)
3243
- return this.debugLogSubmitLabel;
3244
- if (this.submittingDebugLog)
3245
- return 'Sending…';
3246
- if (this.debugLogSubmitResult === 'sent')
3247
- return 'Sent';
3248
- if (this.debugLogSubmitResult === 'error')
3249
- return 'Failed — retry';
3250
- return this.debugLogSubmitLabel;
3251
- }
3252
- /**
3253
- * The compose box's footer hint: a failure first, then the "required" nudge, else the
3254
- * live counter. Visual only — the same information reaches assistive technology via
3255
- * `debugLogNoteAriaLabel` (counter, required) and `debugLogSubmitAnnouncement` (outcome),
3256
- * because IDREF attributes such as `aria-describedby` cannot point across the
3257
- * design-system text-area's shadow boundary.
3258
- */
3259
- get debugLogComposeHint() {
3260
- var _a;
3261
- if (this.debugLogSubmitResult === 'error')
3262
- return 'Sending failed — try again.';
3263
- if (((_a = this.debugLogNoteConfig) === null || _a === void 0 ? void 0 : _a.required) && this.debugLogNoteMissing) {
3264
- return 'A short note is required.';
3265
- }
3266
- return this.debugLogNoteCounter;
3267
- }
3268
- /**
3269
- * Accessible name for the note. Deliberately STATIC apart from "(required)": a name
3270
- * that changed per keystroke would be re-read in full by NVDA on every key and never
3271
- * updated by JAWS. The running count reaches AT through `debugLogSubmitAnnouncement`
3272
- * at the thresholds where it matters.
3273
- */
3274
- get debugLogNoteAriaLabel() {
3275
- const note = this.debugLogNoteConfig;
3276
- const required = (note === null || note === void 0 ? void 0 : note.required) ? ' (required)' : '';
3277
- const max = note ? `, maximum ${note.maxLength} characters` : '';
3278
- return `Note to send with the agent log${required}${max}.`;
3279
- }
3280
- /**
3281
- * Text for the always-present live region beside the agent-log row, so the outcome of
3282
- * a submission is announced even when the compose box is closed or opted out
3283
- * (`note: false`), where the only visible change is the button label.
3284
- */
3285
- get debugLogSubmitAnnouncement() {
3286
- var _a;
3287
- if (this.submittingDebugLog)
3288
- return 'Sending the agent log.';
3289
- if (this.debugLogSubmitResult === 'sent')
3290
- return 'Agent log sent.';
3291
- if (this.debugLogSubmitResult === 'error')
3292
- return 'Sending the agent log failed. Try again.';
3293
- // The note's length, only as it nears the cap: `maxlength` is invisible to AT, so at
3294
- // the limit keystrokes would be silently dropped with nothing changing anywhere.
3295
- const max = (_a = this.debugLogNoteConfig) === null || _a === void 0 ? void 0 : _a.maxLength;
3296
- if (this.debugLogComposeOpen && max) {
3297
- const remaining = max - this.debugLogNote.length;
3298
- if (remaining <= 0) {
3299
- return `Note is at its ${max} character limit; further typing is dropped.`;
3300
- }
3301
- if (remaining <= DEBUG_LOG_NOTE_REMAINING_WARN)
3302
- return `${remaining} characters remaining.`;
3303
- }
3304
- return '';
3305
- }
3306
- /**
3307
- * The agent-log row's description, phrased for whichever actions the host enabled.
3308
- * Send is called out as transmitting: Download keeps the log on the user's machine,
3309
- * Send hands the full conversation to wherever the host's transport delivers it.
3310
- */
3311
- get debugLogRowDescription() {
3312
- var _a;
3313
- const ui = this.chatConfig.ui;
3314
- const download = (ui === null || ui === void 0 ? void 0 : ui.allowDebugDownload) === true;
3315
- const send = (ui === null || ui === void 0 ? void 0 : ui.debugLogSubmit) != null;
3316
- if (send && ((_a = ui === null || ui === void 0 ? void 0 : ui.debugLogSubmit) === null || _a === void 0 ? void 0 : _a.description))
3317
- return ui.debugLogSubmit.description;
3318
- const timeline = "a structured debug timeline of this assistant's activity";
3319
- // What actually travels (see `ChatDebugLogSubmission.logJson`): the lifetime stream,
3320
- // not just this conversation — say so where the user commits to it.
3321
- const transmits = 'transmits the full lifetime log — every conversation held here, including cleared ' +
3322
- 'ones, with attachments, system prompts and agent configuration.';
3323
- if (download && send)
3324
- return `Export ${timeline}, or send it to support. Sending ${transmits}`;
3325
- if (send)
3326
- return `Send ${timeline} to support. This ${transmits}`;
3327
- return "Export a structured debug timeline of this session's agent activity.";
3328
- }
3329
- /**
3330
- * Whether the compose box's Send button is inert: a send is already in flight, or the
3331
- * host made the note required and it is still blank.
3332
- */
3333
- get debugLogSendDisabled() {
3334
- var _a;
3335
- if (this.submittingDebugLog)
3336
- return true;
3337
- return ((_a = this.debugLogNoteConfig) === null || _a === void 0 ? void 0 : _a.required) === true && this.debugLogNoteMissing;
3338
- }
3339
- /** Live "typed / max" counter for the compose box. */
3340
- get debugLogNoteCounter() {
3341
- var _a;
3342
- const max = (_a = this.debugLogNoteConfig) === null || _a === void 0 ? void 0 : _a.maxLength;
3343
- return max ? `${this.debugLogNote.length}/${max}` : '';
3344
- }
3345
3143
  /** Whether the chat header (and settings cog) should render. */
3346
3144
  get settingsCogVisible() {
3347
3145
  return this.settings.cogVisible;
@@ -3507,11 +3305,11 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3507
3305
  * `onActivate` ran, so only its `getDebugSnapshot` closure holds state.
3508
3306
  */
3509
3307
  buildMetaSnapshot() {
3510
- var _a, _b, _c;
3308
+ var _a, _b;
3511
3309
  return buildMetaSnapshot({
3512
3310
  agents: this.agents,
3513
3311
  activeAgent: this.activeAgent,
3514
- liveActiveAgent: (_b = (_a = this.driver) === null || _a === void 0 ? void 0 : _a.getActiveAgent) === null || _b === void 0 ? void 0 : _b.call(_a),
3312
+ liveActiveAgent: (_a = this.driver) === null || _a === void 0 ? void 0 : _a.getActiveAgent(),
3515
3313
  activeFoldStack: this.driver instanceof ChatDriver ? this.driver.getActiveFoldNames() : undefined,
3516
3314
  activeModel: this.activeModel,
3517
3315
  contextTokens: this.contextTokens,
@@ -3519,17 +3317,21 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3519
3317
  sessionCostUsd: this.sessionCostUsd,
3520
3318
  sessionTokensConsumed: this.sessionTokensConsumed,
3521
3319
  sessionUsage: this.sessionUsage,
3522
- debugState: (_c = this.debugStateFactory) === null || _c === void 0 ? void 0 : _c.call(this),
3320
+ debugState: (_b = this.debugStateFactory) === null || _b === void 0 ? void 0 : _b.call(this),
3523
3321
  host: window.location.host,
3524
3322
  });
3525
3323
  }
3526
3324
  downloadDebugLog() {
3527
3325
  return __awaiter(this, void 0, void 0, function* () {
3326
+ var _a, _b, _c;
3528
3327
  // Guard re-entry: the button is disabled while this runs, but a programmatic
3529
3328
  // or double-fire can't kick off a second stitch either.
3530
3329
  if (this.downloadingDebugLog)
3531
3330
  return;
3532
- const filename = this.debugLogFilename();
3331
+ const timestamp = new Date().toISOString().replace(/:/g, '-');
3332
+ const agentName = ((_c = (_b = (_a = this.activeAgent) === null || _a === void 0 ? void 0 : _a.name) !== null && _b !== void 0 ? _b : this.headerTitle) !== null && _c !== void 0 ? _c : 'chat')
3333
+ .toLowerCase()
3334
+ .replace(/\s+/g, '-');
3533
3335
  this.downloadingDebugLog = true;
3534
3336
  try {
3535
3337
  const payload = yield this.buildDownloadLog();
@@ -3537,7 +3339,7 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3537
3339
  const url = URL.createObjectURL(blob);
3538
3340
  const a = document.createElement('a');
3539
3341
  a.href = url;
3540
- a.download = filename;
3342
+ a.download = `${agentName}-${timestamp}.json`;
3541
3343
  a.click();
3542
3344
  URL.revokeObjectURL(url);
3543
3345
  }
@@ -3546,187 +3348,6 @@ let FoundationAiAssistant = FoundationAiAssistant_1 = class FoundationAiAssistan
3546
3348
  }
3547
3349
  });
3548
3350
  }
3549
- /**
3550
- * Hand the agent log to the host's `ui.debugLogSubmit.send` callback — the Send
3551
- * button next to Download. Reuses `buildDownloadLog`, so the submitted log is
3552
- * byte-identical to what Download saves (lifetime-stitched when the provider
3553
- * persists diagnostics). The assistant is vendor-agnostic: the callback owns the
3554
- * transport (Sentry feedback, a support API, an upload endpoint). Outcome lands in
3555
- * `debugLogSubmitResult` so the button can flash 'Sent'/'Failed'; failures also go
3556
- * to the logger with the cause.
3557
- */
3558
- submitDebugLog() {
3559
- return __awaiter(this, void 0, void 0, function* () {
3560
- var _a, _b;
3561
- if (this.submittingDebugLog || this.debugLogSendDisabled)
3562
- return;
3563
- const config = (_a = this.chatConfig.ui) === null || _a === void 0 ? void 0 : _a.debugLogSubmit;
3564
- if (!config)
3565
- return;
3566
- const generation = this.debugLogSubmitGeneration;
3567
- const agentName = this.debugLogAgentName;
3568
- const filename = this.debugLogFilename();
3569
- // Read at click time, BEFORE the async stitch: the user pressed Send on this note.
3570
- // Only a note the user could actually type travels with the log: with the compose box
3571
- // opted out there is no note, whatever a stale `debugLogNote` might hold.
3572
- const message = this.debugLogNoteConfig === null ? undefined : normalizeDebugLogNote(this.debugLogNote);
3573
- this.submittingDebugLog = true;
3574
- try {
3575
- const payload = yield this.buildDownloadLog();
3576
- if (generation !== this.debugLogSubmitGeneration)
3577
- return;
3578
- yield settleWithin(config.send({
3579
- logJson: JSON.stringify(payload, null, 2),
3580
- filename,
3581
- agentName,
3582
- host: window.location.host,
3583
- message,
3584
- }), (_b = config.timeoutMs) !== null && _b !== void 0 ? _b : DEBUG_LOG_SUBMIT_TIMEOUT_MS, 'debugLogSubmit.send');
3585
- if (generation !== this.debugLogSubmitGeneration)
3586
- return;
3587
- // Success consumes the note; a failure (below) keeps the box open with it intact.
3588
- this.debugLogComposeOpen = false;
3589
- this.debugLogNote = '';
3590
- this.setDebugLogSubmitResult('sent');
3591
- this.restoreDebugLogTriggerFocus();
3592
- }
3593
- catch (e) {
3594
- if (generation !== this.debugLogSubmitGeneration)
3595
- return;
3596
- logger.error('Submitting agent log failed:', e);
3597
- // Persists (no flash timer) until the user acts — see `setDebugLogSubmitResult`.
3598
- this.setDebugLogSubmitResult('error');
3599
- this.restoreDebugLogRetryFocus();
3600
- }
3601
- finally {
3602
- if (generation === this.debugLogSubmitGeneration)
3603
- this.submittingDebugLog = false;
3604
- }
3605
- });
3606
- }
3607
- /** The agent name stamped on the log: the active agent, else the header title. */
3608
- get debugLogAgentName() {
3609
- var _a, _b, _c;
3610
- return (_c = (_b = (_a = this.activeAgent) === null || _a === void 0 ? void 0 : _a.name) !== null && _b !== void 0 ? _b : this.headerTitle) !== null && _c !== void 0 ? _c : 'chat';
3611
- }
3612
- /**
3613
- * Filename for the agent log — the ONE derivation Download saves under and Send hands
3614
- * to the host, so `ChatDebugLogSubmission.filename`'s "same stem as the download"
3615
- * promise is enforced rather than relying on two copies agreeing.
3616
- */
3617
- debugLogFilename() {
3618
- const stem = this.debugLogAgentName.toLowerCase().replace(/\s+/g, '-');
3619
- return `${stem}-${new Date().toISOString().replace(/:/g, '-')}.json`;
3620
- }
3621
- /**
3622
- * Back to idle: nothing in flight, no flash, no open compose box, no note. Called on
3623
- * disconnect and on a session switch / Clear (a note typed against one conversation
3624
- * must not caption the next one's log). On disconnect — the
3625
- * flash timer would otherwise fire against a torn-down element, and clearing ONLY the
3626
- * timer would strand `debugLogSubmitResult` at 'sent'/'error' for good on a pop-out /
3627
- * pop-in (nothing else resets it), with the box remounting open on a stale note.
3628
- */
3629
- resetDebugLogSubmitState() {
3630
- this.debugLogSubmitGeneration += 1;
3631
- clearTimeout(this.debugLogSubmitResultTimer);
3632
- this.debugLogSubmitResultTimer = undefined;
3633
- // Including the in-flight flag: every escape route (Send, Cancel, the note, the row
3634
- // button) is gated on it, so a host transport that never settles would otherwise
3635
- // wedge the feature until reload.
3636
- this.submittingDebugLog = false;
3637
- this.debugLogSubmitResult = null;
3638
- this.debugLogComposeOpen = false;
3639
- this.debugLogNote = '';
3640
- }
3641
- /**
3642
- * The row's Send button. With a compose box configured (the default) it opens the box
3643
- * and focuses the note so the user can caption the log; with `note: false` it sends
3644
- * straight away, as before.
3645
- */
3646
- openDebugLogCompose() {
3647
- if (this.submittingDebugLog)
3648
- return;
3649
- if (this.debugLogNoteConfig === null) {
3650
- void this.submitDebugLog();
3651
- return;
3652
- }
3653
- // Opening again resets a lingering 'Failed' flash so the box starts clean.
3654
- clearTimeout(this.debugLogSubmitResultTimer);
3655
- this.debugLogSubmitResultTimer = undefined;
3656
- this.debugLogSubmitResult = null;
3657
- this.debugLogComposeOpen = true;
3658
- // Next frame so the `when` block has rendered the text-area. The design-system
3659
- // text-area does not delegate focus (see `maybeAutoFocusChatInput`), so drill in.
3660
- requestAnimationFrame(() => {
3661
- var _a, _b, _c;
3662
- if (!this.debugLogComposeOpen || !this.isConnected)
3663
- return;
3664
- const el = this.debugLogNoteEl;
3665
- (_c = ((_b = (_a = el === null || el === void 0 ? void 0 : el.shadowRoot) === null || _a === void 0 ? void 0 : _a.querySelector('textarea')) !== null && _b !== void 0 ? _b : el)) === null || _c === void 0 ? void 0 : _c.focus();
3666
- });
3667
- }
3668
- /** The note's `@input`: track the text, and let typing dismiss a standing failure. */
3669
- noteDebugLogInput(value) {
3670
- this.debugLogNote = value;
3671
- if (this.debugLogSubmitResult === 'error')
3672
- this.debugLogSubmitResult = null;
3673
- }
3674
- /** Close the compose box and discard the typed note. */
3675
- cancelDebugLogCompose() {
3676
- if (this.submittingDebugLog)
3677
- return;
3678
- this.debugLogComposeOpen = false;
3679
- this.debugLogNote = '';
3680
- this.restoreDebugLogTriggerFocus();
3681
- }
3682
- /**
3683
- * Closing the compose box unmounts the focused text-area, which drops focus to the
3684
- * document body and strands keyboard and screen-reader users. Hand it back to the row's
3685
- * Send button — next frame, once the `when` block has torn down and the button, disabled
3686
- * while the box was open, is interactive again.
3687
- */
3688
- restoreDebugLogTriggerFocus() {
3689
- requestAnimationFrame(() => {
3690
- var _a, _b;
3691
- if (!this.isConnected || this.debugLogComposeOpen)
3692
- return;
3693
- (_b = (_a = this.shadowRoot) === null || _a === void 0 ? void 0 : _a.querySelector('[part="submit-log-button"]')) === null || _b === void 0 ? void 0 : _b.focus();
3694
- });
3695
- }
3696
- /**
3697
- * After a FAILED send the controls come back but the element that started the send
3698
- * was disabled meanwhile, so focus has already dropped to the document body. Put it
3699
- * where the retry happens: the note when the box is open, else the row trigger.
3700
- */
3701
- restoreDebugLogRetryFocus() {
3702
- if (!this.debugLogComposeOpen) {
3703
- this.restoreDebugLogTriggerFocus();
3704
- return;
3705
- }
3706
- requestAnimationFrame(() => {
3707
- var _a, _b, _c;
3708
- if (!this.isConnected || !this.debugLogComposeOpen)
3709
- return;
3710
- const el = this.debugLogNoteEl;
3711
- (_c = ((_b = (_a = el === null || el === void 0 ? void 0 : el.shadowRoot) === null || _a === void 0 ? void 0 : _a.querySelector('textarea')) !== null && _b !== void 0 ? _b : el)) === null || _c === void 0 ? void 0 : _c.focus();
3712
- });
3713
- }
3714
- /**
3715
- * Record the submit outcome. 'sent' flashes and falls back to idle; 'error' PERSISTS
3716
- * until the user acts (types, reopens the box, cancels, or retries) — a failure that
3717
- * silently reverted to the counter after four seconds left no trace it had happened.
3718
- */
3719
- setDebugLogSubmitResult(result) {
3720
- clearTimeout(this.debugLogSubmitResultTimer);
3721
- this.debugLogSubmitResultTimer = undefined;
3722
- this.debugLogSubmitResult = result;
3723
- if (result !== 'sent')
3724
- return;
3725
- this.debugLogSubmitResultTimer = setTimeout(() => {
3726
- this.debugLogSubmitResult = null;
3727
- this.debugLogSubmitResultTimer = undefined;
3728
- }, this.debugLogSubmitResultFlashMs);
3729
- }
3730
3351
  /**
3731
3352
  * The log to download (GENC-1351 §5.8). When the provider persists diagnostics,
3732
3353
  * stitch the **whole lifetime** stream (every page load) rather than just the
@@ -4347,18 +3968,6 @@ __decorate([
4347
3968
  __decorate([
4348
3969
  observable
4349
3970
  ], FoundationAiAssistant.prototype, "downloadingDebugLog", void 0);
4350
- __decorate([
4351
- observable
4352
- ], FoundationAiAssistant.prototype, "submittingDebugLog", void 0);
4353
- __decorate([
4354
- observable
4355
- ], FoundationAiAssistant.prototype, "debugLogSubmitResult", void 0);
4356
- __decorate([
4357
- observable
4358
- ], FoundationAiAssistant.prototype, "debugLogComposeOpen", void 0);
4359
- __decorate([
4360
- observable
4361
- ], FoundationAiAssistant.prototype, "debugLogNote", void 0);
4362
3971
  __decorate([
4363
3972
  observable
4364
3973
  ], FoundationAiAssistant.prototype, "persistenceBroken", void 0);
@@ -4407,39 +4016,6 @@ __decorate([
4407
4016
  __decorate([
4408
4017
  volatile
4409
4018
  ], FoundationAiAssistant.prototype, "agentPickerEnabled", null);
4410
- __decorate([
4411
- volatile
4412
- ], FoundationAiAssistant.prototype, "settingsAgentLogSectionVisible", null);
4413
- __decorate([
4414
- volatile
4415
- ], FoundationAiAssistant.prototype, "debugLogNoteConfig", null);
4416
- __decorate([
4417
- volatile
4418
- ], FoundationAiAssistant.prototype, "debugLogNoteMissing", null);
4419
- __decorate([
4420
- volatile
4421
- ], FoundationAiAssistant.prototype, "debugLogSubmitLabel", null);
4422
- __decorate([
4423
- volatile
4424
- ], FoundationAiAssistant.prototype, "debugLogSubmitButtonLabel", null);
4425
- __decorate([
4426
- volatile
4427
- ], FoundationAiAssistant.prototype, "debugLogComposeHint", null);
4428
- __decorate([
4429
- volatile
4430
- ], FoundationAiAssistant.prototype, "debugLogNoteAriaLabel", null);
4431
- __decorate([
4432
- volatile
4433
- ], FoundationAiAssistant.prototype, "debugLogSubmitAnnouncement", null);
4434
- __decorate([
4435
- volatile
4436
- ], FoundationAiAssistant.prototype, "debugLogRowDescription", null);
4437
- __decorate([
4438
- volatile
4439
- ], FoundationAiAssistant.prototype, "debugLogSendDisabled", null);
4440
- __decorate([
4441
- volatile
4442
- ], FoundationAiAssistant.prototype, "debugLogNoteCounter", null);
4443
4019
  __decorate([
4444
4020
  volatile
4445
4021
  ], FoundationAiAssistant.prototype, "pinnedAgentHint", null);