71 lines
1.7 KiB
TypeScript
71 lines
1.7 KiB
TypeScript
import { LitElement } from "lit";
|
|
import { customElement, property } from "lit/decorators.js";
|
|
|
|
// @ts-ignore - browser global exists in Firefox
|
|
declare const browser: any;
|
|
|
|
@customElement("sandbox-iframe")
|
|
export class SandboxIframe extends LitElement {
|
|
@property() content = "";
|
|
private iframe?: HTMLIFrameElement;
|
|
|
|
createRenderRoot() {
|
|
return this;
|
|
}
|
|
|
|
override connectedCallback() {
|
|
super.connectedCallback();
|
|
window.addEventListener("message", this.handleMessage);
|
|
this.createIframe();
|
|
}
|
|
|
|
override disconnectedCallback() {
|
|
super.disconnectedCallback();
|
|
window.removeEventListener("message", this.handleMessage);
|
|
this.iframe?.remove();
|
|
}
|
|
|
|
private handleMessage = (e: MessageEvent) => {
|
|
if (e.data.type === "sandbox-ready" && e.source === this.iframe?.contentWindow) {
|
|
// Sandbox is ready, send content
|
|
this.iframe?.contentWindow?.postMessage(
|
|
{
|
|
type: "loadContent",
|
|
content: this.content,
|
|
artifactId: "test",
|
|
attachments: [],
|
|
},
|
|
"*",
|
|
);
|
|
}
|
|
};
|
|
|
|
private createIframe() {
|
|
this.iframe = document.createElement("iframe");
|
|
this.iframe.sandbox.add("allow-scripts");
|
|
this.iframe.sandbox.add("allow-modals");
|
|
this.iframe.style.width = "100%";
|
|
this.iframe.style.height = "100%";
|
|
this.iframe.style.border = "none";
|
|
|
|
const isFirefox = typeof browser !== "undefined" && browser.runtime !== undefined;
|
|
if (isFirefox) {
|
|
this.iframe.src = browser.runtime.getURL("sandbox.html");
|
|
} else {
|
|
this.iframe.src = chrome.runtime.getURL("sandbox.html");
|
|
}
|
|
|
|
this.appendChild(this.iframe);
|
|
}
|
|
|
|
public updateContent(newContent: string) {
|
|
this.content = newContent;
|
|
// Recreate iframe for clean state
|
|
if (this.iframe) {
|
|
this.iframe.remove();
|
|
this.iframe = undefined;
|
|
}
|
|
this.createIframe();
|
|
}
|
|
}
|