From 7bd431242178eaeedfc005bbdfb861432753b28e Mon Sep 17 00:00:00 2001 From: Cezar Augusto Date: Fri, 22 Nov 2024 11:20:25 -0300 Subject: [PATCH] Basic support for shadow-dom content_scripts --- programs/cli/types/index.d.ts | 4 ++ .../plugin-css/common-style-loaders.ts | 42 ++++++++++++++++++- 2 files changed, 45 insertions(+), 1 deletion(-) diff --git a/programs/cli/types/index.d.ts b/programs/cli/types/index.d.ts index b928f4bd..36e4e429 100644 --- a/programs/cli/types/index.d.ts +++ b/programs/cli/types/index.d.ts @@ -20,3 +20,7 @@ interface ImportMetaEnv { interface ImportMeta { readonly env: ImportMetaEnv } + +interface Window { + __EXTENSION_SHADOW_ROOT__: ShadowRoot +} diff --git a/programs/develop/webpack/plugin-css/common-style-loaders.ts b/programs/develop/webpack/plugin-css/common-style-loaders.ts index 77b4e076..9d3366f7 100644 --- a/programs/develop/webpack/plugin-css/common-style-loaders.ts +++ b/programs/develop/webpack/plugin-css/common-style-loaders.ts @@ -13,6 +13,41 @@ export interface StyleLoaderOptions { loader?: string } +function whereToInsertStyleTag(element: HTMLElement) { + // Function to check if the shadow root exists + const insertElement = () => { + // @ts-expect-error - global reference. + const shadowRoot = window.__EXTENSION_SHADOW_ROOT__ + + if (shadowRoot) { + shadowRoot.appendChild(element) + console.log('Element inserted into shadowRoot') + } else { + document.head.appendChild(element) + console.log('Element inserted into document.head') + } + } + + // If the shadowRoot is already available, insert immediately + // @ts-expect-error - global reference. + if (window.__EXTENSION_SHADOW_ROOT__) { + insertElement() + return + } + + // Use MutationObserver to wait for the shadow root to be available + const observer = new MutationObserver(() => { + // @ts-expect-error - global reference. + if (window.__EXTENSION_SHADOW_ROOT__) { + insertElement() + observer.disconnect() // Stop observing once the shadow root is found + } + }) + + // Observe changes to the `document.body` or `document.head` + observer.observe(document.body, {childList: true, subtree: true}) +} + export async function commonStyleLoaders( projectPath: string, opts: StyleLoaderOptions @@ -23,7 +58,12 @@ export async function commonStyleLoaders( ? miniCssLoader : isUsingVue(projectPath) ? require.resolve('vue-style-loader') - : require.resolve('style-loader'), + : { + loader: require.resolve('style-loader'), + options: { + insert: whereToInsertStyleTag + } + }, { loader: require.resolve('css-loader'), options: {