instantsearch.js 4.86.1 → 4.87.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.
Files changed (47) hide show
  1. package/cjs/connectors/autocomplete/connectAutocomplete.js +13 -5
  2. package/cjs/connectors/chat/connectChat.js +89 -17
  3. package/cjs/connectors/filter-suggestions/connectFilterSuggestions.js +255 -0
  4. package/cjs/connectors/index.js +7 -0
  5. package/cjs/connectors/index.umd.js +7 -0
  6. package/cjs/lib/chat/chat.js +3 -3
  7. package/cjs/lib/chat/index.js +5 -2
  8. package/cjs/lib/version.js +1 -1
  9. package/cjs/widgets/autocomplete/autocomplete.js +15 -6
  10. package/cjs/widgets/chat/chat.js +32 -3
  11. package/cjs/widgets/filter-suggestions/filter-suggestions.js +131 -0
  12. package/cjs/widgets/index.js +7 -0
  13. package/cjs/widgets/index.umd.js +7 -0
  14. package/dist/instantsearch.development.d.ts +885 -72
  15. package/dist/instantsearch.development.js +731 -184
  16. package/dist/instantsearch.development.js.map +1 -1
  17. package/dist/instantsearch.production.d.ts +885 -72
  18. package/dist/instantsearch.production.min.d.ts +885 -72
  19. package/dist/instantsearch.production.min.js +2 -2
  20. package/dist/instantsearch.production.min.js.map +1 -1
  21. package/es/connectors/autocomplete/connectAutocomplete.d.ts +10 -0
  22. package/es/connectors/autocomplete/connectAutocomplete.js +13 -5
  23. package/es/connectors/chat/connectChat.d.ts +10 -0
  24. package/es/connectors/chat/connectChat.js +89 -17
  25. package/es/connectors/filter-suggestions/connectFilterSuggestions.d.ts +95 -0
  26. package/es/connectors/filter-suggestions/connectFilterSuggestions.js +249 -0
  27. package/es/connectors/index.d.ts +1 -0
  28. package/es/connectors/index.js +2 -1
  29. package/es/connectors/index.umd.d.ts +1 -0
  30. package/es/connectors/index.umd.js +2 -1
  31. package/es/lib/chat/chat.d.ts +1 -1
  32. package/es/lib/chat/chat.js +3 -3
  33. package/es/lib/chat/index.d.ts +3 -0
  34. package/es/lib/chat/index.js +4 -1
  35. package/es/lib/version.d.ts +1 -1
  36. package/es/lib/version.js +1 -1
  37. package/es/widgets/autocomplete/autocomplete.d.ts +2 -1
  38. package/es/widgets/autocomplete/autocomplete.js +15 -6
  39. package/es/widgets/chat/chat.d.ts +8 -0
  40. package/es/widgets/chat/chat.js +33 -4
  41. package/es/widgets/filter-suggestions/filter-suggestions.d.ts +689 -0
  42. package/es/widgets/filter-suggestions/filter-suggestions.js +124 -0
  43. package/es/widgets/index.d.ts +1 -0
  44. package/es/widgets/index.js +2 -1
  45. package/es/widgets/index.umd.d.ts +1 -0
  46. package/es/widgets/index.umd.js +2 -1
  47. package/package.json +6 -6
@@ -21,7 +21,11 @@ var connectAutocomplete = function connectAutocomplete(renderFn) {
21
21
  return function (widgetParams) {
22
22
  var _ref = widgetParams || {},
23
23
  _ref$escapeHTML = _ref.escapeHTML,
24
- escapeHTML = _ref$escapeHTML === void 0 ? true : _ref$escapeHTML;
24
+ escapeHTML = _ref$escapeHTML === void 0 ? true : _ref$escapeHTML,
25
+ _ref$transformItems = _ref.transformItems,
26
+ transformItems = _ref$transformItems === void 0 ? function (indices) {
27
+ return indices;
28
+ } : _ref$transformItems;
25
29
  process.env.NODE_ENV === 'development' ? (0, _utils.warning)(!widgetParams.indices, "\nThe option `indices` has been removed from the Autocomplete connector.\n\nThe indices to target are now inferred from the widgets tree.\n".concat(Array.isArray(widgetParams.indices) ? "\nAn alternative would be:\n\nconst autocomplete = connectAutocomplete(renderer);\n\nsearch.addWidgets([\n ".concat(widgetParams.indices.map(function (_ref2) {
26
30
  var value = _ref2.value;
27
31
  return "index({ indexName: '".concat(value, "' }),");
@@ -63,6 +67,7 @@ var connectAutocomplete = function connectAutocomplete(renderFn) {
63
67
  helper.setQuery(query).search();
64
68
  };
65
69
  }
70
+ var sendEventMap = {};
66
71
  var indices = scopedResults.map(function (scopedResult) {
67
72
  var _scopedResult$results, _scopedResult$results2;
68
73
  // We need to escape the hits because highlighting
@@ -70,7 +75,7 @@ var connectAutocomplete = function connectAutocomplete(renderFn) {
70
75
  if (scopedResult.results) {
71
76
  scopedResult.results.hits = escapeHTML ? (0, _utils.escapeHits)(scopedResult.results.hits) : scopedResult.results.hits;
72
77
  }
73
- var sendEvent = (0, _utils.createSendEventForHits)({
78
+ sendEventMap[scopedResult.indexId] = (0, _utils.createSendEventForHits)({
74
79
  instantSearchInstance: instantSearchInstance,
75
80
  helper: scopedResult.helper,
76
81
  widgetType: _this.$$type
@@ -79,13 +84,16 @@ var connectAutocomplete = function connectAutocomplete(renderFn) {
79
84
  indexId: scopedResult.indexId,
80
85
  indexName: ((_scopedResult$results = scopedResult.results) === null || _scopedResult$results === void 0 ? void 0 : _scopedResult$results.index) || '',
81
86
  hits: ((_scopedResult$results2 = scopedResult.results) === null || _scopedResult$results2 === void 0 ? void 0 : _scopedResult$results2.hits) || [],
82
- results: scopedResult.results || {},
83
- sendEvent: sendEvent
87
+ results: scopedResult.results || {}
84
88
  };
85
89
  });
86
90
  return {
87
91
  currentRefinement: state.query || '',
88
- indices: indices,
92
+ indices: transformItems(indices).map(function (transformedIndex) {
93
+ return _objectSpread(_objectSpread({}, transformedIndex), {}, {
94
+ sendEvent: sendEventMap[transformedIndex.indexId]
95
+ });
96
+ }),
89
97
  refine: connectorState.refine,
90
98
  widgetParams: widgetParams
91
99
  };
@@ -8,7 +8,8 @@ exports.default = void 0;
8
8
  var _ai = require("ai");
9
9
  var _chat = require("../../lib/chat");
10
10
  var _utils = require("../../lib/utils");
11
- var _excluded = ["resume", "tools"];
11
+ var _excluded = ["resume", "tools", "type"],
12
+ _excluded2 = ["messages", "trigger"];
12
13
  function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
13
14
  function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
14
15
  function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
@@ -16,10 +17,14 @@ function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol"
16
17
  function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
17
18
  function _slicedToArray(r, e) { return _arrayWithHoles(r) || _iterableToArrayLimit(r, e) || _unsupportedIterableToArray(r, e) || _nonIterableRest(); }
18
19
  function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
19
- function _unsupportedIterableToArray(r, a) { if (r) { if ("string" == typeof r) return _arrayLikeToArray(r, a); var t = {}.toString.call(r).slice(8, -1); return "Object" === t && r.constructor && (t = r.constructor.name), "Map" === t || "Set" === t ? Array.from(r) : "Arguments" === t || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(t) ? _arrayLikeToArray(r, a) : void 0; } }
20
- function _arrayLikeToArray(r, a) { (null == a || a > r.length) && (a = r.length); for (var e = 0, n = Array(a); e < a; e++) n[e] = r[e]; return n; }
21
20
  function _iterableToArrayLimit(r, l) { var t = null == r ? null : "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (null != t) { var e, n, i, u, a = [], f = !0, o = !1; try { if (i = (t = t.call(r)).next, 0 === l) { if (Object(t) !== t) return; f = !1; } else for (; !(f = (e = i.call(t)).done) && (a.push(e.value), a.length !== l); f = !0); } catch (r) { o = !0, n = r; } finally { try { if (!f && null != t.return && (u = t.return(), Object(u) !== u)) return; } finally { if (o) throw n; } } return a; } }
22
21
  function _arrayWithHoles(r) { if (Array.isArray(r)) return r; }
22
+ function _toConsumableArray(r) { return _arrayWithoutHoles(r) || _iterableToArray(r) || _unsupportedIterableToArray(r) || _nonIterableSpread(); }
23
+ function _nonIterableSpread() { throw new TypeError("Invalid attempt to spread non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
24
+ function _unsupportedIterableToArray(r, a) { if (r) { if ("string" == typeof r) return _arrayLikeToArray(r, a); var t = {}.toString.call(r).slice(8, -1); return "Object" === t && r.constructor && (t = r.constructor.name), "Map" === t || "Set" === t ? Array.from(r) : "Arguments" === t || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(t) ? _arrayLikeToArray(r, a) : void 0; } }
25
+ function _iterableToArray(r) { if ("undefined" != typeof Symbol && null != r[Symbol.iterator] || null != r["@@iterator"]) return Array.from(r); }
26
+ function _arrayWithoutHoles(r) { if (Array.isArray(r)) return _arrayLikeToArray(r); }
27
+ function _arrayLikeToArray(r, a) { (null == a || a > r.length) && (a = r.length); for (var e = 0, n = Array(a); e < a; e++) n[e] = r[e]; return n; }
23
28
  function _objectWithoutProperties(e, t) { if (null == e) return {}; var o, r, i = _objectWithoutPropertiesLoose(e, t); if (Object.getOwnPropertySymbols) { var n = Object.getOwnPropertySymbols(e); for (r = 0; r < n.length; r++) o = n[r], -1 === t.indexOf(o) && {}.propertyIsEnumerable.call(e, o) && (i[o] = e[o]); } return i; }
24
29
  function _objectWithoutPropertiesLoose(r, e) { if (null == r) return {}; var t = {}; for (var n in r) if ({}.hasOwnProperty.call(r, n)) { if (-1 !== e.indexOf(n)) continue; t[n] = r[n]; } return t; }
25
30
  var withUsage = (0, _utils.createDocumentationMessageGenerator)({
@@ -36,6 +41,8 @@ var connectChat = exports.default = function connectChat(renderFn) {
36
41
  resume = _ref$resume === void 0 ? false : _ref$resume,
37
42
  _ref$tools = _ref.tools,
38
43
  tools = _ref$tools === void 0 ? {} : _ref$tools,
44
+ _ref$type = _ref.type,
45
+ type = _ref$type === void 0 ? 'chat' : _ref$type,
39
46
  options = _objectWithoutProperties(_ref, _excluded);
40
47
  var _chatInstance;
41
48
  var input = '';
@@ -45,6 +52,25 @@ var connectChat = exports.default = function connectChat(renderFn) {
45
52
  var setInput;
46
53
  var setOpen;
47
54
  var setIsClearing;
55
+ var agentId = 'agentId' in options ? options.agentId : undefined;
56
+
57
+ // Extract suggestions from the last assistant message's data-suggestions part
58
+ var getSuggestionsFromMessages = function getSuggestionsFromMessages(messages) {
59
+ // Find the last assistant message (iterate from end)
60
+ var lastAssistantMessage = _toConsumableArray(messages).reverse().find(function (message) {
61
+ return message.role === 'assistant' && message.parts;
62
+ });
63
+ if (!(lastAssistantMessage !== null && lastAssistantMessage !== void 0 && lastAssistantMessage.parts)) {
64
+ return undefined;
65
+ }
66
+
67
+ // Find the data-suggestions part
68
+ var suggestionsPart = lastAssistantMessage.parts.find(function (part) {
69
+ var _data;
70
+ return 'type' in part && part.type === 'data-suggestions' && 'data' in part && Array.isArray((_data = part.data) === null || _data === void 0 ? void 0 : _data.suggestions);
71
+ });
72
+ return suggestionsPart === null || suggestionsPart === void 0 ? void 0 : suggestionsPart.data.suggestions;
73
+ };
48
74
  var setMessages = function setMessages(messagesParam) {
49
75
  if (typeof messagesParam === 'function') {
50
76
  messagesParam = messagesParam(_chatInstance.messages);
@@ -68,20 +94,67 @@ var connectChat = exports.default = function connectChat(renderFn) {
68
94
  _getAppIdAndApiKey2 = _slicedToArray(_getAppIdAndApiKey, 2),
69
95
  appId = _getAppIdAndApiKey2[0],
70
96
  apiKey = _getAppIdAndApiKey2[1];
97
+
98
+ // Filter out custom data parts (like data-suggestions) that the backend doesn't accept
99
+ var filterDataParts = function filterDataParts(messages) {
100
+ return messages.map(function (message) {
101
+ var _message$parts;
102
+ return _objectSpread(_objectSpread({}, message), {}, {
103
+ parts: (_message$parts = message.parts) === null || _message$parts === void 0 ? void 0 : _message$parts.filter(function (part) {
104
+ return !('type' in part && part.type.startsWith('data-'));
105
+ })
106
+ });
107
+ });
108
+ };
71
109
  if ('transport' in options && options.transport) {
72
- transport = new _ai.DefaultChatTransport(options.transport);
110
+ var originalPrepare = options.transport.prepareSendMessagesRequest;
111
+ transport = new _ai.DefaultChatTransport(_objectSpread(_objectSpread({}, options.transport), {}, {
112
+ prepareSendMessagesRequest: function prepareSendMessagesRequest(params) {
113
+ // Call the original prepareSendMessagesRequest if it exists,
114
+ // otherwise construct the default body
115
+ var preparedOrPromise = originalPrepare ? originalPrepare(params) : {
116
+ body: _objectSpread({}, params)
117
+ };
118
+ // Then filter out data-* parts
119
+ var applyFilter = function applyFilter(prepared) {
120
+ return _objectSpread(_objectSpread({}, prepared), {}, {
121
+ body: _objectSpread(_objectSpread({}, prepared.body), {}, {
122
+ messages: filterDataParts(prepared.body.messages)
123
+ })
124
+ });
125
+ };
126
+
127
+ // Handle both sync and async cases
128
+ if (preparedOrPromise && 'then' in preparedOrPromise) {
129
+ return preparedOrPromise.then(applyFilter);
130
+ }
131
+ return applyFilter(preparedOrPromise);
132
+ }
133
+ }));
73
134
  }
74
135
  if ('agentId' in options && options.agentId) {
75
- var agentId = options.agentId;
76
136
  if (!appId || !apiKey) {
77
137
  throw new Error(withUsage('Could not extract Algolia credentials from the search client.'));
78
138
  }
139
+ var baseApi = "https://".concat(appId, ".algolia.net/agent-studio/1/agents/").concat(agentId, "/completions?compatibilityMode=ai-sdk-5");
79
140
  transport = new _ai.DefaultChatTransport({
80
- api: "https://".concat(appId, ".algolia.net/agent-studio/1/agents/").concat(agentId, "/completions?compatibilityMode=ai-sdk-5"),
141
+ api: baseApi,
81
142
  headers: {
82
143
  'x-algolia-application-id': appId,
83
144
  'x-algolia-api-Key': apiKey,
84
145
  'x-algolia-agent': (0, _utils.getAlgoliaAgent)(instantSearchInstance.client)
146
+ },
147
+ prepareSendMessagesRequest: function prepareSendMessagesRequest(_ref2) {
148
+ var messages = _ref2.messages,
149
+ trigger = _ref2.trigger,
150
+ rest = _objectWithoutProperties(_ref2, _excluded2);
151
+ return {
152
+ // Bypass cache when regenerating to ensure fresh responses
153
+ api: trigger === 'regenerate-message' ? "".concat(baseApi, "&cache=false") : baseApi,
154
+ body: _objectSpread(_objectSpread({}, rest), {}, {
155
+ messages: filterDataParts(messages)
156
+ })
157
+ };
85
158
  }
86
159
  });
87
160
  }
@@ -94,8 +167,8 @@ var connectChat = exports.default = function connectChat(renderFn) {
94
167
  return new _chat.Chat(_objectSpread(_objectSpread({}, options), {}, {
95
168
  transport: transport,
96
169
  sendAutomaticallyWhen: _ai.lastAssistantMessageIsCompleteWithToolCalls,
97
- onToolCall: function onToolCall(_ref2) {
98
- var toolCall = _ref2.toolCall;
170
+ onToolCall: function onToolCall(_ref3) {
171
+ var toolCall = _ref3.toolCall;
99
172
  var tool = tools[toolCall.toolName];
100
173
  if (!tool) {
101
174
  if (process.env.NODE_ENV === 'development') {
@@ -108,8 +181,8 @@ var connectChat = exports.default = function connectChat(renderFn) {
108
181
  });
109
182
  }
110
183
  if (tool.onToolCall) {
111
- var addToolResult = function addToolResult(_ref3) {
112
- var output = _ref3.output;
184
+ var addToolResult = function addToolResult(_ref4) {
185
+ var output = _ref4.output;
113
186
  return _chatInstance.addToolResult({
114
187
  output: output,
115
188
  tool: toolCall.toolName,
@@ -165,9 +238,7 @@ var connectChat = exports.default = function connectChat(renderFn) {
165
238
  getRenderState: function getRenderState(renderState, renderOptions
166
239
  // Type is explicitly redefined, to avoid having the TWidgetParams type in the definition
167
240
  ) {
168
- return _objectSpread(_objectSpread({}, renderState), {}, {
169
- chat: this.getWidgetRenderState(renderOptions)
170
- });
241
+ return _objectSpread(_objectSpread({}, renderState), {}, _defineProperty({}, type, this.getWidgetRenderState(renderOptions)));
171
242
  },
172
243
  getWidgetRenderState: function getWidgetRenderState(renderOptions) {
173
244
  var instantSearchInstance = renderOptions.instantSearchInstance,
@@ -186,10 +257,10 @@ var connectChat = exports.default = function connectChat(renderFn) {
186
257
  });
187
258
  }
188
259
  var toolsWithAddToolResult = {};
189
- Object.entries(tools).forEach(function (_ref4) {
190
- var _ref5 = _slicedToArray(_ref4, 2),
191
- key = _ref5[0],
192
- tool = _ref5[1];
260
+ Object.entries(tools).forEach(function (_ref5) {
261
+ var _ref6 = _slicedToArray(_ref5, 2),
262
+ key = _ref6[0],
263
+ tool = _ref6[1];
193
264
  var toolWithAddToolResult = _objectSpread(_objectSpread({}, tool), {}, {
194
265
  addToolResult: _chatInstance.addToolResult
195
266
  });
@@ -204,6 +275,7 @@ var connectChat = exports.default = function connectChat(renderFn) {
204
275
  setInput: setInput,
205
276
  setOpen: setOpen,
206
277
  setMessages: setMessages,
278
+ suggestions: getSuggestionsFromMessages(_chatInstance.messages),
207
279
  isClearing: isClearing,
208
280
  clearMessages: clearMessages,
209
281
  onClearTransitionEnd: onClearTransitionEnd,
@@ -0,0 +1,255 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _utils = require("../../lib/utils");
8
+ function _typeof(o) { "@babel/helpers - typeof"; return _typeof = "function" == typeof Symbol && "symbol" == typeof Symbol.iterator ? function (o) { return typeof o; } : function (o) { return o && "function" == typeof Symbol && o.constructor === Symbol && o !== Symbol.prototype ? "symbol" : typeof o; }, _typeof(o); }
9
+ function _slicedToArray(r, e) { return _arrayWithHoles(r) || _iterableToArrayLimit(r, e) || _unsupportedIterableToArray(r, e) || _nonIterableRest(); }
10
+ function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
11
+ function _unsupportedIterableToArray(r, a) { if (r) { if ("string" == typeof r) return _arrayLikeToArray(r, a); var t = {}.toString.call(r).slice(8, -1); return "Object" === t && r.constructor && (t = r.constructor.name), "Map" === t || "Set" === t ? Array.from(r) : "Arguments" === t || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(t) ? _arrayLikeToArray(r, a) : void 0; } }
12
+ function _arrayLikeToArray(r, a) { (null == a || a > r.length) && (a = r.length); for (var e = 0, n = Array(a); e < a; e++) n[e] = r[e]; return n; }
13
+ function _iterableToArrayLimit(r, l) { var t = null == r ? null : "undefined" != typeof Symbol && r[Symbol.iterator] || r["@@iterator"]; if (null != t) { var e, n, i, u, a = [], f = !0, o = !1; try { if (i = (t = t.call(r)).next, 0 === l) { if (Object(t) !== t) return; f = !1; } else for (; !(f = (e = i.call(t)).done) && (a.push(e.value), a.length !== l); f = !0); } catch (r) { o = !0, n = r; } finally { try { if (!f && null != t.return && (u = t.return(), Object(u) !== u)) return; } finally { if (o) throw n; } } return a; } }
14
+ function _arrayWithHoles(r) { if (Array.isArray(r)) return r; }
15
+ function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
16
+ function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { _defineProperty(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
17
+ function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
18
+ function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : i + ""; }
19
+ function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
20
+ var withUsage = (0, _utils.createDocumentationMessageGenerator)({
21
+ name: 'filter-suggestions',
22
+ connector: true
23
+ });
24
+ var connectFilterSuggestions = function connectFilterSuggestions(renderFn) {
25
+ var unmountFn = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : _utils.noop;
26
+ (0, _utils.checkRendering)(renderFn, withUsage());
27
+ return function (widgetParams) {
28
+ var agentId = widgetParams.agentId,
29
+ attributes = widgetParams.attributes,
30
+ _widgetParams$maxSugg = widgetParams.maxSuggestions,
31
+ maxSuggestions = _widgetParams$maxSugg === void 0 ? 3 : _widgetParams$maxSugg,
32
+ _widgetParams$debounc = widgetParams.debounceMs,
33
+ debounceMs = _widgetParams$debounc === void 0 ? 300 : _widgetParams$debounc,
34
+ _widgetParams$hitsToS = widgetParams.hitsToSample,
35
+ hitsToSample = _widgetParams$hitsToS === void 0 ? 5 : _widgetParams$hitsToS,
36
+ _widgetParams$transfo = widgetParams.transformItems,
37
+ transformItems = _widgetParams$transfo === void 0 ? function (items) {
38
+ return items;
39
+ } : _widgetParams$transfo,
40
+ transport = widgetParams.transport;
41
+ if (!agentId && !transport) {
42
+ throw new Error(withUsage('The `agentId` option is required unless a custom `transport` is provided.'));
43
+ }
44
+ var endpoint;
45
+ var headers;
46
+ var suggestions = [];
47
+ var isLoading = false;
48
+ var debounceTimer;
49
+ var lastStateSignature = null; // null means never fetched
50
+ var refine;
51
+ var searchHelper = null;
52
+ var latestRenderOptions = null;
53
+
54
+ // Create a signature of the current search state (query + refinements)
55
+ var getStateSignature = function getStateSignature(results) {
56
+ var query = results.query || '';
57
+ var refinements = searchHelper ? JSON.stringify(searchHelper.state.facetsRefinements) + JSON.stringify(searchHelper.state.disjunctiveFacetsRefinements) + JSON.stringify(searchHelper.state.hierarchicalFacetsRefinements) : '';
58
+ return "".concat(query, "|").concat(refinements);
59
+ };
60
+ var _getWidgetRenderState = function getWidgetRenderState(renderOptions) {
61
+ var results = 'results' in renderOptions ? renderOptions.results : undefined;
62
+ var transformedSuggestions = transformItems(suggestions, {
63
+ results: results
64
+ });
65
+ return {
66
+ suggestions: transformedSuggestions,
67
+ isLoading: isLoading,
68
+ refine: refine,
69
+ widgetParams: widgetParams
70
+ };
71
+ };
72
+
73
+ // Minimum duration to show skeleton to avoid flash when results are cached
74
+ var MIN_SKELETON_DURATION_MS = 300;
75
+ var fetchSuggestions = function fetchSuggestions(results, renderOptions) {
76
+ var _results$hits, _rawResults$;
77
+ if (!(results !== null && results !== void 0 && (_results$hits = results.hits) !== null && _results$hits !== void 0 && _results$hits.length)) {
78
+ suggestions = [];
79
+ isLoading = false;
80
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(renderOptions)), {}, {
81
+ instantSearchInstance: renderOptions.instantSearchInstance
82
+ }), false);
83
+ return;
84
+ }
85
+ var loadingStartTime = Date.now();
86
+ isLoading = true;
87
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(renderOptions)), {}, {
88
+ instantSearchInstance: renderOptions.instantSearchInstance
89
+ }), false);
90
+
91
+ // Get facets from raw results (results.facets is processed differently)
92
+ var rawResults = results._rawResults;
93
+ var rawFacets = (rawResults === null || rawResults === void 0 ? void 0 : (_rawResults$ = rawResults[0]) === null || _rawResults$ === void 0 ? void 0 : _rawResults$.facets) || {};
94
+ var facetsToSend = attributes ? Object.fromEntries(Object.entries(rawFacets).filter(function (_ref) {
95
+ var _ref2 = _slicedToArray(_ref, 1),
96
+ key = _ref2[0];
97
+ return attributes.includes(key);
98
+ })) : rawFacets;
99
+
100
+ // Collect current refinements to exclude from suggestions
101
+ var currentRefinements = searchHelper ? (0, _utils.getRefinements)(results, searchHelper.state).map(function (refinement) {
102
+ return {
103
+ attribute: refinement.attribute,
104
+ value: refinement.name
105
+ };
106
+ }) : [];
107
+ var messageText = JSON.stringify({
108
+ query: results.query,
109
+ facets: facetsToSend,
110
+ hitsSample: results.hits.slice(0, hitsToSample),
111
+ currentRefinements: currentRefinements,
112
+ maxSuggestions: maxSuggestions
113
+ });
114
+ var payload = {
115
+ messages: [{
116
+ id: "sr-".concat(Date.now()),
117
+ createdAt: new Date().toISOString(),
118
+ role: 'user',
119
+ parts: [{
120
+ type: 'text',
121
+ text: messageText
122
+ }]
123
+ }]
124
+ };
125
+
126
+ // Apply custom body transformation if provided
127
+ var finalPayload = transport !== null && transport !== void 0 && transport.prepareSendMessagesRequest ? transport.prepareSendMessagesRequest(payload).body : payload;
128
+ fetch(endpoint, {
129
+ method: 'POST',
130
+ headers: _objectSpread(_objectSpread({}, headers), {}, {
131
+ 'Content-Type': 'application/json'
132
+ }),
133
+ body: JSON.stringify(finalPayload)
134
+ }).then(function (response) {
135
+ if (!response.ok) {
136
+ throw new Error("HTTP error ".concat(response.status));
137
+ }
138
+ return response.json();
139
+ }).then(function (data) {
140
+ var parsedSuggestions = JSON.parse(data.parts[1].text);
141
+ var validSuggestions = (Array.isArray(parsedSuggestions) ? parsedSuggestions : []).filter(function (suggestion) {
142
+ if (!(suggestion !== null && suggestion !== void 0 && suggestion.attribute) || !(suggestion !== null && suggestion !== void 0 && suggestion.value) || !(suggestion !== null && suggestion !== void 0 && suggestion.label)) {
143
+ return false;
144
+ }
145
+ // If attributes filter is specified, only allow suggestions for those attributes
146
+ if (attributes && !attributes.includes(suggestion.attribute)) {
147
+ return false;
148
+ }
149
+ return true;
150
+ }).slice(0, maxSuggestions);
151
+ suggestions = validSuggestions;
152
+ }).catch(function () {
153
+ suggestions = [];
154
+ }).finally(function () {
155
+ var elapsed = Date.now() - loadingStartTime;
156
+ var remainingDelay = Math.max(0, MIN_SKELETON_DURATION_MS - elapsed);
157
+ var finishLoading = function finishLoading() {
158
+ isLoading = false;
159
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(renderOptions)), {}, {
160
+ instantSearchInstance: renderOptions.instantSearchInstance
161
+ }), false);
162
+ };
163
+ if (remainingDelay > 0) {
164
+ setTimeout(finishLoading, remainingDelay);
165
+ } else {
166
+ finishLoading();
167
+ }
168
+ });
169
+ };
170
+ return {
171
+ $$type: 'ais.filterSuggestions',
172
+ init: function init(initOptions) {
173
+ var instantSearchInstance = initOptions.instantSearchInstance,
174
+ helper = initOptions.helper;
175
+ searchHelper = helper;
176
+ if (transport) {
177
+ // Use custom transport configuration
178
+ endpoint = transport.api;
179
+ headers = transport.headers || {};
180
+ } else {
181
+ // Use default Algolia agent endpoint
182
+ var _getAppIdAndApiKey = (0, _utils.getAppIdAndApiKey)(instantSearchInstance.client),
183
+ _getAppIdAndApiKey2 = _slicedToArray(_getAppIdAndApiKey, 2),
184
+ appId = _getAppIdAndApiKey2[0],
185
+ apiKey = _getAppIdAndApiKey2[1];
186
+ if (!appId || !apiKey) {
187
+ throw new Error(withUsage('Could not extract Algolia credentials from the search client.'));
188
+ }
189
+ endpoint = "https://".concat(appId, ".algolia.net/agent-studio/1/agents/").concat(agentId, "/completions?compatibilityMode=ai-sdk-5&stream=false");
190
+ headers = {
191
+ 'x-algolia-application-id': appId,
192
+ 'x-algolia-api-key': apiKey,
193
+ 'x-algolia-agent': (0, _utils.getAlgoliaAgent)(instantSearchInstance.client)
194
+ };
195
+ }
196
+ refine = function refine(attribute, value) {
197
+ var _helper$state$hierarc;
198
+ // Check if the attribute belongs to a hierarchical facet
199
+ // by finding a hierarchical facet that includes this attribute
200
+ var attr = ((_helper$state$hierarc = helper.state.hierarchicalFacets.find(function (facet) {
201
+ return facet.attributes.includes(attribute);
202
+ })) === null || _helper$state$hierarc === void 0 ? void 0 : _helper$state$hierarc.name) || attribute;
203
+ helper.toggleFacetRefinement(attr, value);
204
+ helper.search();
205
+ };
206
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(initOptions)), {}, {
207
+ instantSearchInstance: instantSearchInstance
208
+ }), true);
209
+ },
210
+ render: function render(renderOptions) {
211
+ var results = renderOptions.results,
212
+ instantSearchInstance = renderOptions.instantSearchInstance;
213
+
214
+ // Always store the latest render options
215
+ latestRenderOptions = renderOptions;
216
+ if (!results) {
217
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(renderOptions)), {}, {
218
+ instantSearchInstance: instantSearchInstance
219
+ }), false);
220
+ return;
221
+ }
222
+
223
+ // Debounce: only fetch if search state changed (query or refinements) and after delay
224
+ var stateSignature = getStateSignature(results);
225
+ if (stateSignature !== lastStateSignature) {
226
+ lastStateSignature = stateSignature;
227
+ clearTimeout(debounceTimer);
228
+ debounceTimer = setTimeout(function () {
229
+ var _latestRenderOptions;
230
+ // Use the latest render options when the timeout fires
231
+ if ((_latestRenderOptions = latestRenderOptions) !== null && _latestRenderOptions !== void 0 && _latestRenderOptions.results) {
232
+ fetchSuggestions(latestRenderOptions.results, latestRenderOptions);
233
+ }
234
+ }, debounceMs);
235
+ }
236
+ renderFn(_objectSpread(_objectSpread({}, _getWidgetRenderState(renderOptions)), {}, {
237
+ instantSearchInstance: instantSearchInstance
238
+ }), false);
239
+ },
240
+ dispose: function dispose() {
241
+ clearTimeout(debounceTimer);
242
+ unmountFn();
243
+ },
244
+ getRenderState: function getRenderState(renderState, renderOptions) {
245
+ return _objectSpread(_objectSpread({}, renderState), {}, {
246
+ filterSuggestions: this.getWidgetRenderState(renderOptions)
247
+ });
248
+ },
249
+ getWidgetRenderState: function getWidgetRenderState(renderOptions) {
250
+ return _getWidgetRenderState(renderOptions);
251
+ }
252
+ };
253
+ };
254
+ };
255
+ var _default = exports.default = connectFilterSuggestions;
@@ -46,6 +46,12 @@ Object.defineProperty(exports, "connectDynamicWidgets", {
46
46
  return _connectDynamicWidgets.default;
47
47
  }
48
48
  });
49
+ Object.defineProperty(exports, "connectFilterSuggestions", {
50
+ enumerable: true,
51
+ get: function get() {
52
+ return _connectFilterSuggestions.default;
53
+ }
54
+ });
49
55
  Object.defineProperty(exports, "connectFrequentlyBoughtTogether", {
50
56
  enumerable: true,
51
57
  get: function get() {
@@ -231,6 +237,7 @@ var _connectRelevantSort = _interopRequireDefault(require("./relevant-sort/conne
231
237
  var _connectFrequentlyBoughtTogether = _interopRequireDefault(require("./frequently-bought-together/connectFrequentlyBoughtTogether"));
232
238
  var _connectLookingSimilar = _interopRequireDefault(require("./looking-similar/connectLookingSimilar"));
233
239
  var _connectChat = _interopRequireDefault(require("./chat/connectChat"));
240
+ var _connectFilterSuggestions = _interopRequireDefault(require("./filter-suggestions/connectFilterSuggestions"));
234
241
  function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
235
242
  /** @deprecated answers is no longer supported */
236
243
  var EXPERIMENTAL_connectAnswers = exports.EXPERIMENTAL_connectAnswers = (0, _utils.deprecate)(_connectAnswers.default, 'answers is no longer supported');
@@ -41,6 +41,12 @@ Object.defineProperty(exports, "connectDynamicWidgets", {
41
41
  return _connectDynamicWidgets.default;
42
42
  }
43
43
  });
44
+ Object.defineProperty(exports, "connectFilterSuggestions", {
45
+ enumerable: true,
46
+ get: function get() {
47
+ return _connectFilterSuggestions.default;
48
+ }
49
+ });
44
50
  Object.defineProperty(exports, "connectFrequentlyBoughtTogether", {
45
51
  enumerable: true,
46
52
  get: function get() {
@@ -225,6 +231,7 @@ var _connectVoiceSearch = _interopRequireDefault(require("./voice-search/connect
225
231
  var _connectRelevantSort = _interopRequireDefault(require("./relevant-sort/connectRelevantSort"));
226
232
  var _connectFrequentlyBoughtTogether = _interopRequireDefault(require("./frequently-bought-together/connectFrequentlyBoughtTogether"));
227
233
  var _connectLookingSimilar = _interopRequireDefault(require("./looking-similar/connectLookingSimilar"));
234
+ var _connectFilterSuggestions = _interopRequireDefault(require("./filter-suggestions/connectFilterSuggestions"));
228
235
  function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
229
236
  /** @deprecated answers is no longer supported */
230
237
  var EXPERIMENTAL_connectAnswers = exports.EXPERIMENTAL_connectAnswers = (0, _utils.deprecate)(_connectAnswers.default, 'answers is no longer supported');
@@ -36,9 +36,9 @@ function _createClass(e, r, t) { return r && _defineProperties(e.prototype, r),
36
36
  function _defineProperty(e, r, t) { return (r = _toPropertyKey(r)) in e ? Object.defineProperty(e, r, { value: t, enumerable: !0, configurable: !0, writable: !0 }) : e[r] = t, e; }
37
37
  function _toPropertyKey(t) { var i = _toPrimitive(t, "string"); return "symbol" == _typeof(i) ? i : i + ""; }
38
38
  function _toPrimitive(t, r) { if ("object" != _typeof(t) || !t) return t; var e = t[Symbol.toPrimitive]; if (void 0 !== e) { var i = e.call(t, r || "default"); if ("object" != _typeof(i)) return i; throw new TypeError("@@toPrimitive must return a primitive value."); } return ("string" === r ? String : Number)(t); }
39
- var CACHE_KEY = exports.CACHE_KEY = 'instantsearch-chat-initial-messages-';
39
+ var CACHE_KEY = exports.CACHE_KEY = 'instantsearch-chat-initial-messages';
40
40
  function getDefaultInitialMessages(id) {
41
- var initialMessages = sessionStorage.getItem(CACHE_KEY + id);
41
+ var initialMessages = sessionStorage.getItem(CACHE_KEY + (id ? "-".concat(id) : ''));
42
42
  return initialMessages ? JSON.parse(initialMessages) : [];
43
43
  }
44
44
  var ChatState = exports.ChatState = /*#__PURE__*/function () {
@@ -108,7 +108,7 @@ var ChatState = exports.ChatState = /*#__PURE__*/function () {
108
108
  var saveMessagesInLocalStorage = function saveMessagesInLocalStorage() {
109
109
  if (_this.status === 'ready') {
110
110
  try {
111
- sessionStorage.setItem(CACHE_KEY + id, JSON.stringify(_this.messages));
111
+ sessionStorage.setItem(CACHE_KEY + (id ? "-".concat(id) : ''), JSON.stringify(_this.messages));
112
112
  } catch (e) {
113
113
  // Do nothing if sessionStorage is not available or full
114
114
  }
@@ -21,7 +21,10 @@ Object.defineProperty(exports, "ChatState", {
21
21
  return _chat.ChatState;
22
22
  }
23
23
  });
24
- exports.SearchIndexToolType = exports.RecommendToolType = void 0;
24
+ exports.SearchIndexToolType = exports.RecommendToolType = exports.PonderToolType = exports.MemorySearchToolType = exports.MemorizeToolType = void 0;
25
25
  var _chat = require("./chat");
26
26
  var SearchIndexToolType = exports.SearchIndexToolType = 'algolia_search_index';
27
- var RecommendToolType = exports.RecommendToolType = 'algolia_recommend';
27
+ var RecommendToolType = exports.RecommendToolType = 'algolia_recommend';
28
+ var MemorizeToolType = exports.MemorizeToolType = 'algolia_memorize';
29
+ var MemorySearchToolType = exports.MemorySearchToolType = 'algolia_memory_search';
30
+ var PonderToolType = exports.PonderToolType = 'algolia_ponder';
@@ -4,4 +4,4 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.default = void 0;
7
- var _default = exports.default = '4.86.1';
7
+ var _default = exports.default = '4.87.0';
@@ -178,7 +178,8 @@ function AutocompleteWrapper(_ref4) {
178
178
  query: searchboxQuery,
179
179
  showRecent: showRecent,
180
180
  indices: indices,
181
- indicesConfig: indicesConfig
181
+ indicesConfig: indicesConfig,
182
+ suggestionsIndexName: showSuggestions === null || showSuggestions === void 0 ? void 0 : showSuggestions.indexName
182
183
  }),
183
184
  storage = _useStorage.storage,
184
185
  storageHits = _useStorage.storageHits,
@@ -262,18 +263,24 @@ function AutocompleteWrapper(_ref4) {
262
263
  });
263
264
  }
264
265
  indices.forEach(function (_ref8, i) {
265
- var _indicesConfig$i$temp;
266
+ var _currentIndexConfig$t;
266
267
  var indexId = _ref8.indexId,
267
268
  indexName = _ref8.indexName,
268
269
  hits = _ref8.hits;
270
+ var currentIndexConfig = (0, _utils.find)(indicesConfig, function (config) {
271
+ return config.indexName === indexName;
272
+ });
273
+ if (!currentIndexConfig) {
274
+ return;
275
+ }
269
276
  if (!renderState.indexTemplateProps[i]) {
270
277
  renderState.indexTemplateProps[i] = (0, _templating.prepareTemplateProps)({
271
278
  defaultTemplates: {},
272
279
  templatesConfig: instantSearchInstance.templatesConfig,
273
- templates: indicesConfig[i].templates
280
+ templates: currentIndexConfig.templates
274
281
  });
275
282
  }
276
- var headerComponent = (_indicesConfig$i$temp = indicesConfig[i].templates) !== null && _indicesConfig$i$temp !== void 0 && _indicesConfig$i$temp.header ? function (_ref9) {
283
+ var headerComponent = (_currentIndexConfig$t = currentIndexConfig.templates) !== null && _currentIndexConfig$t !== void 0 && _currentIndexConfig$t.header ? function (_ref9) {
277
284
  var items = _ref9.items;
278
285
  return (0, _preact.h)(_Template.default, _extends({}, renderState.indexTemplateProps[i], {
279
286
  templateKey: "header",
@@ -313,7 +320,7 @@ function AutocompleteWrapper(_ref4) {
313
320
  });
314
321
  }),
315
322
  getItemProps: getItemProps,
316
- classNames: indicesConfig[i].cssClasses
323
+ classNames: currentIndexConfig.cssClasses
317
324
  });
318
325
  });
319
326
  return (0, _preact.h)(Autocomplete, _extends({}, getRootProps(), {
@@ -353,6 +360,7 @@ function EXPERIMENTAL_autocomplete(widgetParams) {
353
360
  onSelect = _ref1.onSelect,
354
361
  _ref1$templates = _ref1.templates,
355
362
  templates = _ref1$templates === void 0 ? {} : _ref1$templates,
363
+ transformItems = _ref1.transformItems,
356
364
  _ref1$cssClasses = _ref1.cssClasses,
357
365
  userCssClasses = _ref1$cssClasses === void 0 ? {} : _ref1$cssClasses,
358
366
  placeholder = _ref1.placeholder;
@@ -437,7 +445,8 @@ function EXPERIMENTAL_autocomplete(widgetParams) {
437
445
  indexId: indexName
438
446
  }).addWidgets([(0, _configure.default)(indexSearchParameters || {})]);
439
447
  })), [_objectSpread(_objectSpread({}, makeWidget({
440
- escapeHTML: escapeHTML
448
+ escapeHTML: escapeHTML,
449
+ transformItems: transformItems
441
450
  })), {}, {
442
451
  $$widgetType: 'ais.autocomplete'
443
452
  })]))];