Created
August 10, 2022 14:34
-
-
Save marcosmapf/4ab9c30dfd78656bb4d6c4ca33e239e3 to your computer and use it in GitHub Desktop.
Util module that helps handling load and registration of Module Federated containers
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| type FederatedAppRender = (props?: any) => void | |
| export interface FederatedAppList { | |
| [key: string]: () => Promise<FederatedAppRender> | |
| } | |
| export interface FederatedApp { | |
| render?: FederatedAppRender | |
| root: HTMLElement | |
| } | |
| const handleFederatedApp = (appList?: FederatedAppList) => { | |
| const getAppRoot = (appName: string) => { | |
| return window[appName]?.root as HTMLElement | |
| } | |
| const setAppRoot = (appName: string, rootElement: HTMLElement) => { | |
| if (!window[appName]) { | |
| window[appName] = {} | |
| } | |
| window[appName].root = rootElement | |
| } | |
| const isAppInsideShadowRoot = (appName: string) => { | |
| return getAppRoot(appName) instanceof ShadowRoot | |
| } | |
| /** | |
| * Returns the render function of a Module Federation container | |
| * Module federation containers are automatically added to the window object upon module loading. | |
| * This module loading occurs if there is an async definition of module (appList) provided to this function or if the module is loaded in any way | |
| */ | |
| const getRenderFederatedApp = async (appName: string, appModule: string): Promise<FederatedAppRender> => { | |
| try { | |
| const factory = await window[appName]?.get?.(appModule) | |
| if (factory) { | |
| const { default: render } = factory() | |
| return render | |
| } | |
| const appImportFunction = appList?.[appName] | |
| if (appImportFunction) { | |
| return await appImportFunction() | |
| } | |
| throw new Error(`Missing federated module render function for app: ${appName}`) | |
| } catch (error) { | |
| const errorMessage = `App ${appName} was not imported correctly, check the module import key or the module entrypoint file.` | |
| console.error(`${errorMessage} \n\n`, error) | |
| Promise.reject(error) | |
| } | |
| return Promise.reject(new Error()) | |
| } | |
| return { getRenderFederatedApp, getAppRoot, isAppInsideShadowRoot, setAppRoot } | |
| } | |
| export default handleFederatedApp |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
how to use in project?