@tarojs/plugin-generator
Version:
Taro 生成器插件
169 lines • 6.74 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
__setModuleDefault(result, mod);
return result;
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.injectTailwindCSSToEntry = exports.emit = void 0;
/* eslint-disable no-console */
const node_path_1 = __importDefault(require("node:path"));
const generator_1 = __importDefault(require("@babel/generator"));
const parser = __importStar(require("@babel/parser"));
const traverse_1 = __importDefault(require("@babel/traverse"));
const t = __importStar(require("@babel/types"));
const dedent_1 = __importDefault(require("dedent"));
const error_1 = require("../../utils/error");
async function emit(ctx) {
return Promise.all([emitCSS(ctx), injectTailwindCSSToEntry(ctx), emitPostcssConfig(ctx)]);
}
exports.emit = emit;
async function emitPostcssConfig(ctx) {
const { fs } = ctx.helper;
const { sourcePath } = ctx.paths;
const configFiles = ['postcss.config.js', 'postcss.config.mjs'];
let configPath = null;
for (const file of configFiles) {
const fullPath = node_path_1.default.join(sourcePath, file);
if (await fs.pathExists(fullPath)) {
configPath = fullPath;
break;
}
}
const code = (0, dedent_1.default)(`
export default {
plugins: {
"@tailwindcss/postcss": {},
}
}
`);
try {
if (!configPath) {
await fs.writeFile(node_path_1.default.join(sourcePath, 'postcss.config.mjs'), code, { encoding: 'utf-8' });
return;
}
const rawCode = await fs.readFile(configPath, 'utf-8');
if (rawCode.trim().length === 0) {
await fs.writeFile(configPath, code, { encoding: 'utf-8' });
return;
}
const ast = parser.parse(rawCode, {
sourceType: 'module',
plugins: ['typescript'],
});
let modified = false;
(0, traverse_1.default)(ast, {
ObjectExpression(path) {
const node = path.node;
// 找到 plugins 节点
const pluginsProp = node.properties.find((prop) => t.isObjectProperty(prop) &&
t.isIdentifier(prop.key, { name: 'plugins' }) &&
t.isObjectExpression(prop.value));
if (pluginsProp) {
const pluginsNode = pluginsProp.value;
const hasTailwind = pluginsNode.properties.some((prop) => {
return (t.isObjectProperty(prop) &&
((t.isStringLiteral(prop.key) && prop.key.value === '@tailwindcss/postcss') ||
(t.isIdentifier(prop.key) && prop.key.name === '@tailwindcss/postcss')));
});
if (!hasTailwind) {
pluginsNode.properties.push(t.objectProperty(t.stringLiteral('@tailwindcss/postcss'), t.objectExpression([])));
modified = true;
}
}
},
});
if (modified) {
const { code } = (0, generator_1.default)(ast, { retainLines: true });
return fs.writeFile(configPath, code);
}
}
catch {
throw new error_1.GeneratorError({
type: error_1.GeneratorErrorType.emitFile,
targetFile: configPath ?? 'postcss.config.mjs',
message: code,
});
}
}
async function emitCSS(ctx) {
const { fs } = ctx.helper;
const outputPath = node_path_1.default.join(ctx.paths.sourcePath, 'tailwind.css');
const importStmt = `@import "weapp-tailwindcss";\n`;
try {
if (await fs.pathExists(outputPath)) {
const existingContent = await fs.readFile(outputPath, 'utf-8');
const alreadyImported = /@import\s+["']weapp-tailwindcss["'];?/.test(existingContent);
if (alreadyImported) {
return;
}
const newContent = `${importStmt}${existingContent.trim()}`;
return fs.writeFile(outputPath, newContent, { encoding: 'utf-8' });
}
return fs.writeFile(outputPath, importStmt, { encoding: 'utf-8' });
}
catch {
throw new error_1.GeneratorError({
type: error_1.GeneratorErrorType.emitFile,
targetFile: outputPath,
message: `@import "weapp-tailwindcss";`,
});
}
}
async function injectTailwindCSSToEntry(ctx) {
const { fs } = ctx.helper;
const { sourcePath } = ctx.paths;
const possibleEntryFiles = ['app.ts', 'app.tsx', 'app.js', 'app.jsx'];
let entryPath;
// 找到存在的入口文件
for (const file of possibleEntryFiles) {
const fullPath = node_path_1.default.join(sourcePath, file);
if (await fs.pathExists(fullPath)) {
entryPath = fullPath;
break;
}
}
if (!entryPath) {
throw new Error('❌ 找不到入口文件');
}
const importStatement = `import './tailwind.css'\n`;
const content = await fs.readFile(entryPath, 'utf-8');
// 如果已导入 tailwind.css,跳过处理
if (/import\s+['"]\.\/tailwind\.css['"]/.test(content)) {
return;
}
const updatedContent = importStatement + content;
try {
await fs.writeFile(entryPath, updatedContent, { encoding: 'utf-8' });
}
catch {
throw new error_1.GeneratorError({
type: error_1.GeneratorErrorType.emitFile,
targetFile: entryPath,
message: importStatement,
});
}
}
exports.injectTailwindCSSToEntry = injectTailwindCSSToEntry;
//# sourceMappingURL=emit.js.map