import type { LDService } from '@servicetitan/launchdarkly-service'; import type { Log } from '@servicetitan/log-service'; import type { Entries, IWebComponent } from './common'; import type { EventBus } from './event-bus'; import { WEB_COMPONENT_NAME } from './globals'; import { Serializable } from './types'; type HeadlessCallbackArgs = Pick< Entries, 'ldService' | 'logService' > & { eventBus?: TEventBus; mfeData?: Serializable; }; export type HeadlessCallback = ( params: HeadlessCallbackArgs ) => void; export function registerHeadless( connectedCallback?: HeadlessCallback, disconnectedCallback?: HeadlessCallback ) { class Headless extends HTMLElement implements IWebComponent { private ldService?: LDService; private logService?: Log; private eventBus?: EventBus; private readonly readyPromise: Promise; private resolveReadyPromise!: () => void; constructor() { super(); this.readyPromise = new Promise(resolve => { this.resolveReadyPromise = resolve; }); } provide = (entries: Entries) => { this.ldService = entries.ldService; this.logService = entries.logService; this.eventBus = entries.eventBus; this.resolveReadyPromise(); }; async connectedCallback() { await this.readyPromise; connectedCallback?.({ ...this.services, mfeData: this.mfeData, }); } async disconnectedCallback() { await this.readyPromise; disconnectedCallback?.({ ...this.services, mfeData: this.mfeData, }); } connectedMoveCallback() { /* * Defining connectedMoveCallback prevents connectedCallback or disconnectedCallback * from running when the element is moved in the DOM * https://developer.mozilla.org/en-US/docs/Web/API/Web_components/Using_custom_elements#custom_element_lifecycle_callbacks */ } private get services() { return { ldService: this.ldService, logService: this.logService, eventBus: this.eventBus, }; } private get mfeData() { return JSON.parse(this.dataset.mfeData ?? '{}'); } } if (!WEB_COMPONENT_NAME) { // eslint-disable-next-line no-console console.error('"WEB_COMPONENT_NAME" is not defined!'); return; } window.customElements.define(`headless-${WEB_COMPONENT_NAME}`, Headless); }