instantsearch.js 4.75.2 → 4.75.3

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.
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Create UUID according to
3
+ * https://www.ietf.org/rfc/rfc4122.txt.
4
+ *
5
+ * @returns Generated UUID.
6
+ */
7
+ export declare function createUUID(): string;
@@ -0,0 +1,15 @@
1
+ /**
2
+ * Create UUID according to
3
+ * https://www.ietf.org/rfc/rfc4122.txt.
4
+ *
5
+ * @returns Generated UUID.
6
+ */
7
+ export function createUUID() {
8
+ return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function (c) {
9
+ /* eslint-disable no-bitwise */
10
+ var r = Math.random() * 16 | 0;
11
+ var v = c === 'x' ? r : r & 0x3 | 0x8;
12
+ /* eslint-enable */
13
+ return v.toString(16);
14
+ });
15
+ }
@@ -1,2 +1,2 @@
1
- declare const _default: "4.75.2";
1
+ declare const _default: "4.75.3";
2
2
  export default _default;
package/es/lib/version.js CHANGED
@@ -1 +1 @@
1
- export default '4.75.2';
1
+ export default '4.75.3';
@@ -16,6 +16,7 @@ function _arrayWithoutHoles(arr) { if (Array.isArray(arr)) return _arrayLikeToAr
16
16
  function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i]; return arr2; }
17
17
  import { getInsightsAnonymousUserTokenInternal } from "../helpers/index.js";
18
18
  import { warning, noop, getAppIdAndApiKey, find, safelyRunOnBrowser } from "../lib/utils/index.js";
19
+ import { createUUID } from "../lib/utils/uuid.js";
19
20
  var ALGOLIA_INSIGHTS_VERSION = '2.15.0';
20
21
  var ALGOLIA_INSIGHTS_SRC = "https://cdn.jsdelivr.net/npm/search-insights@".concat(ALGOLIA_INSIGHTS_VERSION, "/dist/search-insights.min.js");
21
22
  export function createInsightsMiddleware() {
@@ -27,6 +28,7 @@ export function createInsightsMiddleware() {
27
28
  $$internal = _props$$$internal === void 0 ? false : _props$$$internal,
28
29
  _props$$$automatic = props.$$automatic,
29
30
  $$automatic = _props$$$automatic === void 0 ? false : _props$$$automatic;
31
+ var currentTokenType;
30
32
  var potentialInsightsClient = _insightsClient;
31
33
  if (!_insightsClient && _insightsClient !== null) {
32
34
  safelyRunOnBrowser(function (_ref) {
@@ -73,6 +75,7 @@ export function createInsightsMiddleware() {
73
75
 
74
76
  // search-insights.js also throws an error so dev-only clarification is sufficient
75
77
  process.env.NODE_ENV === 'development' ? warning(Boolean(appId && apiKey), 'could not extract Algolia credentials from searchClient in insights middleware.') : void 0;
78
+ var queuedInitParams = undefined;
76
79
  var queuedUserToken = undefined;
77
80
  var queuedAuthenticatedUserToken = undefined;
78
81
  var userTokenBeforeInit = undefined;
@@ -89,7 +92,7 @@ export function createInsightsMiddleware() {
89
92
  // At this point, even though `search-insights` is not loaded yet,
90
93
  // we still want to read the token from the queue.
91
94
  // Otherwise, the first search call will be fired without the token.
92
- var _map = ['setUserToken', 'setAuthenticatedUserToken'].map(function (key) {
95
+ var _map = ['setUserToken', 'setAuthenticatedUserToken', 'init'].map(function (key) {
93
96
  var _ref3 = find(queue.slice().reverse(), function (_ref5) {
94
97
  var _ref6 = _slicedToArray(_ref5, 1),
95
98
  method = _ref6[0];
@@ -99,9 +102,10 @@ export function createInsightsMiddleware() {
99
102
  value = _ref4[1];
100
103
  return value;
101
104
  });
102
- var _map2 = _slicedToArray(_map, 2);
105
+ var _map2 = _slicedToArray(_map, 3);
103
106
  queuedUserToken = _map2[0];
104
107
  queuedAuthenticatedUserToken = _map2[1];
108
+ queuedInitParams = _map2[2];
105
109
  }
106
110
 
107
111
  // If user called `aa('setUserToken')` or `aa('setAuthenticatedUserToken')`
@@ -152,6 +156,23 @@ export function createInsightsMiddleware() {
152
156
  started: function started() {
153
157
  insightsClient('addAlgoliaAgent', 'insights-middleware');
154
158
  helper = instantSearchInstance.mainHelper;
159
+ var queueAtStart = insightsClient.queue;
160
+ if (Array.isArray(queueAtStart)) {
161
+ var _map3 = ['setUserToken', 'setAuthenticatedUserToken', 'init'].map(function (key) {
162
+ var _ref7 = find(queueAtStart.slice().reverse(), function (_ref9) {
163
+ var _ref10 = _slicedToArray(_ref9, 1),
164
+ method = _ref10[0];
165
+ return method === key;
166
+ }) || [],
167
+ _ref8 = _slicedToArray(_ref7, 2),
168
+ value = _ref8[1];
169
+ return value;
170
+ });
171
+ var _map4 = _slicedToArray(_map3, 3);
172
+ queuedUserToken = _map4[0];
173
+ queuedAuthenticatedUserToken = _map4[1];
174
+ queuedInitParams = _map4[2];
175
+ }
155
176
  initialParameters = {
156
177
  userToken: helper.state.userToken,
157
178
  clickAnalytics: helper.state.clickAnalytics
@@ -167,8 +188,9 @@ export function createInsightsMiddleware() {
167
188
  if (!$$internal) {
168
189
  instantSearchInstance.scheduleSearch();
169
190
  }
170
- var setUserTokenToSearch = function setUserTokenToSearch(userToken) {
171
- var immediate = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false;
191
+ var setUserTokenToSearch = function setUserTokenToSearch(userToken, tokenType) {
192
+ var immediate = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;
193
+ var unsetAuthenticatedUserToken = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : false;
172
194
  var normalizedUserToken = normalizeUserToken(userToken);
173
195
  if (!normalizedUserToken) {
174
196
  return;
@@ -181,6 +203,13 @@ export function createInsightsMiddleware() {
181
203
  if (existingToken && existingToken !== userToken) {
182
204
  instantSearchInstance.scheduleSearch();
183
205
  }
206
+ currentTokenType = tokenType;
207
+ }
208
+
209
+ // the authenticated user token cannot be overridden by a user or anonymous token
210
+ // for instant search query requests
211
+ if (currentTokenType && currentTokenType === 'authenticated' && tokenType === 'default' && !unsetAuthenticatedUserToken) {
212
+ return;
184
213
  }
185
214
 
186
215
  // Delay the token application to the next render cycle
@@ -190,14 +219,8 @@ export function createInsightsMiddleware() {
190
219
  applyToken();
191
220
  }
192
221
  };
193
- var anonymousUserToken = getInsightsAnonymousUserTokenInternal();
194
- if (anonymousUserToken) {
195
- // When `aa('init', { ... })` is called, it creates an anonymous user token in cookie.
196
- // We can set it as userToken.
197
- setUserTokenToSearch(anonymousUserToken, true);
198
- }
199
222
  function setUserToken(token, userToken, authenticatedUserToken) {
200
- setUserTokenToSearch(token, true);
223
+ setUserTokenToSearch(token, authenticatedUserToken ? 'authenticated' : 'default', true);
201
224
  if (userToken) {
202
225
  insightsClient('setUserToken', userToken);
203
226
  }
@@ -205,19 +228,66 @@ export function createInsightsMiddleware() {
205
228
  insightsClient('setAuthenticatedUserToken', authenticatedUserToken);
206
229
  }
207
230
  }
231
+ var anonymousUserToken = undefined;
232
+ var anonymousTokenFromInsights = getInsightsAnonymousUserTokenInternal();
233
+ if (anonymousTokenFromInsights) {
234
+ // When `aa('init', { ... })` is called, it creates an anonymous user token in cookie.
235
+ // We can set it as userToken on instantsearch and insights. If it's not set as an insights
236
+ // userToken before a sendEvent, insights automatically generates a new anonymous token,
237
+ // causing a state change and an unnecessary query on instantsearch.
238
+ anonymousUserToken = anonymousTokenFromInsights;
239
+ } else {
240
+ var token = "anonymous-".concat(createUUID());
241
+ anonymousUserToken = token;
242
+ }
243
+ var authenticatedUserTokenFromInit;
244
+ var userTokenFromInit;
245
+
246
+ // With SSR, the token could be be set on the state. We make sure
247
+ // that insights is in sync with that token since, there is no
248
+ // insights lib on the server.
249
+ var tokenFromSearchParameters = initialParameters.userToken;
250
+
251
+ // When the first query is sent, the token is possibly not yet be set by
252
+ // the insights onChange callbacks (if insights isn't yet loaded).
253
+ // It is explicitly being set here so that the first query has the
254
+ // initial tokens set and ensure a second query isn't automatically
255
+ // made when the onChange callback actually changes the state.
256
+ if (insightsInitParams) {
257
+ if (insightsInitParams.authenticatedUserToken) {
258
+ authenticatedUserTokenFromInit = insightsInitParams.authenticatedUserToken;
259
+ } else if (insightsInitParams.userToken) {
260
+ userTokenFromInit = insightsInitParams.userToken;
261
+ }
262
+ }
208
263
 
209
264
  // We consider the `userToken` or `authenticatedUserToken` before an
210
- // `init` call of higher importance than one from the queue.
265
+ // `init` call of higher importance than one from the queue and ones set
266
+ // from the init props to be higher than that.
267
+ var tokenFromInit = authenticatedUserTokenFromInit || userTokenFromInit;
211
268
  var tokenBeforeInit = authenticatedUserTokenBeforeInit || userTokenBeforeInit;
212
- var queuedToken = queuedAuthenticatedUserToken || queuedUserToken;
213
- if (tokenBeforeInit) {
269
+ var tokenFromQueue = queuedAuthenticatedUserToken || queuedUserToken;
270
+ if (tokenFromInit) {
271
+ setUserToken(tokenFromInit, userTokenFromInit, authenticatedUserTokenFromInit);
272
+ } else if (tokenFromSearchParameters) {
273
+ setUserToken(tokenFromSearchParameters, tokenFromSearchParameters, undefined);
274
+ } else if (tokenBeforeInit) {
214
275
  setUserToken(tokenBeforeInit, userTokenBeforeInit, authenticatedUserTokenBeforeInit);
215
- } else if (queuedToken) {
216
- setUserToken(queuedToken, queuedUserToken, queuedAuthenticatedUserToken);
276
+ } else if (tokenFromQueue) {
277
+ setUserToken(tokenFromQueue, queuedUserToken, queuedAuthenticatedUserToken);
278
+ } else if (anonymousUserToken) {
279
+ var _queuedInitParams;
280
+ setUserToken(anonymousUserToken, anonymousUserToken, undefined);
281
+ if (insightsInitParams !== null && insightsInitParams !== void 0 && insightsInitParams.useCookie || (_queuedInitParams = queuedInitParams) !== null && _queuedInitParams !== void 0 && _queuedInitParams.useCookie) {
282
+ var _queuedInitParams2;
283
+ saveTokenAsCookie(anonymousUserToken, (insightsInitParams === null || insightsInitParams === void 0 ? void 0 : insightsInitParams.cookieDuration) || ((_queuedInitParams2 = queuedInitParams) === null || _queuedInitParams2 === void 0 ? void 0 : _queuedInitParams2.cookieDuration));
284
+ }
217
285
  }
218
286
 
219
287
  // This updates userToken which is set explicitly by `aa('setUserToken', userToken)`
220
- insightsClient('onUserTokenChange', setUserTokenToSearch, {
288
+ insightsClient('onUserTokenChange', function (token) {
289
+ return setUserTokenToSearch(token, 'default', true);
290
+ }, {
221
291
  immediate: true
222
292
  });
223
293
 
@@ -226,10 +296,10 @@ export function createInsightsMiddleware() {
226
296
  // If we're unsetting the `authenticatedUserToken`, we revert to the `userToken`
227
297
  if (!authenticatedUserToken) {
228
298
  insightsClient('getUserToken', null, function (_, userToken) {
229
- setUserTokenToSearch(userToken);
299
+ setUserTokenToSearch(userToken, 'default', true, true);
230
300
  });
231
301
  }
232
- setUserTokenToSearch(authenticatedUserToken);
302
+ setUserTokenToSearch(authenticatedUserToken, 'authenticated', true);
233
303
  }, {
234
304
  immediate: true
235
305
  });
@@ -278,6 +348,13 @@ export function createInsightsMiddleware() {
278
348
  };
279
349
  };
280
350
  }
351
+ function saveTokenAsCookie(token, cookieDuration) {
352
+ var MONTH = 30 * 24 * 60 * 60 * 1000;
353
+ var d = new Date();
354
+ d.setTime(d.getTime() + (cookieDuration || MONTH * 6));
355
+ var expires = "expires=".concat(d.toUTCString());
356
+ document.cookie = "_ALGOLIA=".concat(token, ";").concat(expires, ";path=/");
357
+ }
281
358
 
282
359
  /**
283
360
  * Determines if a given insights `client` supports the optional call to `init`
@@ -32,7 +32,7 @@ type QueueItemMap = {
32
32
  ...args: InsightsMethodMap[MethodName]
33
33
  ];
34
34
  };
35
- type QueueItem = QueueItemMap[keyof QueueItemMap];
35
+ export type QueueItem = QueueItemMap[keyof QueueItemMap];
36
36
  export type InsightsClient = _InsightsClient & {
37
37
  queue?: QueueItem[];
38
38
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "instantsearch.js",
3
- "version": "4.75.2",
3
+ "version": "4.75.3",
4
4
  "description": "InstantSearch.js is a JavaScript library for building performant and instant search experiences with Algolia.",
5
5
  "homepage": "https://www.algolia.com/doc/guides/building-search-ui/what-is-instantsearch/js/",
6
6
  "types": "es/index.d.ts",
@@ -56,9 +56,9 @@
56
56
  "watch:es": "yarn --silent build:es:base --watch"
57
57
  },
58
58
  "devDependencies": {
59
- "@instantsearch/mocks": "1.60.0",
60
- "@instantsearch/tests": "1.60.0",
61
- "@instantsearch/testutils": "1.49.0",
59
+ "@instantsearch/mocks": "1.61.0",
60
+ "@instantsearch/tests": "1.61.0",
61
+ "@instantsearch/testutils": "1.50.0",
62
62
  "@storybook/html": "5.3.9",
63
63
  "@types/scriptjs": "0.0.2",
64
64
  "algoliasearch": "5.1.1",
@@ -66,5 +66,5 @@
66
66
  "scriptjs": "2.5.9",
67
67
  "webpack": "4.47.0"
68
68
  },
69
- "gitHead": "c5f9a44d3f97363b1a0486a18696edbeafc193d5"
69
+ "gitHead": "de88914192c35bf88a6ccf1019ea640d4e8bfde2"
70
70
  }