导入库时 SvelteKit 控制台错误 "window is not defined"

SvelteKit console error "window is not defined" when i import library

我想导入使用“window”属性 的 apexChart 库,但我在控制台中遇到错误。

[vite] Error when evaluating SSR module /src/routes/prehled.svelte:
ReferenceError: window is not defined

挂载后我尝试使用apexCharts,但错误并没有消失。

<script>
 import ApexCharts from 'apexcharts'
 import { onMount } from 'svelte'
 const myOptions = {...myOptions}
 onMount(() => {
   const chart = new ApexCharts(document.querySelector('[data-chart="profit"]'), myOptions)
   chart.render()
 })
</script>

当我确定浏览器存在时,我尝试导入 apexCharts。

 import { browser } from '$app/env'
 if (browser) {
   import ApexCharts from 'apexcharts'
 }

但我收到错误消息“'import' 和 'export' 可能只出现在顶层”

我尝试在 svelte.config.js

中禁用 ssr
import adapter from '@sveltejs/adapter-static';
const config = {
    kit: {
        adapter: adapter(),
    prerender: {
      enabled: false
    },
    ssr: false,
}

我尝试创建一个组件,在其中导入 apexChart 库,并且我创建了一个条件,仅当存在浏览器时才使用该组件

{ #if browser }
  <ProfitChart />
{ /if }

没有任何帮助。

有谁知道如何帮助我吗?

最简单的方法是简单地将 apexcharts 作为独立库包含在您的网页中,如下所示:

<script src="https://cdn.jsdelivr.net/npm/apexcharts"></script>

然后在 onMount:

中简单地使用它
onMount(() => {
  const chart = new ApexCharts(container, options)
  chart.render()
})

您可以在 app.html 中添加此行,也可以将其包含在 <svelte:head> 块中需要的地方。

另一种方法是在 onMount 期间动态导入:

onMount(async () => {
  const ApexCharts = (await import('apexcharts')).default
  const chart = new ApexCharts(container, options)
  chart.render()
})

作为额外的:使用 bind:this 而不是 document.querySelector 来获取 DOM 元素,这将是更 'svelte' 的方式。

我发现 Vite 插件的最后一个选项在代码较少的情况下效果最好,但会在 vscode 中失去智能感知并看到导入突出显示为错误(最后的临时解决方法):https://kit.svelte.dev/faq#how-do-i-use-x-with-sveltekit-how-do-i-use-a-client-side-only-library-that-depends-on-document-or-window

  1. 安装vite插件:npm i -D vite-plugin-iso-import
  2. 将插件添加到 svelte.config.js:
       kit: {
          vite: {
            plugins: [
                isoImport(),
            ],
  1. 将插件添加到 TypeScript 配置(如果您使用 TS):
"compilerOptions": {
    "plugins": [{ "name": "vite-plugin-iso-import" }],
  1. 正常使用,但注意导入时的“?client”:
<script context="module">
    import { chart } from 'svelte-apexcharts?client';
    import { onMount } from 'svelte'
    let myOptions = {...myOptions}
    onMount(() => {
        myOptions = {...updated options/data}
    });
</script>

<div use:chart={myOptions} />

调试说明: 要让 import 暂时不高亮显示为错误,只需:

  1. npm run dev,您的项目将编译正常,然后在浏览器中测试至少执行一次。
  2. 现在删除?client,保存并照常继续调试。