更改 Svelte / Sapper 中预处理器的顺序

Change the order of preprocessors in Svelte / Sapper

我的 sapper 应用程序遇到了很大的问题。我将汇总与 svelte-preprocess 插件一起使用,将我的 scss 转换为 css:

const preprocess = sveltePreprocess({
  scss: {
    data: `@import '${join(process.cwd(), "src/styles/main.scss")}';`,
    includePaths: ["node_modules", "src"],
  },
  postcss: {
    plugins: [...],
  },
});

之后,我想 运行 另一个预处理器 svelte-image 来优化我的图像。这里的问题是,根据预处理器的设计,影响标记的总是 运行 首先。这将导致我的图像预处理器失败,因为他将遇到 scss 个文件并且无法通过它们。

对我来说最好的解决方案是编写我自己的预处理器,它进行样式设置然后调用图像库。 docs里面有一些例子,但我不是很懂。如果我试试这个例子:

const svelte = require('svelte/compiler');

const { code } = await svelte.preprocess(source, [
    {
        markup: () => myPreprocess()
        style: () => imagePreprocess()
    }
], {
    filename: 'App.svelte' // Which file would that be for sapper?
});

我收到来源未知的错误消息。那么任何人都可以指出正确的方向如何正确调用那个特定的预处理器吗?或者也许是更好的解决方案 ;-)

tl;博士

我在解释如何执行此操作的过程中学到了一半,并意识到它将成为一个有用的实用程序。我创建了一个包来处理这个问题:svelte-sequential-preprocessor.

// rollup.config.js
import svelte from 'rollup-plugin-svelte';
import seqPreprocessor from 'svelte-sequential-preprocessor'
import autoPreprocess from 'svelte-preprocess'
import image from 'svelte-image'
 
export default {
  ...,
  plugins: [
    svelte({
      preprocess: seqPreprocessor([ autoPreprocess(), image() ])
    })
  ]
}

说明

文档中的预处理用法示例用于将预处理函数用作独立实用程序。要将自定义预处理器与汇总一起使用,您可以执行以下操作:

export default {
  ...,
  plugins: [
    svelte({
      preprocess: {
        markup: ({ content, filename }) => myPreprocess(content)
      }
    })
  ]
}

注意:传递给markup()的内容将是一个完整的 svelte 文件,表示为字符串。

但是,即使考虑到这一点,您的提议也不会像您描述的那样奏效。问题是样式预处理器只获取样式作为内容。 svelte-image 需要 markup() 得到的完整 Svelte 组件。

如果你做最后的调整,你可以让它工作。您可以通过使用上面引用的库中的预处理函数,强制每个预处理器 运行 通过所有阶段,然后再调用下一个阶段,而不是尝试在不同阶段调用预处理器。可以找到一个完整的示例 here,但这里是逻辑的基本轮廓。

export default {
  ...,
  plugins: [
    svelte({
      preprocess: {
        markup: async ({ content, filename }) => {
          const processed = await svelte.preprocess(content, autoPreprocess({ options }), { filename });
          // Handle return value and repeat for other preprocessors
          return {
            code: ...,
            dependencies: ...
          };
      }
    })
  ]
}