ShowerLoop-cc/docker/showerloop/public/uncss.js

139 lines
3.9 KiB
JavaScript

import uncss from 'uncss';
import fs from 'fs';
import path from 'path';
import { fileURLToPath } from 'url';
import { dirname } from 'path';
import * as globModule from 'glob';
import cleanCss from 'clean-css';
const CleanCSS = cleanCss;
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);
const { glob } = globModule;
// Find all CSS files in the static directory
const findCssFiles = () => {
const staticDir = path.join(__dirname, 'static');
const cssFiles = [];
if (fs.existsSync(staticDir)) {
// Look for CSS files in static/css and static/css/vendor
const vendorFiles = glob.sync(path.join(staticDir, 'css', 'vendor', '*.css'));
const regularFiles = glob.sync(path.join(staticDir, 'css', '*.css'));
cssFiles.push(...vendorFiles, ...regularFiles);
}
return cssFiles;
};
// Get all HTML files from the public directory
const findHtmlFiles = () => {
const publicDir = path.join(__dirname, 'public');
if (fs.existsSync(publicDir)) {
return glob.sync(path.join(publicDir, '**', '*.html'));
}
return [];
};
// Create a directory if it doesn't exist
const ensureDir = (dir) => {
if (!fs.existsSync(dir)) {
fs.mkdirSync(dir, { recursive: true });
}
};
// Create the optimized directory
const createOptimizedDir = () => {
const optimizedDir = path.join(__dirname, 'public', 'css', 'optimized');
ensureDir(optimizedDir);
return optimizedDir;
};
// Process CSS files
const processCssFiles = (cssFiles, htmlFiles) => {
// If no HTML files found, exit
if (htmlFiles.length === 0) {
console.log('No HTML files found. Make sure to run Hugo build first.');
return;
}
// If no CSS files found, look in the public directory
if (cssFiles.length === 0) {
console.log('No CSS files found in static directory, looking in public directory...');
const publicCssDir = path.join(__dirname, 'public', 'css');
const publicVendorCssDir = path.join(publicCssDir, 'vendor');
if (fs.existsSync(publicVendorCssDir)) {
const vendorFiles = glob.sync(path.join(publicVendorCssDir, '*.css'));
cssFiles.push(...vendorFiles);
}
if (fs.existsSync(publicCssDir)) {
const regularFiles = glob.sync(path.join(publicCssDir, '*.css'));
cssFiles.push(...regularFiles);
}
}
if (cssFiles.length === 0) {
console.log('No CSS files found. Exiting.');
return;
}
console.log(`Found ${cssFiles.length} CSS files and ${htmlFiles.length} HTML files.`);
// Options for uncss
const options = {
ignoreSheets: [/fonts.googleapis/],
ignore: [
/\.video-js/,
/\.vjs-/,
/\.material-/,
/\.mdl-/,
/\.fa-/,
/\.is-/,
/\.has-/,
// Add more selectors to ignore as needed
],
timeout: 5000,
report: true
};
const optimizedDir = createOptimizedDir();
// Process each CSS file
cssFiles.forEach((cssFile) => {
console.log(`Processing ${cssFile}...`);
const filename = path.basename(cssFile);
const outputFile = path.join(optimizedDir, filename);
// Process the CSS
uncss(htmlFiles, { ...options, stylesheets: [cssFile] }, (error, output) => {
if (error) {
console.error(`Error processing ${cssFile}:`, error);
return;
}
// Minify the CSS
const minifier = new CleanCSS();
const minified = minifier.minify(output);
// Write the output
fs.writeFileSync(outputFile, minified.styles);
// Report
const originalSize = fs.statSync(cssFile).size;
const optimizedSize = minified.styles.length;
const savings = ((originalSize - optimizedSize) / originalSize * 100).toFixed(2);
console.log(`${filename}: ${originalSize} bytes -> ${optimizedSize} bytes (${savings}% saved)`);
});
});
};
// Main execution
const htmlFiles = findHtmlFiles();
const cssFiles = findCssFiles();
processCssFiles(cssFiles, htmlFiles);