@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.
- package/README.md +68 -20
- package/dist/avatar-live-view/index.d.mts +7 -2
- package/dist/avatar-live-view/index.d.ts +7 -2
- package/dist/avatar-live-view/index.js +183 -59
- package/dist/avatar-live-view/index.js.map +1 -1
- package/dist/avatar-live-view/index.mjs +181 -57
- package/dist/avatar-live-view/index.mjs.map +1 -1
- package/dist/{chunk-23H4JUL4.js → chunk-FQH3AJN3.js} +20 -3
- package/dist/chunk-FQH3AJN3.js.map +1 -0
- package/dist/{chunk-BX2USEWF.mjs → chunk-SFT3WHN5.mjs} +19 -4
- package/dist/chunk-SFT3WHN5.mjs.map +1 -0
- package/dist/{explore-avatar-live-config-BGsGwbcq.d.mts → explore-avatar-live-config-Bp3kQbU2.d.mts} +21 -6
- package/dist/{explore-avatar-live-config-B171o1Yo.d.ts → explore-avatar-live-config-Cetx8-Zu.d.ts} +21 -6
- package/dist/index.d.mts +17 -7
- package/dist/index.d.ts +17 -7
- package/dist/index.js +19 -15
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +16 -12
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
- package/dist/chunk-23H4JUL4.js.map +0 -1
- package/dist/chunk-BX2USEWF.mjs.map +0 -1
package/README.md
CHANGED
|
@@ -298,8 +298,9 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
298
298
|
live: {
|
|
299
299
|
site: 'healthybowl',
|
|
300
300
|
load: () => import('@burdenoff/website-sdk/avatar-live'),
|
|
301
|
-
turnstileSiteKey: TURNSTILE_SITE_KEY,
|
|
302
301
|
manifestVersion: 'hb-en-1', // the version of `suggestedQuestions`
|
|
302
|
+
// Optional: used only where the server checks for bots (see "The bot check is the server's setting").
|
|
303
|
+
turnstileSiteKey: TURNSTILE_SITE_KEY,
|
|
303
304
|
},
|
|
304
305
|
}}
|
|
305
306
|
/>
|
|
@@ -339,7 +340,24 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
339
340
|
- **Needs the panel under an `ExploreChatProvider`.** The live avatar reads the
|
|
340
341
|
provider's conversation. Without a provider, on a shared (read-only)
|
|
341
342
|
conversation, in a locale whose strings have not been reviewed yet (English
|
|
342
|
-
only, for now), or with an incomplete `live
|
|
343
|
+
only, for now), or with an incomplete `live` (no `site`, `load` or
|
|
344
|
+
`manifestVersion`, or a `turnstileSiteKey` or `allowTestSiteKey` of the wrong
|
|
345
|
+
shape), the Avatar view stays as it was.
|
|
346
|
+
- **The bot check is the server's setting (web API contract v1.2, additive).**
|
|
347
|
+
The availability answer says whether the server checks for bots when a
|
|
348
|
+
session is created: `"botCheck": {"mode": "off"}` or
|
|
349
|
+
`{"mode": "turnstile"}`. With `off`, Start loads the room module and creates
|
|
350
|
+
the session, and nothing else: no Cloudflare script, no widget, no WebCrypto
|
|
351
|
+
needed and no `x-web-avatar-bot-token` header; the server's own guards and
|
|
352
|
+
caps decide. With `turnstile`, Start runs the Cloudflare Turnstile check with
|
|
353
|
+
the page's own `turnstileSiteKey`, as before; without a key the page may use
|
|
354
|
+
(none, or one of Cloudflare's test keys where `allowTestSiteKey` is `false`)
|
|
355
|
+
the Avatar view stays as it was. A server older than v1.2 sends no `botCheck`
|
|
356
|
+
and always checks, so it is read as `turnstile`. Any other `botCheck` (an
|
|
357
|
+
unknown mode, another field, another shape) leaves the view as it was. So
|
|
358
|
+
turning the bot check on or off is a server config change: a site needs no
|
|
359
|
+
new build for it, as long as its build carries a site key for `turnstile` and
|
|
360
|
+
its CSP allows Cloudflare (below).
|
|
343
361
|
- **One answer: the first, to a suggested question.** The avatar service
|
|
344
362
|
accepts a conversation only when it holds exactly two messages: the first user
|
|
345
363
|
message (a suggested question) and the first assistant answer, completed. The
|
|
@@ -350,14 +368,23 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
350
368
|
asked again without Retry), it asks the visitor to start a new chat and choose
|
|
351
369
|
a suggested question. Whether the first question really is one of the
|
|
352
370
|
suggested ones is the service's to judge (`not_eligible`).
|
|
371
|
+
- **A fresh answer only.** The service also refuses an answer more than fifteen
|
|
372
|
+
minutes old (from the answer's `createdAt`): a conversation restored from the
|
|
373
|
+
browser's history, say. The view stops offering an answer fourteen minutes
|
|
374
|
+
after its `createdAt` (a minute's margin; a missing or unreadable time counts
|
|
375
|
+
as too old), also while the visitor is on the consent card: one timer moves
|
|
376
|
+
the card to the start-over step at that moment. The start-over step and the
|
|
377
|
+
`not_eligible` refusal both have a **New chat** button, which is the chat's
|
|
378
|
+
own New chat (the shared conversation's `reset`) followed by the Chat tab; no
|
|
379
|
+
host prop is needed for it.
|
|
353
380
|
- **What the visitor sees.** Opening the Avatar view asks the gateway (the
|
|
354
381
|
origin of your configured `gatewayUrl`, at `/api/web-avatar/v1/availability`)
|
|
355
382
|
whether the live avatar is offered for this site and locale. When it is and
|
|
356
383
|
the conversation has its first answer, a consent card explains what happens
|
|
357
384
|
and links to `/privacy#live-avatar`; with no answer yet, the view asks the
|
|
358
385
|
visitor to choose a suggested question in Chat first. Start runs a
|
|
359
|
-
Cloudflare Turnstile check (action `avatar_start`)
|
|
360
|
-
joins its room: the video, the captions, an "AI avatar · not a real person"
|
|
386
|
+
Cloudflare Turnstile check (action `avatar_start`) where the server checks
|
|
387
|
+
for bots, creates the session and joins its room: the video, the captions, an "AI avatar · not a real person"
|
|
361
388
|
badge, a countdown, Stop and Continue in Chat. Where a browser holds sound
|
|
362
389
|
back (Safari, iOS), a "Tap to turn on sound" button appears. A refusal (busy,
|
|
363
390
|
limits, region, language, paused, a question the avatar cannot read) is one
|
|
@@ -379,6 +406,14 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
379
406
|
digest for all of them (the card's title, intro, processing, storage and
|
|
380
407
|
privacy-link lines, each ending with a line feed: 760 bytes, SHA-256
|
|
381
408
|
`2e02b051ceb1163c14bc58fa63a954a12c0d1f2695029a6d4805922d74c793f7`).
|
|
409
|
+
`web-consent-2026-11-03` is the same card without "When you start,
|
|
410
|
+
Cloudflare checks for bots.", for a server whose bot check is `off` (716
|
|
411
|
+
bytes, SHA-256
|
|
412
|
+
`bb7516df3cf3a910c6ec1623391f859e6c48e7e7d305d4fb333f18d4115da203`).
|
|
413
|
+
Each version says which bot check its words describe, and the card is shown
|
|
414
|
+
only where the server's `botCheck` is the same: a server that runs no bot
|
|
415
|
+
check must name `web-consent-2026-11-03`, and one that checks must name a
|
|
416
|
+
version that says so, or the view stays as it was.
|
|
382
417
|
`web-consent-2026-10-31` (which names the product, "a suggested Healthy Bowl
|
|
383
418
|
question") and `web-consent-2026-11` stay, unchanged, for servers that still
|
|
384
419
|
name them.
|
|
@@ -389,22 +424,24 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
389
424
|
apps-first hand-over, so it does not say which.
|
|
390
425
|
- **Requests.** All three go to the gateway without credentials. The create
|
|
391
426
|
request carries `content-type: application/json`, `idempotency-key` (a UUID
|
|
392
|
-
v4) and `x-web-avatar-bot-token` (the
|
|
393
|
-
verifies and does not forward); the
|
|
394
|
-
carry no header of the SDK's own. The conversation token is sent in the create
|
|
427
|
+
v4) and, only where the server checks for bots, `x-web-avatar-bot-token` (the
|
|
428
|
+
Turnstile token, which the gateway verifies and does not forward); the
|
|
429
|
+
availability request and the end request carry no header of the SDK's own. The conversation token is sent in the create
|
|
395
430
|
body only. Neither it, nor the session's end secret, nor the room token, nor
|
|
396
431
|
the bot check's token is ever written into the page, the console or storage by
|
|
397
432
|
the live avatar (the chat keeps its own copy of the conversation in
|
|
398
433
|
`localStorage`, as it always has).
|
|
399
|
-
- **Bot-check binding (web API contract v1.1, additive
|
|
434
|
+
- **Bot-check binding (web API contract v1.1, additive; `turnstile` mode
|
|
435
|
+
only).** The Turnstile widget
|
|
400
436
|
is rendered with `cData` set to
|
|
401
437
|
`base64url_nopad(SHA-256(UTF-8("boff-web-avatar-cdata/v1\n" + site + "\n" + locale + "\n" + conversationToken + "\n" + messageId)))`,
|
|
402
438
|
made with WebCrypto from the exact values the create body then carries, before
|
|
403
439
|
the widget is rendered, so the gateway can check that the token was minted for
|
|
404
440
|
this request. The action stays `avatar_start`, and nothing else in v1
|
|
405
|
-
changes.
|
|
406
|
-
cannot start the live avatar: Start loads
|
|
407
|
-
check's script there, and shows the view
|
|
441
|
+
changes. Where the server checks for bots, a browser without WebCrypto (a
|
|
442
|
+
page that is not a secure context) cannot start the live avatar: Start loads
|
|
443
|
+
neither the room module nor the bot check's script there, and shows the view
|
|
444
|
+
as it was. Pinned vector: site
|
|
408
445
|
`healthybowl`, locale `en`, conversation token
|
|
409
446
|
`ct_vector_0123456789abcdefghijklmnopqrstuvwx`, message id
|
|
410
447
|
`11111111-2222-4333-8444-555555555555` give
|
|
@@ -418,7 +455,9 @@ publishes audio, video or data, and it sends the avatar nothing to say.
|
|
|
418
455
|
preflight.
|
|
419
456
|
- **Your page's headers.** A site with a Content Security Policy must allow:
|
|
420
457
|
- `script-src` and `frame-src`: `https://challenges.cloudflare.com` (the
|
|
421
|
-
Turnstile bot check)
|
|
458
|
+
Turnstile bot check). Only needed where the server's bot check is
|
|
459
|
+
`turnstile`; keep it anyway, so that turning the bot check on later is a
|
|
460
|
+
server change and not a new release of the site;
|
|
422
461
|
- `connect-src`, the gateway origin (the three requests);
|
|
423
462
|
- `connect-src`, the media room: `wss://<project>.livekit.cloud`. For a
|
|
424
463
|
LiveKit Cloud room the media library also asks
|
|
@@ -587,14 +626,23 @@ A site adds these lines.
|
|
|
587
626
|
usual place whenever the banner is not on screen.
|
|
588
627
|
|
|
589
628
|
4. **The build env var** `VITE_AVATAR_TURNSTILE_SITE_KEY`: the site's
|
|
590
|
-
Cloudflare Turnstile site key
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
`
|
|
629
|
+
Cloudflare Turnstile site key, used only where the server checks for bots
|
|
630
|
+
(its availability's `botCheck` is `turnstile`). The server decides whether
|
|
631
|
+
the live avatar is offered on the site (its reviewed site list, its pause,
|
|
632
|
+
its caps) and whether it checks for bots, so the key is no longer the
|
|
633
|
+
opt-in: when it is unset or empty, `websiteAvatarLive` returns the live
|
|
634
|
+
config without a key, which runs where the server's bot check is `off` and
|
|
635
|
+
stays the still picture where it is `turnstile`. On alpha
|
|
636
|
+
(`VITE_DEPLOY_ENV=alpha`) it accepts Cloudflare's always-pass test key
|
|
637
|
+
`1x00000000000000000000AA` (the alpha gateway runs Turnstile in dummy mode)
|
|
638
|
+
or a real key; everywhere else, production included, only a real-looking key
|
|
639
|
+
(`0x…`, letters, digits, `_` and `-`, 18 to 64 characters) that is not one of
|
|
640
|
+
Cloudflare's test keys (`1x…AA`, `2x…AB`, `1x…BB`, `2x…BB`, `3x…FF`, or
|
|
641
|
+
anything of their shape). A key that is set but refused returns `undefined`
|
|
642
|
+
(the still picture and "Live avatar coming soon"), never a live avatar
|
|
643
|
+
without it. It also sets `allowTestSiteKey` (true on alpha only), so the
|
|
644
|
+
view itself refuses a test key on any other build. Pass `enabled: false` to
|
|
645
|
+
keep the still picture on a build whatever the server offers. Install
|
|
598
646
|
`livekit-client` on the site (see [Live avatar](#live-avatar-opt-in-receive-only)),
|
|
599
647
|
and declare the variable in `vite-env.d.ts`.
|
|
600
648
|
`websiteAvatarLive` trusts `VITE_DEPLOY_ENV`, so a production build must
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode } from 'react';
|
|
3
|
-
import { E as ExplorePanelAvatarLive, a as ExploreLocale, A as AvatarConversation } from '../explore-avatar-live-config-
|
|
3
|
+
import { E as ExplorePanelAvatarLive, a as ExploreLocale, A as AvatarConversation } from '../explore-avatar-live-config-Bp3kQbU2.mjs';
|
|
4
4
|
import '../types-CndbmBK-.mjs';
|
|
5
5
|
import '../use-explore-chat-zRuoAin6.mjs';
|
|
6
6
|
import '../explore-types-Bb2Ih3d8.mjs';
|
|
@@ -23,6 +23,11 @@ interface AvatarLiveViewProps {
|
|
|
23
23
|
onContinueInChat: () => void;
|
|
24
24
|
/** "Continue in Chat" in the panel's language: the panel's own word for it, so this chunk carries none of the panel's. */
|
|
25
25
|
continueInChat: string;
|
|
26
|
+
/**
|
|
27
|
+
* "New chat" in the panel's language, the panel's own word for it: the button that starts over (the conversation's
|
|
28
|
+
* `reset`, as the chat's own New chat button does, then the Chat tab) where this conversation can never be read.
|
|
29
|
+
*/
|
|
30
|
+
newChat: string;
|
|
26
31
|
/**
|
|
27
32
|
* Nothing to ask the server about: an incomplete config, no gateway, no shared conversation to read (no provider, or a
|
|
28
33
|
* read-only shared one), or a locale whose strings have not been reviewed. The tab stays as it was. Decided by
|
|
@@ -37,6 +42,6 @@ interface AvatarLiveViewProps {
|
|
|
37
42
|
/** The panel's conversation, null when there is no provider. */
|
|
38
43
|
conversation: AvatarConversation | null;
|
|
39
44
|
}
|
|
40
|
-
declare function AvatarLiveView({ live, active, locale, productName, still, fallback, onContinueInChat, continueInChat, off, base, headers, conversation, }: AvatarLiveViewProps): react.JSX.Element;
|
|
45
|
+
declare function AvatarLiveView({ live, active, locale, productName, still, fallback, onContinueInChat, continueInChat, newChat, off, base, headers, conversation, }: AvatarLiveViewProps): react.JSX.Element;
|
|
41
46
|
|
|
42
47
|
export { AvatarLiveView, type AvatarLiveViewProps };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
2
|
import { ReactNode } from 'react';
|
|
3
|
-
import { E as ExplorePanelAvatarLive, a as ExploreLocale, A as AvatarConversation } from '../explore-avatar-live-config-
|
|
3
|
+
import { E as ExplorePanelAvatarLive, a as ExploreLocale, A as AvatarConversation } from '../explore-avatar-live-config-Cetx8-Zu.js';
|
|
4
4
|
import '../types-CndbmBK-.js';
|
|
5
5
|
import '../use-explore-chat-DunjG-3p.js';
|
|
6
6
|
import '../explore-types-Bb2Ih3d8.js';
|
|
@@ -23,6 +23,11 @@ interface AvatarLiveViewProps {
|
|
|
23
23
|
onContinueInChat: () => void;
|
|
24
24
|
/** "Continue in Chat" in the panel's language: the panel's own word for it, so this chunk carries none of the panel's. */
|
|
25
25
|
continueInChat: string;
|
|
26
|
+
/**
|
|
27
|
+
* "New chat" in the panel's language, the panel's own word for it: the button that starts over (the conversation's
|
|
28
|
+
* `reset`, as the chat's own New chat button does, then the Chat tab) where this conversation can never be read.
|
|
29
|
+
*/
|
|
30
|
+
newChat: string;
|
|
26
31
|
/**
|
|
27
32
|
* Nothing to ask the server about: an incomplete config, no gateway, no shared conversation to read (no provider, or a
|
|
28
33
|
* read-only shared one), or a locale whose strings have not been reviewed. The tab stays as it was. Decided by
|
|
@@ -37,6 +42,6 @@ interface AvatarLiveViewProps {
|
|
|
37
42
|
/** The panel's conversation, null when there is no provider. */
|
|
38
43
|
conversation: AvatarConversation | null;
|
|
39
44
|
}
|
|
40
|
-
declare function AvatarLiveView({ live, active, locale, productName, still, fallback, onContinueInChat, continueInChat, off, base, headers, conversation, }: AvatarLiveViewProps): react.JSX.Element;
|
|
45
|
+
declare function AvatarLiveView({ live, active, locale, productName, still, fallback, onContinueInChat, continueInChat, newChat, off, base, headers, conversation, }: AvatarLiveViewProps): react.JSX.Element;
|
|
41
46
|
|
|
42
47
|
export { AvatarLiveView, type AvatarLiveViewProps };
|