@memori.ai/memori-react 8.39.0 → 8.40.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 (49) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/dist/components/MemoriWidget/MemoriWidget.d.ts +2 -1
  3. package/dist/components/MemoriWidget/MemoriWidget.js +450 -146
  4. package/dist/components/MemoriWidget/MemoriWidget.js.map +1 -1
  5. package/dist/helpers/credits.d.ts +3 -2
  6. package/dist/helpers/credits.js +4 -3
  7. package/dist/helpers/credits.js.map +1 -1
  8. package/dist/helpers/nats/getNatsConfig.d.ts +5 -0
  9. package/dist/helpers/nats/getNatsConfig.js +29 -0
  10. package/dist/helpers/nats/getNatsConfig.js.map +1 -0
  11. package/dist/helpers/nats/useNats.d.ts +12 -0
  12. package/dist/helpers/nats/useNats.js +72 -0
  13. package/dist/helpers/nats/useNats.js.map +1 -0
  14. package/dist/helpers/nats/useNatsSession.d.ts +27 -0
  15. package/dist/helpers/nats/useNatsSession.js +108 -0
  16. package/dist/helpers/nats/useNatsSession.js.map +1 -0
  17. package/dist/index.js +1 -1
  18. package/dist/index.js.map +1 -1
  19. package/dist/version.d.ts +1 -1
  20. package/dist/version.js +1 -1
  21. package/esm/components/MemoriWidget/MemoriWidget.d.ts +2 -1
  22. package/esm/components/MemoriWidget/MemoriWidget.js +453 -147
  23. package/esm/components/MemoriWidget/MemoriWidget.js.map +1 -1
  24. package/esm/helpers/credits.d.ts +3 -2
  25. package/esm/helpers/credits.js +4 -3
  26. package/esm/helpers/credits.js.map +1 -1
  27. package/esm/helpers/nats/getNatsConfig.d.ts +5 -0
  28. package/esm/helpers/nats/getNatsConfig.js +25 -0
  29. package/esm/helpers/nats/getNatsConfig.js.map +1 -0
  30. package/esm/helpers/nats/useNats.d.ts +12 -0
  31. package/esm/helpers/nats/useNats.js +68 -0
  32. package/esm/helpers/nats/useNats.js.map +1 -0
  33. package/esm/helpers/nats/useNatsSession.d.ts +27 -0
  34. package/esm/helpers/nats/useNatsSession.js +103 -0
  35. package/esm/helpers/nats/useNatsSession.js.map +1 -0
  36. package/esm/index.js +1 -1
  37. package/esm/index.js.map +1 -1
  38. package/esm/version.d.ts +1 -1
  39. package/esm/version.js +1 -1
  40. package/package.json +3 -2
  41. package/src/components/MemoriWidget/MemoriWidget.tsx +543 -149
  42. package/src/components/layouts/layouts.stories.tsx +29 -35
  43. package/src/helpers/credits.ts +6 -3
  44. package/src/helpers/nats/getNatsConfig.ts +69 -0
  45. package/src/helpers/nats/useNats.ts +122 -0
  46. package/src/helpers/nats/useNatsSession.ts +210 -0
  47. package/src/index.stories.tsx +19 -3
  48. package/src/index.tsx +1 -0
  49. package/src/version.ts +1 -1
@@ -38,6 +38,7 @@ import { sanitizeText } from '../../helpers/sanitizer';
38
38
  import { useTTS } from '../../helpers/tts/useTTS';
39
39
  import ChatHistoryDrawer from '../ChatHistoryDrawer/ChatHistory';
40
40
  import { useSTT } from '../../helpers/stt/useSTT';
41
+ import { useNats } from '../../helpers/nats/useNats';
41
42
  const getMemoriState = (integrationId) => {
42
43
  var _a, _b, _c, _d, _f;
43
44
  let widget = integrationId
@@ -65,6 +66,11 @@ const NULL_PLACE_SPEC = {
65
66
  longitude: null,
66
67
  uncertaintyKm: null,
67
68
  };
69
+ const ENTER_TEXT_NATS_TIMEOUT_MS = 120000;
70
+ function readCorrelationID(response) {
71
+ const value = response.correlationID;
72
+ return typeof value === 'string' && value.length > 0 ? value : undefined;
73
+ }
68
74
  const typeMessage = (message, waitForPrevious = true, hidden = false, typingText, useLoaderTextAsMsg = false, hasBatchQueued = false) => {
69
75
  const e = new CustomEvent('MemoriTextEntered', {
70
76
  detail: {
@@ -161,7 +167,7 @@ window.typeBatchMessages = typeBatchMessages;
161
167
  let audioContext;
162
168
  let memoriPassword;
163
169
  let userToken;
164
- const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang, uiLang, spokenLang, multilingual, integration, layout, customLayout, showShare, preview = false, embed = false, showCopyButton = true, showTranslationOriginal = false, showInputs = true, showDates = false, showContextPerLine = false, showMessageConsumption = false, showSettings, showTypingText = false, showClear = false, showLogin = false, showUpload, showOnlyLastMessages, showChatHistory, showReasoning, avatar3dHidden, height = '100vh', secret, baseUrl = 'https://aisuru-staging.aclambda.online', apiURL = 'https://backend-staging.memori.ai', engineURL = 'https://engine-staging.memori.ai', initialContextVars, initialQuestion, ttsProvider, ogImage, sessionID: initialSessionID, tenant, personification, authToken, enableAudio, defaultSpeakerActive = true, disableTextEnteredEvents = false, onStateChange, additionalInfo, additionalSettings, customMediaRenderer, userAvatar, __WEBCOMPONENT__ = false, useMathFormatting = false, autoStart = false, applyVarsToRoot = false, showFunctionCache = false, maxTotalMessagePayload, maxTextareaCharacters, }) => {
170
+ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, ownerUserName, tenantID, memoriLang, uiLang, spokenLang, multilingual, integration, layout, customLayout, showShare, preview = false, embed = false, showCopyButton = true, showTranslationOriginal = false, showInputs = true, showDates = false, showContextPerLine = false, showMessageConsumption = false, showSettings, showTypingText = false, showClear = false, showLogin = false, showUpload, showOnlyLastMessages, showChatHistory, showReasoning, avatar3dHidden, height = '100vh', secret, baseUrl = 'https://aisuru-staging.aclambda.online', apiURL = 'https://backend-staging.memori.ai', engineURL = 'https://engine-staging.memori.ai', initialContextVars, initialQuestion, ttsProvider, ogImage, sessionID: initialSessionID, tenant, personification, authToken, enableAudio, defaultSpeakerActive = true, disableTextEnteredEvents = false, onStateChange, additionalInfo, additionalSettings, customMediaRenderer, userAvatar, __WEBCOMPONENT__ = false, useMathFormatting = false, autoStart = false, applyVarsToRoot = false, showFunctionCache = false, maxTotalMessagePayload, maxTextareaCharacters, }) => {
165
171
  var _a, _b, _c, _d, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w, _x, _y, _z, _0, _1, _2, _3, _4, _5, _6, _7, _8, _9, _10, _11, _12, _13, _14, _15, _16, _17, _18;
166
172
  const { t, i18n } = useTranslation();
167
173
  const [isClient, setIsClient] = useState(false);
@@ -169,7 +175,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
169
175
  setIsClient(true);
170
176
  }, []);
171
177
  const client = memoriApiClient(apiURL, engineURL);
172
- const { initSession, deleteSession, postTextEnteredEvent, postPlaceChangedEvent, postDateChangedEvent, postTagChangedEvent, getSession, getExpertReferences, getSessionChatLogs, } = client;
178
+ const { initSession, deleteSession, postEnterTextAsync, postTextEnteredEvent, postPlaceChangedEvent, postDateChangedEvent, postTagChangedEvent, getSession, getExpertReferences, getSessionChatLogs, } = client;
173
179
  const [instruct, setInstruct] = useState(false);
174
180
  const [enableFocusChatInput, setEnableFocusChatInput] = useState(true);
175
181
  const [loginToken, setLoginToken] = useState((_a = additionalInfo === null || additionalInfo === void 0 ? void 0 : additionalInfo.loginToken) !== null && _a !== void 0 ? _a : authToken);
@@ -199,6 +205,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
199
205
  }, [loginToken, user === null || user === void 0 ? void 0 : user.userID]);
200
206
  const [showLoginDrawer, setShowLoginDrawer] = useState(false);
201
207
  const [clickedStart, setClickedStart] = useState(false);
208
+ const sessionStartingRef = useRef(false);
202
209
  const language = ((_d = (_c = (_b = memori.culture) === null || _b === void 0 ? void 0 : _b.split('-')) === null || _c === void 0 ? void 0 : _c[0]) === null || _d === void 0 ? void 0 : _d.toUpperCase()) ||
203
210
  ((_j = (_h = (_g = (_f = memoriConfigs === null || memoriConfigs === void 0 ? void 0 : memoriConfigs.find(c => c.memoriConfigID === memori.memoriConfigurationID)) === null || _f === void 0 ? void 0 : _f.culture) === null || _g === void 0 ? void 0 : _g.split('-')) === null || _h === void 0 ? void 0 : _h[0]) === null || _j === void 0 ? void 0 : _j.toUpperCase());
204
211
  const integrationConfig = (integration === null || integration === void 0 ? void 0 : integration.customData)
@@ -234,6 +241,8 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
234
241
  const [loading, setLoading] = useState(false);
235
242
  const [memoriTyping, setMemoriTyping] = useState(false);
236
243
  const [typingText, setTypingText] = useState();
244
+ const pendingEnterTextRef = useRef(new Map());
245
+ const bufferedNatsResponsesRef = useRef(new Map());
237
246
  const layoutName = typeof layout === 'string'
238
247
  ? layout
239
248
  : typeof (integrationConfig === null || integrationConfig === void 0 ? void 0 : integrationConfig.layout) === 'string'
@@ -382,7 +391,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
382
391
  };
383
392
  const [chatLogID, setChatLogID] = useState(undefined);
384
393
  const sendMessage = async (text, media, newSessionId, translate = true, translatedText, hidden = false, typingText, useLoaderTextAsMsg = false, hasBatchQueued = false) => {
385
- var _a, _b, _c, _d, _f, _g;
394
+ var _a, _b, _c, _d;
386
395
  const sessionID = newSessionId ||
387
396
  sessionId ||
388
397
  ((_a = window.getMemoriState()) === null || _a === void 0 ? void 0 : _a.sessionID);
@@ -436,12 +445,16 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
436
445
  ? !!newSessionId && newSessionId !== sessionId
437
446
  : !!newSessionId,
438
447
  });
439
- setMemoriTyping(true);
440
- setTypingText(typingText);
441
448
  let gotError = false;
442
449
  try {
443
450
  const placeSpec = getPlaceSpecForEnterText(position);
444
- const { currentState, ...response } = await postTextEnteredEvent({
451
+ console.debug('[EnterText] sendMessage: posting', {
452
+ sessionId: sessionID,
453
+ textLength: msg.length,
454
+ hasBatchQueued,
455
+ typingText,
456
+ });
457
+ const response = await postEnterTextAsync({
445
458
  sessionId: sessionID,
446
459
  text: msg,
447
460
  ...(memori.needsDateTime && {
@@ -449,57 +462,35 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
449
462
  }),
450
463
  ...(placeSpec !== undefined && { place: placeSpec }),
451
464
  });
452
- if (response.resultCode === 0 && currentState) {
453
- setChatLogID(undefined);
454
- const emission = useLoaderTextAsMsg && typingText
455
- ? typingText
456
- : (_c = currentState.emission) !== null && _c !== void 0 ? _c : currentDialogState === null || currentDialogState === void 0 ? void 0 : currentDialogState.emission;
457
- if (userLang.toLowerCase() !== language.toLowerCase() &&
458
- emission &&
459
- isMultilanguageEnabled) {
460
- currentState.emission = emission;
461
- translateDialogState(currentState, userLang, msg).then(ts => {
462
- let text = ts.translatedEmission || ts.emission;
463
- if (text && shouldPlayAudio(text)) {
464
- handleSpeak(text);
465
- }
466
- });
467
- }
468
- else {
469
- setCurrentDialogState({
470
- ...currentState,
471
- emission,
472
- });
473
- if (emission) {
474
- pushMessage({
475
- text: emission,
476
- emitter: currentState.emitter,
477
- media: (_d = currentState.emittedMedia) !== null && _d !== void 0 ? _d : currentState.media,
478
- llmUsage: currentState.llmUsage,
479
- fromUser: false,
480
- questionAnswered: msg,
481
- generatedByAI: !!currentState.completion,
482
- contextVars: currentState.contextVars,
483
- date: currentState.currentDate,
484
- placeName: currentState.currentPlaceName,
485
- placeLatitude: currentState.currentLatitude,
486
- placeLongitude: currentState.currentLongitude,
487
- placeUncertaintyKm: currentState.currentUncertaintyKm,
488
- tag: currentState.currentTag,
489
- memoryTags: currentState.memoryTags,
490
- });
491
- if (emission && shouldPlayAudio(emission)) {
492
- handleSpeak(emission);
493
- }
494
- }
495
- }
465
+ console.debug('[EnterText] sendMessage: HTTP response', {
466
+ resultCode: response.resultCode,
467
+ correlationID: readCorrelationID(response),
468
+ resultMessage: response.resultMessage,
469
+ });
470
+ const correlationID = readCorrelationID(response);
471
+ if (response.resultCode === 0 && correlationID) {
472
+ registerPendingEnterText(correlationID, {
473
+ msg,
474
+ typingText,
475
+ useLoaderTextAsMsg,
476
+ hasBatchQueued,
477
+ });
478
+ console.info('[EnterText] sendMessage: accepted, showing typing indicator', {
479
+ correlationID: correlationID,
480
+ typingText,
481
+ });
482
+ setMemoriTyping(true);
483
+ setTypingText(typingText);
484
+ }
485
+ else if (response.resultCode === 0) {
486
+ console.error('[EnterText] sendMessage: HTTP 200 but missing correlationID — cannot match NATS response', response);
496
487
  }
497
488
  else if (response.resultCode === 404) {
498
489
  setHistory(h => [...h.slice(0, h.length - 1)]);
499
490
  reopenSession(true, memoriPwd || memori.secretToken, memoriTokens, undefined, undefined, {
500
491
  LANG: userLang,
501
492
  PATHNAME: window.location.pathname,
502
- ROUTE: ((_g = (_f = window.location.pathname) === null || _f === void 0 ? void 0 : _f.split('/')) === null || _g === void 0 ? void 0 : _g.pop()) || '',
493
+ ROUTE: ((_d = (_c = window.location.pathname) === null || _c === void 0 ? void 0 : _c.split('/')) === null || _d === void 0 ? void 0 : _d.pop()) || '',
503
494
  ...(initialContextVars || {}),
504
495
  }, initialQuestion, undefined, undefined, undefined, undefined, true).then(state => {
505
496
  console.info('session timeout');
@@ -529,16 +520,11 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
529
520
  }
530
521
  }
531
522
  catch (error) {
532
- console.log('error', error);
533
- console.error(error);
523
+ console.error('[EnterText] sendMessage: request failed', error);
534
524
  gotError = true;
535
525
  setTypingText(undefined);
536
526
  setMemoriTyping(false);
537
527
  }
538
- if (!hasBatchQueued) {
539
- setTypingText(undefined);
540
- setMemoriTyping(false);
541
- }
542
528
  };
543
529
  const translateDialogState = async (state, userLang, msg, avoidPushingMessage = false) => {
544
530
  var _a, _b, _c, _d, _f, _g;
@@ -760,7 +746,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
760
746
  setAuthModalState('password');
761
747
  return;
762
748
  }
763
- if (!(await checkCredits({ notify: true, goBack: true }))) {
749
+ if (!(await checkCredits({ notify: true }))) {
764
750
  return;
765
751
  }
766
752
  setLoading(true);
@@ -843,7 +829,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
843
829
  setAuthModalState('password');
844
830
  return;
845
831
  }
846
- if (!(await checkCredits({ notify: true, goBack: true }))) {
832
+ if (!(await checkCredits({ notify: true }))) {
847
833
  setLoading(false);
848
834
  return null;
849
835
  }
@@ -1058,6 +1044,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1058
1044
  return () => {
1059
1045
  setHasUserActivatedSpeak(false);
1060
1046
  setClickedStart(false);
1047
+ sessionStartingRef.current = false;
1061
1048
  clearInteractionTimeout();
1062
1049
  timeoutRef.current = undefined;
1063
1050
  };
@@ -1156,6 +1143,277 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1156
1143
  setHasUserActivatedSpeak,
1157
1144
  speakerMuted,
1158
1145
  ]);
1146
+ const processEnterTextDialogResponse = useCallback((event, pending) => {
1147
+ var _a, _b;
1148
+ console.debug('[EnterText] processDialogResponse', {
1149
+ correlationID: event.correlationID,
1150
+ resultCode: event.resultCode,
1151
+ hasCurrentState: !!event.currentState,
1152
+ hasBatchQueued: pending.hasBatchQueued,
1153
+ });
1154
+ const { msg, typingText: pendingTypingText, useLoaderTextAsMsg, } = pending;
1155
+ const currentState = event.currentState;
1156
+ if (event.resultCode !== 0 || !currentState) {
1157
+ if (event.resultCode === 500 && event.resultMessage) {
1158
+ console.warn('[EnterText] processDialogResponse: server error', {
1159
+ correlationID: event.correlationID,
1160
+ resultMessage: event.resultMessage,
1161
+ });
1162
+ setHistory(h => [
1163
+ ...h,
1164
+ {
1165
+ text: 'Error: ' + event.resultMessage,
1166
+ emitter: 'system',
1167
+ fromUser: false,
1168
+ initial: false,
1169
+ contextVars: {},
1170
+ date: new Date().toISOString(),
1171
+ },
1172
+ ]);
1173
+ }
1174
+ else if (event.resultCode !== 0) {
1175
+ console.warn('[SEND_MESSAGE/NATS]', event);
1176
+ }
1177
+ return;
1178
+ }
1179
+ if (!msg) {
1180
+ console.debug('[EnterText] processDialogResponse: no msg in pending, skipping');
1181
+ return;
1182
+ }
1183
+ setChatLogID(undefined);
1184
+ const emission = useLoaderTextAsMsg && pendingTypingText
1185
+ ? pendingTypingText
1186
+ : (_a = currentState.emission) !== null && _a !== void 0 ? _a : currentDialogState === null || currentDialogState === void 0 ? void 0 : currentDialogState.emission;
1187
+ console.debug('[EnterText] processDialogResponse: rendering emission', {
1188
+ correlationID: event.correlationID,
1189
+ emissionPreview: emission === null || emission === void 0 ? void 0 : emission.slice(0, 80),
1190
+ state: currentState.state,
1191
+ });
1192
+ if (userLang.toLowerCase() !== language.toLowerCase() &&
1193
+ emission &&
1194
+ isMultilanguageEnabled) {
1195
+ currentState.emission = emission;
1196
+ translateDialogState(currentState, userLang, msg).then(ts => {
1197
+ const text = ts.translatedEmission || ts.emission;
1198
+ if (text && shouldPlayAudio(text)) {
1199
+ handleSpeak(text);
1200
+ }
1201
+ });
1202
+ }
1203
+ else {
1204
+ setCurrentDialogState({
1205
+ ...currentState,
1206
+ emission,
1207
+ });
1208
+ if (emission) {
1209
+ pushMessage({
1210
+ text: emission,
1211
+ emitter: currentState.emitter,
1212
+ media: (_b = currentState.emittedMedia) !== null && _b !== void 0 ? _b : currentState.media,
1213
+ llmUsage: currentState.llmUsage,
1214
+ fromUser: false,
1215
+ questionAnswered: msg,
1216
+ generatedByAI: !!currentState.completion,
1217
+ contextVars: currentState.contextVars,
1218
+ date: currentState.currentDate,
1219
+ placeName: currentState.currentPlaceName,
1220
+ placeLatitude: currentState.currentLatitude,
1221
+ placeLongitude: currentState.currentLongitude,
1222
+ placeUncertaintyKm: currentState.currentUncertaintyKm,
1223
+ tag: currentState.currentTag,
1224
+ memoryTags: currentState.memoryTags,
1225
+ });
1226
+ if (emission && shouldPlayAudio(emission)) {
1227
+ handleSpeak(emission);
1228
+ }
1229
+ }
1230
+ }
1231
+ }, [
1232
+ userLang,
1233
+ language,
1234
+ isMultilanguageEnabled,
1235
+ currentDialogState === null || currentDialogState === void 0 ? void 0 : currentDialogState.emission,
1236
+ translateDialogState,
1237
+ handleSpeak,
1238
+ shouldPlayAudio,
1239
+ ]);
1240
+ const clearEnterTextPending = useCallback((correlationID, pending) => {
1241
+ var _a;
1242
+ if (pending.natsTimeoutId) {
1243
+ clearTimeout(pending.natsTimeoutId);
1244
+ }
1245
+ if ((_a = pending.waitForResponse) === null || _a === void 0 ? void 0 : _a.timeoutId) {
1246
+ clearTimeout(pending.waitForResponse.timeoutId);
1247
+ }
1248
+ pendingEnterTextRef.current.delete(correlationID);
1249
+ }, []);
1250
+ const deliverEnterTextNatsError = useCallback((event) => {
1251
+ var _a, _b, _c;
1252
+ const correlationID = event.correlationID;
1253
+ const errorText = event.errorMessage
1254
+ ? `Error: ${event.errorMessage}`
1255
+ : event.errorCode
1256
+ ? `Error: ${event.errorCode}`
1257
+ : 'Error: An unexpected error occurred';
1258
+ console.error('[EnterText] NATS error event', {
1259
+ correlationID,
1260
+ errorCode: event.errorCode,
1261
+ errorMessage: event.errorMessage,
1262
+ });
1263
+ pushMessage({
1264
+ text: errorText,
1265
+ emitter: 'system',
1266
+ fromUser: false,
1267
+ initial: false,
1268
+ contextVars: {},
1269
+ date: new Date().toISOString(),
1270
+ });
1271
+ if (correlationID) {
1272
+ const pending = pendingEnterTextRef.current.get(correlationID);
1273
+ if (pending) {
1274
+ clearEnterTextPending(correlationID, pending);
1275
+ (_a = pending.waitForResponse) === null || _a === void 0 ? void 0 : _a.reject(new Error((_b = event.errorMessage) !== null && _b !== void 0 ? _b : String((_c = event.errorCode) !== null && _c !== void 0 ? _c : 'NATS error')));
1276
+ }
1277
+ }
1278
+ setMemoriTyping(false);
1279
+ setTypingText(undefined);
1280
+ }, [clearEnterTextPending]);
1281
+ const deliverEnterTextNatsResponse = useCallback((correlationID, event) => {
1282
+ const pending = pendingEnterTextRef.current.get(correlationID);
1283
+ if (!pending) {
1284
+ const pendingCorrelationIDs = [...pendingEnterTextRef.current.keys()];
1285
+ console.warn('[EnterText] NATS response buffered (no matching pending)', {
1286
+ receivedCorrelationID: correlationID,
1287
+ resultCode: event.resultCode,
1288
+ pendingCorrelationIDs,
1289
+ hint: pendingCorrelationIDs.length > 0
1290
+ ? 'Use one of pendingCorrelationIDs in your nats pub correlation_id'
1291
+ : 'Send a message in the widget first, then copy correlationID from HTTP response logs',
1292
+ });
1293
+ bufferedNatsResponsesRef.current.set(correlationID, event);
1294
+ return;
1295
+ }
1296
+ clearEnterTextPending(correlationID, pending);
1297
+ if (pending.waitForResponse) {
1298
+ console.info('[EnterText] NATS response delivered to waiter', {
1299
+ correlationID,
1300
+ resultCode: event.resultCode,
1301
+ });
1302
+ pending.waitForResponse.resolve(event);
1303
+ setMemoriTyping(false);
1304
+ setTypingText(undefined);
1305
+ return;
1306
+ }
1307
+ processEnterTextDialogResponse(event, pending);
1308
+ if (!pending.hasBatchQueued) {
1309
+ console.info('[EnterText] typing indicator cleared', { correlationID });
1310
+ setMemoriTyping(false);
1311
+ setTypingText(undefined);
1312
+ }
1313
+ else {
1314
+ console.debug('[EnterText] typing kept (batch queued)', {
1315
+ correlationID,
1316
+ });
1317
+ }
1318
+ }, [processEnterTextDialogResponse, clearEnterTextPending]);
1319
+ const registerPendingEnterText = useCallback((correlationID, pending) => {
1320
+ const buffered = bufferedNatsResponsesRef.current.get(correlationID);
1321
+ if (buffered) {
1322
+ console.info('[EnterText] replaying buffered NATS response', {
1323
+ correlationID,
1324
+ waitForResponse: !!pending.waitForResponse,
1325
+ });
1326
+ bufferedNatsResponsesRef.current.delete(correlationID);
1327
+ pendingEnterTextRef.current.set(correlationID, pending);
1328
+ deliverEnterTextNatsResponse(correlationID, buffered);
1329
+ return;
1330
+ }
1331
+ if (!pending.waitForResponse && !pending.natsTimeoutId) {
1332
+ pending.natsTimeoutId = setTimeout(() => {
1333
+ var _a;
1334
+ const current = pendingEnterTextRef.current.get(correlationID);
1335
+ if (!current)
1336
+ return;
1337
+ clearEnterTextPending(correlationID, current);
1338
+ console.error('[EnterText] NATS response timeout', {
1339
+ correlationID,
1340
+ timeoutMs: ENTER_TEXT_NATS_TIMEOUT_MS,
1341
+ });
1342
+ if (!current.hasBatchQueued) {
1343
+ setMemoriTyping(false);
1344
+ setTypingText(undefined);
1345
+ }
1346
+ (_a = current.waitForResponse) === null || _a === void 0 ? void 0 : _a.reject(new Error('NATS enter-text response timeout'));
1347
+ }, ENTER_TEXT_NATS_TIMEOUT_MS);
1348
+ }
1349
+ console.debug('[EnterText] pending registered', {
1350
+ correlationID,
1351
+ waitForResponse: !!pending.waitForResponse,
1352
+ hasBatchQueued: pending.hasBatchQueued,
1353
+ });
1354
+ pendingEnterTextRef.current.set(correlationID, pending);
1355
+ }, [deliverEnterTextNatsResponse, clearEnterTextPending]);
1356
+ const waitForEnterTextNatsResponse = useCallback((correlationID, timeoutMs = 120000) => new Promise((resolve, reject) => {
1357
+ console.debug('[EnterText] waiting for NATS response', {
1358
+ correlationID,
1359
+ timeoutMs,
1360
+ });
1361
+ const timeoutId = setTimeout(() => {
1362
+ const current = pendingEnterTextRef.current.get(correlationID);
1363
+ if (current) {
1364
+ clearEnterTextPending(correlationID, current);
1365
+ }
1366
+ console.error('[EnterText] NATS response timeout', {
1367
+ correlationID,
1368
+ timeoutMs,
1369
+ });
1370
+ reject(new Error('NATS enter-text response timeout'));
1371
+ }, timeoutMs);
1372
+ registerPendingEnterText(correlationID, {
1373
+ waitForResponse: {
1374
+ resolve: event => {
1375
+ clearTimeout(timeoutId);
1376
+ resolve(event);
1377
+ },
1378
+ reject: error => {
1379
+ clearTimeout(timeoutId);
1380
+ reject(error);
1381
+ },
1382
+ timeoutId,
1383
+ },
1384
+ });
1385
+ }), [registerPendingEnterText, clearEnterTextPending]);
1386
+ useNats({
1387
+ baseUrl,
1388
+ sessionId,
1389
+ onProgress: useCallback((event) => {
1390
+ console.debug('[EnterText] NATS progress', {
1391
+ correlationID: event.correlationID,
1392
+ step: event.currentStep,
1393
+ finalStep: event.finalStep,
1394
+ message: event.message,
1395
+ });
1396
+ if (event.message) {
1397
+ setTypingText(event.message);
1398
+ }
1399
+ }, []),
1400
+ onDialogResponse: useCallback((event) => {
1401
+ const correlationID = event.correlationID;
1402
+ console.debug('[EnterText] NATS dialog.text_entered_response received', {
1403
+ correlationID,
1404
+ resultCode: event.resultCode,
1405
+ requestID: event.requestID,
1406
+ });
1407
+ if (!correlationID) {
1408
+ console.warn('[EnterText] dialog_text_entered_response without correlationID', event);
1409
+ setMemoriTyping(false);
1410
+ setTypingText(undefined);
1411
+ return;
1412
+ }
1413
+ deliverEnterTextNatsResponse(correlationID, event);
1414
+ }, [deliverEnterTextNatsResponse]),
1415
+ onError: deliverEnterTextNatsError,
1416
+ });
1159
1417
  const focusChatInput = () => {
1160
1418
  let textarea = document.querySelector('#chat-fieldset textarea');
1161
1419
  if (textarea && enableFocusChatInput) {
@@ -1350,7 +1608,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1350
1608
  };
1351
1609
  }, [sessionId, userLang, disableTextEnteredEvents]);
1352
1610
  const onClickStart = useCallback(async (session, initialSessionExpired = false, chatLog, targetSessionID) => {
1353
- var _a, _b, _c, _d, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v, _w;
1611
+ var _a, _b, _c, _d, _f, _g, _h, _j, _k, _l, _m, _o, _p, _q, _r, _s, _t, _u, _v;
1354
1612
  const sessionID = chatLog ? undefined : (session === null || session === void 0 ? void 0 : session.sessionID) || sessionId;
1355
1613
  const dialogState = chatLog
1356
1614
  ? undefined
@@ -1367,7 +1625,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1367
1625
  setShowPositionDrawer(true);
1368
1626
  return;
1369
1627
  }
1370
- if (!(await checkCredits({ notify: true, goBack: true }))) {
1628
+ if (!(await checkCredits({ notify: true }))) {
1371
1629
  setClickedStart(false);
1372
1630
  setLoading(false);
1373
1631
  return;
@@ -1375,6 +1633,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1375
1633
  if (!sessionID && !!minAge && !birth) {
1376
1634
  setShowAgeVerification(true);
1377
1635
  setClickedStart(false);
1636
+ return;
1378
1637
  }
1379
1638
  else if (!sessionID &&
1380
1639
  memori.privacyType !== 'PUBLIC' &&
@@ -1386,82 +1645,95 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1386
1645
  return;
1387
1646
  }
1388
1647
  else if (!sessionID || initialSessionExpired) {
1389
- setClickedStart(false);
1390
- const session = await fetchSession({
1391
- memoriID: memori.engineMemoriID,
1392
- password: secret || memoriPwd || memori.secretToken,
1393
- tag: personification === null || personification === void 0 ? void 0 : personification.tag,
1394
- pin: personification === null || personification === void 0 ? void 0 : personification.pin,
1395
- continueFromChatLogID: chatLog === null || chatLog === void 0 ? void 0 : chatLog.chatLogID,
1396
- initialContextVars: {
1397
- LANG: userLang,
1398
- PATHNAME: (_a = window.location.pathname) === null || _a === void 0 ? void 0 : _a.toUpperCase(),
1399
- ROUTE: ((_d = (_c = (_b = window.location.pathname) === null || _b === void 0 ? void 0 : _b.split('/')) === null || _c === void 0 ? void 0 : _c.pop()) === null || _d === void 0 ? void 0 : _d.toUpperCase()) || '',
1400
- ...((!chatLog
1401
- ? initialContextVars
1402
- : chatLog.lines[chatLog.lines.length - 1].contextVars) || {}),
1403
- },
1404
- initialQuestion: chatLog ? undefined : initialQuestion,
1405
- birthDate: birth,
1406
- additionalInfo: {
1407
- ...(additionalInfo || {}),
1408
- loginToken: (_g = (_f = userToken !== null && userToken !== void 0 ? userToken : loginToken) !== null && _f !== void 0 ? _f : additionalInfo === null || additionalInfo === void 0 ? void 0 : additionalInfo.loginToken) !== null && _g !== void 0 ? _g : authToken,
1409
- language: ((_k = userLang !== null && userLang !== void 0 ? userLang : (_j = (_h = memori.culture) === null || _h === void 0 ? void 0 : _h.split('-')) === null || _j === void 0 ? void 0 : _j[0]) !== null && _k !== void 0 ? _k : 'IT').toLowerCase(),
1410
- timeZoneOffset: new Date().getTimezoneOffset().toString(),
1411
- },
1412
- });
1413
- if (session === null || session === void 0 ? void 0 : session.dialogState) {
1414
- if (!chatLog) {
1415
- setHistory([]);
1416
- await translateAndSpeak(session.dialogState, userLang);
1417
- setHasUserActivatedSpeak(true);
1418
- }
1419
- else {
1420
- const messages = chatLog.lines.map((l, i) => {
1421
- var _a, _b;
1422
- return ({
1423
- text: l.text,
1424
- media: (_b = (_a = l.media) === null || _a === void 0 ? void 0 : _a.filter(m => allowedMediaTypes.includes(m.mimeType))) === null || _b === void 0 ? void 0 : _b.map(m => ({
1425
- mediumID: `${i}-${m.mimeType}`,
1426
- ...m,
1427
- })),
1428
- fromUser: l.inbound,
1429
- llmUsage: l.llmUsage,
1430
- timestamp: l.timestamp,
1431
- emitter: l.emitter,
1432
- initial: i === 0,
1433
- });
1434
- });
1435
- translatedMessages = messages !== null && messages !== void 0 ? messages : [];
1436
- if (language.toUpperCase() !== userLang.toUpperCase() &&
1437
- isMultilanguageEnabled) {
1438
- try {
1439
- translatedMessages = await Promise.all(messages.map(async (m) => {
1440
- if ('originalText' in m && m.originalText) {
1441
- return m;
1442
- }
1443
- return {
1648
+ if (sessionStartingRef.current) {
1649
+ return;
1650
+ }
1651
+ sessionStartingRef.current = true;
1652
+ try {
1653
+ const session = await fetchSession({
1654
+ memoriID: memori.engineMemoriID,
1655
+ password: secret || memoriPwd || memori.secretToken,
1656
+ tag: personification === null || personification === void 0 ? void 0 : personification.tag,
1657
+ pin: personification === null || personification === void 0 ? void 0 : personification.pin,
1658
+ continueFromChatLogID: chatLog === null || chatLog === void 0 ? void 0 : chatLog.chatLogID,
1659
+ initialContextVars: {
1660
+ LANG: userLang,
1661
+ PATHNAME: (_a = window.location.pathname) === null || _a === void 0 ? void 0 : _a.toUpperCase(),
1662
+ ROUTE: ((_d = (_c = (_b = window.location.pathname) === null || _b === void 0 ? void 0 : _b.split('/')) === null || _c === void 0 ? void 0 : _c.pop()) === null || _d === void 0 ? void 0 : _d.toUpperCase()) ||
1663
+ '',
1664
+ ...((!chatLog
1665
+ ? initialContextVars
1666
+ : chatLog.lines[chatLog.lines.length - 1].contextVars) || {}),
1667
+ },
1668
+ initialQuestion: chatLog ? undefined : initialQuestion,
1669
+ birthDate: birth,
1670
+ additionalInfo: {
1671
+ ...(additionalInfo || {}),
1672
+ loginToken: (_g = (_f = userToken !== null && userToken !== void 0 ? userToken : loginToken) !== null && _f !== void 0 ? _f : additionalInfo === null || additionalInfo === void 0 ? void 0 : additionalInfo.loginToken) !== null && _g !== void 0 ? _g : authToken,
1673
+ language: ((_k = userLang !== null && userLang !== void 0 ? userLang : (_j = (_h = memori.culture) === null || _h === void 0 ? void 0 : _h.split('-')) === null || _j === void 0 ? void 0 : _j[0]) !== null && _k !== void 0 ? _k : 'IT').toLowerCase(),
1674
+ timeZoneOffset: new Date().getTimezoneOffset().toString(),
1675
+ },
1676
+ });
1677
+ if (session === null || session === void 0 ? void 0 : session.dialogState) {
1678
+ if (!chatLog) {
1679
+ setHistory([]);
1680
+ await translateAndSpeak(session.dialogState, userLang);
1681
+ setHasUserActivatedSpeak(true);
1682
+ setClickedStart(false);
1683
+ }
1684
+ else {
1685
+ const messages = chatLog.lines.map((l, i) => {
1686
+ var _a, _b;
1687
+ return ({
1688
+ text: l.text,
1689
+ media: (_b = (_a = l.media) === null || _a === void 0 ? void 0 : _a.filter(m => allowedMediaTypes.includes(m.mimeType))) === null || _b === void 0 ? void 0 : _b.map(m => ({
1690
+ mediumID: `${i}-${m.mimeType}`,
1444
1691
  ...m,
1445
- originalText: m.text,
1446
- text: (await getTranslation(m.text, userLang, language, baseUrl)).text,
1447
- };
1448
- }));
1449
- }
1450
- catch (e) {
1451
- console.error('[onClickStart] Error translating messages:', e);
1692
+ })),
1693
+ fromUser: l.inbound,
1694
+ llmUsage: l.llmUsage,
1695
+ timestamp: l.timestamp,
1696
+ emitter: l.emitter,
1697
+ initial: i === 0,
1698
+ });
1699
+ });
1700
+ translatedMessages = messages !== null && messages !== void 0 ? messages : [];
1701
+ if (language.toUpperCase() !== userLang.toUpperCase() &&
1702
+ isMultilanguageEnabled) {
1703
+ try {
1704
+ translatedMessages = await Promise.all(messages.map(async (m) => {
1705
+ if ('originalText' in m && m.originalText) {
1706
+ return m;
1707
+ }
1708
+ return {
1709
+ ...m,
1710
+ originalText: m.text,
1711
+ text: (await getTranslation(m.text, userLang, language, baseUrl)).text,
1712
+ };
1713
+ }));
1714
+ }
1715
+ catch (e) {
1716
+ console.error('[onClickStart] Error translating messages:', e);
1717
+ }
1452
1718
  }
1719
+ setHistory(translatedMessages);
1720
+ translateDialogState(session.dialogState, userLang, undefined, true).finally(() => {
1721
+ setHasUserActivatedSpeak(true);
1722
+ setClickedStart(false);
1723
+ });
1453
1724
  }
1454
- setHistory(translatedMessages);
1455
- translateDialogState(session.dialogState, userLang, undefined, true).finally(() => {
1456
- setHasUserActivatedSpeak(true);
1457
- });
1725
+ }
1726
+ else if ((session === null || session === void 0 ? void 0 : session.resultCode) === 0) {
1727
+ sessionStartingRef.current = false;
1728
+ await onClickStart(session || undefined);
1729
+ }
1730
+ else {
1731
+ setLoading(false);
1732
+ setClickedStart(false);
1458
1733
  }
1459
1734
  }
1460
- else if ((session === null || session === void 0 ? void 0 : session.resultCode) === 0) {
1461
- await onClickStart(session || undefined);
1462
- }
1463
- else {
1464
- setLoading(false);
1735
+ finally {
1736
+ sessionStartingRef.current = false;
1465
1737
  }
1466
1738
  return;
1467
1739
  }
@@ -1471,7 +1743,6 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1471
1743
  if (response.resultCode !== 0 || !currentState) {
1472
1744
  const { chatLogs } = await getSessionChatLogs(sessionID, sessionID);
1473
1745
  setSessionId(undefined);
1474
- setClickedStart(false);
1475
1746
  await onClickStart(undefined, true, chatLogs === null || chatLogs === void 0 ? void 0 : chatLogs[0]);
1476
1747
  return;
1477
1748
  }
@@ -1498,6 +1769,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1498
1769
  ...(initialContextVars || {}),
1499
1770
  }, initialQuestion, birth).then(() => {
1500
1771
  setHasUserActivatedSpeak(true);
1772
+ setClickedStart(false);
1501
1773
  });
1502
1774
  }
1503
1775
  }
@@ -1524,6 +1796,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1524
1796
  ...(initialContextVars || {}),
1525
1797
  }, initialQuestion, birth).then(() => {
1526
1798
  setHasUserActivatedSpeak(true);
1799
+ setClickedStart(false);
1527
1800
  });
1528
1801
  }
1529
1802
  }
@@ -1567,15 +1840,18 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1567
1840
  if ((!!(translatedMessages === null || translatedMessages === void 0 ? void 0 : translatedMessages.length) && translatedMessages.length > 1) ||
1568
1841
  !initialQuestion) {
1569
1842
  setHasUserActivatedSpeak(true);
1843
+ setClickedStart(false);
1570
1844
  await translateAndSpeak(currentState, userLang, undefined, !!(translatedMessages === null || translatedMessages === void 0 ? void 0 : translatedMessages.length));
1571
1845
  }
1572
1846
  else {
1573
1847
  console.log('[onClickStart] Starting with initial question');
1574
1848
  translatedMessages = [];
1575
1849
  setHistory([]);
1576
- setMemoriTyping(true);
1577
1850
  const placeSpec = getPlaceSpecForEnterText(position);
1578
- const response = await postTextEnteredEvent({
1851
+ console.debug('[EnterText] onClickStart: posting initial question', {
1852
+ sessionId: sessionID,
1853
+ });
1854
+ const response = await postEnterTextAsync({
1579
1855
  sessionId: sessionID,
1580
1856
  text: initialQuestion,
1581
1857
  ...(memori.needsDateTime && {
@@ -1583,6 +1859,10 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1583
1859
  }),
1584
1860
  ...(placeSpec !== undefined && { place: placeSpec }),
1585
1861
  });
1862
+ console.debug('[EnterText] onClickStart: HTTP response', {
1863
+ resultCode: response.resultCode,
1864
+ correlationID: readCorrelationID(response),
1865
+ });
1586
1866
  if (response.resultCode === 500 && response.resultMessage) {
1587
1867
  setHistory(h => [
1588
1868
  ...h,
@@ -1595,10 +1875,33 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1595
1875
  date: new Date().toISOString(),
1596
1876
  },
1597
1877
  ]);
1598
- setMemoriTyping(false);
1599
1878
  return;
1600
1879
  }
1601
- await translateAndSpeak((_w = response.currentState) !== null && _w !== void 0 ? _w : currentState, userLang, undefined, false);
1880
+ const onClickStartCorrelationID = readCorrelationID(response);
1881
+ if (response.resultCode === 0 && onClickStartCorrelationID) {
1882
+ console.info('[EnterText] onClickStart: accepted, showing typing indicator', {
1883
+ correlationID: onClickStartCorrelationID,
1884
+ });
1885
+ setMemoriTyping(true);
1886
+ try {
1887
+ const natsEvent = await waitForEnterTextNatsResponse(onClickStartCorrelationID);
1888
+ console.info('[EnterText] onClickStart: NATS response received', {
1889
+ correlationID: onClickStartCorrelationID,
1890
+ resultCode: natsEvent.resultCode,
1891
+ });
1892
+ if (natsEvent.resultCode === 0 && natsEvent.currentState) {
1893
+ await translateAndSpeak(natsEvent.currentState, userLang, undefined, false);
1894
+ }
1895
+ }
1896
+ catch (e) {
1897
+ console.error('[EnterText] onClickStart: NATS wait failed', e);
1898
+ setMemoriTyping(false);
1899
+ setTypingText(undefined);
1900
+ }
1901
+ }
1902
+ else if (response.resultCode === 0) {
1903
+ console.error('[EnterText] onClickStart: HTTP 200 but missing correlationID', response);
1904
+ }
1602
1905
  }
1603
1906
  }
1604
1907
  }
@@ -1608,10 +1911,14 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1608
1911
  }
1609
1912
  }, [memoriPwd, memori, memoriTokens, birthDate, sessionId, userLang, position]);
1610
1913
  useEffect(() => {
1611
- if (!clickedStart && autoStart && selectedLayout !== 'HIDDEN_CHAT') {
1914
+ if (!clickedStart &&
1915
+ !sessionStartingRef.current &&
1916
+ !sessionId &&
1917
+ autoStart &&
1918
+ selectedLayout !== 'HIDDEN_CHAT') {
1612
1919
  onClickStart();
1613
1920
  }
1614
- }, [clickedStart, autoStart, selectedLayout]);
1921
+ }, [clickedStart, autoStart, selectedLayout, sessionId]);
1615
1922
  useEffect(() => {
1616
1923
  const targetNode = document.querySelector(`memori-client[memoriname="${memori.name}"]`) ||
1617
1924
  document.querySelector(`memori-client[memoriid="${memori.memoriID}"]`) ||
@@ -1669,21 +1976,18 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1669
1976
  (user === null || user === void 0 ? void 0 : user.pAndCUAccepted);
1670
1977
  const needsCredits = tenant === null || tenant === void 0 ? void 0 : tenant.billingDelegation;
1671
1978
  const [hasEnoughCredits, setHasEnoughCredits] = useState(true);
1672
- const handleNotEnoughCredits = useCallback((goBack = false) => {
1979
+ const handleNotEnoughCredits = useCallback(() => {
1673
1980
  setHasEnoughCredits(false);
1674
1981
  setAuthModalState(null);
1675
1982
  toast.error(t('notEnoughCredits'));
1676
- if (goBack && window.history.length > 1) {
1677
- window.history.back();
1678
- }
1679
1983
  }, [t]);
1680
1984
  const checkCredits = useCallback(async (options) => {
1681
1985
  if (!(tenant === null || tenant === void 0 ? void 0 : tenant.billingDelegation))
1682
1986
  return true;
1683
- if (!ownerUserID) {
1684
- console.warn('Cannot verify credits: missing ownerUserID');
1987
+ if (!ownerUserID && !ownerUserName) {
1988
+ console.warn('Cannot verify credits: missing owner identifier');
1685
1989
  if (options === null || options === void 0 ? void 0 : options.notify) {
1686
- handleNotEnoughCredits(!!options.goBack);
1990
+ handleNotEnoughCredits();
1687
1991
  }
1688
1992
  else {
1689
1993
  setHasEnoughCredits(false);
@@ -1697,6 +2001,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1697
2001
  : 'session_creation',
1698
2002
  baseUrl: baseUrl,
1699
2003
  userID: ownerUserID,
2004
+ userName: ownerUserName,
1700
2005
  tenant: tenantID,
1701
2006
  });
1702
2007
  if (resp.enough) {
@@ -1706,7 +2011,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1706
2011
  else {
1707
2012
  console.warn('Not enough credits. Required:', resp.required);
1708
2013
  if (options === null || options === void 0 ? void 0 : options.notify) {
1709
- handleNotEnoughCredits(!!options.goBack);
2014
+ handleNotEnoughCredits();
1710
2015
  }
1711
2016
  else {
1712
2017
  setHasEnoughCredits(false);
@@ -1724,6 +2029,7 @@ const MemoriWidget = ({ memori, memoriConfigs, ownerUserID, tenantID, memoriLang
1724
2029
  deepThoughtEnabled,
1725
2030
  handleNotEnoughCredits,
1726
2031
  ownerUserID,
2032
+ ownerUserName,
1727
2033
  tenant === null || tenant === void 0 ? void 0 : tenant.billingDelegation,
1728
2034
  tenantID,
1729
2035
  ]);