I’m working on a library that I publish as ESM. A primary goal is to allow it to be used without a build step, or even without using node/npm at all (just clone the repo and import). But I also realize most devs will want to use npm and consume the library that way.
It wouldn’t be a problem to support both workflows, except that my library depends on d3js. If I want ESM to work, I have to either vendor d3, or import it directly through URLs with a CDN. But this breaks NPM’s dependency resolution, ie if someone used my library and also used d3js directly, their app would include 2 separate copies of d3, even if it was the exact same version.
The best workaround I’ve found so far is to import d3 with a bare specifier (ie import * as d3 from 'd3'
) and use an import map with ESM to override it to import from jsdelivr (example below). This works, but I would love to ditch the import map. Is this possible?
Here’s an example (codepen):
<script type=importmap>
{
"imports": {
"d3": "https://cdn.jsdelivr.net/npm/d3@7/+esm"
}
}
</script>
<script type='module' src="https://cdn.jsdelivr.net/npm/[email protected]/index.js"></script>
<iobio-data-broker
url="https://s3.amazonaws.com/iobio/NA12878/NA12878.autsome.bam">
</iobio-data-broker>
<iobio-histogram
broker-key="coverage_hist">
</iobio-histogram>