@web-applets/sdk 0.1.5 → 0.2.0-alpha.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,11 @@
1
+ export class AppletEvent extends Event {
2
+ constructor(type, init) {
3
+ super(type, {
4
+ bubbles: init?.bubbles,
5
+ composed: init?.composed,
6
+ cancelable: init?.cancelable,
7
+ });
8
+ this.data = init?.data;
9
+ this.actions = init?.actions;
10
+ }
11
+ }
@@ -0,0 +1,5 @@
1
+ export declare const RESPONSE_MESSAGE_TIMEOUT: number;
2
+ export declare const APPLET_CONNECT_TIMEOUT: number;
3
+ export declare const errorCodes: {
4
+ APPLET_ACTION_EXECUTION_ERROR: string;
5
+ };
@@ -0,0 +1,5 @@
1
+ export const RESPONSE_MESSAGE_TIMEOUT = 10 * 1000;
2
+ export const APPLET_CONNECT_TIMEOUT = 10 * 1000;
3
+ export const errorCodes = {
4
+ APPLET_ACTION_EXECUTION_ERROR: 'APPLET_ACTION_EXECUTION_ERROR',
5
+ };
@@ -0,0 +1,5 @@
1
+ declare function log(location: string, ...messages: any[]): void;
2
+ export declare const debug: {
3
+ log: typeof log;
4
+ };
5
+ export {};
package/dist/debug.js ADDED
@@ -0,0 +1,6 @@
1
+ function log(location, ...messages) {
2
+ console.log(`[${location}]`, ...messages);
3
+ }
4
+ export const debug = {
5
+ log,
6
+ };
@@ -0,0 +1,16 @@
1
+ import { AppletEvent } from '../index.js';
2
+ export declare class AppletFrameElement extends HTMLElement {
3
+ #private;
4
+ onload: (event: Event) => Promise<void> | void;
5
+ onactions: (event: AppletEvent) => Promise<void> | void;
6
+ ondata: (event: AppletEvent) => Promise<void> | void;
7
+ static observedAttributes: string[];
8
+ connectedCallback(): void;
9
+ get contentWindow(): Window;
10
+ set src(value: string);
11
+ get src(): string;
12
+ attributeChangedCallback(name: string, oldValue: string, newValue: string): void;
13
+ get applet(): import("../applets/applet.js").Applet<unknown>;
14
+ set data(data: any);
15
+ get styles(): string;
16
+ }
@@ -0,0 +1,110 @@
1
+ var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
2
+ if (kind === "m") throw new TypeError("Private method is not writable");
3
+ if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
4
+ if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
5
+ return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
6
+ };
7
+ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
8
+ if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
9
+ if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
10
+ return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
11
+ };
12
+ var _AppletFrameElement_instances, _AppletFrameElement_root, _AppletFrameElement_src, _AppletFrameElement_applet, _AppletFrameElement_dispatchEventAndHandler, _AppletFrameElement_iframe, _AppletFrameElement_loadApplet, _AppletFrameElement_resizeContainer;
13
+ import { applets } from '../index.js';
14
+ import { dispatchEventAndHandler } from '../utils.js';
15
+ export class AppletFrameElement extends HTMLElement {
16
+ constructor() {
17
+ super(...arguments);
18
+ _AppletFrameElement_instances.add(this);
19
+ _AppletFrameElement_root.set(this, void 0);
20
+ _AppletFrameElement_src.set(this, void 0);
21
+ _AppletFrameElement_applet.set(this, void 0);
22
+ _AppletFrameElement_dispatchEventAndHandler.set(this, dispatchEventAndHandler.bind(this));
23
+ _AppletFrameElement_iframe.set(this, document.createElement('iframe'));
24
+ }
25
+ connectedCallback() {
26
+ __classPrivateFieldSet(this, _AppletFrameElement_root, this.attachShadow({ mode: 'closed' }), "f");
27
+ __classPrivateFieldGet(this, _AppletFrameElement_root, "f").appendChild(__classPrivateFieldGet(this, _AppletFrameElement_iframe, "f"));
28
+ const styles = document.createElement('style');
29
+ styles.textContent = this.styles;
30
+ __classPrivateFieldGet(this, _AppletFrameElement_root, "f").appendChild(styles);
31
+ this.src = this.getAttribute('src');
32
+ }
33
+ get contentWindow() {
34
+ return __classPrivateFieldGet(this, _AppletFrameElement_iframe, "f").contentWindow;
35
+ }
36
+ set src(value) {
37
+ __classPrivateFieldSet(this, _AppletFrameElement_src, value, "f");
38
+ __classPrivateFieldSet(this, _AppletFrameElement_applet, undefined, "f");
39
+ __classPrivateFieldGet(this, _AppletFrameElement_instances, "m", _AppletFrameElement_loadApplet).call(this, value);
40
+ }
41
+ get src() {
42
+ return __classPrivateFieldGet(this, _AppletFrameElement_src, "f") || '';
43
+ }
44
+ attributeChangedCallback(name, oldValue, newValue) {
45
+ if (name === 'src') {
46
+ this.src = newValue;
47
+ }
48
+ }
49
+ get applet() {
50
+ return __classPrivateFieldGet(this, _AppletFrameElement_applet, "f");
51
+ }
52
+ set data(data) {
53
+ if (this.applet) {
54
+ this.applet.data = data;
55
+ }
56
+ else {
57
+ const listener = () => {
58
+ if (this.applet)
59
+ this.applet.data = data;
60
+ this.removeEventListener('load', listener);
61
+ };
62
+ this.addEventListener('load', listener);
63
+ }
64
+ }
65
+ get styles() {
66
+ return /*css*/ `
67
+ :host {
68
+ display: flex;
69
+ flex-direction: column;
70
+ height: 350px;
71
+ }
72
+
73
+ iframe {
74
+ border: none;
75
+ height: 100%;
76
+ width: 100%;
77
+ }
78
+ `;
79
+ }
80
+ }
81
+ _AppletFrameElement_root = new WeakMap(), _AppletFrameElement_src = new WeakMap(), _AppletFrameElement_applet = new WeakMap(), _AppletFrameElement_dispatchEventAndHandler = new WeakMap(), _AppletFrameElement_iframe = new WeakMap(), _AppletFrameElement_instances = new WeakSet(), _AppletFrameElement_loadApplet = async function _AppletFrameElement_loadApplet(url) {
82
+ __classPrivateFieldGet(this, _AppletFrameElement_iframe, "f").src = url;
83
+ const window = __classPrivateFieldGet(this, _AppletFrameElement_iframe, "f").contentWindow;
84
+ if (!window)
85
+ return;
86
+ __classPrivateFieldSet(this, _AppletFrameElement_applet, await applets.connect(window), "f");
87
+ // When data received, bubble the event up
88
+ __classPrivateFieldGet(this, _AppletFrameElement_applet, "f").ondata = (event) => {
89
+ __classPrivateFieldGet(this, _AppletFrameElement_dispatchEventAndHandler, "f").call(this, event);
90
+ };
91
+ // Resize
92
+ __classPrivateFieldGet(this, _AppletFrameElement_applet, "f").onresize = (event) => {
93
+ __classPrivateFieldGet(this, _AppletFrameElement_instances, "m", _AppletFrameElement_resizeContainer).call(this, {
94
+ width: __classPrivateFieldGet(this, _AppletFrameElement_applet, "f").width,
95
+ height: __classPrivateFieldGet(this, _AppletFrameElement_applet, "f").height,
96
+ });
97
+ };
98
+ __classPrivateFieldGet(this, _AppletFrameElement_applet, "f").onactions = (event) => {
99
+ __classPrivateFieldGet(this, _AppletFrameElement_dispatchEventAndHandler, "f").call(this, event);
100
+ };
101
+ // Emit load event when setup & connection complete
102
+ __classPrivateFieldGet(this, _AppletFrameElement_dispatchEventAndHandler, "f").call(this, new Event('load'));
103
+ if (this['load'] && typeof this['load'] === 'function') {
104
+ this.onload(new Event('load'));
105
+ }
106
+ }, _AppletFrameElement_resizeContainer = function _AppletFrameElement_resizeContainer(dimensions) {
107
+ this.style.height = `${dimensions.height}px`;
108
+ };
109
+ AppletFrameElement.observedAttributes = ['src'];
110
+ customElements.define('applet-frame', AppletFrameElement);
package/dist/index.d.ts CHANGED
@@ -1,9 +1,10 @@
1
- export * from './core/shared';
2
- export * from './core/applet';
3
- export * from './core/context';
4
- import { load } from './core/applet';
5
- import { getContext } from './core/context';
6
- export declare const applets: {
7
- load: typeof load;
8
- getContext: typeof getContext;
9
- };
1
+ import { AppletFactory } from './applets/applet-factory.js';
2
+ export declare const applets: AppletFactory;
3
+ import { Applet as AppletClass } from './applets/applet.js';
4
+ import { AppletScope as AppletScopeClass } from './applets/applet-scope.js';
5
+ export type Applet = InstanceType<typeof AppletClass>;
6
+ export type AppletScope = InstanceType<typeof AppletScopeClass>;
7
+ import './elements/applet-frame.js';
8
+ export { AppletFrameElement } from './elements/applet-frame.js';
9
+ export { AppletEvent } from './applets/events.js';
10
+ export { type AppletActionDescriptor } from './applets/actions.js';
package/dist/index.js CHANGED
@@ -1,9 +1,8 @@
1
- export * from './core/shared';
2
- export * from './core/applet';
3
- export * from './core/context';
4
- import { load } from './core/applet';
5
- import { getContext } from './core/context';
6
- export const applets = {
7
- load,
8
- getContext,
9
- };
1
+ // AppletFactory
2
+ import { AppletFactory } from './applets/applet-factory.js';
3
+ export const applets = new AppletFactory();
4
+ // AppletFrame
5
+ import './elements/applet-frame.js';
6
+ export { AppletFrameElement } from './elements/applet-frame.js';
7
+ // AppletEvent
8
+ export { AppletEvent } from './applets/events.js';
@@ -0,0 +1,46 @@
1
+ import { AppletActionDescriptor } from './applets/actions.js';
2
+ import { AppletManifest } from './utils.js';
3
+ export interface AppletMessage {
4
+ type: string;
5
+ }
6
+ export interface AppletConnectMessage {
7
+ type: 'appletconnect';
8
+ }
9
+ export interface AppletRegisterMessage {
10
+ type: 'register';
11
+ manifest?: AppletManifest;
12
+ actions?: {
13
+ [id: string]: AppletActionDescriptor;
14
+ };
15
+ data?: any;
16
+ }
17
+ export interface AppletActionMessage extends AppletMessage {
18
+ type: 'action';
19
+ id: string;
20
+ actionId: string;
21
+ arguments: any;
22
+ }
23
+ export interface AppletActionCompleteMessage extends AppletMessage {
24
+ type: 'actioncomplete';
25
+ id: string;
26
+ }
27
+ export interface AppletActionErrorMessage extends AppletMessage {
28
+ type: 'actionerror';
29
+ id: string;
30
+ message: string;
31
+ }
32
+ export interface AppletActionsMessage extends AppletMessage {
33
+ type: 'actions';
34
+ actions: {
35
+ [key: string]: AppletActionDescriptor;
36
+ };
37
+ }
38
+ export interface AppletDataMessage<T = any> extends AppletMessage {
39
+ type: 'data';
40
+ data: T;
41
+ }
42
+ export interface AppletResizeMessage extends AppletMessage {
43
+ type: 'resize';
44
+ height: number;
45
+ width: number;
46
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,11 @@
1
+ import { AppletFrameElement } from './index.js';
2
+ import './index.js';
3
+ import { type AppletFactory } from './applets/applet-factory.js';
4
+ import { AppletEvent } from './applets/events.js';
5
+ declare global {
6
+ interface Window {
7
+ applets: AppletFactory;
8
+ AppletEvent: typeof AppletEvent;
9
+ AppletFrameElement: typeof AppletFrameElement;
10
+ }
11
+ }
@@ -0,0 +1,6 @@
1
+ import { AppletFrameElement, applets } from './index.js';
2
+ import './index.js';
3
+ import { AppletEvent } from './applets/events.js';
4
+ window.applets = applets;
5
+ window.AppletEvent = AppletEvent;
6
+ window.AppletFrameElement = AppletFrameElement;
package/dist/utils.d.ts CHANGED
@@ -1 +1,28 @@
1
- export declare function parseUrl(url: string, base?: string): string;
1
+ import { AppletActionDescriptor } from './applets/actions.js';
2
+ export declare function dispatchEventAndHandler(event: Event): void;
3
+ export interface AppletManifest {
4
+ name?: string;
5
+ short_name?: string;
6
+ icons?: {
7
+ src: string;
8
+ purpose?: string;
9
+ sizes?: string;
10
+ type?: string;
11
+ }[];
12
+ description?: string;
13
+ display?: string;
14
+ start_url?: string;
15
+ actions?: {
16
+ [id: string]: AppletActionDescriptor;
17
+ };
18
+ [key: string]: any;
19
+ }
20
+ export interface JSONSchemaObject {
21
+ type: 'object' | 'string' | 'number' | 'integer' | 'array' | 'boolean' | 'null';
22
+ description?: string;
23
+ properties?: {
24
+ [key: string]: JSONSchemaObject;
25
+ };
26
+ required?: string[];
27
+ additionalProperties?: boolean;
28
+ }
package/dist/utils.js CHANGED
@@ -1,28 +1,6 @@
1
- // Adds http/https to URLs, and prepends with window location if relative
2
- export function parseUrl(url, base) {
3
- if (!url)
4
- return '';
5
- try {
6
- // If the base URL is provided, ensure it has a trailing slash for proper path resolution
7
- if (base) {
8
- // Don't add trailing slash if the base already ends with a file extension
9
- if (!base.match(/\.[a-zA-Z0-9]+$/)) {
10
- base = base.endsWith('/') ? base : base + '/';
11
- }
12
- }
13
- // Use URL constructor to properly resolve relative paths
14
- const resolvedUrl = new URL(url, base ?? window.location.href);
15
- return trimTrailingSlash(resolvedUrl.href);
1
+ export function dispatchEventAndHandler(event) {
2
+ if (typeof this[`on${event.type}`] === 'function') {
3
+ this[`on${event.type}`](event);
16
4
  }
17
- catch (e) {
18
- // Return original URL if parsing fails
19
- console.warn('Failed to parse URL:', e);
20
- return url;
21
- }
22
- }
23
- function trimTrailingSlash(url) {
24
- if (url.endsWith('/')) {
25
- return url.slice(0, -1);
26
- }
27
- return url;
5
+ this.dispatchEvent(event);
28
6
  }
@@ -0,0 +1,13 @@
1
+ (()=>{var h=class extends Error{constructor(e){super(e),this.name="AppletExecutionError"}},A=class extends Error{constructor(e){super(e),this.name="AppletConnectionError"}};function c(p){typeof this[`on${p.type}`]=="function"&&this[`on${p.type}`](p),this.dispatchEvent(p)}var o=class extends Event{constructor(e,t){super(e,{bubbles:t?.bubbles,composed:t?.composed,cancelable:t?.cancelable}),this.data=t?.data,this.actions=t?.actions}};function b(p,...e){console.log(`[${p}]`,...e)}var a={log:b};var f=class extends EventTarget{#s;#o={};#t;#i;#n;#e;#a;#p;#r;constructor(e){super(),a.log("Applet","Constructor called"),this.#s=e,this.#n=c.bind(this),this.#c();let t=s=>{s.source===this.#s&&"type"in s.data&&s.data.type==="appletconnect"&&(a.log("Applet","Recieved message",s.data),this.#c(),this.removeEventListener("message",t))};window.addEventListener("message",t)}#c(){this.#e&&this.#e.close();let e=new MessageChannel,t={type:"appletconnect"};a.log("Applet","Send message",t),this.#e=e.port1,this.#e.onmessage=this.#h.bind(this),this.#s.postMessage(t,"*",[e.port2]),this.#a=this.#e.postMessage.bind(this.#e)}#h(e){let t=e.data;switch(a.log("Applet","Recieved message",t),t.type){case"register":let s=t;this.#t=s.manifest;let n=new o("connect");this.#n(n),this.#o=s.actions,this.#d(s.actions),this.#i=s.data,this.#l(s.data);break;case"data":let i=t;this.#i=i.data,this.#l(i.data);break;case"resize":let r=t;this.#p=r.width,this.#r=r.height;let g=new o("resize");this.#n(g);break;case"actions":let m=t;this.#o=m.actions,this.#d(m.actions);break}}#l(e){let t=new o("data",{data:e});this.#n(t)}#d(e){let t=new o("actions",{actions:e});this.#n(t)}async sendAction(e,t){let s={id:crypto.randomUUID(),type:"action",actionId:e,arguments:t};return new Promise((n,i)=>{this.#a(s);let r=setTimeout(()=>{i(new h(`Applet action handler failed to complete before timeout (${1e4}ms)`))},1e4),g=m=>{let d=m.data;if(["actioncomplete","actionerror"].includes(d.type)&&"id"in d&&d.id===s.id)if(this.#e.removeEventListener("message",g),clearTimeout(r),d.type==="actionerror"){let w=d;i(new h(w.message))}else n()};this.#e.addEventListener("message",g)})}get data(){return this.#i}set data(e){this.#i=e;let t={type:"data",data:e};this.#a(t)}get window(){return this.#s}get manifest(){return this.#t}get actions(){return this.#o}get width(){return this.#p}get height(){return this.#r}};var E=class extends EventTarget{#s={};#o;#t;#i;#n;#e;#a;#p;constructor(e){super(),a.log("AppletScope","Constructor called"),this.#n=c.bind(this),e&&(this.#o=e);let t=n=>{if(n.source===window.parent&&n.data.type==="appletconnect"&&n.ports&&n.ports.length>0){a.log("AppletScope","Recieved message",n.data);let i=n.ports[0];this.#e=i.postMessage.bind(i),i.onmessage=this.#c.bind(this),this.removeEventListener("message",t),this.#r()}};window.addEventListener("message",t);let s={type:"appletconnect"};window.parent.postMessage(s,"*"),a.log("AppletScope","Send message",s)}async#r(){let e=this.manifest??await this.#g();this.#o=e||{},this.#t=this.#t||e?.actions||{};let t={type:"register",manifest:this.#o,actions:this.#t,data:this.#i};this.#e(t),a.log("AppletScope","Send message",t);let s=new o("connect");this.#n(s),this.#l()}#c(e){let t=e.data;switch(a.log("AppletScope","Recieved message",t),t.type){case"data":"data"in t&&(this.data=t.data);break;case"action":"type"in t&&t.type==="action"&&"id"in t&&typeof t.id=="string"&&"actionId"in t&&typeof t.actionId=="string"&&"arguments"in t&&this.#h(t);break}}async#h(e){if(Object.keys(this.#s).includes(e.actionId))try{await this.#s[e.actionId](e.arguments);let t={type:"actioncomplete",id:e.id};this.#e(t)}catch(t){let s={type:"actionerror",id:e.id,message:t.message};this.#e(s),console.error(t)}}#l(){new ResizeObserver(t=>{for(let s of t)this.#d({width:s.contentRect.width,height:s.contentRect.height})}).observe(document.querySelector("html"))}#d({width:e,height:t}){this.#a=e,this.#p=t;let s={type:"resize",width:e,height:t};a.log("AppletScope","Send message",s),this.#e(s)}async#g(){let e=document.querySelector('link[rel="manifest"]');if(e)try{let s=await(await fetch(e.href)).json();for(let n in s.actions){let i=s.actions[n];i.params_schema&&!Object.keys(i.params_schema).length&&(i.params_schema=void 0)}return s}catch{return}}setActionHandler(e,t){this.#s[e]=t}defineAction(e,t){let{handler:s,...n}=t;s&&(this.#s[e]=s),this.actions={...this.actions,[e]:n}}set actions(e){if(!e)return;this.#t=e;let t={type:"actions",actions:this.#t};a.log("AppletScope","Send message",t),this.#e&&this.#e(t);let s=new o("actions",{actions:e});setTimeout(()=>this.#n(s),1)}get actions(){return this.#t}get manifest(){return this.#o}get actionHandlers(){return this.#s}set actionHandlers(e){this.#s=e}set data(e){this.#i=e;let t={type:"data",data:e};a.log("AppletScope","Send message",t),this.#e&&this.#e(t);let s=new o("data",{data:e});setTimeout(()=>this.#n(s),1)}get data(){return this.#i}get width(){return this.#a}get height(){return this.#p}};var u=class{async connect(e){return new Promise((t,s)=>{let n=new f(e),i=setTimeout(()=>{s(new A(`Applet failed to connect before the timeout was reached (${1e4}ms)`))},1e4),r=()=>{t(n),n.removeEventListener("connect",r),clearTimeout(i)};n.addEventListener("connect",r)})}register(e){return new E(e)}};var l=class extends HTMLElement{#s;#o;#t;#i=c.bind(this);#n=document.createElement("iframe");static{this.observedAttributes=["src"]}connectedCallback(){this.#s=this.attachShadow({mode:"closed"}),this.#s.appendChild(this.#n);let e=document.createElement("style");e.textContent=this.styles,this.#s.appendChild(e),this.src=this.getAttribute("src")}get contentWindow(){return this.#n.contentWindow}set src(e){this.#o=e,this.#t=void 0,this.#e(e)}get src(){return this.#o||""}attributeChangedCallback(e,t,s){e==="src"&&(this.src=s)}async#e(e){this.#n.src=e;let t=this.#n.contentWindow;t&&(this.#t=await y.connect(t),this.#t.ondata=s=>{this.#i(s)},this.#t.onresize=s=>{this.#a({width:this.#t.width,height:this.#t.height})},this.#t.onactions=s=>{this.#i(s)},this.#i(new Event("load")),this.load&&typeof this.load=="function"&&this.onload(new Event("load")))}get applet(){return this.#t}set data(e){if(this.applet)this.applet.data=e;else{let t=()=>{this.applet&&(this.applet.data=e),this.removeEventListener("load",t)};this.addEventListener("load",t)}}#a(e){this.style.height=`${e.height}px`}get styles(){return`
2
+ :host {
3
+ display: flex;
4
+ flex-direction: column;
5
+ height: 350px;
6
+ }
7
+
8
+ iframe {
9
+ border: none;
10
+ height: 100%;
11
+ width: 100%;
12
+ }
13
+ `}};customElements.define("applet-frame",l);var y=new u;window.applets=y;window.AppletEvent=o;window.AppletFrameElement=l;})();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@web-applets/sdk",
3
- "version": "0.1.5",
3
+ "version": "0.2.0-alpha.9",
4
4
  "description": "The Web Applets SDK, for creating & hosting Web Applets.",
5
5
  "author": "Rupert Manfredi <rupert@unternet.co>",
6
6
  "license": "MIT",
@@ -18,10 +18,14 @@
18
18
  "url": "git+https://github.com/unternet-co/web-applets.git"
19
19
  },
20
20
  "scripts": {
21
- "build": "tsc && cp ../README.md ./README.md",
21
+ "build": "npm run build:module && npm run build:shim",
22
+ "build:module": "tsc && cp ../README.md ./README.md",
23
+ "build:shim": "node ./scripts/build.js",
22
24
  "prepublishOnly": "npm run build"
23
25
  },
24
26
  "devDependencies": {
27
+ "@types/node": "^22.13.9",
28
+ "esbuild": "^0.25.0",
25
29
  "typescript": "^5.6.2"
26
30
  }
27
31
  }
@@ -1,19 +0,0 @@
1
- import { Applet } from '../index';
2
- export declare class AppletFrame extends HTMLElement {
3
- #private;
4
- container?: HTMLIFrameElement;
5
- applet?: Applet;
6
- loaded?: boolean;
7
- static observedAttributes: string[];
8
- connectedCallback(): void;
9
- set src(value: string);
10
- get src(): string;
11
- attributeChangedCallback(name: string, oldValue: string, newValue: string): void;
12
- loadApplet(url: string): Promise<void>;
13
- set data(data: any);
14
- resizeContainer(dimensions: {
15
- height: number;
16
- width: number;
17
- }): void;
18
- get styles(): string;
19
- }
@@ -1,94 +0,0 @@
1
- var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
2
- if (kind === "m") throw new TypeError("Private method is not writable");
3
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
4
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
5
- return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
6
- };
7
- var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
8
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
9
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
10
- return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
11
- };
12
- var _AppletFrame_root, _AppletFrame_src;
13
- import { applets, } from '../index';
14
- // TODO: Add resize event handler, and resize DOM element
15
- export class AppletFrame extends HTMLElement {
16
- constructor() {
17
- super(...arguments);
18
- _AppletFrame_root.set(this, void 0);
19
- _AppletFrame_src.set(this, void 0);
20
- }
21
- connectedCallback() {
22
- __classPrivateFieldSet(this, _AppletFrame_root, this.attachShadow({ mode: 'open' }), "f");
23
- this.container = document.createElement('iframe');
24
- __classPrivateFieldGet(this, _AppletFrame_root, "f").appendChild(this.container);
25
- const styles = document.createElement('style');
26
- styles.textContent = this.styles;
27
- __classPrivateFieldGet(this, _AppletFrame_root, "f").appendChild(styles);
28
- const url = this.getAttribute('src');
29
- if (url)
30
- this.loadApplet(url);
31
- }
32
- set src(value) {
33
- __classPrivateFieldSet(this, _AppletFrame_src, value, "f");
34
- this.loadApplet(value);
35
- }
36
- get src() {
37
- return __classPrivateFieldGet(this, _AppletFrame_src, "f");
38
- }
39
- attributeChangedCallback(name, oldValue, newValue) {
40
- if (name === 'src') {
41
- this.src = newValue;
42
- }
43
- }
44
- async loadApplet(url) {
45
- if (!this.container)
46
- return;
47
- this.applet = await applets.load(url, this.container);
48
- // When data received, bubble the event up
49
- this.applet.ondata = (dataEvent) => {
50
- this.dispatchEvent(dataEvent);
51
- };
52
- // Resize
53
- this.applet.onresize = (resizeEvent) => {
54
- this.resizeContainer(resizeEvent.dimensions);
55
- };
56
- this.applet.onactions = (e) => { };
57
- // Emit a load event when loading complete
58
- this.dispatchEvent(new Event('load'));
59
- this.loaded = true;
60
- }
61
- set data(data) {
62
- if (this.applet && this.loaded) {
63
- this.applet.data = data;
64
- }
65
- else {
66
- const loadListener = () => {
67
- this.applet.data = data;
68
- this.removeEventListener('load', loadListener);
69
- };
70
- this.addEventListener('load', loadListener);
71
- }
72
- }
73
- resizeContainer(dimensions) {
74
- this.style.height = `${dimensions.height}px`;
75
- }
76
- get styles() {
77
- return /*css*/ `
78
- :host {
79
- display: flex;
80
- flex-direction: column;
81
- height: 350px;
82
- }
83
-
84
- iframe {
85
- border: none;
86
- height: 100%;
87
- width: 100%;
88
- }
89
- `;
90
- }
91
- }
92
- _AppletFrame_root = new WeakMap(), _AppletFrame_src = new WeakMap();
93
- AppletFrame.observedAttributes = ['src'];
94
- customElements.define('applet-frame', AppletFrame);
@@ -1,21 +0,0 @@
1
- import { AppletAction, ActionParams, AppletManifest, AppletDataEvent, AppletResizeEvent, AppletActionsEvent, AppletMessageRelay, AppletReadyEvent } from './shared';
2
- export declare function load(url: string, container?: HTMLIFrameElement): Promise<Applet>;
3
- export interface AppletOptions {
4
- manifest: AppletManifest;
5
- container: HTMLIFrameElement;
6
- }
7
- export declare class Applet<T = any> extends EventTarget {
8
- #private;
9
- messageRelay: AppletMessageRelay;
10
- actions: AppletAction[];
11
- container: HTMLIFrameElement;
12
- constructor(manifest: AppletManifest, targetWindow: Window);
13
- dispatchAction(actionId: string, params?: ActionParams): Promise<import("./shared").AppletMessage>;
14
- get data(): T;
15
- set data(data: T);
16
- get manifest(): AppletManifest;
17
- onready(event: AppletReadyEvent): void;
18
- onresize(event: AppletResizeEvent): void;
19
- onactions(event: AppletActionsEvent): void;
20
- ondata(event: AppletDataEvent): void;
21
- }
@@ -1,117 +0,0 @@
1
- var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {
2
- if (kind === "m") throw new TypeError("Private method is not writable");
3
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a setter");
4
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot write private member to an object whose class did not declare it");
5
- return (kind === "a" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;
6
- };
7
- var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {
8
- if (kind === "a" && !f) throw new TypeError("Private accessor was defined without a getter");
9
- if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
10
- return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
11
- };
12
- var _Applet_instances, _Applet_manifest, _Applet_data, _Applet_addListeners;
13
- import { parseUrl } from '../utils';
14
- import { AppletDataMessage, AppletInitMessage, AppletDataEvent, AppletResizeEvent, AppletActionsEvent, AppletMessageRelay, loadManifest, AppletReadyEvent, AppletActionMessage, } from './shared';
15
- // Container for initializing applets without an explicit container
16
- const hiddenContainer = document.createElement('iframe');
17
- hiddenContainer.style.display = 'none';
18
- document.body.appendChild(hiddenContainer);
19
- // Options for loading an applet
20
- // interface LoadOpts {
21
- // unsafe?: boolean;
22
- // }
23
- // const defaultOpts: LoadOpts = {
24
- // unsafe: false,
25
- // };
26
- // Load an applet object from a URL
27
- export async function load(url, container
28
- // opts?: LoadOpts
29
- ) {
30
- if (!container)
31
- container = hiddenContainer;
32
- url = parseUrl(url);
33
- const manifest = await loadManifest(url);
34
- // If unsafe enabled, allow same origin sandbox
35
- // This is required for e.g. YouTube embeds
36
- // const _opts = Object.assign(defaultOpts, opts ?? {});
37
- // if (_opts.unsafe && manifest.unsafe) {
38
- // container.setAttribute(
39
- // 'sandbox',
40
- // 'allow-scripts allow-forms allow-same-origin'
41
- // );
42
- // } else {
43
- // container.setAttribute('sandbox', 'allow-scripts allow-forms');
44
- // }
45
- container.setAttribute('sandbox', 'allow-scripts allow-forms allow-same-origin');
46
- container.src = url;
47
- const applet = new Applet(manifest, container.contentWindow);
48
- return new Promise((resolve) => {
49
- applet.onready = () => resolve(applet);
50
- });
51
- }
52
- export class Applet extends EventTarget {
53
- constructor(manifest, targetWindow) {
54
- super();
55
- _Applet_instances.add(this);
56
- this.actions = [];
57
- _Applet_manifest.set(this, void 0);
58
- _Applet_data.set(this, void 0);
59
- this.messageRelay = new AppletMessageRelay(targetWindow);
60
- __classPrivateFieldSet(this, _Applet_manifest, manifest, "f");
61
- __classPrivateFieldGet(this, _Applet_instances, "m", _Applet_addListeners).call(this);
62
- this.messageRelay.on('ready', () => {
63
- this.messageRelay.send(new AppletInitMessage());
64
- });
65
- }
66
- async dispatchAction(actionId, params) {
67
- const actionMessage = new AppletActionMessage({
68
- actionId,
69
- params,
70
- });
71
- return await this.messageRelay.send(actionMessage);
72
- }
73
- get data() {
74
- return __classPrivateFieldGet(this, _Applet_data, "f");
75
- }
76
- set data(data) {
77
- __classPrivateFieldSet(this, _Applet_data, data, "f");
78
- this.messageRelay.send(new AppletDataMessage({ data }));
79
- }
80
- get manifest() {
81
- return __classPrivateFieldGet(this, _Applet_manifest, "f");
82
- }
83
- onready(event) { }
84
- onresize(event) { }
85
- onactions(event) { }
86
- ondata(event) { }
87
- }
88
- _Applet_manifest = new WeakMap(), _Applet_data = new WeakMap(), _Applet_instances = new WeakSet(), _Applet_addListeners = function _Applet_addListeners() {
89
- this.messageRelay.on('ready', (message) => {
90
- const readyEvent = new AppletReadyEvent();
91
- if (typeof this.onready === 'function')
92
- this.onready(readyEvent);
93
- this.dispatchEvent(readyEvent);
94
- });
95
- this.messageRelay.on('data', (message) => {
96
- __classPrivateFieldSet(this, _Applet_data, message.data, "f");
97
- const dataEvent = new AppletDataEvent({ data: message.data });
98
- if (typeof this.ondata === 'function')
99
- this.ondata(dataEvent);
100
- this.dispatchEvent(dataEvent);
101
- });
102
- this.messageRelay.on('resize', (message) => {
103
- const resizeEvent = new AppletResizeEvent({
104
- dimensions: message.dimensions,
105
- });
106
- if (typeof this.onresize === 'function')
107
- this.onresize(resizeEvent);
108
- this.dispatchEvent(resizeEvent);
109
- });
110
- this.messageRelay.on('actions', (message) => {
111
- this.actions = message.actions;
112
- const actionsEvent = new AppletActionsEvent({ actions: message.actions });
113
- if (typeof this.onactions === 'function')
114
- this.onactions(actionsEvent);
115
- this.dispatchEvent(actionsEvent);
116
- });
117
- };