如何解决Vite打包npm工具库时静态资源(如SVG)的路径问题?

我在本地开发环境路径是没有问题的。而且我的svg很小1kb左右,使用
new URL(./assets/${fileName}.svg, import.meta.url).pathname
的方式,他变成了data: URL编码了。
一切在没上传到npm之前都没有问题,
我尝试了各种方法但是svg的读取,始终是基于使用工具库的路径。(http://localhost:5173/*.svg)
以下是我vite的代码

import { defineConfig } from "vite";
import { resolve } from "path";
import path from "path";
import dts from "vite-plugin-dts";

export default defineConfig({
  publicDir: "public",
  base: "./",
  resolve: {
    alias: {
      "@": path.resolve(__dirname, "./"),
    },
  },
  plugins: [dts()],
  build: {
    lib: {
      entry: resolve(__dirname, "lib/index.ts"),
      name: "imhdChannelization", // the proper extensions will be added
      fileName: "imhd-channelization",
    },
    minify: false,
    outDir: "dist", // 输出目录
    assetsDir: "assets", // 静态资源目录
  },
});

下面是我打包的结构
image.png
以下是报错信息,我不明白为什么在node_moudles中的资源会以这种请求路径,而且我都是data: URL编码了还要在请求资源吗?
image.png
image.png

阅读 1.1k
avatarAI BotBETA

在Vite中打包npm工具库时处理静态资源(如SVG)的路径问题,通常涉及确保这些资源在库被消费时能够被正确访问。由于你的库在npm上发布后,静态资源(如SVG)的路径将不再基于开发时的本地路径(如http://localhost:5173/*.svg),而是需要相对于库文件的位置来解析。

以下是一些解决此问题的步骤和建议:

  1. 确保静态资源包含在打包输出中
    你的vite.config.ts配置中已经设置了assetsDir: "assets",这是正确的。这意味着Vite会将public/assets目录下的文件复制到dist/assets中。
  2. 修改资源引用方式
    在你的库代码中,当你需要引用SVG时,应确保路径是相对于最终打包后文件的位置。由于SVG被放在dist/assets下,你可以通过修改你的代码来确保这一点。但是,由于你是在构建一个库,直接引用文件系统路径可能不是最佳选择,因为库的消费者可能希望以不同的方式处理这些资源。

    一种更灵活的方式是将SVG作为模块导入到你的组件或JavaScript模块中,并让Vite在构建时自动处理它们。例如,如果你使用的是Vue、React等前端框架,你可以将SVG作为React组件或Vue单文件组件导入,这样它们就可以被框架的打包系统正确处理。

    如果你仍然需要直接引用SVG文件(如作为CSS背景图等),你可能需要编写一些代码来在运行时动态地构建正确的URL。但请注意,这可能会使库的使用变得更加复杂。

  3. 考虑使用Webpack或Rollup等打包工具的替代方案
    如果你发现Vite在处理某些类型的库时有限制,你可以考虑使用Webpack或Rollup等更传统的打包工具。这些工具提供了更多的配置选项和插件生态系统,可能更适合构建npm库。
  4. 测试库的使用
    在将库发布到npm之前,最好在一个示例项目中测试它,以确保一切按预期工作。这可以帮助你发现任何潜在的问题,并在问题影响到库的消费者之前解决它们。
  5. 文档和示例
    为你的库提供清晰的文档和示例,说明如何正确地使用库中的静态资源。这可以帮助库的消费者更好地理解如何集成和使用你的库。

对于你的具体情况,如果SVG文件很小,并且你希望它们被内联为base64编码的字符串,你可以考虑在构建过程中使用插件(如vite-svg-loader)来自动处理这种转换。但是,请注意,这种方法可能会增加打包后文件的大小,并可能不适用于所有情况。

1 个回答

找到一种解决办法,我不应该使用pathname属性,应该使用href

new URL(./assets/${fileName}.svg, import.meta.url).href

href:获取完整的 URL,包括协议、主机名、端口号、路径、查询字符串和哈希,适用于在浏览器中加载资源。
pathname 属性: 返回 URL 的路径部分,对于 data: URL,这个部分基本上不适用,因为 data: URL 没有传统意义上的路径。
但是在vite中有很多加载静态资源的方式,其他几种方式还没有尝试,不过直接使用默认public文件下的静态资源的方式是行不通的。

推荐问题
logo
Microsoft
子站问答
访问
宣传栏