我可以使用 CDN 中的 ES 模块库吗?



我想通过CDN使用这个库。
https://www.jsdelivr.com/package/npm/lit-element

我的js代码在这里。

import { LitElement, html } from "https://cdn.jsdelivr.net/npm/lit-element@2.1.0/lit-element.js";
class MyElement extends LitElement {
render(){
return html`ABCD`
}
}
customElements.define("my-element", MyElement)

我收到以下错误。

未捕获的类型错误:无法解析模块说明符"lit-html"。相对引用必须以"/"、"./"或"../".

我必须使用 npm 构建吗?


更新

以下代码有效。

import { LitElement, html } from "https://unpkg.com/lit-element/lit-element.js?module"
class MyElement extends LitElement {
render(){
return html`ABCD`
}
}
customElements.define("my-element", MyElement)

内部 LitHtml 和 LitElement 模块在内部使用裸模块说明符来导入依赖项,而 JS 模块尚不支持这些说明符。LitElementimport { TemplateResult } from 'lit-html',但JS需要将其'lit-html'替换为实际文件的任何路径(而不是包的抽象名称)。

如果你使用 npm 包(cdn.jsdelivr.net在这里提供),你必须使用构建步骤(WebPack、Rollup 等)将所有这些import语句解析为 JS 支持的文件路径或将所有文件内联在一起。

前者是unpkg.com ... ?module所做的,它用绝对https://unpkg.com/lit-html@^1.1.1/lit-html.js?module代替了对lit-html的裸引用。

接受的答案很棒;核心问题是您的 CDN 文件使用"模块说明符",即"裸"说明符(即不使用"/"或"./"或">../") .我用一个importmap解决了我的问题,将我的"裸"模块说明符映射到完整的 URL/baseURL 说明符,即

<script type="importmap">
{ "imports": { 'bare-specificer': 'https://full-url-specifier' } } 
</script>

当前方法的详细信息:

importmap

我在像ColladaLoader这样的模块中使用 jsmthree.js,但我收到此错误:

Uncaught TypeError: Failed to resolve module specifier "three". Relative references must start with either "/", "./", or "../"

发生这种情况是因为我导入了这个ColladaLoader.js文件,该文件从'three'("裸模块说明符")导入了许多内容:

import {
AmbientLight,
// ...etc....
sRGBEncoding
} from 'three';
//--------^ this is the "bare" module specifier problem

我从 three.js 中阅读 collada 加载器示例中学到了修复程序,该示例为其 html 添加了importmap。我认为importmap仍然是一个草稿功能,但它很好地将"裸模块说明符"映射到完整的 URL/baseURL——这正是我们所需要的!(更多在这里和这里):

<script type="importmap">
{
"imports": {
"three": "../build/three.module.js"
}
}
</script>
<script type="module">
//...
</script>

就我而言,我使用的是位于此处的three.js文件: https://cdnjs.cloudflare.com/ajax/libs/three.js/r123/three.module.js

因此,我的importmap如下所示:

<script type="importmap">
{
"imports": {
"three": "https://cdnjs.cloudflare.com/ajax/libs/three.js/r123/three.module.js"
}
}
</script>
<script type="module">
//...
</script>

我希望即使您有一个来自three.js以外的其他地方的"裸"模块说明符,importmap也可以为您工作; 但importmap方法可能仅适用于某些浏览器(即 caniuse 建议 Edge 89+、Chrome 89+ 和 Opera 76+ 支持type="importmap"截至 2022 年 5 月 4 日)

关于替代方法的详细信息:

skypack

下面的答案取决于托管最新模块skypack;即最新的ColladaLoader应该使用BufferGeometry而不是Geometry,随着R125的更改而被弃用,但最新的ColladaLoader在SKYPACK AFAIK上不可用

我提供这个答案是为了建议skypack作为您的 CDN 的替代品,它特别适用于three.js的上下文(显然甚至unpkg也可能不起作用;请继续阅读)

此 github 问题中讨论了该解决方案,其中引用了此迁移指南

NPM:examples/jsm 中的 ES6 模块现在使用裸说明符3 导入。此更改中断了在 cdn 中使用模块,例如 https://www.jsdelivr.com/和 https://unpkg.com/。请使用 https://www.skypack.dev/相反。

所以就我而言,我替换了这一行

import { ColladaLoader } from 'https://cdn.jsdelivr.net/gh/mrdoob/three.js/examples/jsm/loaders/ColladaLoader.js';

用这一行:

import ColladaLoader from 'https://cdn.skypack.dev/three-collada-loader';

这修复了错误"无法解析模块说明符"。但我确实面临着一个不同的问题,但这three.js具体;即使用已弃用的Geometry构造函数,因为我想skypack.dev/three-collada-loader不是最新的代码......

最新更新