@burdenoff/fe-libs 2026.521.1 → 2026.521.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/shared/events/index.d.ts +13 -1
- package/dist/shared/events/index.d.ts.map +1 -1
- package/dist/shared/plugins/iframe-mount/PluginIframe.d.ts +75 -0
- package/dist/shared/plugins/iframe-mount/PluginIframe.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/PluginIframe.js +147 -0
- package/dist/shared/plugins/iframe-mount/PluginMount.d.ts +59 -0
- package/dist/shared/plugins/iframe-mount/PluginMount.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/PluginMount.js +129 -0
- package/dist/shared/plugins/iframe-mount/client/index.d.ts +3 -0
- package/dist/shared/plugins/iframe-mount/client/index.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/client/message-bus.d.ts +71 -0
- package/dist/shared/plugins/iframe-mount/client/message-bus.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/client/message-bus.js +65 -0
- package/dist/shared/plugins/iframe-mount/client/rpc.d.ts +25 -0
- package/dist/shared/plugins/iframe-mount/client/rpc.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/client/rpc.js +63 -0
- package/dist/shared/plugins/iframe-mount/index.d.ts +6 -0
- package/dist/shared/plugins/iframe-mount/index.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/index.js +4 -0
- package/dist/shared/plugins/iframe-mount/protocol/contribution.d.ts +83 -0
- package/dist/shared/plugins/iframe-mount/protocol/contribution.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/protocol/envelope.d.ts +136 -0
- package/dist/shared/plugins/iframe-mount/protocol/envelope.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/protocol/envelope.js +10 -0
- package/dist/shared/plugins/iframe-mount/protocol/index.d.ts +3 -0
- package/dist/shared/plugins/iframe-mount/protocol/index.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/sandbox.d.ts +3 -0
- package/dist/shared/plugins/iframe-mount/sandbox.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/sandbox.js +19 -0
- package/dist/shared/plugins/iframe-mount/types.d.ts +57 -0
- package/dist/shared/plugins/iframe-mount/types.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/useFetchContributions.d.ts +31 -0
- package/dist/shared/plugins/iframe-mount/useFetchContributions.d.ts.map +1 -0
- package/dist/shared/plugins/iframe-mount/useFetchContributions.js +68 -0
- package/dist/shared/plugins/index.d.ts +1 -0
- package/dist/shared/plugins/index.d.ts.map +1 -1
- package/dist/shared-events.js +27 -15
- package/dist/shared-plugins.js +6 -1
- package/package.json +1 -1
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { isEnvelope as e, isPluginEnvelope as t } from "../protocol/envelope.js";
|
|
2
|
+
//#region src/shared/plugins/iframe-mount/client/message-bus.ts
|
|
3
|
+
function n(e, t) {
|
|
4
|
+
return t.includes("*") ? !0 : t.includes(e);
|
|
5
|
+
}
|
|
6
|
+
function r() {
|
|
7
|
+
if (typeof globalThis > "u" || !("window" in globalThis)) throw Error("No `window` available — postMessage transport unavailable");
|
|
8
|
+
return globalThis.window;
|
|
9
|
+
}
|
|
10
|
+
var i = class {
|
|
11
|
+
handlers = /* @__PURE__ */ new Set();
|
|
12
|
+
disposed = !1;
|
|
13
|
+
listener;
|
|
14
|
+
hostWindow;
|
|
15
|
+
constructor(e) {
|
|
16
|
+
this.options = e, this.hostWindow = e.window ?? r(), this.listener = (e) => this.handleMessage(e), this.hostWindow.addEventListener("message", this.listener);
|
|
17
|
+
}
|
|
18
|
+
on(e) {
|
|
19
|
+
return this.handlers.add(e), () => this.handlers.delete(e);
|
|
20
|
+
}
|
|
21
|
+
dispose() {
|
|
22
|
+
this.disposed || (this.disposed = !0, this.handlers.clear(), this.hostWindow.removeEventListener("message", this.listener));
|
|
23
|
+
}
|
|
24
|
+
send(e) {
|
|
25
|
+
if (!this.disposed) {
|
|
26
|
+
if (e.v !== 1) throw Error(`Refusing to send envelope with version ${e.v} — runtime expects v1`);
|
|
27
|
+
this.target.postMessage(e, this.targetOrigin);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
handleMessage(t) {
|
|
31
|
+
if (!this.disposed && n(t.origin, this.options.allowedOrigins) && !(this.options.expectedSource !== void 0 && this.options.expectedSource !== null && t.source !== this.options.expectedSource) && e(t.data) && this.isExpectedDirection(t.data)) for (let e of this.handlers) try {
|
|
32
|
+
e(t.data);
|
|
33
|
+
} catch (e) {
|
|
34
|
+
console.error("[vibecontrols-ui-plugin-sdk] handler threw", e);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
}, a = class extends i {
|
|
38
|
+
iframe;
|
|
39
|
+
origin;
|
|
40
|
+
constructor(e) {
|
|
41
|
+
super(e), this.iframe = e.iframe, this.origin = e.allowedOrigins.length === 1 ? e.allowedOrigins[0] : e.allowedOrigins[0] ?? "*";
|
|
42
|
+
}
|
|
43
|
+
get target() {
|
|
44
|
+
let e = this.iframe.contentWindow;
|
|
45
|
+
if (!e) throw Error("iframe.contentWindow is null — iframe is not yet loaded");
|
|
46
|
+
return e;
|
|
47
|
+
}
|
|
48
|
+
get targetOrigin() {
|
|
49
|
+
return this.origin;
|
|
50
|
+
}
|
|
51
|
+
isExpectedDirection(e) {
|
|
52
|
+
return t(e);
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
function o(e, t, n) {
|
|
56
|
+
return {
|
|
57
|
+
v: 1,
|
|
58
|
+
source: "host",
|
|
59
|
+
kind: e,
|
|
60
|
+
payload: t,
|
|
61
|
+
requestId: n
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
//#endregion
|
|
65
|
+
export { a as ParentMessageBus, o as buildHostEnvelope };
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { HostRpcProgressPayload, HostRpcResponsePayload } from '../protocol/envelope.js';
|
|
2
|
+
export type RpcMethod = string;
|
|
3
|
+
export interface RpcCallOpts<TProgress = unknown> {
|
|
4
|
+
/** Receive intermediate progress events for a streaming call. */
|
|
5
|
+
onProgress?: (progress: TProgress) => void;
|
|
6
|
+
/** Optional abort. The dispatcher fires `controller.abort` reasons through. */
|
|
7
|
+
signal?: AbortSignal;
|
|
8
|
+
/** Overrides the default 30s timeout. Set to `null` to disable. */
|
|
9
|
+
timeoutMs?: number | null;
|
|
10
|
+
}
|
|
11
|
+
export interface RpcSender {
|
|
12
|
+
/** Push the outbound RPC over the underlying transport. */
|
|
13
|
+
send(requestId: string, method: RpcMethod, args: unknown, streaming: boolean): void;
|
|
14
|
+
}
|
|
15
|
+
export declare class RpcDispatcher {
|
|
16
|
+
private readonly sender;
|
|
17
|
+
private readonly pending;
|
|
18
|
+
constructor(sender: RpcSender);
|
|
19
|
+
call<TResult = unknown, TProgress = unknown>(method: RpcMethod, args: unknown, opts?: RpcCallOpts<TProgress>): Promise<TResult>;
|
|
20
|
+
handleResponse(requestId: string, payload: HostRpcResponsePayload): void;
|
|
21
|
+
handleProgress(requestId: string, payload: HostRpcProgressPayload): void;
|
|
22
|
+
rejectAll(reason: unknown): void;
|
|
23
|
+
private settle;
|
|
24
|
+
}
|
|
25
|
+
//# sourceMappingURL=rpc.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rpc.d.ts","sourceRoot":"","sources":["../../../../../src/shared/plugins/iframe-mount/client/rpc.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAEH,OAAO,KAAK,EAAE,sBAAsB,EAAE,sBAAsB,EAAE,MAAM,yBAAyB,CAAC;AAE9F,MAAM,MAAM,SAAS,GAAG,MAAM,CAAC;AAE/B,MAAM,WAAW,WAAW,CAAC,SAAS,GAAG,OAAO;IAC9C,iEAAiE;IACjE,UAAU,CAAC,EAAE,CAAC,QAAQ,EAAE,SAAS,KAAK,IAAI,CAAC;IAC3C,+EAA+E;IAC/E,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB,mEAAmE;IACnE,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAWD,MAAM,WAAW,SAAS;IACxB,2DAA2D;IAC3D,IAAI,CAAC,SAAS,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,IAAI,EAAE,OAAO,EAAE,SAAS,EAAE,OAAO,GAAG,IAAI,CAAC;CACrF;AAUD,qBAAa,aAAa;IAGZ,OAAO,CAAC,QAAQ,CAAC,MAAM;IAFnC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAiC;gBAE5B,MAAM,EAAE,SAAS;IAE9C,IAAI,CAAC,OAAO,GAAG,OAAO,EAAE,SAAS,GAAG,OAAO,EACzC,MAAM,EAAE,SAAS,EACjB,IAAI,EAAE,OAAO,EACb,IAAI,GAAE,WAAW,CAAC,SAAS,CAAM,GAChC,OAAO,CAAC,OAAO,CAAC;IAqCnB,cAAc,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,sBAAsB,GAAG,IAAI;IAaxE,cAAc,CAAC,SAAS,EAAE,MAAM,EAAE,OAAO,EAAE,sBAAsB,GAAG,IAAI;IAKxE,SAAS,CAAC,MAAM,EAAE,OAAO,GAAG,IAAI;IAMhC,OAAO,CAAC,MAAM;CAWf"}
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
//#region src/shared/plugins/iframe-mount/client/rpc.ts
|
|
2
|
+
var e = 3e4, t = 0;
|
|
3
|
+
function n() {
|
|
4
|
+
return t = (t + 1) % (2 ** 53 - 1), `rpc-${Date.now().toString(36)}-${t.toString(36)}-${Math.random().toString(36).slice(2, 8)}`;
|
|
5
|
+
}
|
|
6
|
+
var r = class {
|
|
7
|
+
pending = /* @__PURE__ */ new Map();
|
|
8
|
+
constructor(e) {
|
|
9
|
+
this.sender = e;
|
|
10
|
+
}
|
|
11
|
+
call(t, r, i = {}) {
|
|
12
|
+
let a = n(), o = !!i.onProgress;
|
|
13
|
+
return new Promise((n, s) => {
|
|
14
|
+
let c = i.timeoutMs === null ? null : i.timeoutMs ?? e, l = {
|
|
15
|
+
resolve: (e) => n(e),
|
|
16
|
+
reject: s,
|
|
17
|
+
onProgress: i.onProgress,
|
|
18
|
+
signal: i.signal
|
|
19
|
+
};
|
|
20
|
+
if (this.pending.set(a, l), c !== null && c > 0 && (l.timeoutHandle = setTimeout(() => {
|
|
21
|
+
this.settle(a, !1, /* @__PURE__ */ Error(`RPC timed out after ${c}ms`));
|
|
22
|
+
}, c)), i.signal) {
|
|
23
|
+
if (i.signal.aborted) {
|
|
24
|
+
this.settle(a, !1, /* @__PURE__ */ Error("RPC aborted"));
|
|
25
|
+
return;
|
|
26
|
+
}
|
|
27
|
+
l.abortHandler = () => {
|
|
28
|
+
this.settle(a, !1, /* @__PURE__ */ Error("RPC aborted"));
|
|
29
|
+
}, i.signal.addEventListener("abort", l.abortHandler, { once: !0 });
|
|
30
|
+
}
|
|
31
|
+
try {
|
|
32
|
+
this.sender.send(a, t, r, o);
|
|
33
|
+
} catch (e) {
|
|
34
|
+
this.settle(a, !1, e);
|
|
35
|
+
}
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
handleResponse(e, t) {
|
|
39
|
+
if (t.ok) this.settle(e, !0, t.result);
|
|
40
|
+
else {
|
|
41
|
+
let n = t.error ?? {
|
|
42
|
+
code: "rpc_unknown_error",
|
|
43
|
+
message: "Unknown RPC error"
|
|
44
|
+
}, r = Object.assign(Error(n.message), {
|
|
45
|
+
code: n.code,
|
|
46
|
+
data: n.data
|
|
47
|
+
});
|
|
48
|
+
this.settle(e, !1, r);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
handleProgress(e, t) {
|
|
52
|
+
this.pending.get(e)?.onProgress?.(t.progress);
|
|
53
|
+
}
|
|
54
|
+
rejectAll(e) {
|
|
55
|
+
for (let [t] of this.pending) this.settle(t, !1, e);
|
|
56
|
+
}
|
|
57
|
+
settle(e, t, n) {
|
|
58
|
+
let r = this.pending.get(e);
|
|
59
|
+
r && (this.pending.delete(e), r.timeoutHandle !== void 0 && clearTimeout(r.timeoutHandle), r.signal && r.abortHandler && r.signal.removeEventListener("abort", r.abortHandler), t ? r.resolve(n) : r.reject(n));
|
|
60
|
+
}
|
|
61
|
+
};
|
|
62
|
+
//#endregion
|
|
63
|
+
export { r as RpcDispatcher };
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
export * from './types';
|
|
2
|
+
export { deriveSandbox } from './sandbox';
|
|
3
|
+
export { usePluginContributions, type UsePluginContributionsOptions, } from './useFetchContributions';
|
|
4
|
+
export { PluginIframe, type PluginIframeProps, type PluginIframeRpcContext, type PluginIframeRpcHandler, } from './PluginIframe';
|
|
5
|
+
export { PluginMount, type PluginMountProps, type PluginMountChildProps } from './PluginMount';
|
|
6
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/shared/plugins/iframe-mount/index.ts"],"names":[],"mappings":"AAAA,cAAc,SAAS,CAAC;AACxB,OAAO,EAAE,aAAa,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EACL,sBAAsB,EACtB,KAAK,6BAA6B,GACnC,MAAM,yBAAyB,CAAC;AACjC,OAAO,EACL,YAAY,EACZ,KAAK,iBAAiB,EACtB,KAAK,sBAAsB,EAC3B,KAAK,sBAAsB,GAC5B,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,WAAW,EAAE,KAAK,gBAAgB,EAAE,KAAK,qBAAqB,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Plugin contribution shape — the manifest entry a plugin author writes to
|
|
3
|
+
* declare that they want to be mounted at a given extension point.
|
|
4
|
+
*
|
|
5
|
+
* Mount points are open-ended strings the host page declares
|
|
6
|
+
* (`vibe.detailTab`, `agent.detailTab`, `target.detailTab`,
|
|
7
|
+
* `dashboard.widget`, …). Adding a new mount point does NOT require an
|
|
8
|
+
* SDK release: the host page consumes the matching contributions and
|
|
9
|
+
* interprets `meta` however it needs.
|
|
10
|
+
*/
|
|
11
|
+
export type PluginRuntime = 'iframe' | 'in-process';
|
|
12
|
+
export interface PluginCapabilities {
|
|
13
|
+
/**
|
|
14
|
+
* REST path prefixes the plugin is allowed to hit via the iframe token.
|
|
15
|
+
* Globs (`*`) are honoured by `request-security` on the agent.
|
|
16
|
+
*
|
|
17
|
+
* Example: `["/api/profiles/*\/my-plugin/*"]`
|
|
18
|
+
*/
|
|
19
|
+
restPaths: string[];
|
|
20
|
+
/** WebSocket topics this plugin subscribes to via the host relay. */
|
|
21
|
+
wsTopics: string[];
|
|
22
|
+
/**
|
|
23
|
+
* Host RPC methods the plugin may call (e.g. `navigate`, `toast`,
|
|
24
|
+
* `storage.get`). The host enforces this allow-list before invocation;
|
|
25
|
+
* mismatches return a structured error rather than executing.
|
|
26
|
+
*/
|
|
27
|
+
rpcMethods: string[];
|
|
28
|
+
}
|
|
29
|
+
export interface ContributionGate {
|
|
30
|
+
/** Vibe-level feature catalog id (`isFeatureEnabled(feature)`). */
|
|
31
|
+
feature?: string;
|
|
32
|
+
/** Platform-level GrowthBook flag (`isPlatformTabEnabled(flag)`). */
|
|
33
|
+
platformFlag?: string;
|
|
34
|
+
/** Hide the contribution when no agent is attached to the surface. */
|
|
35
|
+
requiresAgent?: boolean;
|
|
36
|
+
}
|
|
37
|
+
export interface PluginContribution {
|
|
38
|
+
/** Open-ended mount point id. The host page knows how to read it. */
|
|
39
|
+
mountPoint: string;
|
|
40
|
+
/** Unique within (pluginKey, mountPoint). */
|
|
41
|
+
id: string;
|
|
42
|
+
title: string;
|
|
43
|
+
/** Lucide icon name. Host resolves to a component; SDK stays icon-set agnostic. */
|
|
44
|
+
icon?: string;
|
|
45
|
+
/** Lower = earlier in the strip / grid. */
|
|
46
|
+
order?: number;
|
|
47
|
+
/**
|
|
48
|
+
* Which runtimes this contribution supports. The host picks the first
|
|
49
|
+
* entry that matches its preference and is available; warns and skips
|
|
50
|
+
* the contribution when nothing matches.
|
|
51
|
+
*/
|
|
52
|
+
runtimes: PluginRuntime[];
|
|
53
|
+
capabilities: PluginCapabilities;
|
|
54
|
+
gate?: ContributionGate;
|
|
55
|
+
/** Mount-point-specific extras (e.g. `defaultSize` for dashboard widgets). */
|
|
56
|
+
meta?: Record<string, unknown>;
|
|
57
|
+
}
|
|
58
|
+
export interface PluginManifest {
|
|
59
|
+
/** Globally unique. Convention: npm-package-style (`vibe-plugin-ui-git`). */
|
|
60
|
+
id: string;
|
|
61
|
+
/** Human-readable. */
|
|
62
|
+
name?: string;
|
|
63
|
+
/** CalVer version of the plugin package itself. */
|
|
64
|
+
version?: string;
|
|
65
|
+
description?: string;
|
|
66
|
+
contributions: PluginContribution[];
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* `defineUiPlugin` is a typed identity helper — it lets the plugin author
|
|
70
|
+
* declare the manifest + render function once and have the resulting
|
|
71
|
+
* object accepted by both adapters without `as const` ceremony.
|
|
72
|
+
*
|
|
73
|
+
* The `render` thunk runs *inside* the chosen adapter, after the host
|
|
74
|
+
* handshake has populated `VibeHostContext`. The hooks in `./react` are
|
|
75
|
+
* what consumers actually use; this signature is intentionally untyped
|
|
76
|
+
* for React to keep the protocol module DOM-free.
|
|
77
|
+
*/
|
|
78
|
+
export interface UiPluginDefinition<TRender = unknown> {
|
|
79
|
+
manifest: PluginManifest;
|
|
80
|
+
render: () => TRender;
|
|
81
|
+
}
|
|
82
|
+
export declare function defineUiPlugin<TRender>(plugin: UiPluginDefinition<TRender>): UiPluginDefinition<TRender>;
|
|
83
|
+
//# sourceMappingURL=contribution.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"contribution.d.ts","sourceRoot":"","sources":["../../../../../src/shared/plugins/iframe-mount/protocol/contribution.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,MAAM,MAAM,aAAa,GAAG,QAAQ,GAAG,YAAY,CAAC;AAEpD,MAAM,WAAW,kBAAkB;IACjC;;;;;OAKG;IACH,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,qEAAqE;IACrE,QAAQ,EAAE,MAAM,EAAE,CAAC;IACnB;;;;OAIG;IACH,UAAU,EAAE,MAAM,EAAE,CAAC;CACtB;AAED,MAAM,WAAW,gBAAgB;IAC/B,mEAAmE;IACnE,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,qEAAqE;IACrE,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,sEAAsE;IACtE,aAAa,CAAC,EAAE,OAAO,CAAC;CACzB;AAED,MAAM,WAAW,kBAAkB;IACjC,qEAAqE;IACrE,UAAU,EAAE,MAAM,CAAC;IACnB,6CAA6C;IAC7C,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,mFAAmF;IACnF,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,2CAA2C;IAC3C,KAAK,CAAC,EAAE,MAAM,CAAC;IACf;;;;OAIG;IACH,QAAQ,EAAE,aAAa,EAAE,CAAC;IAC1B,YAAY,EAAE,kBAAkB,CAAC;IACjC,IAAI,CAAC,EAAE,gBAAgB,CAAC;IACxB,8EAA8E;IAC9E,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAChC;AAED,MAAM,WAAW,cAAc;IAC7B,6EAA6E;IAC7E,EAAE,EAAE,MAAM,CAAC;IACX,sBAAsB;IACtB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,mDAAmD;IACnD,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,aAAa,EAAE,kBAAkB,EAAE,CAAC;CACrC;AAED;;;;;;;;;GASG;AACH,MAAM,WAAW,kBAAkB,CAAC,OAAO,GAAG,OAAO;IACnD,QAAQ,EAAE,cAAc,CAAC;IACzB,MAAM,EAAE,MAAM,OAAO,CAAC;CACvB;AAED,wBAAgB,cAAc,CAAC,OAAO,EACpC,MAAM,EAAE,kBAAkB,CAAC,OAAO,CAAC,GAClC,kBAAkB,CAAC,OAAO,CAAC,CAE7B"}
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Versioned envelope shared by every postMessage between a UI plugin
|
|
3
|
+
* (iframe-mounted or in-process) and its host shell.
|
|
4
|
+
*
|
|
5
|
+
* Both sides import these types from this module — there is no other
|
|
6
|
+
* source of truth for the wire format. Bumping the envelope is a
|
|
7
|
+
* deliberate breaking-change event; the major version embedded in
|
|
8
|
+
* `ENVELOPE_VERSION` rides independently of the package's CalVer.
|
|
9
|
+
*/
|
|
10
|
+
export declare const ENVELOPE_VERSION: 1;
|
|
11
|
+
export type EnvelopeVersion = typeof ENVELOPE_VERSION;
|
|
12
|
+
/** Operations the host sends to the plugin. */
|
|
13
|
+
export type HostOp = 'host:init' | 'host:theme-change' | 'host:locale-change' | 'host:feature-flag' | 'host:context-change' | 'host:event' | 'host:rpc-response' | 'host:rpc-progress' | 'host:dispose';
|
|
14
|
+
/** Operations the plugin sends to the host. */
|
|
15
|
+
export type PluginOp = 'plugin:ready' | 'plugin:rpc-request' | 'plugin:event-emit' | 'plugin:set-badge' | 'plugin:set-title' | 'plugin:resize-request' | 'plugin:error';
|
|
16
|
+
export interface HostEnvelope<P = unknown> {
|
|
17
|
+
v: EnvelopeVersion;
|
|
18
|
+
source: 'host';
|
|
19
|
+
kind: HostOp;
|
|
20
|
+
/** Set when this envelope answers (or progresses) a prior plugin RPC. */
|
|
21
|
+
requestId?: string;
|
|
22
|
+
payload: P;
|
|
23
|
+
}
|
|
24
|
+
export interface PluginEnvelope<P = unknown> {
|
|
25
|
+
v: EnvelopeVersion;
|
|
26
|
+
source: 'plugin';
|
|
27
|
+
kind: PluginOp;
|
|
28
|
+
/** Set on rpc-request / set on plugin:error when caused by a specific RPC. */
|
|
29
|
+
requestId?: string;
|
|
30
|
+
payload: P;
|
|
31
|
+
}
|
|
32
|
+
export type Envelope<P = unknown> = HostEnvelope<P> | PluginEnvelope<P>;
|
|
33
|
+
/**
|
|
34
|
+
* Type guard that an unknown postMessage payload looks like a valid v1
|
|
35
|
+
* envelope. Origin and `event.source` checks are *not* performed here —
|
|
36
|
+
* the caller must do those *before* trusting the payload, because a
|
|
37
|
+
* well-formed envelope from a hostile origin is still hostile.
|
|
38
|
+
*/
|
|
39
|
+
export declare function isEnvelope(value: unknown): value is Envelope;
|
|
40
|
+
/** Convenience: narrow to a HostEnvelope (caller already trusts the origin). */
|
|
41
|
+
export declare function isHostEnvelope(value: unknown): value is HostEnvelope;
|
|
42
|
+
/** Convenience: narrow to a PluginEnvelope (caller already trusts the origin). */
|
|
43
|
+
export declare function isPluginEnvelope(value: unknown): value is PluginEnvelope;
|
|
44
|
+
/** Sent in reply to `plugin:ready`. The plugin blocks render until it arrives. */
|
|
45
|
+
export interface HostInitPayload {
|
|
46
|
+
/** Scoped iframe token. Bounded by manifest capabilities. */
|
|
47
|
+
iframeToken: string;
|
|
48
|
+
tunnelUrl: string;
|
|
49
|
+
mountPoint: string;
|
|
50
|
+
context: Record<string, unknown>;
|
|
51
|
+
agentId: string;
|
|
52
|
+
profile: string;
|
|
53
|
+
theme: {
|
|
54
|
+
colorMode: 'light' | 'dark';
|
|
55
|
+
tokens: Record<string, string>;
|
|
56
|
+
};
|
|
57
|
+
locale: string;
|
|
58
|
+
capabilities: {
|
|
59
|
+
restPaths: string[];
|
|
60
|
+
wsTopics: string[];
|
|
61
|
+
rpcMethods: string[];
|
|
62
|
+
};
|
|
63
|
+
featureFlags: Record<string, boolean>;
|
|
64
|
+
sdkVersion: string;
|
|
65
|
+
hostVersion: string;
|
|
66
|
+
}
|
|
67
|
+
export interface HostThemeChangePayload {
|
|
68
|
+
colorMode: 'light' | 'dark';
|
|
69
|
+
tokens: Record<string, string>;
|
|
70
|
+
}
|
|
71
|
+
export interface HostLocaleChangePayload {
|
|
72
|
+
locale: string;
|
|
73
|
+
}
|
|
74
|
+
export interface HostFeatureFlagPayload {
|
|
75
|
+
flag: string;
|
|
76
|
+
value: boolean;
|
|
77
|
+
}
|
|
78
|
+
export interface HostContextChangePayload {
|
|
79
|
+
context: Record<string, unknown>;
|
|
80
|
+
}
|
|
81
|
+
export interface HostEventPayload<T = unknown> {
|
|
82
|
+
name: string;
|
|
83
|
+
data: T;
|
|
84
|
+
}
|
|
85
|
+
export interface HostRpcResponsePayload<T = unknown> {
|
|
86
|
+
ok: boolean;
|
|
87
|
+
result?: T;
|
|
88
|
+
error?: {
|
|
89
|
+
code: string;
|
|
90
|
+
message: string;
|
|
91
|
+
data?: unknown;
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
export interface HostRpcProgressPayload<T = unknown> {
|
|
95
|
+
progress: T;
|
|
96
|
+
}
|
|
97
|
+
export type HostDisposePayload = Record<string, never>;
|
|
98
|
+
export interface PluginReadyPayload {
|
|
99
|
+
pluginId: string;
|
|
100
|
+
pluginVersion: string;
|
|
101
|
+
sdkVersion: string;
|
|
102
|
+
declaredCapabilities: {
|
|
103
|
+
restPaths: string[];
|
|
104
|
+
wsTopics: string[];
|
|
105
|
+
rpcMethods: string[];
|
|
106
|
+
};
|
|
107
|
+
}
|
|
108
|
+
export interface PluginRpcRequestPayload {
|
|
109
|
+
method: string;
|
|
110
|
+
args: unknown;
|
|
111
|
+
/** Caller hint that the RPC may stream progress before terminal response. */
|
|
112
|
+
streaming?: boolean;
|
|
113
|
+
}
|
|
114
|
+
export interface PluginEventEmitPayload<T = unknown> {
|
|
115
|
+
name: string;
|
|
116
|
+
data: T;
|
|
117
|
+
}
|
|
118
|
+
export interface PluginSetBadgePayload {
|
|
119
|
+
value: string | number | null;
|
|
120
|
+
}
|
|
121
|
+
export interface PluginSetTitlePayload {
|
|
122
|
+
value: string;
|
|
123
|
+
}
|
|
124
|
+
export interface PluginResizeRequestPayload {
|
|
125
|
+
/** Suggested iframe height in pixels. Host may ignore. */
|
|
126
|
+
height?: number;
|
|
127
|
+
width?: number;
|
|
128
|
+
}
|
|
129
|
+
export interface PluginErrorPayload {
|
|
130
|
+
code: string;
|
|
131
|
+
message: string;
|
|
132
|
+
stack?: string;
|
|
133
|
+
/** Optional reference to a specific in-flight requestId. */
|
|
134
|
+
requestId?: string;
|
|
135
|
+
}
|
|
136
|
+
//# sourceMappingURL=envelope.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"envelope.d.ts","sourceRoot":"","sources":["../../../../../src/shared/plugins/iframe-mount/protocol/envelope.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
function e(e) {
|
|
2
|
+
if (typeof e != "object" || !e) return !1;
|
|
3
|
+
let t = e;
|
|
4
|
+
return t.v !== 1 || t.source !== "host" && t.source !== "plugin" || typeof t.kind != "string" || "requestId" in t && typeof t.requestId != "string" && t.requestId !== void 0 ? !1 : "payload" in t;
|
|
5
|
+
}
|
|
6
|
+
function t(t) {
|
|
7
|
+
return e(t) && t.source === "plugin";
|
|
8
|
+
}
|
|
9
|
+
//#endregion
|
|
10
|
+
export { e as isEnvelope, t as isPluginEnvelope };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../src/shared/plugins/iframe-mount/protocol/index.ts"],"names":[],"mappings":"AAAA,cAAc,eAAe,CAAC;AAC9B,cAAc,mBAAmB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sandbox.d.ts","sourceRoot":"","sources":["../../../../src/shared/plugins/iframe-mount/sandbox.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAuC9D,wBAAgB,aAAa,CAAC,YAAY,EAAE,kBAAkB,GAAG,SAAS,GAAG,IAAI,GAAG,MAAM,CAmBzF"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
//#region src/shared/plugins/iframe-mount/sandbox.ts
|
|
2
|
+
var e = ["allow-scripts", "allow-same-origin"], t = {
|
|
3
|
+
"clipboard.write": ["allow-clipboard-write"],
|
|
4
|
+
"clipboard.read": ["allow-clipboard-read"],
|
|
5
|
+
openExternal: ["allow-popups", "allow-popups-to-escape-sandbox"],
|
|
6
|
+
downloads: ["allow-downloads"],
|
|
7
|
+
pointerLock: ["allow-pointer-lock"],
|
|
8
|
+
fullscreen: ["allow-presentation"]
|
|
9
|
+
};
|
|
10
|
+
function n(n) {
|
|
11
|
+
let r = new Set(e), i = n?.rpcMethods ?? [];
|
|
12
|
+
for (let e of i) {
|
|
13
|
+
let n = t[e];
|
|
14
|
+
if (n) for (let e of n) r.add(e);
|
|
15
|
+
}
|
|
16
|
+
return Array.from(r).join(" ");
|
|
17
|
+
}
|
|
18
|
+
//#endregion
|
|
19
|
+
export { n as deriveSandbox };
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { PluginCapabilities, PluginContribution, PluginRuntime } from './protocol/index.js';
|
|
2
|
+
/**
|
|
3
|
+
* A "tunnel" the host page can query for contributions and from which
|
|
4
|
+
* iframe-mounted plugins are served. For VibeControls this is the
|
|
5
|
+
* vibecontrols-agent's Cloudflare tunnel + the current profile name;
|
|
6
|
+
* other products map to whatever serves their plugins.
|
|
7
|
+
*/
|
|
8
|
+
export interface MountTunnel {
|
|
9
|
+
/** Base URL — used for both fetch + iframe src. */
|
|
10
|
+
tunnelUrl: string;
|
|
11
|
+
/** Profile or scope segment the agent uses to namespace plugins. */
|
|
12
|
+
profile: string;
|
|
13
|
+
/** Optional human-readable label for picker UIs / errors. */
|
|
14
|
+
label?: string;
|
|
15
|
+
/**
|
|
16
|
+
* Factory that mints a fresh iframe token scoped to a contribution's
|
|
17
|
+
* capability `restPaths`. Called once on first mount + on each
|
|
18
|
+
* scheduled refresh. The host supplies this so the SDK stays
|
|
19
|
+
* transport-agnostic.
|
|
20
|
+
*/
|
|
21
|
+
mintIframeToken: (input: {
|
|
22
|
+
pathPrefixes: string[];
|
|
23
|
+
}) => Promise<{
|
|
24
|
+
token: string;
|
|
25
|
+
expiresAt: string;
|
|
26
|
+
}>;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* What `usePluginContributions` returns per-contribution after
|
|
30
|
+
* fetching from one or more tunnels. The `tunnel` is the source the
|
|
31
|
+
* contribution came from; multiple tunnels' results are unioned (last
|
|
32
|
+
* wins on id collisions).
|
|
33
|
+
*/
|
|
34
|
+
export interface DiscoveredContribution {
|
|
35
|
+
pluginKey: string;
|
|
36
|
+
pluginPackageName?: string;
|
|
37
|
+
contribution: PluginContribution;
|
|
38
|
+
capabilities: PluginCapabilities;
|
|
39
|
+
/**
|
|
40
|
+
* Relative URL — the host concatenates with `tunnel.tunnelUrl` to
|
|
41
|
+
* mount the iframe. Returned by the agent as e.g. `/ui/<pluginKey>`.
|
|
42
|
+
*/
|
|
43
|
+
url: string;
|
|
44
|
+
tunnel: MountTunnel;
|
|
45
|
+
}
|
|
46
|
+
export type RuntimePreference = PluginRuntime | 'auto';
|
|
47
|
+
export interface InProcessPluginEntry {
|
|
48
|
+
/** Matches `contribution.id`. */
|
|
49
|
+
id: string;
|
|
50
|
+
/** Matches `contribution.mountPoint`. */
|
|
51
|
+
mountPoint: string;
|
|
52
|
+
/** React component to render. Receives the same context object the iframe would. */
|
|
53
|
+
Component: React.ComponentType<{
|
|
54
|
+
context: Record<string, unknown>;
|
|
55
|
+
}>;
|
|
56
|
+
}
|
|
57
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../src/shared/plugins/iframe-mount/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,kBAAkB,EAAE,kBAAkB,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AAEjG;;;;;GAKG;AACH,MAAM,WAAW,WAAW;IAC1B,mDAAmD;IACnD,SAAS,EAAE,MAAM,CAAC;IAClB,oEAAoE;IACpE,OAAO,EAAE,MAAM,CAAC;IAChB,6DAA6D;IAC7D,KAAK,CAAC,EAAE,MAAM,CAAC;IACf;;;;;OAKG;IACH,eAAe,EAAE,CAAC,KAAK,EAAE;QAAE,YAAY,EAAE,MAAM,EAAE,CAAA;KAAE,KAAK,OAAO,CAAC;QAC9D,KAAK,EAAE,MAAM,CAAC;QACd,SAAS,EAAE,MAAM,CAAC;KACnB,CAAC,CAAC;CACJ;AAED;;;;;GAKG;AACH,MAAM,WAAW,sBAAsB;IACrC,SAAS,EAAE,MAAM,CAAC;IAClB,iBAAiB,CAAC,EAAE,MAAM,CAAC;IAC3B,YAAY,EAAE,kBAAkB,CAAC;IACjC,YAAY,EAAE,kBAAkB,CAAC;IACjC;;;OAGG;IACH,GAAG,EAAE,MAAM,CAAC;IACZ,MAAM,EAAE,WAAW,CAAC;CACrB;AAED,MAAM,MAAM,iBAAiB,GAAG,aAAa,GAAG,MAAM,CAAC;AAEvD,MAAM,WAAW,oBAAoB;IACnC,iCAAiC;IACjC,EAAE,EAAE,MAAM,CAAC;IACX,yCAAyC;IACzC,UAAU,EAAE,MAAM,CAAC;IACnB,oFAAoF;IACpF,SAAS,EAAE,KAAK,CAAC,aAAa,CAAC;QAAE,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;KAAE,CAAC,CAAC;CACtE"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { DiscoveredContribution, MountTunnel } from './types';
|
|
2
|
+
export interface UsePluginContributionsOptions {
|
|
3
|
+
/**
|
|
4
|
+
* Filter to a single mount point. When omitted, the hook returns the
|
|
5
|
+
* union of every contribution across every mount point so the host
|
|
6
|
+
* can seed multiple tab strips from one request.
|
|
7
|
+
*/
|
|
8
|
+
mountPoint?: string;
|
|
9
|
+
/**
|
|
10
|
+
* Polling cadence. Defaults to 60s. Set to `false` to disable; the
|
|
11
|
+
* hook will only refetch on tunnel reconnect / focus.
|
|
12
|
+
*/
|
|
13
|
+
refetchIntervalMs?: number | false;
|
|
14
|
+
enabled?: boolean;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Fetch plugin contributions from every supplied tunnel. Results are
|
|
18
|
+
* unioned; if two tunnels report contributions with the same `id`, the
|
|
19
|
+
* one whose tunnel.label is lexicographically smaller wins (stable,
|
|
20
|
+
* deterministic, debuggable). Authors should pick unique ids anyway.
|
|
21
|
+
*/
|
|
22
|
+
export declare function usePluginContributions(tunnels: MountTunnel[], opts?: UsePluginContributionsOptions): {
|
|
23
|
+
data: DiscoveredContribution[];
|
|
24
|
+
isFetching: boolean;
|
|
25
|
+
errors: Array<{
|
|
26
|
+
tunnel: MountTunnel;
|
|
27
|
+
error: unknown;
|
|
28
|
+
}>;
|
|
29
|
+
refetch: () => void;
|
|
30
|
+
};
|
|
31
|
+
//# sourceMappingURL=useFetchContributions.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"useFetchContributions.d.ts","sourceRoot":"","sources":["../../../../src/shared/plugins/iframe-mount/useFetchContributions.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,sBAAsB,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AAwCnE,MAAM,WAAW,6BAA6B;IAC5C;;;;OAIG;IACH,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB;;;OAGG;IACH,iBAAiB,CAAC,EAAE,MAAM,GAAG,KAAK,CAAC;IACnC,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED;;;;;GAKG;AACH,wBAAgB,sBAAsB,CACpC,OAAO,EAAE,WAAW,EAAE,EACtB,IAAI,GAAE,6BAAkC,GACvC;IACD,IAAI,EAAE,sBAAsB,EAAE,CAAC;IAC/B,UAAU,EAAE,OAAO,CAAC;IACpB,MAAM,EAAE,KAAK,CAAC;QAAE,MAAM,EAAE,WAAW,CAAC;QAAC,KAAK,EAAE,OAAO,CAAA;KAAE,CAAC,CAAC;IACvD,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB,CA0EA"}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { useMemo as e } from "react";
|
|
2
|
+
import { useQueries as t } from "@tanstack/react-query";
|
|
3
|
+
//#region src/shared/plugins/iframe-mount/useFetchContributions.ts
|
|
4
|
+
var n = 6e4;
|
|
5
|
+
async function r(e, t, n) {
|
|
6
|
+
let r = `${e.tunnelUrl.replace(/\/$/, "")}/api/profiles/${encodeURIComponent(e.profile)}/plugins/contributions${t ? `?mountPoint=${encodeURIComponent(t)}` : ""}`, i = await fetch(r, {
|
|
7
|
+
signal: n,
|
|
8
|
+
headers: { Accept: "application/json" }
|
|
9
|
+
});
|
|
10
|
+
if (!i.ok) throw Error(`Contributions fetch failed: ${i.status} ${i.statusText}`);
|
|
11
|
+
return ((await i.json()).contributions ?? []).map((t) => ({
|
|
12
|
+
pluginKey: t.pluginKey,
|
|
13
|
+
pluginPackageName: t.pluginPackageName,
|
|
14
|
+
contribution: t.contribution,
|
|
15
|
+
capabilities: t.capabilities,
|
|
16
|
+
url: t.url,
|
|
17
|
+
tunnel: e
|
|
18
|
+
}));
|
|
19
|
+
}
|
|
20
|
+
function i(i, a = {}) {
|
|
21
|
+
let { mountPoint: o, refetchIntervalMs: s = n, enabled: c = !0 } = a, l = t({ queries: i.map((e) => ({
|
|
22
|
+
queryKey: [
|
|
23
|
+
"vibe-plugin-contributions",
|
|
24
|
+
e.tunnelUrl,
|
|
25
|
+
e.profile,
|
|
26
|
+
o
|
|
27
|
+
],
|
|
28
|
+
queryFn: ({ signal: t }) => r(e, o, t),
|
|
29
|
+
refetchInterval: s === !1 ? !1 : s,
|
|
30
|
+
staleTime: 3e4,
|
|
31
|
+
enabled: c
|
|
32
|
+
})) }), u = l.map((e) => `${e.dataUpdatedAt}:${e.data?.length ?? 0}`).join("|"), d = l.map((e) => e.error ? `${e.errorUpdatedAt}` : "").join("|"), f = e(() => {
|
|
33
|
+
let e = (e) => `${e.pluginKey}::${e.contribution.mountPoint}::${e.contribution.id}`, t = /* @__PURE__ */ new Map();
|
|
34
|
+
for (let n = 0; n < l.length; n += 1) {
|
|
35
|
+
let r = l[n].data ?? [];
|
|
36
|
+
for (let n of r) {
|
|
37
|
+
let r = e(n), i = t.get(r);
|
|
38
|
+
if (!i) {
|
|
39
|
+
t.set(r, n);
|
|
40
|
+
continue;
|
|
41
|
+
}
|
|
42
|
+
let a = i.tunnel.label ?? i.tunnel.tunnelUrl;
|
|
43
|
+
(n.tunnel.label ?? n.tunnel.tunnelUrl) < a && t.set(r, n);
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
return Array.from(t.values());
|
|
47
|
+
}, [u]), p = e(() => {
|
|
48
|
+
let e = [];
|
|
49
|
+
for (let t = 0; t < l.length; t += 1) {
|
|
50
|
+
let n = l[t]?.error;
|
|
51
|
+
n && e.push({
|
|
52
|
+
tunnel: i[t],
|
|
53
|
+
error: n
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
return e;
|
|
57
|
+
}, [d, i]);
|
|
58
|
+
return {
|
|
59
|
+
data: f,
|
|
60
|
+
isFetching: l.some((e) => e.isFetching),
|
|
61
|
+
errors: p,
|
|
62
|
+
refetch: () => {
|
|
63
|
+
for (let e of l) e.refetch();
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
}
|
|
67
|
+
//#endregion
|
|
68
|
+
export { i as usePluginContributions };
|
|
@@ -37,4 +37,5 @@ export { useSettingsRegistryStore } from './registries/useSettingsRegistry';
|
|
|
37
37
|
export { useWidgetRegistryStore } from './registries/useWidgetRegistry';
|
|
38
38
|
export { useToolbarRegistryStore } from './registries/useToolbarRegistry';
|
|
39
39
|
export { useContextMenuRegistryStore } from './registries/useContextMenuRegistry';
|
|
40
|
+
export * from './iframe-mount';
|
|
40
41
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/shared/plugins/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAGH,YAAY,EACV,QAAQ,EACR,gBAAgB,EAChB,mBAAmB,EACnB,aAAa,EACb,eAAe,EACf,yBAAyB,EACzB,gBAAgB,EAChB,eAAe,EACf,kBAAkB,EAClB,mBAAmB,EACnB,iBAAiB,EACjB,iBAAiB,EACjB,UAAU,EACV,qBAAqB,EACrB,oBAAoB,EACpB,kBAAkB,EAClB,mBAAmB,EACnB,uBAAuB,EACvB,eAAe,EACf,WAAW,EACX,YAAY,EACZ,SAAS,GACV,MAAM,SAAS,CAAC;AAGjB,OAAO,EAAE,oBAAoB,EAAE,KAAK,UAAU,EAAE,MAAM,cAAc,CAAC;AAGrE,OAAO,EACL,QAAQ,EACR,cAAc,EACd,KAAK,YAAY,EACjB,KAAK,oBAAoB,EACzB,KAAK,eAAe,GACrB,MAAM,aAAa,CAAC;AAGrB,OAAO,EAAE,aAAa,EAAE,KAAK,mBAAmB,EAAE,MAAM,WAAW,CAAC;AAGpE,OAAO,EACL,mBAAmB,EACnB,KAAK,aAAa,EAClB,KAAK,YAAY,EACjB,KAAK,mBAAmB,EACxB,KAAK,kBAAkB,GACxB,MAAM,WAAW,CAAC;AAGnB,OAAO,EACL,qBAAqB,EACrB,gBAAgB,EAChB,KAAK,0BAA0B,EAC/B,KAAK,0BAA0B,GAChC,MAAM,yBAAyB,CAAC;AAGjC,OAAO,EACL,0BAA0B,EAC1B,KAAK,YAAY,EACjB,KAAK,yBAAyB,GAC/B,MAAM,yCAAyC,CAAC;AACjD,OAAO,EAAE,uBAAuB,EAAE,MAAM,iCAAiC,CAAC;AAC1E,OAAO,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AACtE,OAAO,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AACtE,OAAO,EAAE,yBAAyB,EAAE,MAAM,mCAAmC,CAAC;AAC9E,OAAO,EAAE,wBAAwB,EAAE,MAAM,kCAAkC,CAAC;AAC5E,OAAO,EAAE,sBAAsB,EAAE,MAAM,gCAAgC,CAAC;AACxE,OAAO,EAAE,uBAAuB,EAAE,MAAM,iCAAiC,CAAC;AAC1E,OAAO,EAAE,2BAA2B,EAAE,MAAM,qCAAqC,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/shared/plugins/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAGH,YAAY,EACV,QAAQ,EACR,gBAAgB,EAChB,mBAAmB,EACnB,aAAa,EACb,eAAe,EACf,yBAAyB,EACzB,gBAAgB,EAChB,eAAe,EACf,kBAAkB,EAClB,mBAAmB,EACnB,iBAAiB,EACjB,iBAAiB,EACjB,UAAU,EACV,qBAAqB,EACrB,oBAAoB,EACpB,kBAAkB,EAClB,mBAAmB,EACnB,uBAAuB,EACvB,eAAe,EACf,WAAW,EACX,YAAY,EACZ,SAAS,GACV,MAAM,SAAS,CAAC;AAGjB,OAAO,EAAE,oBAAoB,EAAE,KAAK,UAAU,EAAE,MAAM,cAAc,CAAC;AAGrE,OAAO,EACL,QAAQ,EACR,cAAc,EACd,KAAK,YAAY,EACjB,KAAK,oBAAoB,EACzB,KAAK,eAAe,GACrB,MAAM,aAAa,CAAC;AAGrB,OAAO,EAAE,aAAa,EAAE,KAAK,mBAAmB,EAAE,MAAM,WAAW,CAAC;AAGpE,OAAO,EACL,mBAAmB,EACnB,KAAK,aAAa,EAClB,KAAK,YAAY,EACjB,KAAK,mBAAmB,EACxB,KAAK,kBAAkB,GACxB,MAAM,WAAW,CAAC;AAGnB,OAAO,EACL,qBAAqB,EACrB,gBAAgB,EAChB,KAAK,0BAA0B,EAC/B,KAAK,0BAA0B,GAChC,MAAM,yBAAyB,CAAC;AAGjC,OAAO,EACL,0BAA0B,EAC1B,KAAK,YAAY,EACjB,KAAK,yBAAyB,GAC/B,MAAM,yCAAyC,CAAC;AACjD,OAAO,EAAE,uBAAuB,EAAE,MAAM,iCAAiC,CAAC;AAC1E,OAAO,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AACtE,OAAO,EAAE,qBAAqB,EAAE,MAAM,+BAA+B,CAAC;AACtE,OAAO,EAAE,yBAAyB,EAAE,MAAM,mCAAmC,CAAC;AAC9E,OAAO,EAAE,wBAAwB,EAAE,MAAM,kCAAkC,CAAC;AAC5E,OAAO,EAAE,sBAAsB,EAAE,MAAM,gCAAgC,CAAC;AACxE,OAAO,EAAE,uBAAuB,EAAE,MAAM,iCAAiC,CAAC;AAC1E,OAAO,EAAE,2BAA2B,EAAE,MAAM,qCAAqC,CAAC;AAKlF,cAAc,gBAAgB,CAAC"}
|