UNPKG

@yinxulai/babel-plugin-less

Version:

一个 `Babel` 插件,用来帮助你对文件中引用的 `less` 进行预处理、转换成 `css` 并自动管理, 支持 `cssModule`, `autoPrefix`

80 lines 3.09 kB
import path from 'path'; import hash from './hash'; import * as t from '@babel/types'; import { execFileSync } from 'child_process'; import { insertStyleElement, styleTokenMap } from './template'; function isDevelopment() { return process.env.NODE_ENV === 'development'; } // 同步调用 PostCss 处理资源 function transformStyle(options) { const isDev = isDevelopment(); const optionsStr = JSON.stringify(options); const transform = path.resolve(__dirname, `./transform.${isDev ? 'ts' : 'js'}`); const result = execFileSync(isDev ? 'ts-node' : 'node', [transform, optionsStr]); return JSON.parse(result.toString()); } function getImportDefaultSpecifier(node) { const defaultImport = node.specifiers.find(s => t.isImportDefaultSpecifier(s)); if (t.isImportDefaultSpecifier(defaultImport)) { return defaultImport; } return null; } function generateImportStyleAST(data, node) { const nodeArray = []; if (data.css) { const elementID = hash(data.css); nodeArray.push(insertStyleElement(elementID, data.css)); } if (data.tokens) { // 获取默认导入的信息 // import * from '*' const defaultImport = getImportDefaultSpecifier(node); // 用户没有默认导入 // TODO: 支持其他类型的导入 if (!defaultImport) { return nodeArray; } // TODO: 考虑允许用户其他方式导入 const variableName = defaultImport.local.name; nodeArray.push(styleTokenMap(variableName, data.tokens)); } return nodeArray; } function plugin() { return { name: 'less', // 语法转换 visitor: { // import styles from './style.css'; ImportDeclaration: { enter: function (data, state) { const { source } = data.node; const pluginOptions = state.opts; const matcher = /(.less)|(.css)$/i; const entryfile = state.file.opts.filename; const importSourceliteralValue = source.value; const styleFileName = path.resolve(path.dirname(entryfile), importSourceliteralValue); // 匹配文件后缀 if (!matcher.test(importSourceliteralValue)) { return; } // import '*' // 关闭 css module if (!data.node.specifiers.length) { pluginOptions.cssModule = false; } // 转换 css const result = transformStyle(Object.assign(Object.assign({}, pluginOptions), { fileName: styleFileName })); // 生成 AST const newImportAST = generateImportStyleAST(result, data.node); // 替换当前节点 data.replaceWithMultiple(newImportAST); } }, } }; } export default plugin; //# sourceMappingURL=index.js.map