From a7c79702f9a6bc17fdf47fe6f2d4806330bbcf6c Mon Sep 17 00:00:00 2001 From: Joel Denning Date: Wed, 2 Oct 2024 00:48:42 -0600 Subject: [PATCH] New use-injector attribute and resetDefaultMap api (#117) --- .changeset/bright-bats-smell.md | 7 +++++++ docs/api.md | 21 ++++++++++++--------- docs/configuration.md | 31 +++++++++++++++++++++++++++++++ src/api/js-api.js | 14 +++++++++++--- 4 files changed, 61 insertions(+), 12 deletions(-) create mode 100644 .changeset/bright-bats-smell.md diff --git a/.changeset/bright-bats-smell.md b/.changeset/bright-bats-smell.md new file mode 100644 index 0000000..e4f3651 --- /dev/null +++ b/.changeset/bright-bats-smell.md @@ -0,0 +1,7 @@ +--- +"import-map-overrides": minor +--- + +New `use-injector` attribute on `` element + +New `resetDefaultMap` js api diff --git a/docs/api.md b/docs/api.md index 02600aa..b44ce0d 100644 --- a/docs/api.md +++ b/docs/api.md @@ -24,9 +24,8 @@ const overrideMap = window.importMapOverrides.getOverrideMap(); } */ -const overrideMapWithDisabledOverrides = window.importMapOverrides.getOverrideMap( - true -); +const overrideMapWithDisabledOverrides = + window.importMapOverrides.getOverrideMap(true); /* { "imports": { @@ -79,7 +78,7 @@ port number: ```js const defaultOverrideUrl = window.importMapOverrides.getUrlFromPort( "module1", - "8085" + "8085", ); console.log(defaultOverrideUrl); // "//localhost:8085/module1.js" ``` @@ -125,6 +124,10 @@ window.importMapOverrides.getDefaultMap().then((importMap) => { }); ``` +### resetDefaultMap + +The [`getDefaultMap`](#getDefaultMap) function only derives the default map once upfront and then caches it. Calling the `resetDefaultMap()` function clears that cache, so that a subsequent call to `getDefaultMap()` derives the default map again. + ### getCurrentPageMap This function returns a promise that resolves the final import map (including overrides) that was applied to the current page. Any overrides set after the page load will not be included. @@ -196,7 +199,7 @@ A function that accepts one argument, `urlToImportMap`, that sets up an override ```js window.importMapOverrides.addExternalOverride( - "https://localhost:8080/my-override-import-map.json" + "https://localhost:8080/my-override-import-map.json", ); ``` @@ -207,7 +210,7 @@ A function that accepts one argument, `urlToImportMap`, that removes an external ```js // A return value of true means the override existed in the first place window.importMapOverrides.removeExternalOverride( - "https://localhost:8080/my-override-import-map.json" + "https://localhost:8080/my-override-import-map.json", ); ``` @@ -254,7 +257,7 @@ Takes one argument, `urlToImport`, and returns a promise that resolves with a bo ```js // true | false. True means the external map was successfully downloaded and parsed as json window.importMapOverrides.isExternalMapValid( - "https://localhost:8080/my-custom-override-import-mapm.json" + "https://localhost:8080/my-custom-override-import-mapm.json", ); ``` @@ -266,8 +269,8 @@ The import-map-overrides library fires an event called `import-map-overrides:ini ```js window.addEventListener("import-map-overrides:init", () => { - console.log('init'); -}) + console.log("init"); +}); ``` #### Change diff --git a/docs/configuration.md b/docs/configuration.md index 60532f1..e780c8a 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -16,6 +16,12 @@ element to your html file **before the import-map-overrides library is loaded**. ```html + + + + + + ``` | Import Map type | `importmap-type` | @@ -28,12 +34,19 @@ element to your html file **before the import-map-overrides library is loaded**. 1. Native import maps are only supported in Chrome@>=76 under the _Experimental Web Platform Features_ flag. Only one import map (including the import-map-overrides map) can be on a web page at a time when using native import maps. ([Details](https://github.com/WICG/import-maps/issues/199)). +### use-injector + +The `use-injector` attribute instructs import-map-overrides to skip inserting an import-map into the DOM, instead expecting the [import-map-injector](https://github.com/single-spa/import-map-injector) project to do so. This is necessary since browsers do not support multiple import maps on the same page. + +For more details, see [injector override mode](#client-side-injector) [import-map-injector docs](https://github.com/single-spa/import-map-injector#compatibility) + ## Override Mode To support a variety of use cases, import map overrides has four "override modes" that control how and whether import-map-overrides inserts import maps into the DOM: 1. [Client-side multiple maps](#client-side-multiple-maps) (default) 1. [Client-side single map](#client-side-single-map) +1. [Client-side import-map-injector](#client-side-injector) 1. [Server-side multiple maps](#server-side-multiple-maps) 1. [Server-side single map](#server-side-single-map) @@ -106,6 +119,24 @@ The `overridable-importmap` will be ignored by the browser, but import-map-overr Note that `overridable-importmap` scripts must be inline import maps, not external maps (those with `src=""`). This is because import-map-overrides executes synchronously to inject the single map, but downloading an external map is inherently asynchronous. +### Client-side injector + +If using [import-map-injector](https://github.com/single-spa/import-map-injector), import-map-overrides is not responsible for inserting the importmap script element into the DOM. To use the two projects together, do the following: + +1. Load import-map-overrides.js **before** import-map-injector.js + +```html + + + +``` + +2. Add the `use-injector` attribute to the `` element that configures import-map-overrides. See [import-map-overrides docs](https://github.com/single-spa/import-map-overrides/blob/main/docs/configuration.md#import-map-type) for more details + +```html + +``` + ### Server-side multiple maps If your server needs to be aware of import map overrides, you may use server-side multiple maps mode. To enable this mode, add a `server` attribute to your `` element: diff --git a/src/api/js-api.js b/src/api/js-api.js index 1533ec1..66a68ff 100644 --- a/src/api/js-api.js +++ b/src/api/js-api.js @@ -19,9 +19,8 @@ const domainsElement = document.querySelector(`meta[name="${domainsMeta}"]`); const externalOverrideMapPromises = {}; -export const importMapType = importMapMetaElement - ? importMapMetaElement.getAttribute("content") - : "importmap"; +export const importMapType = + importMapMetaElement?.getAttribute("content") ?? "importmap"; export let isDisabled; @@ -197,6 +196,9 @@ function init() { } return outMap; }, + resetDefaultMap() { + defaultMapPromise = null; + }, getDefaultMap() { return ( defaultMapPromise || @@ -439,6 +441,12 @@ function init() { fireEvent("init"); function insertOverrideMap(map, id, referenceNode) { + if (importMapMetaElement?.hasAttribute("use-injector")) { + // import-map-injector will take care of calling into import-map-overrides + // and then inject the final import map + return; + } + const overrideMapElement = document.createElement("script"); overrideMapElement.type = importMapType; overrideMapElement.id = id; // for debugging and for UI to identify this import map as special