@burdenoff/website-sdk 2026.1101.4 → 2026.1102.2

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.
@@ -1,6 +1,6 @@
1
1
  'use strict';
2
2
 
3
- var chunk23H4JUL4_js = require('../chunk-23H4JUL4.js');
3
+ var chunkFQH3AJN3_js = require('../chunk-FQH3AJN3.js');
4
4
  var chunkO4GS3XPZ_js = require('../chunk-O4GS3XPZ.js');
5
5
  var chunkC6OJIHNO_js = require('../chunk-C6OJIHNO.js');
6
6
  require('../chunk-ZSTFX7FV.js');
@@ -35,6 +35,20 @@ var AVAILABILITY_REASONS = /* @__PURE__ */ new Map([
35
35
  ["busy", "busy"],
36
36
  ["limits", "limits"]
37
37
  ]);
38
+ var BOT_CHECK_MODES = /* @__PURE__ */ new Set([
39
+ "off",
40
+ "turnstile"
41
+ ]);
42
+ function readBotCheck(value) {
43
+ if (value === void 0) return "turnstile";
44
+ if (!isRecord(value)) return null;
45
+ const keys = Object.keys(value);
46
+ const { mode } = value;
47
+ if (keys.length !== 1 || keys[0] !== "mode" || typeof mode !== "string" || !BOT_CHECK_MODES.has(mode)) {
48
+ return null;
49
+ }
50
+ return mode === "off" ? "off" : "turnstile";
51
+ }
38
52
  function readAvailability(status, body) {
39
53
  if (status !== 200 || !isRecord(body)) return INERT;
40
54
  const { available, reason } = body;
@@ -43,10 +57,14 @@ function readAvailability(status, body) {
43
57
  }
44
58
  if (reason === "ok") {
45
59
  const { consentVersion, maxSessionSeconds } = body;
46
- if (available !== true || typeof consentVersion !== "string" || !chunk23H4JUL4_js.isAvatarVersion(consentVersion) || typeof maxSessionSeconds !== "number" || !Number.isInteger(maxSessionSeconds) || maxSessionSeconds < 1) {
60
+ const botCheck = readBotCheck(body.botCheck);
61
+ if (available !== true || typeof consentVersion !== "string" || !chunkFQH3AJN3_js.isAvatarVersion(consentVersion) || typeof maxSessionSeconds !== "number" || !Number.isInteger(maxSessionSeconds) || maxSessionSeconds < 1 || botCheck === null) {
47
62
  return INERT;
48
63
  }
49
- return { kind: "available", offer: { consentVersion, maxSessionSeconds } };
64
+ return {
65
+ kind: "available",
66
+ offer: { consentVersion, maxSessionSeconds, botCheck }
67
+ };
50
68
  }
51
69
  const meaning = available ? void 0 : AVAILABILITY_REASONS.get(reason);
52
70
  return meaning === void 0 || meaning === "inert" ? INERT : { kind: "refused", reason: meaning };
@@ -128,7 +146,7 @@ function deadline(timeoutMs, outer) {
128
146
  };
129
147
  }
130
148
  async function requestAvailability(target) {
131
- if (!chunk23H4JUL4_js.isAvatarSite(target.site) || !LOCALE.test(target.locale)) return INERT;
149
+ if (!chunkFQH3AJN3_js.isAvatarSite(target.site) || !LOCALE.test(target.locale)) return INERT;
132
150
  const query = new URLSearchParams({
133
151
  site: target.site,
134
152
  locale: target.locale
@@ -169,7 +187,7 @@ async function requestCreate(target) {
169
187
  ...target.headers,
170
188
  "Content-Type": "application/json",
171
189
  "Idempotency-Key": target.idempotencyKey,
172
- "x-web-avatar-bot-token": target.botToken
190
+ ...target.botToken === void 0 ? {} : { "x-web-avatar-bot-token": target.botToken }
173
191
  },
174
192
  body: payload,
175
193
  signal: timer.signal
@@ -244,7 +262,7 @@ var EN = {
244
262
  needsAnswer: "Choose a suggested question in Chat first.",
245
263
  needsAnswerDetail: "The avatar can read only the first answer aloud.",
246
264
  startNewChat: "Start a new chat to use the avatar.",
247
- startNewChatDetail: "The avatar reads aloud only the first answer in a chat, and only to a suggested question. Start a new chat and choose a suggested question.",
265
+ startNewChatDetail: "The avatar reads aloud only the first answer in a chat, to a suggested question, within fifteen minutes. Start a new chat and choose a suggested question.",
248
266
  start: "Start live avatar",
249
267
  notNow: "Not now",
250
268
  opensInNewTab: "(opens in a new tab)",
@@ -268,7 +286,7 @@ var EN = {
268
286
  region: "The live avatar isn't offered in your region yet.",
269
287
  locale: "The live avatar isn't offered in this language yet.",
270
288
  paused: "The live avatar is paused right now.",
271
- notEligible: "The avatar can read answers to the suggested questions.",
289
+ notEligible: "The avatar reads the first answer to a suggested question, within fifteen minutes. Start a new chat and choose a suggested question.",
272
290
  answerClaimed: "The avatar has already read this answer."
273
291
  };
274
292
  var ZH = {
@@ -277,7 +295,7 @@ var ZH = {
277
295
  needsAnswerDetail: "\u865A\u62DF\u5F62\u8C61\u53EA\u80FD\u6717\u8BFB\u7B2C\u4E00\u4E2A\u56DE\u7B54\u3002",
278
296
  // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
279
297
  startNewChat: "\u8BF7\u5F00\u59CB\u65B0\u7684\u804A\u5929\uFF0C\u518D\u4F7F\u7528\u865A\u62DF\u5F62\u8C61\u3002",
280
- startNewChatDetail: "\u865A\u62DF\u5F62\u8C61\u53EA\u6717\u8BFB\u4E00\u6B21\u804A\u5929\u4E2D\u7684\u7B2C\u4E00\u4E2A\u56DE\u7B54\uFF0C\u4E14\u4EC5\u9650\u56DE\u7B54\u63A8\u8350\u95EE\u9898\u3002\u8BF7\u5F00\u59CB\u65B0\u7684\u804A\u5929\uFF0C\u5E76\u9009\u62E9\u4E00\u4E2A\u63A8\u8350\u95EE\u9898\u3002",
298
+ startNewChatDetail: "\u865A\u62DF\u5F62\u8C61\u53EA\u6717\u8BFB\u4E00\u6B21\u804A\u5929\u4E2D\u7684\u7B2C\u4E00\u4E2A\u56DE\u7B54\uFF0C\u4E14\u4EC5\u9650\u63A8\u8350\u95EE\u9898\u7684\u56DE\u7B54\u3001\u5728\u5341\u4E94\u5206\u949F\u5185\u3002\u8BF7\u5F00\u59CB\u65B0\u7684\u804A\u5929\uFF0C\u5E76\u9009\u62E9\u4E00\u4E2A\u63A8\u8350\u95EE\u9898\u3002",
281
299
  start: "\u542F\u52A8\u5B9E\u65F6\u865A\u62DF\u5F62\u8C61",
282
300
  notNow: "\u6682\u4E0D",
283
301
  opensInNewTab: "\uFF08\u5728\u65B0\u6807\u7B7E\u9875\u4E2D\u6253\u5F00\uFF09",
@@ -301,7 +319,8 @@ var ZH = {
301
319
  region: "\u60A8\u6240\u5728\u7684\u5730\u533A\u6682\u4E0D\u63D0\u4F9B\u5B9E\u65F6\u865A\u62DF\u5F62\u8C61\u3002",
302
320
  locale: "\u6B64\u8BED\u8A00\u6682\u4E0D\u63D0\u4F9B\u5B9E\u65F6\u865A\u62DF\u5F62\u8C61\u3002",
303
321
  paused: "\u5B9E\u65F6\u865A\u62DF\u5F62\u8C61\u76EE\u524D\u5DF2\u6682\u505C\u3002",
304
- notEligible: "\u865A\u62DF\u5F62\u8C61\u53EF\u4EE5\u6717\u8BFB\u63A8\u8350\u95EE\u9898\u7684\u56DE\u7B54\u3002",
322
+ // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
323
+ notEligible: "\u865A\u62DF\u5F62\u8C61\u53EA\u6717\u8BFB\u63A8\u8350\u95EE\u9898\u7684\u7B2C\u4E00\u4E2A\u56DE\u7B54\uFF0C\u4E14\u987B\u5728\u5341\u4E94\u5206\u949F\u5185\u3002\u8BF7\u5F00\u59CB\u65B0\u7684\u804A\u5929\uFF0C\u5E76\u9009\u62E9\u4E00\u4E2A\u63A8\u8350\u95EE\u9898\u3002",
305
324
  answerClaimed: "\u865A\u62DF\u5F62\u8C61\u5DF2\u7ECF\u6717\u8BFB\u8FC7\u8FD9\u4E2A\u56DE\u7B54\u3002"
306
325
  };
307
326
  var HI = {
@@ -310,7 +329,7 @@ var HI = {
310
329
  needsAnswerDetail: "\u0905\u0935\u0924\u093E\u0930 \u0915\u0947\u0935\u0932 \u092A\u0939\u0932\u093E \u0909\u0924\u094D\u0924\u0930 \u091C\u093C\u094B\u0930 \u0938\u0947 \u092A\u0922\u093C \u0938\u0915\u0924\u093E \u0939\u0948\u0964",
311
330
  // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
312
331
  startNewChat: "\u0905\u0935\u0924\u093E\u0930 \u0915\u093E \u0909\u092A\u092F\u094B\u0917 \u0915\u0930\u0928\u0947 \u0915\u0947 \u0932\u093F\u090F \u0928\u0908 \u091A\u0948\u091F \u0936\u0941\u0930\u0942 \u0915\u0930\u0947\u0902\u0964",
313
- startNewChatDetail: "\u0905\u0935\u0924\u093E\u0930 \u0915\u093F\u0938\u0940 \u091A\u0948\u091F \u0915\u093E \u0915\u0947\u0935\u0932 \u092A\u0939\u0932\u093E \u0909\u0924\u094D\u0924\u0930 \u091C\u093C\u094B\u0930 \u0938\u0947 \u092A\u0922\u093C\u0924\u093E \u0939\u0948, \u0914\u0930 \u0935\u0939 \u092D\u0940 \u0938\u0941\u091D\u093E\u090F \u0917\u090F \u092A\u094D\u0930\u0936\u094D\u0928 \u0915\u093E \u0939\u0940\u0964 \u0928\u0908 \u091A\u0948\u091F \u0936\u0941\u0930\u0942 \u0915\u0930\u0947\u0902 \u0914\u0930 \u0915\u094B\u0908 \u0938\u0941\u091D\u093E\u092F\u093E \u0917\u092F\u093E \u092A\u094D\u0930\u0936\u094D\u0928 \u091A\u0941\u0928\u0947\u0902\u0964",
332
+ startNewChatDetail: "\u0905\u0935\u0924\u093E\u0930 \u0915\u093F\u0938\u0940 \u091A\u0948\u091F \u0915\u093E \u0915\u0947\u0935\u0932 \u092A\u0939\u0932\u093E \u0909\u0924\u094D\u0924\u0930 \u091C\u093C\u094B\u0930 \u0938\u0947 \u092A\u0922\u093C\u0924\u093E \u0939\u0948, \u0935\u0939 \u092D\u0940 \u0938\u0941\u091D\u093E\u090F \u0917\u090F \u092A\u094D\u0930\u0936\u094D\u0928 \u0915\u093E \u0914\u0930 \u092A\u0902\u0926\u094D\u0930\u0939 \u092E\u093F\u0928\u091F \u0915\u0947 \u092D\u0940\u0924\u0930\u0964 \u0928\u0908 \u091A\u0948\u091F \u0936\u0941\u0930\u0942 \u0915\u0930\u0947\u0902 \u0914\u0930 \u0915\u094B\u0908 \u0938\u0941\u091D\u093E\u092F\u093E \u0917\u092F\u093E \u092A\u094D\u0930\u0936\u094D\u0928 \u091A\u0941\u0928\u0947\u0902\u0964",
314
333
  start: "\u0932\u093E\u0907\u0935 \u0905\u0935\u0924\u093E\u0930 \u0936\u0941\u0930\u0942 \u0915\u0930\u0947\u0902",
315
334
  notNow: "\u0905\u092D\u0940 \u0928\u0939\u0940\u0902",
316
335
  opensInNewTab: "(\u0928\u090F \u091F\u0948\u092C \u092E\u0947\u0902 \u0916\u0941\u0932\u0924\u093E \u0939\u0948)",
@@ -334,7 +353,8 @@ var HI = {
334
353
  region: "\u0906\u092A\u0915\u0947 \u0915\u094D\u0937\u0947\u0924\u094D\u0930 \u092E\u0947\u0902 \u0932\u093E\u0907\u0935 \u0905\u0935\u0924\u093E\u0930 \u0905\u092D\u0940 \u0909\u092A\u0932\u092C\u094D\u0927 \u0928\u0939\u0940\u0902 \u0939\u0948\u0964",
335
354
  locale: "\u0907\u0938 \u092D\u093E\u0937\u093E \u092E\u0947\u0902 \u0932\u093E\u0907\u0935 \u0905\u0935\u0924\u093E\u0930 \u0905\u092D\u0940 \u0909\u092A\u0932\u092C\u094D\u0927 \u0928\u0939\u0940\u0902 \u0939\u0948\u0964",
336
355
  paused: "\u0932\u093E\u0907\u0935 \u0905\u0935\u0924\u093E\u0930 \u0905\u092D\u0940 \u0930\u0941\u0915\u093E \u0939\u0941\u0906 \u0939\u0948\u0964",
337
- notEligible: "\u0905\u0935\u0924\u093E\u0930 \u0938\u0941\u091D\u093E\u090F \u0917\u090F \u092A\u094D\u0930\u0936\u094D\u0928\u094B\u0902 \u0915\u0947 \u0909\u0924\u094D\u0924\u0930 \u092A\u0922\u093C \u0938\u0915\u0924\u093E \u0939\u0948\u0964",
356
+ // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
357
+ notEligible: "\u0905\u0935\u0924\u093E\u0930 \u0938\u0941\u091D\u093E\u090F \u0917\u090F \u092A\u094D\u0930\u0936\u094D\u0928 \u0915\u093E \u092A\u0939\u0932\u093E \u0909\u0924\u094D\u0924\u0930 \u0939\u0940 \u092A\u0922\u093C\u0924\u093E \u0939\u0948, \u092A\u0902\u0926\u094D\u0930\u0939 \u092E\u093F\u0928\u091F \u0915\u0947 \u092D\u0940\u0924\u0930\u0964 \u0928\u0908 \u091A\u0948\u091F \u0936\u0941\u0930\u0942 \u0915\u0930\u0947\u0902 \u0914\u0930 \u0915\u094B\u0908 \u0938\u0941\u091D\u093E\u092F\u093E \u0917\u092F\u093E \u092A\u094D\u0930\u0936\u094D\u0928 \u091A\u0941\u0928\u0947\u0902\u0964",
338
358
  answerClaimed: "\u0905\u0935\u0924\u093E\u0930 \u092F\u0939 \u0909\u0924\u094D\u0924\u0930 \u092A\u0939\u0932\u0947 \u0939\u0940 \u092A\u0922\u093C \u091A\u0941\u0915\u093E \u0939\u0948\u0964"
339
359
  };
340
360
  var ES = {
@@ -343,7 +363,7 @@ var ES = {
343
363
  needsAnswerDetail: "El avatar solo puede leer en voz alta la primera respuesta.",
344
364
  // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
345
365
  startNewChat: "Inicia un chat nuevo para usar el avatar.",
346
- startNewChatDetail: "El avatar solo lee en voz alta la primera respuesta de un chat, y solo si es la de una pregunta sugerida. Inicia un chat nuevo y elige una pregunta sugerida.",
366
+ startNewChatDetail: "El avatar solo lee en voz alta la primera respuesta de un chat, si es la de una pregunta sugerida y en un plazo de quince minutos. Inicia un chat nuevo y elige una pregunta sugerida.",
347
367
  start: "Iniciar el avatar en vivo",
348
368
  notNow: "Ahora no",
349
369
  opensInNewTab: "(se abre en una pesta\xF1a nueva)",
@@ -367,7 +387,8 @@ var ES = {
367
387
  region: "El avatar en vivo a\xFAn no est\xE1 disponible en tu regi\xF3n.",
368
388
  locale: "El avatar en vivo a\xFAn no est\xE1 disponible en este idioma.",
369
389
  paused: "El avatar en vivo est\xE1 en pausa en este momento.",
370
- notEligible: "El avatar puede leer las respuestas a las preguntas sugeridas.",
390
+ // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
391
+ notEligible: "El avatar lee la primera respuesta a una pregunta sugerida, en un plazo de quince minutos. Inicia un chat nuevo y elige una pregunta sugerida.",
371
392
  answerClaimed: "El avatar ya ha le\xEDdo esta respuesta."
372
393
  };
373
394
  var AR = {
@@ -376,7 +397,7 @@ var AR = {
376
397
  needsAnswerDetail: "\u064A\u0645\u0643\u0646 \u0644\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0642\u0631\u0627\u0621\u0629 \u0627\u0644\u0625\u062C\u0627\u0628\u0629 \u0627\u0644\u0623\u0648\u0644\u0649 \u0641\u0642\u0637 \u0628\u0635\u0648\u062A \u0639\u0627\u0644\u064D.",
377
398
  // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
378
399
  startNewChat: "\u0627\u0628\u062F\u0623 \u062F\u0631\u062F\u0634\u0629 \u062C\u062F\u064A\u062F\u0629 \u0644\u0627\u0633\u062A\u062E\u062F\u0627\u0645 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631.",
379
- startNewChatDetail: "\u064A\u0642\u0631\u0623 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0628\u0635\u0648\u062A \u0639\u0627\u0644\u064D \u0627\u0644\u0625\u062C\u0627\u0628\u0629 \u0627\u0644\u0623\u0648\u0644\u0649 \u0641\u064A \u0627\u0644\u062F\u0631\u062F\u0634\u0629 \u0641\u0642\u0637\u060C \u0648\u0641\u0642\u0637 \u0625\u0630\u0627 \u0643\u0627\u0646\u062A \u0625\u062C\u0627\u0628\u0629 \u0639\u0646 \u0633\u0624\u0627\u0644 \u0645\u0642\u062A\u0631\u062D. \u0627\u0628\u062F\u0623 \u062F\u0631\u062F\u0634\u0629 \u062C\u062F\u064A\u062F\u0629 \u0648\u0627\u062E\u062A\u0631 \u0633\u0624\u0627\u0644\u064B\u0627 \u0645\u0642\u062A\u0631\u062D\u064B\u0627.",
400
+ startNewChatDetail: "\u064A\u0642\u0631\u0623 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0628\u0635\u0648\u062A \u0639\u0627\u0644\u064D \u0627\u0644\u0625\u062C\u0627\u0628\u0629 \u0627\u0644\u0623\u0648\u0644\u0649 \u0641\u064A \u0627\u0644\u062F\u0631\u062F\u0634\u0629 \u0641\u0642\u0637\u060C \u0625\u0630\u0627 \u0643\u0627\u0646\u062A \u0625\u062C\u0627\u0628\u0629 \u0639\u0646 \u0633\u0624\u0627\u0644 \u0645\u0642\u062A\u0631\u062D \u0648\u062E\u0644\u0627\u0644 \u062E\u0645\u0633 \u0639\u0634\u0631\u0629 \u062F\u0642\u064A\u0642\u0629. \u0627\u0628\u062F\u0623 \u062F\u0631\u062F\u0634\u0629 \u062C\u062F\u064A\u062F\u0629 \u0648\u0627\u062E\u062A\u0631 \u0633\u0624\u0627\u0644\u064B\u0627 \u0645\u0642\u062A\u0631\u062D\u064B\u0627.",
380
401
  start: "\u0628\u062F\u0621 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0627\u0644\u0645\u0628\u0627\u0634\u0631",
381
402
  notNow: "\u0644\u064A\u0633 \u0627\u0644\u0622\u0646",
382
403
  opensInNewTab: "(\u064A\u064F\u0641\u062A\u062D \u0641\u064A \u0639\u0644\u0627\u0645\u0629 \u062A\u0628\u0648\u064A\u0628 \u062C\u062F\u064A\u062F\u0629)",
@@ -400,7 +421,8 @@ var AR = {
400
421
  region: "\u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0627\u0644\u0645\u0628\u0627\u0634\u0631 \u063A\u064A\u0631 \u0645\u062A\u0627\u062D \u0641\u064A \u0645\u0646\u0637\u0642\u062A\u0643 \u0628\u0639\u062F.",
401
422
  locale: "\u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0627\u0644\u0645\u0628\u0627\u0634\u0631 \u063A\u064A\u0631 \u0645\u062A\u0627\u062D \u0628\u0647\u0630\u0647 \u0627\u0644\u0644\u063A\u0629 \u0628\u0639\u062F.",
402
423
  paused: "\u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0627\u0644\u0645\u0628\u0627\u0634\u0631 \u0645\u062A\u0648\u0642\u0641 \u0645\u0624\u0642\u062A\u064B\u0627 \u0627\u0644\u0622\u0646.",
403
- notEligible: "\u064A\u0645\u0643\u0646 \u0644\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0642\u0631\u0627\u0621\u0629 \u0625\u062C\u0627\u0628\u0627\u062A \u0627\u0644\u0623\u0633\u0626\u0644\u0629 \u0627\u0644\u0645\u0642\u062A\u0631\u062D\u0629.",
424
+ // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
425
+ notEligible: "\u064A\u0642\u0631\u0623 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0627\u0644\u0625\u062C\u0627\u0628\u0629 \u0627\u0644\u0623\u0648\u0644\u0649 \u0639\u0646 \u0633\u0624\u0627\u0644 \u0645\u0642\u062A\u0631\u062D\u060C \u062E\u0644\u0627\u0644 \u062E\u0645\u0633 \u0639\u0634\u0631\u0629 \u062F\u0642\u064A\u0642\u0629. \u0627\u0628\u062F\u0623 \u062F\u0631\u062F\u0634\u0629 \u062C\u062F\u064A\u062F\u0629 \u0648\u0627\u062E\u062A\u0631 \u0633\u0624\u0627\u0644\u064B\u0627 \u0645\u0642\u062A\u0631\u062D\u064B\u0627.",
404
426
  answerClaimed: "\u0642\u0631\u0623 \u0627\u0644\u0623\u0641\u0627\u062A\u0627\u0631 \u0647\u0630\u0647 \u0627\u0644\u0625\u062C\u0627\u0628\u0629 \u0645\u0646 \u0642\u0628\u0644."
405
427
  };
406
428
  var TA = {
@@ -409,7 +431,7 @@ var TA = {
409
431
  needsAnswerDetail: "\u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0BAE\u0BC1\u0BA4\u0BB2\u0BCD \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7 \u0B89\u0BB0\u0B95\u0BCD\u0B95\u0BAA\u0BCD \u0BAA\u0B9F\u0BBF\u0B95\u0BCD\u0B95 \u0BAE\u0BC1\u0B9F\u0BBF\u0BAF\u0BC1\u0BAE\u0BCD.",
410
432
  // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
411
433
  startNewChat: "\u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BC8\u0BAA\u0BCD \u0BAA\u0BAF\u0BA9\u0BCD\u0BAA\u0B9F\u0BC1\u0BA4\u0BCD\u0BA4 \u0BAA\u0BC1\u0BA4\u0BBF\u0BAF \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BCA\u0B9F\u0B99\u0BCD\u0B95\u0BB5\u0BC1\u0BAE\u0BCD.",
412
- startNewChatDetail: "\u0B93\u0BB0\u0BCD \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BBF\u0BA9\u0BCD \u0BAE\u0BC1\u0BA4\u0BB2\u0BCD \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7, \u0B85\u0BA4\u0BC1\u0BB5\u0BC1\u0BAE\u0BCD \u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0B95\u0BCD\u0B95\u0BBE\u0BA9 \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B89\u0BB0\u0B95\u0BCD\u0B95\u0BAA\u0BCD \u0BAA\u0B9F\u0BBF\u0B95\u0BCD\u0B95\u0BC1\u0BAE\u0BCD. \u0BAA\u0BC1\u0BA4\u0BBF\u0BAF \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BCA\u0B9F\u0B99\u0BCD\u0B95\u0BBF, \u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B92\u0BB0\u0BC1 \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BC7\u0BB0\u0BCD\u0BA8\u0BCD\u0BA4\u0BC6\u0B9F\u0BC1\u0B95\u0BCD\u0B95\u0BB5\u0BC1\u0BAE\u0BCD.",
434
+ startNewChatDetail: "\u0B93\u0BB0\u0BCD \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BBF\u0BA9\u0BCD \u0BAE\u0BC1\u0BA4\u0BB2\u0BCD \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7, \u0B85\u0BA4\u0BC1\u0BB5\u0BC1\u0BAE\u0BCD \u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0B95\u0BCD\u0B95\u0BBE\u0BA9 \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8, \u0BAA\u0BA4\u0BBF\u0BA9\u0BC8\u0BA8\u0BCD\u0BA4\u0BC1 \u0BA8\u0BBF\u0BAE\u0BBF\u0B9F\u0B99\u0BCD\u0B95\u0BB3\u0BC1\u0B95\u0BCD\u0B95\u0BC1\u0BB3\u0BCD \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B89\u0BB0\u0B95\u0BCD\u0B95\u0BAA\u0BCD \u0BAA\u0B9F\u0BBF\u0B95\u0BCD\u0B95\u0BC1\u0BAE\u0BCD. \u0BAA\u0BC1\u0BA4\u0BBF\u0BAF \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BCA\u0B9F\u0B99\u0BCD\u0B95\u0BBF, \u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B92\u0BB0\u0BC1 \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BC7\u0BB0\u0BCD\u0BA8\u0BCD\u0BA4\u0BC6\u0B9F\u0BC1\u0B95\u0BCD\u0B95\u0BB5\u0BC1\u0BAE\u0BCD.",
413
435
  start: "\u0BA8\u0BC7\u0BB0\u0BB2\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BC8\u0BA4\u0BCD \u0BA4\u0BCA\u0B9F\u0B99\u0BCD\u0B95\u0BC1",
414
436
  notNow: "\u0B87\u0BAA\u0BCD\u0BAA\u0BCB\u0BA4\u0BC1 \u0BB5\u0BC7\u0BA3\u0BCD\u0B9F\u0BBE\u0BAE\u0BCD",
415
437
  opensInNewTab: "(\u0BAA\u0BC1\u0BA4\u0BBF\u0BAF \u0BA4\u0BBE\u0BB5\u0BB2\u0BBF\u0BB2\u0BCD \u0BA4\u0BBF\u0BB1\u0B95\u0BCD\u0B95\u0BC1\u0BAE\u0BCD)",
@@ -433,7 +455,8 @@ var TA = {
433
455
  region: "\u0B89\u0B99\u0BCD\u0B95\u0BB3\u0BCD \u0BAA\u0B95\u0BC1\u0BA4\u0BBF\u0BAF\u0BBF\u0BB2\u0BCD \u0BA8\u0BC7\u0BB0\u0BB2\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B87\u0BA9\u0BCD\u0BA9\u0BC1\u0BAE\u0BCD \u0B95\u0BBF\u0B9F\u0BC8\u0B95\u0BCD\u0B95\u0BB5\u0BBF\u0BB2\u0BCD\u0BB2\u0BC8.",
434
456
  locale: "\u0B87\u0BA8\u0BCD\u0BA4 \u0BAE\u0BCA\u0BB4\u0BBF\u0BAF\u0BBF\u0BB2\u0BCD \u0BA8\u0BC7\u0BB0\u0BB2\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B87\u0BA9\u0BCD\u0BA9\u0BC1\u0BAE\u0BCD \u0B95\u0BBF\u0B9F\u0BC8\u0B95\u0BCD\u0B95\u0BB5\u0BBF\u0BB2\u0BCD\u0BB2\u0BC8.",
435
457
  paused: "\u0BA8\u0BC7\u0BB0\u0BB2\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B87\u0BAA\u0BCD\u0BAA\u0BCB\u0BA4\u0BC1 \u0B87\u0B9F\u0BC8\u0BA8\u0BBF\u0BB1\u0BC1\u0BA4\u0BCD\u0BA4\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F\u0BC1\u0BB3\u0BCD\u0BB3\u0BA4\u0BC1.",
436
- notEligible: "\u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0B95\u0BB3\u0BC1\u0B95\u0BCD\u0B95\u0BBE\u0BA9 \u0BAA\u0BA4\u0BBF\u0BB2\u0BCD\u0B95\u0BB3\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0BAA\u0B9F\u0BBF\u0B95\u0BCD\u0B95 \u0BAE\u0BC1\u0B9F\u0BBF\u0BAF\u0BC1\u0BAE\u0BCD.",
458
+ // TRANSLATION REVIEW PENDING (BOFF-9797): draft.
459
+ notEligible: "\u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0B95\u0BCD\u0B95\u0BBE\u0BA9 \u0BAE\u0BC1\u0BA4\u0BB2\u0BCD \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0BAE\u0B9F\u0BCD\u0B9F\u0BC1\u0BAE\u0BC7, \u0BAA\u0BA4\u0BBF\u0BA9\u0BC8\u0BA8\u0BCD\u0BA4\u0BC1 \u0BA8\u0BBF\u0BAE\u0BBF\u0B9F\u0B99\u0BCD\u0B95\u0BB3\u0BC1\u0B95\u0BCD\u0B95\u0BC1\u0BB3\u0BCD, \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0BAA\u0B9F\u0BBF\u0B95\u0BCD\u0B95\u0BC1\u0BAE\u0BCD. \u0BAA\u0BC1\u0BA4\u0BBF\u0BAF \u0B85\u0BB0\u0B9F\u0BCD\u0B9F\u0BC8\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BCA\u0B9F\u0B99\u0BCD\u0B95\u0BBF, \u0BAA\u0BB0\u0BBF\u0BA8\u0BCD\u0BA4\u0BC1\u0BB0\u0BC8\u0B95\u0BCD\u0B95\u0BAA\u0BCD\u0BAA\u0B9F\u0BCD\u0B9F \u0B92\u0BB0\u0BC1 \u0B95\u0BC7\u0BB3\u0BCD\u0BB5\u0BBF\u0BAF\u0BC8\u0BA4\u0BCD \u0BA4\u0BC7\u0BB0\u0BCD\u0BA8\u0BCD\u0BA4\u0BC6\u0B9F\u0BC1\u0B95\u0BCD\u0B95\u0BB5\u0BC1\u0BAE\u0BCD.",
437
460
  answerClaimed: "\u0B87\u0BA8\u0BCD\u0BA4\u0BAA\u0BCD \u0BAA\u0BA4\u0BBF\u0BB2\u0BC8 \u0B85\u0BB5\u0BA4\u0BBE\u0BB0\u0BCD \u0B8F\u0BB1\u0BCD\u0B95\u0BC6\u0BA9\u0BB5\u0BC7 \u0BAA\u0B9F\u0BBF\u0BA4\u0BCD\u0BA4\u0BC1\u0BB5\u0BBF\u0B9F\u0BCD\u0B9F\u0BA4\u0BC1."
438
461
  };
439
462
  var STRINGS = {
@@ -457,7 +480,8 @@ var CONSENT = /* @__PURE__ */ new Map([
457
480
  intro: "This is an AI avatar, not a real person. It reads the assistant's first eligible answer to a suggested question aloud for up to a minute. The answer is AI-generated and can be wrong.",
458
481
  processing: "When you start, Cloudflare checks for bots. The answer text goes to Google to create the voice. Your browser connects to LiveKit, which sees your IP address. LiveKit fetches our temporary audio file and passes the voice to Protoface, which makes the avatar video streamed through LiveKit.",
459
482
  storage: "Your microphone and camera are not used. We do not record the live session. We temporarily store the generated voice file and keep a record of this consent. The privacy notice explains our safeguards, storage periods and the providers' processing. For people aged eighteen and over.",
460
- privacyLink: "How we handle this"
483
+ privacyLink: "How we handle this",
484
+ botCheck: "turnstile"
461
485
  }
462
486
  }
463
487
  ],
@@ -471,7 +495,8 @@ var CONSENT = /* @__PURE__ */ new Map([
471
495
  intro: "This is an AI avatar, not a real person. It reads the assistant's first eligible answer to a suggested question aloud for up to a minute. The answer is AI-generated and can be wrong.",
472
496
  processing: "When you start, Cloudflare checks for bots. The answer text goes to Google to create the voice. Our server sends that voice through LiveKit to Protoface, which makes the avatar video streamed through LiveKit. Your browser connects to LiveKit, which sees your IP address.",
473
497
  storage: "Your microphone and camera are not used. We do not record the live session or store the generated voice. We keep a record of this consent. The privacy notice explains our safeguards, storage periods and the providers' processing. For people aged eighteen and over.",
474
- privacyLink: "How we handle this"
498
+ privacyLink: "How we handle this",
499
+ botCheck: "turnstile"
475
500
  }
476
501
  }
477
502
  ],
@@ -486,13 +511,30 @@ var CONSENT = /* @__PURE__ */ new Map([
486
511
  intro: "This is an AI avatar, not a real person. It reads the assistant's first eligible answer to a suggested question aloud for up to a minute. The answer is AI-generated and can be wrong.",
487
512
  processing: "When you start, Cloudflare checks for bots. The answer text goes to Google to create the voice. Our server sends that voice through LiveKit to Protoface, which makes the avatar video streamed through LiveKit. Your browser connects to LiveKit, which sees your IP address.",
488
513
  storage: "Your microphone and camera are not used. We do not record the live session or store the generated voice. We keep a record of this consent. The privacy notice explains our safeguards, storage periods and the providers' processing. For people aged eighteen and over.",
489
- privacyLink: "How we handle this"
514
+ privacyLink: "How we handle this",
515
+ botCheck: "turnstile"
516
+ }
517
+ }
518
+ ],
519
+ [
520
+ // The words of web-consent-2026-11-02 without "When you start, Cloudflare checks for bots.", for a server that runs
521
+ // no bot check (its availability's botCheck is `off`). Product-neutral too: one notice and one digest for every site.
522
+ "web-consent-2026-11-03",
523
+ {
524
+ en: {
525
+ title: "Live AI avatar (beta)",
526
+ introProduct: null,
527
+ intro: "This is an AI avatar, not a real person. It reads the assistant's first eligible answer to a suggested question aloud for up to a minute. The answer is AI-generated and can be wrong.",
528
+ processing: "The answer text goes to Google to create the voice. Our server sends that voice through LiveKit to Protoface, which makes the avatar video streamed through LiveKit. Your browser connects to LiveKit, which sees your IP address.",
529
+ storage: "Your microphone and camera are not used. We do not record the live session or store the generated voice. We keep a record of this consent. The privacy notice explains our safeguards, storage periods and the providers' processing. For people aged eighteen and over.",
530
+ privacyLink: "How we handle this",
531
+ botCheck: "off"
490
532
  }
491
533
  }
492
534
  ]
493
535
  ]);
494
536
  function avatarConsentCopy(version, locale) {
495
- if (!chunk23H4JUL4_js.isAvatarLiveLocaleReviewed(locale)) return null;
537
+ if (!chunkFQH3AJN3_js.isAvatarLiveLocaleReviewed(locale)) return null;
496
538
  return CONSENT.get(version)?.[locale] ?? null;
497
539
  }
498
540
 
@@ -614,6 +656,9 @@ var PRIVACY_HREF = "/privacy#live-avatar";
614
656
  var SPEAKER_WAIT_MS = 3e4;
615
657
  var END_GRACE_MS = 1e4;
616
658
  var CLOCK_TOLERANCE_MS = 5e3;
659
+ var SERVICE_MAX_AGE_MS = 15 * 6e4;
660
+ var ANSWER_OFFER_MS = SERVICE_MAX_AGE_MS - 6e4;
661
+ var MAX_TIMER_MS = 2147483647;
617
662
  var PRIMARY = '[data-avatar-primary], [data-boff-explore="panel-continue-chat"]';
618
663
  var IDLE = { name: "idle" };
619
664
  var INERT2 = { name: "inert" };
@@ -626,8 +671,19 @@ var REFUSAL_TEXT = {
626
671
  not_eligible: "notEligible",
627
672
  answer_claimed: "answerClaimed"
628
673
  };
629
- var WAITING = { answerId: null, startOver: false };
630
- var START_OVER = { answerId: null, startOver: true };
674
+ var WAITING = { answerId: null, startOver: false, offerUntil: NaN };
675
+ var START_OVER = {
676
+ answerId: null,
677
+ startOver: true,
678
+ offerUntil: NaN
679
+ };
680
+ function createdAtOf(message) {
681
+ const raw = message.createdAt;
682
+ return typeof raw === "string" && raw !== "" ? Date.parse(raw) : NaN;
683
+ }
684
+ function offeredAt(exchange, now) {
685
+ return exchange.answerId !== null && !(now < exchange.offerUntil) ? START_OVER : exchange;
686
+ }
631
687
  function firstExchange(messages) {
632
688
  if (!messages || messages.length === 0) return WAITING;
633
689
  if (messages.length > 2) return START_OVER;
@@ -641,7 +697,11 @@ function firstExchange(messages) {
641
697
  if (answer.status !== "COMPLETED" || answer.content.trim() === "" || !isAvatarMessageId(answer.id)) {
642
698
  return START_OVER;
643
699
  }
644
- return { answerId: answer.id, startOver: false };
700
+ return {
701
+ answerId: answer.id,
702
+ startOver: false,
703
+ offerUntil: createdAtOf(answer) + ANSWER_OFFER_MS
704
+ };
645
705
  }
646
706
  function offering(offer, messageId, claimed) {
647
707
  return claimed.has(messageId) ? { name: "refused", reason: "answer_claimed" } : { name: "consent", offer, messageId };
@@ -667,6 +727,7 @@ function AvatarLiveView({
667
727
  fallback,
668
728
  onContinueInChat,
669
729
  continueInChat,
730
+ newChat,
670
731
  off,
671
732
  base,
672
733
  headers,
@@ -675,13 +736,16 @@ function AvatarLiveView({
675
736
  const S = avatarLiveStrings(locale);
676
737
  const uid = react.useId();
677
738
  const consentTitleId = `${uid}-consent`;
678
- const { answerId, startOver } = firstExchange(conversation?.messages);
739
+ const exchange = firstExchange(conversation?.messages);
740
+ const [ageTick, setAgeTick] = react.useState(0);
741
+ const { answerId, startOver } = offeredAt(exchange, Date.now());
742
+ const offerUntil = answerId === null ? null : exchange.offerUntil;
679
743
  const [phase, setPhase] = react.useState(IDLE);
680
744
  const [blocked, setBlocked] = react.useState(false);
681
745
  const [now, setNow] = react.useState(() => Date.now());
682
746
  const phaseRef = react.useRef(IDLE);
683
- const latest = react.useRef({ live, locale, base, headers, answerId, off });
684
- latest.current = { live, locale, base, headers, answerId, off };
747
+ const latest = react.useRef({ live, locale, base, headers, exchange, off });
748
+ latest.current = { live, locale, base, headers, exchange, off };
685
749
  const conversationRef = react.useRef(conversation);
686
750
  conversationRef.current = conversation;
687
751
  const checkRef = react.useRef(null);
@@ -697,6 +761,17 @@ function AvatarLiveView({
697
761
  phaseRef.current = next;
698
762
  setPhase(next);
699
763
  }, []);
764
+ const offeredNow = react.useCallback(
765
+ () => offeredAt(latest.current.exchange, Date.now()).answerId,
766
+ []
767
+ );
768
+ const reoffer = react.useCallback(
769
+ (offer) => {
770
+ const messageId = offeredNow();
771
+ return messageId === null ? { name: "needs-answer", offer } : offering(offer, messageId, claimedRef.current);
772
+ },
773
+ [offeredNow]
774
+ );
700
775
  const finish = react.useCallback(
701
776
  (how, reason) => {
702
777
  const handle = sessionRef.current;
@@ -757,17 +832,17 @@ function AvatarLiveView({
757
832
  return;
758
833
  }
759
834
  const copy = avatarConsentCopy(result.offer.consentVersion, locale2);
760
- if (copy === null) {
835
+ if (copy === null || copy.botCheck !== result.offer.botCheck) {
761
836
  go(INERT2);
762
837
  return;
763
838
  }
764
- const offer = { ...result.offer, locale: locale2, copy };
765
- const messageId = latest.current.answerId;
766
- go(
767
- messageId === null ? { name: "needs-answer", offer } : offering(offer, messageId, claimedRef.current)
768
- );
839
+ if (result.offer.botCheck === "turnstile" && chunkFQH3AJN3_js.turnstileSiteKeyOf(live2) === null) {
840
+ go(INERT2);
841
+ return;
842
+ }
843
+ go(reoffer({ ...result.offer, locale: locale2, copy }));
769
844
  });
770
- }, [go]);
845
+ }, [go, reoffer]);
771
846
  const begin = react.useCallback(
772
847
  (session, module, offer, target) => {
773
848
  const received = Date.now();
@@ -853,11 +928,17 @@ function AvatarLiveView({
853
928
  if (current.name !== "consent") return;
854
929
  const { live: live2, base: base2, headers: headers2 } = latest.current;
855
930
  if (base2 === null) return;
856
- if (!canBindBotCheck()) {
931
+ const { offer, messageId } = current;
932
+ if (offeredNow() !== messageId) {
933
+ go(reoffer(offer));
934
+ return;
935
+ }
936
+ const refusedFrom = latest.current.exchange.offerUntil - ANSWER_OFFER_MS + SERVICE_MAX_AGE_MS;
937
+ const siteKey = offer.botCheck === "turnstile" ? chunkFQH3AJN3_js.turnstileSiteKeyOf(live2) : null;
938
+ if (offer.botCheck === "turnstile" && (siteKey === null || !canBindBotCheck())) {
857
939
  go(INERT2);
858
940
  return;
859
941
  }
860
- const { offer, messageId } = current;
861
942
  const conversationToken = conversationRef.current?.getConversationToken() ?? null;
862
943
  const idempotencyKey = newIdempotencyKey();
863
944
  if (conversationToken === null || !isAvatarConversationToken(conversationToken) || idempotencyKey === null) {
@@ -874,31 +955,41 @@ function AvatarLiveView({
874
955
  };
875
956
  const run = { cancelled: null, turnstile: null };
876
957
  startRef.current = run;
877
- go({ name: "bot-check", offer, messageId });
878
958
  const module = loadModule(live2.load);
879
- const turnstile = runTurnstile(
880
- botBoxRef.current,
881
- live2.turnstileSiteKey,
882
- "avatar_start",
883
- avatarBotBinding(body2)
884
- );
885
- run.turnstile = turnstile;
959
+ let turnstile = null;
960
+ if (siteKey === null) {
961
+ go({ name: "creating" });
962
+ } else {
963
+ go({ name: "bot-check", offer, messageId });
964
+ turnstile = runTurnstile(
965
+ botBoxRef.current,
966
+ siteKey,
967
+ "avatar_start",
968
+ avatarBotBinding(body2)
969
+ );
970
+ run.turnstile = turnstile;
971
+ }
886
972
  void (async () => {
887
973
  let loaded;
888
974
  let botToken;
889
975
  try {
890
- [loaded, botToken] = await Promise.all([module, turnstile.token]);
976
+ [loaded, botToken] = await Promise.all([module, turnstile?.token]);
891
977
  } catch {
892
- turnstile.cancel();
978
+ turnstile?.cancel();
893
979
  if (run.cancelled === null) {
894
980
  startRef.current = null;
895
981
  go(INERT2);
896
982
  }
897
983
  return;
898
984
  }
899
- turnstile.cancel();
985
+ turnstile?.cancel();
900
986
  if (run.cancelled !== null) return;
901
- go({ name: "creating" });
987
+ if (!(Date.now() < refusedFrom)) {
988
+ startRef.current = null;
989
+ go({ name: "needs-answer", offer });
990
+ return;
991
+ }
992
+ if (turnstile !== null) go({ name: "creating" });
902
993
  const result = await requestCreate({
903
994
  base: base2,
904
995
  headers: headers2,
@@ -909,12 +1000,12 @@ function AvatarLiveView({
909
1000
  if (startRef.current === run) startRef.current = null;
910
1001
  settle(result, run, { module: loaded, offer, messageId, base: base2, headers: headers2 });
911
1002
  })();
912
- }, [go, settle]);
1003
+ }, [go, offeredNow, reoffer, settle]);
913
1004
  const stop = react.useCallback(() => {
914
1005
  const current = phaseRef.current;
915
1006
  if (current.name === "bot-check") {
916
1007
  cancelStart("user");
917
- go(offering(current.offer, current.messageId, claimedRef.current));
1008
+ go(reoffer(current.offer));
918
1009
  return;
919
1010
  }
920
1011
  if (current.name === "creating") {
@@ -925,7 +1016,7 @@ function AvatarLiveView({
925
1016
  if (current.name === "pending" || current.name === "live") {
926
1017
  finish("stopped", "user");
927
1018
  }
928
- }, [cancelStart, finish, go]);
1019
+ }, [cancelStart, finish, go, reoffer]);
929
1020
  const leave = react.useCallback(
930
1021
  (reason) => {
931
1022
  const current = phaseRef.current;
@@ -941,9 +1032,7 @@ function AvatarLiveView({
941
1032
  }
942
1033
  case "bot-check":
943
1034
  cancelStart(reason);
944
- go(
945
- reason === "user" ? IDLE : offering(current.offer, current.messageId, claimedRef.current)
946
- );
1035
+ go(reason === "user" ? IDLE : reoffer(current.offer));
947
1036
  return;
948
1037
  case "creating":
949
1038
  cancelStart(reason);
@@ -957,7 +1046,7 @@ function AvatarLiveView({
957
1046
  return;
958
1047
  }
959
1048
  },
960
- [cancelStart, finish, go]
1049
+ [cancelStart, finish, go, reoffer]
961
1050
  );
962
1051
  const showing = active && !off;
963
1052
  react.useEffect(() => {
@@ -966,7 +1055,7 @@ function AvatarLiveView({
966
1055
  return;
967
1056
  }
968
1057
  const current = phaseRef.current;
969
- const { answerId: offered } = latest.current;
1058
+ const offered = offeredNow();
970
1059
  const used = offered !== null && claimedRef.current.has(offered);
971
1060
  if (current.name === "ended" && used) return;
972
1061
  if (current.name === "refused" && current.reason === "answer_claimed" && used) {
@@ -978,7 +1067,7 @@ function AvatarLiveView({
978
1067
  current.name === "checking" && checkRef.current === null) {
979
1068
  check();
980
1069
  }
981
- }, [showing, check, leave]);
1070
+ }, [showing, check, leave, offeredNow]);
982
1071
  react.useEffect(() => {
983
1072
  if (askedLocale.current === locale) return;
984
1073
  askedLocale.current = locale;
@@ -1004,6 +1093,18 @@ function AvatarLiveView({
1004
1093
  );
1005
1094
  }
1006
1095
  }, [answerId, go]);
1096
+ react.useEffect(() => {
1097
+ if (offerUntil === null) return;
1098
+ const timer = setTimeout(
1099
+ () => setAgeTick((tick) => tick + 1),
1100
+ Math.min(MAX_TIMER_MS, Math.max(0, offerUntil - Date.now()))
1101
+ );
1102
+ return () => clearTimeout(timer);
1103
+ }, [offerUntil, ageTick]);
1104
+ const startNewChat = react.useCallback(() => {
1105
+ conversationRef.current?.reset();
1106
+ onContinueInChat();
1107
+ }, [onContinueInChat]);
1007
1108
  const onRoomEvent = react.useCallback(
1008
1109
  (handle, event) => {
1009
1110
  if (handle.done || sessionRef.current !== handle) return;
@@ -1199,6 +1300,29 @@ function AvatarLiveView({
1199
1300
  children: continueInChat
1200
1301
  }
1201
1302
  );
1303
+ const startOverActions = /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center justify-center gap-2", children: [
1304
+ /* @__PURE__ */ jsxRuntime.jsx(
1305
+ "button",
1306
+ {
1307
+ type: "button",
1308
+ "data-avatar-primary": "",
1309
+ "data-boff-explore": "avatar-live-new-chat",
1310
+ className: primaryButton,
1311
+ onClick: startNewChat,
1312
+ children: newChat
1313
+ }
1314
+ ),
1315
+ /* @__PURE__ */ jsxRuntime.jsx(
1316
+ "button",
1317
+ {
1318
+ type: "button",
1319
+ "data-boff-explore": "avatar-live-continue",
1320
+ className: secondaryButton,
1321
+ onClick: onContinueInChat,
1322
+ children: continueInChat
1323
+ }
1324
+ )
1325
+ ] });
1202
1326
  const stopButton = /* @__PURE__ */ jsxRuntime.jsx(
1203
1327
  "button",
1204
1328
  {
@@ -1231,7 +1355,7 @@ function AvatarLiveView({
1231
1355
  switch (phase.name) {
1232
1356
  case "needs-answer":
1233
1357
  body = /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: startOver ? S.startNewChatDetail : S.needsAnswerDetail });
1234
- actions = continueButton;
1358
+ actions = startOver ? startOverActions : continueButton;
1235
1359
  break;
1236
1360
  case "consent": {
1237
1361
  const { copy } = phase.offer;
@@ -1293,7 +1417,7 @@ function AvatarLiveView({
1293
1417
  break;
1294
1418
  }
1295
1419
  case "refused":
1296
- actions = continueButton;
1420
+ actions = phase.reason === "not_eligible" ? startOverActions : continueButton;
1297
1421
  break;
1298
1422
  case "bot-check":
1299
1423
  case "creating":