Files
skeleton/packages/plugin/scripts/generate-jss.ts

63 lines
2.0 KiB
TypeScript

import type { CssInJs } from 'postcss-js';
import { generateBaseTWStyles, transpileCssToJs } from './compile-css-to-js.js';
import { mkdir, writeFile } from 'fs/promises';
import plugin from 'tailwindcss/plugin.js';
const INTELLISENSE_FILE_NAME = 'generated-classes.js';
const GENERATED_DIR_PATH = `./src/tailwind/generated`;
async function exec() {
// Makes directory that stores our generated CSS-in-JS
await mkdir(GENERATED_DIR_PATH).catch(() => {
// directory already exists
});
const baseTWStyles = await generateBaseTWStyles();
const generatedComponentJSS = await transpileCssToJs('./src/styles/components.css');
const cleanedComponentClasses = removeDuplicateClasses(generatedComponentJSS, baseTWStyles);
const componentClasses = patchMediaQueries(cleanedComponentClasses);
const componentPlugin = plugin(({ addComponents }) => {
addComponents(componentClasses);
});
const generatedBaseJSS = await transpileCssToJs('./src/styles/base.css', [componentPlugin]);
const baseStyles = removeDuplicateClasses(generatedBaseJSS, baseTWStyles);
// Creates the generated CSS-in-JS file
await writeFile(
`${GENERATED_DIR_PATH}/${INTELLISENSE_FILE_NAME}`,
`module.exports = { components: ${JSON.stringify(componentClasses)}, base: ${JSON.stringify(baseStyles)} };`
).catch((e) => console.error(e));
}
// Purges the generated CSS-in-JS file of duplicate TW classes
function removeDuplicateClasses(cssInJs: CssInJs, baseTWStyles: CssInJs) {
// We'll delete all the TW Base styles (i.e. html {...} body {...} etc.)
for (const key of Object.keys(cssInJs)) {
if (baseTWStyles[key] !== undefined) delete cssInJs[key];
}
return cssInJs;
}
// Moves all of the media queries towards the end of the cssInJs object.
function patchMediaQueries(cssInJs: CssInJs) {
const mediaQueries: CssInJs = {};
for (const key of Object.keys(cssInJs)) {
if (key.startsWith('@media')) {
mediaQueries[key] = cssInJs[key];
delete cssInJs[key];
}
}
for (const key of Object.keys(mediaQueries)) {
cssInJs[key] = mediaQueries[key];
}
return cssInJs;
}
exec();