vite-plugin-vue-css-modules
Version:
✨ Ultimate solution for using CSS modules without any hassle. Automatic replacement for Vue templates and scripts
83 lines (82 loc) • 3.74 kB
JavaScript
import { devNameGeneratorContext, prodNameGeneratorContext, } from "./nameGenerators.js";
import { MagicString, parse as sfcParse } from "@vue/compiler-sfc";
import { transformPug } from "./transformPug2.js";
import { transformHtml } from "./transformHtml2.js";
import { transformScript } from "./transformScript.js";
const IS_DEVELOPMENT = process.env.NODE_ENV !== "production";
function plugin({ preservePrefix = "--", scriptTransform = true, nameGenerator = IS_DEVELOPMENT
? devNameGeneratorContext()
: prodNameGeneratorContext(), } = {}) {
return {
name: "Vue CSS Modules",
enforce: "pre",
config() {
return {
css: {
modules: {
generateScopedName: nameGenerator,
},
},
};
},
transform(code, id) {
if (id.match(/\.vue$/)) {
code = code.replace(/\r\n/g, "\n");
const { descriptor: { template, script, scriptSetup, styles }, } = sfcParse(code);
const styleModule = styles.find(s => s.module);
const styleModuleName = typeof styleModule?.module === "string"
? styleModule.module
: "$style";
if (!styleModule && !template.attrs["css-modules"]) {
return;
}
const localNameGenerator = (name) => nameGenerator(name, id, styleModule?.content ?? "");
const sfcTransform = new MagicString(code);
if (template) {
template.lang ??= "html";
switch (template.lang) {
case "pug":
{
transformPug(template.content, template.loc.start.offset, sfcTransform, {
preservePrefix,
localNameGenerator,
module: scriptTransform ? false : styleModuleName,
});
}
break;
case "html":
{
transformHtml(template.content, template.loc.start.offset, sfcTransform, {
preservePrefix,
localNameGenerator,
module: scriptTransform ? false : styleModuleName,
});
}
break;
default:
console.warn(`[CSS Modules] Unsupported template language "${template.lang}"! Skipped`);
return;
}
}
if (scriptTransform) {
if (scriptSetup) {
transformScript(scriptSetup.content, scriptSetup.loc.start.offset, sfcTransform, localNameGenerator);
}
if (script) {
transformScript(script.content, script.loc.start.offset, sfcTransform, localNameGenerator);
}
}
return {
code: sfcTransform.toString(),
map: sfcTransform.generateMap({
hires: "boundary",
includeContent: true,
}),
};
}
},
};
}
export { plugin as default, plugin as cssm, };
export { prodNameGeneratorContext, devNameGeneratorContext, };
export { removeCssModulesChunk, } from "./removeCssModulesChunk.js";