@matterfact/embed 0.13.0 → 0.15.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.
- package/dist/react.cjs +199 -23
- package/dist/react.cjs.map +1 -1
- package/dist/react.d.cts +140 -11
- package/dist/react.d.ts +140 -11
- package/dist/react.js +192 -18
- package/dist/react.js.map +1 -1
- package/examples/embed-demo/.env.example +9 -0
- package/examples/embed-demo/README.md +66 -12
- package/examples/embed-demo/src/App.tsx +56 -12
- package/examples/embed-demo/src/config.ts +8 -0
- package/package.json +1 -1
package/dist/react.d.cts
CHANGED
|
@@ -159,6 +159,44 @@ type MatterfactEvent = {
|
|
|
159
159
|
source: 'user' | 'context';
|
|
160
160
|
};
|
|
161
161
|
|
|
162
|
+
interface MatterfactAuthProviderProps {
|
|
163
|
+
/**
|
|
164
|
+
* Publishable key (`pk_…`) identifying this embed app. Public and origin-scoped —
|
|
165
|
+
* meant to sit in HTML. Every `MatterfactAgent`/`MatterfactArtifact`/`MatterfactDoc`
|
|
166
|
+
* under this provider inherits it, so you set it once here rather than on each child.
|
|
167
|
+
*/
|
|
168
|
+
publishableKey: string;
|
|
169
|
+
/**
|
|
170
|
+
* Origin serving the matterfact widgets (the app that hosts `/embed/*`). Defaults to
|
|
171
|
+
* production. This is the ONE place to set it — every child inherits it, and the
|
|
172
|
+
* `widgetOrigin` prop on `MatterfactAgent`/`MatterfactArtifact` is deprecated in
|
|
173
|
+
* favour of setting it here.
|
|
174
|
+
*/
|
|
175
|
+
widgetOrigin?: string;
|
|
176
|
+
/**
|
|
177
|
+
* HOST-AUTH PASSTHROUGH (trusted first-party embeds). Return a token this matterfact
|
|
178
|
+
* deployment already trusts — the host app's Entra/Firebase token, whatever its auth
|
|
179
|
+
* provider verifies — and every child iframe signs in SILENTLY with it, no separate
|
|
180
|
+
* sign-in. The provider brokers it: when a child needs auth it asks the provider,
|
|
181
|
+
* which calls this and hands the token back (over `postMessage`, pinned to the widget
|
|
182
|
+
* origin). Called on demand so the token can be fresh; may be async. Omit for the
|
|
183
|
+
* standard interactive sign-in.
|
|
184
|
+
*/
|
|
185
|
+
getAuthToken?: () => string | null | Promise<string | null>;
|
|
186
|
+
/** Colour theme applied to every child widget. Falls back to `'auto'`. */
|
|
187
|
+
theme?: 'light' | 'dark' | 'auto';
|
|
188
|
+
/**
|
|
189
|
+
* Unified telemetry hook, fired for every embed lifecycle moment (`ready`, `auth`,
|
|
190
|
+
* `error`, …) across the children — pipe the whole embed into your own observability
|
|
191
|
+
* from one place. Never blocks or breaks a widget; a throw here is swallowed.
|
|
192
|
+
*/
|
|
193
|
+
onEvent?: (e: MatterfactEvent) => void;
|
|
194
|
+
/** The embed components (`MatterfactAgent`/`MatterfactArtifact`/`MatterfactDoc`) that
|
|
195
|
+
* inherit this provider's config. */
|
|
196
|
+
children: React.ReactNode;
|
|
197
|
+
}
|
|
198
|
+
declare function MatterfactAuthProvider({ publishableKey, widgetOrigin, getAuthToken, theme, onEvent, children, }: MatterfactAuthProviderProps): react_jsx_runtime.JSX.Element;
|
|
199
|
+
|
|
162
200
|
/**
|
|
163
201
|
* The Hoist adapter — a pure transform from a `HoistRuntime` (already read out of
|
|
164
202
|
* `window.XH` by hoist-runtime.ts) into the context/snapshot shapes context.ts sends
|
|
@@ -239,12 +277,25 @@ interface HostToolDef {
|
|
|
239
277
|
}
|
|
240
278
|
|
|
241
279
|
interface MatterfactAgentProps {
|
|
242
|
-
/**
|
|
243
|
-
|
|
244
|
-
|
|
280
|
+
/**
|
|
281
|
+
* Publishable key (`pk_…`) identifying this embed app. Public, origin-scoped.
|
|
282
|
+
*
|
|
283
|
+
* Optional here ONLY because it can instead come from an ancestor
|
|
284
|
+
* `MatterfactAuthProvider` (`prop ?? context`) — one of the two must supply it,
|
|
285
|
+
* or the component throws at mount.
|
|
286
|
+
*/
|
|
287
|
+
publishableKey?: string;
|
|
288
|
+
/**
|
|
289
|
+
* Origin serving the widget (the matterfact app). Defaults to production.
|
|
290
|
+
*
|
|
291
|
+
* @deprecated Prefer setting this once on `<MatterfactAuthProvider>` and letting
|
|
292
|
+
* every `<MatterfactAgent>`/`<MatterfactArtifact>` underneath inherit it. Still
|
|
293
|
+
* fully supported standalone (no provider) — resolved as `prop ?? context ?? default`.
|
|
294
|
+
*/
|
|
245
295
|
widgetOrigin?: string;
|
|
246
296
|
/** Label for THIS embedding, for per-surface usage/history attribution. */
|
|
247
297
|
surface?: string;
|
|
298
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
248
299
|
theme?: 'light' | 'dark' | 'auto';
|
|
249
300
|
/**
|
|
250
301
|
* HOST-AUTH PASSTHROUGH (trusted first-party embeds only). Return a token this
|
|
@@ -252,6 +303,8 @@ interface MatterfactAgentProps {
|
|
|
252
303
|
* token, whatever its auth provider verifies — and the widget signs in SILENTLY with
|
|
253
304
|
* it, no separate sign-in. Called on demand so the token can be fresh. Omit for the
|
|
254
305
|
* standard popup/inline sign-in (third-party hosts).
|
|
306
|
+
*
|
|
307
|
+
* Resolved as `prop ?? MatterfactAuthProvider's getAuthToken`.
|
|
255
308
|
*/
|
|
256
309
|
getAuthToken?: () => string | null | Promise<string | null>;
|
|
257
310
|
/**
|
|
@@ -356,25 +409,101 @@ interface MatterfactAgentProps {
|
|
|
356
409
|
*/
|
|
357
410
|
onEvent?: (e: MatterfactEvent) => void;
|
|
358
411
|
}
|
|
359
|
-
declare function MatterfactAgent({ publishableKey, widgetOrigin, surface, theme, getAuthToken, getPageContext, inline, className, style, pageContext, dev, actions, sitemap, artifacts, resolve, tools, onToolEvent, onEvent, }: MatterfactAgentProps): react_jsx_runtime.JSX.Element | null;
|
|
412
|
+
declare function MatterfactAgent({ publishableKey: publishableKeyProp, widgetOrigin: widgetOriginProp, surface, theme: themeProp, getAuthToken: getAuthTokenProp, getPageContext, inline, className, style, pageContext, dev, actions, sitemap, artifacts, resolve, tools, onToolEvent, onEvent, }: MatterfactAgentProps): react_jsx_runtime.JSX.Element | null;
|
|
360
413
|
interface MatterfactArtifactProps {
|
|
361
|
-
/** The artifact's slug
|
|
362
|
-
|
|
414
|
+
/** The artifact's name (its slug). */
|
|
415
|
+
name?: string;
|
|
416
|
+
/**
|
|
417
|
+
* @deprecated Use `name` instead. Still accepted as an alias — `name` wins
|
|
418
|
+
* when both are given.
|
|
419
|
+
*/
|
|
420
|
+
slug?: string;
|
|
363
421
|
/** The artifact owner's email — same as the Share dialog's `?owner=` param. */
|
|
364
422
|
owner: string;
|
|
365
|
-
/**
|
|
366
|
-
|
|
367
|
-
|
|
423
|
+
/**
|
|
424
|
+
* The artifact's read-only capability token — same as the Share dialog's `?t=`
|
|
425
|
+
* param. This is the standalone share-link path.
|
|
426
|
+
*
|
|
427
|
+
* @deprecated Prefer an ancestor `MatterfactAuthProvider` instead: with no
|
|
428
|
+
* `token`, the iframe authenticates the same way `MatterfactAgent` does — the
|
|
429
|
+
* provider's publishable key (`?k=`) plus the host page's origin (`?o=`) —
|
|
430
|
+
* instead of a share-link capability token. `token` still wins when both a
|
|
431
|
+
* token and a provider are present.
|
|
432
|
+
*/
|
|
433
|
+
token?: string;
|
|
434
|
+
/**
|
|
435
|
+
* Origin serving the widget (the matterfact app). Defaults to production.
|
|
436
|
+
*
|
|
437
|
+
* @deprecated Prefer setting this once on `<MatterfactAuthProvider>` and
|
|
438
|
+
* letting every `<MatterfactAgent>`/`<MatterfactArtifact>` underneath inherit
|
|
439
|
+
* it. Still fully supported standalone (no provider) — resolved as
|
|
440
|
+
* `prop ?? context ?? default`.
|
|
441
|
+
*/
|
|
368
442
|
widgetOrigin?: string;
|
|
443
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
369
444
|
theme?: 'auto' | 'light' | 'dark';
|
|
445
|
+
/** Applied to the `<iframe>` element the artifact renders into. */
|
|
370
446
|
className?: string;
|
|
447
|
+
/** Applied to the `<iframe>` element. Merged over the default fill. */
|
|
371
448
|
style?: React.CSSProperties;
|
|
372
449
|
}
|
|
373
450
|
/**
|
|
374
451
|
* Render a matterfact artifact inline in a host page. Chrome-free, cross-origin. When a
|
|
375
452
|
* MatterfactAgent is embedded on the same page, the loader sees this iframe and both
|
|
376
453
|
* makes the agent aware of it and (via its token) lets the agent read its data.
|
|
454
|
+
*
|
|
455
|
+
* Two auth modes, `token` wins when both are available:
|
|
456
|
+
* - TOKEN mode (`token` given): a standalone share link, `?t=`. This is the LIVE
|
|
457
|
+
* third-party embed path — its `src` format must stay byte-identical.
|
|
458
|
+
* - SESSION mode (no `token`, an ancestor `MatterfactAuthProvider` is present):
|
|
459
|
+
* tokenless, `?k=<publishableKey>&o=<host origin>`, the same authentication
|
|
460
|
+
* `MatterfactAgent` uses.
|
|
461
|
+
* With neither, there is no way for the iframe to authenticate, so no iframe is
|
|
462
|
+
* built at all — matching the "incomplete link" placeholder the embed artifact
|
|
463
|
+
* page itself renders for a missing owner/token.
|
|
464
|
+
*/
|
|
465
|
+
declare function MatterfactArtifact({ name: nameProp, slug, owner, token, widgetOrigin: widgetOriginProp, theme: themeProp, className, style, }: MatterfactArtifactProps): react_jsx_runtime.JSX.Element;
|
|
466
|
+
/** The two live-drivable doc params, mirroring `EmbedDocumentPage`'s `HostDocParams`. */
|
|
467
|
+
type MatterfactDocParams = {
|
|
468
|
+
ticker?: string;
|
|
469
|
+
version?: string;
|
|
470
|
+
};
|
|
471
|
+
interface MatterfactDocProps {
|
|
472
|
+
/** The document catalog key (`EmbedDocumentPage`'s `?key=`). Fixed at mount — not
|
|
473
|
+
* drivable via `params`, unlike `ticker`/`version`. */
|
|
474
|
+
docKey: string;
|
|
475
|
+
/** Initial ticker, seeds the iframe's `?ticker=` query param. */
|
|
476
|
+
ticker?: string;
|
|
477
|
+
/** Initial version. Always sent explicitly on the iframe `src` — defaults to
|
|
478
|
+
* `'latest'` rather than being omitted, so the doc page never has to guess. */
|
|
479
|
+
version?: 'latest' | `${number}-${number}-${number}`;
|
|
480
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
481
|
+
theme?: 'auto' | 'light' | 'dark';
|
|
482
|
+
/**
|
|
483
|
+
* Drive the document's ticker/version from your page after mount. Pass your whole
|
|
484
|
+
* param state; only the keys that actually changed since the last render are pushed
|
|
485
|
+
* to the iframe (as `host.docParams`), and the full set is re-sent once the iframe
|
|
486
|
+
* loads. A push is authoritative for every key it names — dropping a key stops
|
|
487
|
+
* driving it, it does not reset it. Omit this prop entirely for a static document
|
|
488
|
+
* whose ticker/version never change after mount.
|
|
489
|
+
*/
|
|
490
|
+
params?: MatterfactDocParams;
|
|
491
|
+
/** Applied to the `<iframe>` element the document renders into. */
|
|
492
|
+
className?: string;
|
|
493
|
+
/** Applied to the `<iframe>` element. Merged over the default fill. */
|
|
494
|
+
style?: React.CSSProperties;
|
|
495
|
+
}
|
|
496
|
+
/**
|
|
497
|
+
* Render a matterfact catalog document inline in a host page — the `MatterfactArtifact`
|
|
498
|
+
* counterpart for a published document/report instead of an artifact board.
|
|
499
|
+
*
|
|
500
|
+
* ALWAYS session-authed: there's no standalone share-token mode the way
|
|
501
|
+
* `MatterfactArtifact` has, so an ancestor `MatterfactAuthProvider` is required. With
|
|
502
|
+
* none present (or a provider with no `publishableKey`), there's no way for the
|
|
503
|
+
* iframe to authenticate — matching `MatterfactArtifact`'s own no-token-no-provider
|
|
504
|
+
* decision, no iframe is built at all; the same "incomplete link" placeholder shape
|
|
505
|
+
* is rendered instead of throwing.
|
|
377
506
|
*/
|
|
378
|
-
declare function
|
|
507
|
+
declare function MatterfactDoc({ docKey, ticker, version, theme: themeProp, params, className, style, }: MatterfactDocProps): react_jsx_runtime.JSX.Element;
|
|
379
508
|
|
|
380
|
-
export { type HostResolvers, type HostToolDef, MatterfactAgent, type MatterfactAgentProps, MatterfactArtifact, type MatterfactArtifactProps };
|
|
509
|
+
export { type HoistActionsConfig, type HostResolvers, type HostToolDef, MatterfactAgent, type MatterfactAgentProps, MatterfactArtifact, type MatterfactArtifactProps, MatterfactAuthProvider, type MatterfactAuthProviderProps, MatterfactDoc, type MatterfactDocParams, type MatterfactDocProps };
|
package/dist/react.d.ts
CHANGED
|
@@ -159,6 +159,44 @@ type MatterfactEvent = {
|
|
|
159
159
|
source: 'user' | 'context';
|
|
160
160
|
};
|
|
161
161
|
|
|
162
|
+
interface MatterfactAuthProviderProps {
|
|
163
|
+
/**
|
|
164
|
+
* Publishable key (`pk_…`) identifying this embed app. Public and origin-scoped —
|
|
165
|
+
* meant to sit in HTML. Every `MatterfactAgent`/`MatterfactArtifact`/`MatterfactDoc`
|
|
166
|
+
* under this provider inherits it, so you set it once here rather than on each child.
|
|
167
|
+
*/
|
|
168
|
+
publishableKey: string;
|
|
169
|
+
/**
|
|
170
|
+
* Origin serving the matterfact widgets (the app that hosts `/embed/*`). Defaults to
|
|
171
|
+
* production. This is the ONE place to set it — every child inherits it, and the
|
|
172
|
+
* `widgetOrigin` prop on `MatterfactAgent`/`MatterfactArtifact` is deprecated in
|
|
173
|
+
* favour of setting it here.
|
|
174
|
+
*/
|
|
175
|
+
widgetOrigin?: string;
|
|
176
|
+
/**
|
|
177
|
+
* HOST-AUTH PASSTHROUGH (trusted first-party embeds). Return a token this matterfact
|
|
178
|
+
* deployment already trusts — the host app's Entra/Firebase token, whatever its auth
|
|
179
|
+
* provider verifies — and every child iframe signs in SILENTLY with it, no separate
|
|
180
|
+
* sign-in. The provider brokers it: when a child needs auth it asks the provider,
|
|
181
|
+
* which calls this and hands the token back (over `postMessage`, pinned to the widget
|
|
182
|
+
* origin). Called on demand so the token can be fresh; may be async. Omit for the
|
|
183
|
+
* standard interactive sign-in.
|
|
184
|
+
*/
|
|
185
|
+
getAuthToken?: () => string | null | Promise<string | null>;
|
|
186
|
+
/** Colour theme applied to every child widget. Falls back to `'auto'`. */
|
|
187
|
+
theme?: 'light' | 'dark' | 'auto';
|
|
188
|
+
/**
|
|
189
|
+
* Unified telemetry hook, fired for every embed lifecycle moment (`ready`, `auth`,
|
|
190
|
+
* `error`, …) across the children — pipe the whole embed into your own observability
|
|
191
|
+
* from one place. Never blocks or breaks a widget; a throw here is swallowed.
|
|
192
|
+
*/
|
|
193
|
+
onEvent?: (e: MatterfactEvent) => void;
|
|
194
|
+
/** The embed components (`MatterfactAgent`/`MatterfactArtifact`/`MatterfactDoc`) that
|
|
195
|
+
* inherit this provider's config. */
|
|
196
|
+
children: React.ReactNode;
|
|
197
|
+
}
|
|
198
|
+
declare function MatterfactAuthProvider({ publishableKey, widgetOrigin, getAuthToken, theme, onEvent, children, }: MatterfactAuthProviderProps): react_jsx_runtime.JSX.Element;
|
|
199
|
+
|
|
162
200
|
/**
|
|
163
201
|
* The Hoist adapter — a pure transform from a `HoistRuntime` (already read out of
|
|
164
202
|
* `window.XH` by hoist-runtime.ts) into the context/snapshot shapes context.ts sends
|
|
@@ -239,12 +277,25 @@ interface HostToolDef {
|
|
|
239
277
|
}
|
|
240
278
|
|
|
241
279
|
interface MatterfactAgentProps {
|
|
242
|
-
/**
|
|
243
|
-
|
|
244
|
-
|
|
280
|
+
/**
|
|
281
|
+
* Publishable key (`pk_…`) identifying this embed app. Public, origin-scoped.
|
|
282
|
+
*
|
|
283
|
+
* Optional here ONLY because it can instead come from an ancestor
|
|
284
|
+
* `MatterfactAuthProvider` (`prop ?? context`) — one of the two must supply it,
|
|
285
|
+
* or the component throws at mount.
|
|
286
|
+
*/
|
|
287
|
+
publishableKey?: string;
|
|
288
|
+
/**
|
|
289
|
+
* Origin serving the widget (the matterfact app). Defaults to production.
|
|
290
|
+
*
|
|
291
|
+
* @deprecated Prefer setting this once on `<MatterfactAuthProvider>` and letting
|
|
292
|
+
* every `<MatterfactAgent>`/`<MatterfactArtifact>` underneath inherit it. Still
|
|
293
|
+
* fully supported standalone (no provider) — resolved as `prop ?? context ?? default`.
|
|
294
|
+
*/
|
|
245
295
|
widgetOrigin?: string;
|
|
246
296
|
/** Label for THIS embedding, for per-surface usage/history attribution. */
|
|
247
297
|
surface?: string;
|
|
298
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
248
299
|
theme?: 'light' | 'dark' | 'auto';
|
|
249
300
|
/**
|
|
250
301
|
* HOST-AUTH PASSTHROUGH (trusted first-party embeds only). Return a token this
|
|
@@ -252,6 +303,8 @@ interface MatterfactAgentProps {
|
|
|
252
303
|
* token, whatever its auth provider verifies — and the widget signs in SILENTLY with
|
|
253
304
|
* it, no separate sign-in. Called on demand so the token can be fresh. Omit for the
|
|
254
305
|
* standard popup/inline sign-in (third-party hosts).
|
|
306
|
+
*
|
|
307
|
+
* Resolved as `prop ?? MatterfactAuthProvider's getAuthToken`.
|
|
255
308
|
*/
|
|
256
309
|
getAuthToken?: () => string | null | Promise<string | null>;
|
|
257
310
|
/**
|
|
@@ -356,25 +409,101 @@ interface MatterfactAgentProps {
|
|
|
356
409
|
*/
|
|
357
410
|
onEvent?: (e: MatterfactEvent) => void;
|
|
358
411
|
}
|
|
359
|
-
declare function MatterfactAgent({ publishableKey, widgetOrigin, surface, theme, getAuthToken, getPageContext, inline, className, style, pageContext, dev, actions, sitemap, artifacts, resolve, tools, onToolEvent, onEvent, }: MatterfactAgentProps): react_jsx_runtime.JSX.Element | null;
|
|
412
|
+
declare function MatterfactAgent({ publishableKey: publishableKeyProp, widgetOrigin: widgetOriginProp, surface, theme: themeProp, getAuthToken: getAuthTokenProp, getPageContext, inline, className, style, pageContext, dev, actions, sitemap, artifacts, resolve, tools, onToolEvent, onEvent, }: MatterfactAgentProps): react_jsx_runtime.JSX.Element | null;
|
|
360
413
|
interface MatterfactArtifactProps {
|
|
361
|
-
/** The artifact's slug
|
|
362
|
-
|
|
414
|
+
/** The artifact's name (its slug). */
|
|
415
|
+
name?: string;
|
|
416
|
+
/**
|
|
417
|
+
* @deprecated Use `name` instead. Still accepted as an alias — `name` wins
|
|
418
|
+
* when both are given.
|
|
419
|
+
*/
|
|
420
|
+
slug?: string;
|
|
363
421
|
/** The artifact owner's email — same as the Share dialog's `?owner=` param. */
|
|
364
422
|
owner: string;
|
|
365
|
-
/**
|
|
366
|
-
|
|
367
|
-
|
|
423
|
+
/**
|
|
424
|
+
* The artifact's read-only capability token — same as the Share dialog's `?t=`
|
|
425
|
+
* param. This is the standalone share-link path.
|
|
426
|
+
*
|
|
427
|
+
* @deprecated Prefer an ancestor `MatterfactAuthProvider` instead: with no
|
|
428
|
+
* `token`, the iframe authenticates the same way `MatterfactAgent` does — the
|
|
429
|
+
* provider's publishable key (`?k=`) plus the host page's origin (`?o=`) —
|
|
430
|
+
* instead of a share-link capability token. `token` still wins when both a
|
|
431
|
+
* token and a provider are present.
|
|
432
|
+
*/
|
|
433
|
+
token?: string;
|
|
434
|
+
/**
|
|
435
|
+
* Origin serving the widget (the matterfact app). Defaults to production.
|
|
436
|
+
*
|
|
437
|
+
* @deprecated Prefer setting this once on `<MatterfactAuthProvider>` and
|
|
438
|
+
* letting every `<MatterfactAgent>`/`<MatterfactArtifact>` underneath inherit
|
|
439
|
+
* it. Still fully supported standalone (no provider) — resolved as
|
|
440
|
+
* `prop ?? context ?? default`.
|
|
441
|
+
*/
|
|
368
442
|
widgetOrigin?: string;
|
|
443
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
369
444
|
theme?: 'auto' | 'light' | 'dark';
|
|
445
|
+
/** Applied to the `<iframe>` element the artifact renders into. */
|
|
370
446
|
className?: string;
|
|
447
|
+
/** Applied to the `<iframe>` element. Merged over the default fill. */
|
|
371
448
|
style?: React.CSSProperties;
|
|
372
449
|
}
|
|
373
450
|
/**
|
|
374
451
|
* Render a matterfact artifact inline in a host page. Chrome-free, cross-origin. When a
|
|
375
452
|
* MatterfactAgent is embedded on the same page, the loader sees this iframe and both
|
|
376
453
|
* makes the agent aware of it and (via its token) lets the agent read its data.
|
|
454
|
+
*
|
|
455
|
+
* Two auth modes, `token` wins when both are available:
|
|
456
|
+
* - TOKEN mode (`token` given): a standalone share link, `?t=`. This is the LIVE
|
|
457
|
+
* third-party embed path — its `src` format must stay byte-identical.
|
|
458
|
+
* - SESSION mode (no `token`, an ancestor `MatterfactAuthProvider` is present):
|
|
459
|
+
* tokenless, `?k=<publishableKey>&o=<host origin>`, the same authentication
|
|
460
|
+
* `MatterfactAgent` uses.
|
|
461
|
+
* With neither, there is no way for the iframe to authenticate, so no iframe is
|
|
462
|
+
* built at all — matching the "incomplete link" placeholder the embed artifact
|
|
463
|
+
* page itself renders for a missing owner/token.
|
|
464
|
+
*/
|
|
465
|
+
declare function MatterfactArtifact({ name: nameProp, slug, owner, token, widgetOrigin: widgetOriginProp, theme: themeProp, className, style, }: MatterfactArtifactProps): react_jsx_runtime.JSX.Element;
|
|
466
|
+
/** The two live-drivable doc params, mirroring `EmbedDocumentPage`'s `HostDocParams`. */
|
|
467
|
+
type MatterfactDocParams = {
|
|
468
|
+
ticker?: string;
|
|
469
|
+
version?: string;
|
|
470
|
+
};
|
|
471
|
+
interface MatterfactDocProps {
|
|
472
|
+
/** The document catalog key (`EmbedDocumentPage`'s `?key=`). Fixed at mount — not
|
|
473
|
+
* drivable via `params`, unlike `ticker`/`version`. */
|
|
474
|
+
docKey: string;
|
|
475
|
+
/** Initial ticker, seeds the iframe's `?ticker=` query param. */
|
|
476
|
+
ticker?: string;
|
|
477
|
+
/** Initial version. Always sent explicitly on the iframe `src` — defaults to
|
|
478
|
+
* `'latest'` rather than being omitted, so the doc page never has to guess. */
|
|
479
|
+
version?: 'latest' | `${number}-${number}-${number}`;
|
|
480
|
+
/** Resolved as `prop ?? MatterfactAuthProvider's theme ?? 'auto'`. */
|
|
481
|
+
theme?: 'auto' | 'light' | 'dark';
|
|
482
|
+
/**
|
|
483
|
+
* Drive the document's ticker/version from your page after mount. Pass your whole
|
|
484
|
+
* param state; only the keys that actually changed since the last render are pushed
|
|
485
|
+
* to the iframe (as `host.docParams`), and the full set is re-sent once the iframe
|
|
486
|
+
* loads. A push is authoritative for every key it names — dropping a key stops
|
|
487
|
+
* driving it, it does not reset it. Omit this prop entirely for a static document
|
|
488
|
+
* whose ticker/version never change after mount.
|
|
489
|
+
*/
|
|
490
|
+
params?: MatterfactDocParams;
|
|
491
|
+
/** Applied to the `<iframe>` element the document renders into. */
|
|
492
|
+
className?: string;
|
|
493
|
+
/** Applied to the `<iframe>` element. Merged over the default fill. */
|
|
494
|
+
style?: React.CSSProperties;
|
|
495
|
+
}
|
|
496
|
+
/**
|
|
497
|
+
* Render a matterfact catalog document inline in a host page — the `MatterfactArtifact`
|
|
498
|
+
* counterpart for a published document/report instead of an artifact board.
|
|
499
|
+
*
|
|
500
|
+
* ALWAYS session-authed: there's no standalone share-token mode the way
|
|
501
|
+
* `MatterfactArtifact` has, so an ancestor `MatterfactAuthProvider` is required. With
|
|
502
|
+
* none present (or a provider with no `publishableKey`), there's no way for the
|
|
503
|
+
* iframe to authenticate — matching `MatterfactArtifact`'s own no-token-no-provider
|
|
504
|
+
* decision, no iframe is built at all; the same "incomplete link" placeholder shape
|
|
505
|
+
* is rendered instead of throwing.
|
|
377
506
|
*/
|
|
378
|
-
declare function
|
|
507
|
+
declare function MatterfactDoc({ docKey, ticker, version, theme: themeProp, params, className, style, }: MatterfactDocProps): react_jsx_runtime.JSX.Element;
|
|
379
508
|
|
|
380
|
-
export { type HostResolvers, type HostToolDef, MatterfactAgent, type MatterfactAgentProps, MatterfactArtifact, type MatterfactArtifactProps };
|
|
509
|
+
export { type HoistActionsConfig, type HostResolvers, type HostToolDef, MatterfactAgent, type MatterfactAgentProps, MatterfactArtifact, type MatterfactArtifactProps, MatterfactAuthProvider, type MatterfactAuthProviderProps, MatterfactDoc, type MatterfactDocParams, type MatterfactDocProps };
|
package/dist/react.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"use client";
|
|
3
3
|
|
|
4
4
|
// src/react.tsx
|
|
5
|
-
import { useEffect, useRef } from "react";
|
|
5
|
+
import { useEffect as useEffect2, useRef } from "react";
|
|
6
6
|
|
|
7
7
|
// src/protocol.ts
|
|
8
8
|
var PROTOCOL_VERSION = 3;
|
|
@@ -806,9 +806,63 @@ function mount(config) {
|
|
|
806
806
|
return host;
|
|
807
807
|
}
|
|
808
808
|
|
|
809
|
-
// src/react.tsx
|
|
809
|
+
// src/react-context.tsx
|
|
810
|
+
import { createContext, useContext, useEffect, useMemo } from "react";
|
|
810
811
|
import { jsx } from "react/jsx-runtime";
|
|
811
812
|
var DEFAULT_ORIGIN = "https://app.matterfact.com";
|
|
813
|
+
var MatterfactAuthContext = createContext(null);
|
|
814
|
+
function useMatterfactConfig() {
|
|
815
|
+
return useContext(MatterfactAuthContext);
|
|
816
|
+
}
|
|
817
|
+
function MatterfactAuthProvider({
|
|
818
|
+
publishableKey,
|
|
819
|
+
widgetOrigin,
|
|
820
|
+
getAuthToken,
|
|
821
|
+
theme,
|
|
822
|
+
onEvent,
|
|
823
|
+
children
|
|
824
|
+
}) {
|
|
825
|
+
const resolvedWidgetOrigin = widgetOrigin || DEFAULT_ORIGIN;
|
|
826
|
+
const value = useMemo(
|
|
827
|
+
() => ({
|
|
828
|
+
publishableKey,
|
|
829
|
+
widgetOrigin: resolvedWidgetOrigin,
|
|
830
|
+
getAuthToken,
|
|
831
|
+
theme: theme || "auto",
|
|
832
|
+
onEvent
|
|
833
|
+
}),
|
|
834
|
+
[publishableKey, resolvedWidgetOrigin, getAuthToken, theme, onEvent]
|
|
835
|
+
);
|
|
836
|
+
useEffect(() => {
|
|
837
|
+
if (typeof window === "undefined" || !getAuthToken) return;
|
|
838
|
+
let inflight = null;
|
|
839
|
+
const onMessage = (e) => {
|
|
840
|
+
if (e.origin !== resolvedWidgetOrigin) return;
|
|
841
|
+
if (!e.data || e.data.type !== "mf.hostAuth.request") return;
|
|
842
|
+
const source = e.source;
|
|
843
|
+
if (!source) return;
|
|
844
|
+
try {
|
|
845
|
+
inflight = inflight ?? Promise.resolve(getAuthToken()).catch(() => null);
|
|
846
|
+
} catch {
|
|
847
|
+
return;
|
|
848
|
+
}
|
|
849
|
+
const p = inflight;
|
|
850
|
+
void p.then((token) => {
|
|
851
|
+
if (p === inflight) inflight = null;
|
|
852
|
+
if (typeof token === "string" && token) {
|
|
853
|
+
source.postMessage({ type: "mf.hostAuth.grant", token }, resolvedWidgetOrigin);
|
|
854
|
+
}
|
|
855
|
+
});
|
|
856
|
+
};
|
|
857
|
+
window.addEventListener("message", onMessage);
|
|
858
|
+
return () => window.removeEventListener("message", onMessage);
|
|
859
|
+
}, [getAuthToken, resolvedWidgetOrigin]);
|
|
860
|
+
return /* @__PURE__ */ jsx(MatterfactAuthContext.Provider, { value, children });
|
|
861
|
+
}
|
|
862
|
+
|
|
863
|
+
// src/react.tsx
|
|
864
|
+
import { jsx as jsx2 } from "react/jsx-runtime";
|
|
865
|
+
var DEFAULT_ORIGIN2 = "https://app.matterfact.com";
|
|
812
866
|
function writeActionsGlobal(actions) {
|
|
813
867
|
if (typeof window === "undefined") return;
|
|
814
868
|
const w = window;
|
|
@@ -852,11 +906,11 @@ function toolDescriptorKey(artifacts, resolve, tools) {
|
|
|
852
906
|
});
|
|
853
907
|
}
|
|
854
908
|
function MatterfactAgent({
|
|
855
|
-
publishableKey,
|
|
856
|
-
widgetOrigin,
|
|
909
|
+
publishableKey: publishableKeyProp,
|
|
910
|
+
widgetOrigin: widgetOriginProp,
|
|
857
911
|
surface = "",
|
|
858
|
-
theme
|
|
859
|
-
getAuthToken,
|
|
912
|
+
theme: themeProp,
|
|
913
|
+
getAuthToken: getAuthTokenProp,
|
|
860
914
|
getPageContext,
|
|
861
915
|
inline = false,
|
|
862
916
|
className,
|
|
@@ -871,6 +925,16 @@ function MatterfactAgent({
|
|
|
871
925
|
onToolEvent,
|
|
872
926
|
onEvent
|
|
873
927
|
}) {
|
|
928
|
+
const ctx = useMatterfactConfig();
|
|
929
|
+
const publishableKey = publishableKeyProp ?? ctx?.publishableKey;
|
|
930
|
+
if (!publishableKey) {
|
|
931
|
+
throw new Error(
|
|
932
|
+
"MatterfactAgent requires publishableKey (as a prop or via MatterfactAuthProvider)"
|
|
933
|
+
);
|
|
934
|
+
}
|
|
935
|
+
const widgetOrigin = widgetOriginProp ?? ctx?.widgetOrigin ?? DEFAULT_ORIGIN2;
|
|
936
|
+
const getAuthToken = getAuthTokenProp ?? ctx?.getAuthToken;
|
|
937
|
+
const theme = themeProp ?? ctx?.theme ?? "auto";
|
|
874
938
|
const authRef = useRef(getAuthToken);
|
|
875
939
|
authRef.current = getAuthToken;
|
|
876
940
|
const pageContextRef = useRef(getPageContext);
|
|
@@ -880,21 +944,22 @@ function MatterfactAgent({
|
|
|
880
944
|
const actionsKey = JSON.stringify(actions ?? null);
|
|
881
945
|
const slot = useRef(null);
|
|
882
946
|
const sitemapKey = JSON.stringify(sitemap ?? null);
|
|
883
|
-
|
|
947
|
+
useEffect2(() => {
|
|
884
948
|
writeSitemapGlobal(sitemap);
|
|
885
949
|
}, [sitemapKey]);
|
|
886
|
-
|
|
950
|
+
useEffect2(() => {
|
|
887
951
|
writeToolGlobals(artifacts, resolve, tools, onToolEvent, onEvent);
|
|
888
952
|
});
|
|
889
953
|
const toolsKey = toolDescriptorKey(artifacts, resolve, tools);
|
|
890
|
-
|
|
954
|
+
useEffect2(() => {
|
|
891
955
|
if (typeof window === "undefined") return;
|
|
892
956
|
if (inline && !slot.current) return;
|
|
893
957
|
writeActionsGlobal(actionsRef.current);
|
|
894
958
|
writeToolGlobals(artifacts, resolve, tools, onToolEvent, onEvent);
|
|
895
959
|
const config = {
|
|
896
960
|
publishableKey,
|
|
897
|
-
|
|
961
|
+
// Already fully resolved above (prop ?? context ?? DEFAULT_ORIGIN).
|
|
962
|
+
origin: widgetOrigin,
|
|
898
963
|
theme,
|
|
899
964
|
surface,
|
|
900
965
|
// Always present; a null return (no getAuthToken supplied) makes the core fall
|
|
@@ -936,7 +1001,7 @@ function MatterfactAgent({
|
|
|
936
1001
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
937
1002
|
]);
|
|
938
1003
|
if (!inline) return null;
|
|
939
|
-
return /* @__PURE__ */
|
|
1004
|
+
return /* @__PURE__ */ jsx2(
|
|
940
1005
|
"div",
|
|
941
1006
|
{
|
|
942
1007
|
ref: slot,
|
|
@@ -947,29 +1012,138 @@ function MatterfactAgent({
|
|
|
947
1012
|
}
|
|
948
1013
|
var DEFAULT_ARTIFACT_ORIGIN = "https://app.matterfact.com";
|
|
949
1014
|
function MatterfactArtifact({
|
|
1015
|
+
name: nameProp,
|
|
950
1016
|
slug,
|
|
951
1017
|
owner,
|
|
952
1018
|
token,
|
|
953
|
-
widgetOrigin,
|
|
954
|
-
theme
|
|
1019
|
+
widgetOrigin: widgetOriginProp,
|
|
1020
|
+
theme: themeProp,
|
|
955
1021
|
className,
|
|
956
1022
|
style
|
|
957
1023
|
}) {
|
|
958
|
-
const
|
|
959
|
-
const
|
|
960
|
-
|
|
1024
|
+
const ctx = useMatterfactConfig();
|
|
1025
|
+
const artifactName = nameProp ?? slug;
|
|
1026
|
+
if (!artifactName) {
|
|
1027
|
+
throw new Error(
|
|
1028
|
+
"MatterfactArtifact requires name (or its deprecated alias, slug)"
|
|
1029
|
+
);
|
|
1030
|
+
}
|
|
1031
|
+
const origin = widgetOriginProp ?? ctx?.widgetOrigin ?? DEFAULT_ARTIFACT_ORIGIN;
|
|
1032
|
+
const theme = themeProp ?? ctx?.theme ?? "auto";
|
|
1033
|
+
let src;
|
|
1034
|
+
if (token) {
|
|
1035
|
+
src = `${origin}/embed/artifacts/${encodeURIComponent(artifactName)}?owner=${encodeURIComponent(owner)}&t=${encodeURIComponent(token)}&theme=${theme}`;
|
|
1036
|
+
} else if (ctx) {
|
|
1037
|
+
const hostOrigin = typeof window === "undefined" ? "" : window.location.origin;
|
|
1038
|
+
src = `${origin}/embed/artifacts/${encodeURIComponent(artifactName)}?owner=${encodeURIComponent(owner)}&k=${encodeURIComponent(ctx.publishableKey)}&o=${encodeURIComponent(hostOrigin)}&theme=${theme}`;
|
|
1039
|
+
} else {
|
|
1040
|
+
return /* @__PURE__ */ jsx2(
|
|
1041
|
+
"div",
|
|
1042
|
+
{
|
|
1043
|
+
className,
|
|
1044
|
+
style: {
|
|
1045
|
+
width: "100%",
|
|
1046
|
+
height: 600,
|
|
1047
|
+
display: "flex",
|
|
1048
|
+
alignItems: "center",
|
|
1049
|
+
justifyContent: "center",
|
|
1050
|
+
textAlign: "center",
|
|
1051
|
+
...style
|
|
1052
|
+
},
|
|
1053
|
+
children: /* @__PURE__ */ jsx2("p", { children: "This embedded artifact link is incomplete." })
|
|
1054
|
+
}
|
|
1055
|
+
);
|
|
1056
|
+
}
|
|
1057
|
+
return /* @__PURE__ */ jsx2(
|
|
961
1058
|
"iframe",
|
|
962
1059
|
{
|
|
963
1060
|
src,
|
|
964
|
-
title: `matterfact artifact ${
|
|
1061
|
+
title: `matterfact artifact ${artifactName}`,
|
|
965
1062
|
className,
|
|
966
1063
|
style: { width: "100%", height: 600, border: 0, ...style },
|
|
967
1064
|
sandbox: "allow-scripts allow-same-origin allow-forms allow-popups allow-popups-to-escape-sandbox allow-downloads"
|
|
968
1065
|
}
|
|
969
1066
|
);
|
|
970
1067
|
}
|
|
1068
|
+
var DEFAULT_DOC_ORIGIN = "https://app.matterfact.com";
|
|
1069
|
+
function diffDocParams(params, sent) {
|
|
1070
|
+
const changed = {};
|
|
1071
|
+
for (const [key, value] of Object.entries(params)) {
|
|
1072
|
+
if (value === void 0) continue;
|
|
1073
|
+
const snapshot = JSON.stringify(value);
|
|
1074
|
+
if (sent.get(key) === snapshot) continue;
|
|
1075
|
+
changed[key] = value;
|
|
1076
|
+
sent.set(key, snapshot);
|
|
1077
|
+
}
|
|
1078
|
+
return changed;
|
|
1079
|
+
}
|
|
1080
|
+
function MatterfactDoc({
|
|
1081
|
+
docKey,
|
|
1082
|
+
ticker = "",
|
|
1083
|
+
version = "latest",
|
|
1084
|
+
theme: themeProp,
|
|
1085
|
+
params,
|
|
1086
|
+
className,
|
|
1087
|
+
style
|
|
1088
|
+
}) {
|
|
1089
|
+
const ctx = useMatterfactConfig();
|
|
1090
|
+
const iframeRef = useRef(null);
|
|
1091
|
+
const sentParamsRef = useRef(/* @__PURE__ */ new Map());
|
|
1092
|
+
const origin = ctx?.widgetOrigin ?? DEFAULT_DOC_ORIGIN;
|
|
1093
|
+
const paramsKey = JSON.stringify(params ?? null);
|
|
1094
|
+
const pushParams = (force) => {
|
|
1095
|
+
if (!params) return;
|
|
1096
|
+
const win = iframeRef.current?.contentWindow;
|
|
1097
|
+
if (!win) return;
|
|
1098
|
+
if (force) sentParamsRef.current.clear();
|
|
1099
|
+
const changed = diffDocParams(params, sentParamsRef.current);
|
|
1100
|
+
if (Object.keys(changed).length === 0) return;
|
|
1101
|
+
win.postMessage({ type: "host.docParams", params: changed }, origin);
|
|
1102
|
+
};
|
|
1103
|
+
useEffect2(() => {
|
|
1104
|
+
pushParams(false);
|
|
1105
|
+
}, [paramsKey]);
|
|
1106
|
+
if (!docKey) {
|
|
1107
|
+
throw new Error("MatterfactDoc requires docKey");
|
|
1108
|
+
}
|
|
1109
|
+
if (!ctx || !ctx.publishableKey) {
|
|
1110
|
+
return /* @__PURE__ */ jsx2(
|
|
1111
|
+
"div",
|
|
1112
|
+
{
|
|
1113
|
+
className,
|
|
1114
|
+
style: {
|
|
1115
|
+
width: "100%",
|
|
1116
|
+
height: 600,
|
|
1117
|
+
display: "flex",
|
|
1118
|
+
alignItems: "center",
|
|
1119
|
+
justifyContent: "center",
|
|
1120
|
+
textAlign: "center",
|
|
1121
|
+
...style
|
|
1122
|
+
},
|
|
1123
|
+
children: /* @__PURE__ */ jsx2("p", { children: "This embedded document link is incomplete." })
|
|
1124
|
+
}
|
|
1125
|
+
);
|
|
1126
|
+
}
|
|
1127
|
+
const theme = themeProp ?? ctx.theme ?? "auto";
|
|
1128
|
+
const hostOrigin = typeof window === "undefined" ? "" : window.location.origin;
|
|
1129
|
+
const src = `${origin}/embed/document?k=${encodeURIComponent(ctx.publishableKey)}&o=${encodeURIComponent(hostOrigin)}&key=${encodeURIComponent(docKey)}&ticker=${encodeURIComponent(ticker)}&version=${encodeURIComponent(version)}&theme=${theme}`;
|
|
1130
|
+
return /* @__PURE__ */ jsx2(
|
|
1131
|
+
"iframe",
|
|
1132
|
+
{
|
|
1133
|
+
ref: iframeRef,
|
|
1134
|
+
src,
|
|
1135
|
+
title: `matterfact document ${docKey}`,
|
|
1136
|
+
className,
|
|
1137
|
+
style: { width: "100%", height: 600, border: 0, ...style },
|
|
1138
|
+
sandbox: "allow-scripts allow-same-origin allow-forms allow-popups allow-popups-to-escape-sandbox allow-downloads",
|
|
1139
|
+
onLoad: () => pushParams(true)
|
|
1140
|
+
}
|
|
1141
|
+
);
|
|
1142
|
+
}
|
|
971
1143
|
export {
|
|
972
1144
|
MatterfactAgent,
|
|
973
|
-
MatterfactArtifact
|
|
1145
|
+
MatterfactArtifact,
|
|
1146
|
+
MatterfactAuthProvider,
|
|
1147
|
+
MatterfactDoc
|
|
974
1148
|
};
|
|
975
1149
|
//# sourceMappingURL=react.js.map
|