diff --git a/build.js b/build.js index aef1f65b7..d6b873a38 100644 --- a/build.js +++ b/build.js @@ -5,17 +5,15 @@ import {dequal} from 'dequal' import esbuild from 'esbuild' import fsExtra from 'fs-extra' import glob from 'glob' +import {Features, bundle, composeVisitors} from 'lightningcss' +import {pxToRem, suffixes} from 'lightningcss-plugins' import {builtinModules} from 'module' import fs from 'node:fs' import path from 'node:path' import {pathToFileURL} from 'node:url' -import postcss from 'postcss' -import postcssModules from 'postcss-modules' -import pxtorem from 'postcss-pxtorem' import sade from 'sade' -// Interestingly sass seems to outperform sass-embedded about 2x -import * as sass from 'sass' +const {fromEntries, entries} = Object const BROWSER_TARGET = 'browser' const SERVER_TARGET = 'server' @@ -366,57 +364,55 @@ function jsEntry({watch, test}) { } } -const sassExports = new Map() const sassCache = new Map() -const postCssPlugins = [ - pxtorem({ - minPixelValue: 2, - propList: ['*'] - }), - postcssModules({ - localsConvention: 'dashes', - generateScopedName(name, fileName, css) { - const module = path.basename(fileName).split('.')[0] - if (name.startsWith('root-')) name = name.slice(5) - if (name.startsWith('root')) name = name.slice(4) - return `alinea-${module}${name ? '-' + name : ''}` - }, - getJSON(file, json) { - sassExports.set(file, `export default ${JSON.stringify(json, null, 2)}`) - } - }) -] - async function processScss(file) { const prev = sassCache.get(file) if (prev) { const key = hash(prev.watchFiles) if (key === prev.key) return prev } - const {css, loadedUrls, sourceMap} = sass.compile(file, scssOptions) - const watchFiles = loadedUrls.map(url => { - return url.pathname.substring(isWindows ? 1 : 0) + const isModule = file.endsWith('.module.scss') + const {code, map, exports, dependencies} = bundle({ + filename: file, + code: fs.readFileSync(file), + sourceMap: true, + include: Features.Nesting, + visitor: composeVisitors([suffixes, pxToRem()]), + errorRecovery: true, + cssModules: isModule + ? { + pattern: 'alinea-[name]-[local]' + } + : undefined }) + const watchFiles = [file].concat( + dependencies?.map(dependency => { + return dependency.url + }) ?? [] + ) const key = hash(watchFiles) - if (!file.endsWith('.module.scss')) { - const result = {key, css, watchFiles} - sassCache.set(file, result) - return result - } - const processed = await postcss(postCssPlugins).process(css, { - from: file, - map: { - inline: true, - prev: sourceMap - } - }) const result = { key, - css: processed.css, + css: Buffer.concat([ + code, + Buffer.from('\n/*# sourceMappingURL=data:application/json;base64,'), + Buffer.from(map.toString('base64')), + Buffer.from(' */') + ]), watchFiles, - isModule: true, - json: sassExports.get(file) + isModule: isModule, + json: `export default ${ + exports + ? JSON.stringify( + fromEntries( + entries(exports).map(([key, value]) => [key, value.name]) + ), + null, + 2 + ) + : '{}' + }` } sassCache.set(file, result) return result diff --git a/package.json b/package.json index 36eb843c1..56c5ef9d0 100644 --- a/package.json +++ b/package.json @@ -88,6 +88,8 @@ "esbx": "^0.0.18", "find-config": "^1.0.0", "glob": "^7.2.0", + "lightningcss": "^1.22.0", + "lightningcss-plugins": "^0.0.1", "memfs": "^3.4.1", "npm-run-all": "^4.1.5", "postcss-pxtorem": "^6.0.0", diff --git a/yarn.lock b/yarn.lock index 5ca670b3a..069efae97 100644 --- a/yarn.lock +++ b/yarn.lock @@ -2701,6 +2701,8 @@ __metadata: esbx: ^0.0.18 find-config: ^1.0.0 glob: ^7.2.0 + lightningcss: ^1.22.0 + lightningcss-plugins: ^0.0.1 memfs: ^3.4.1 npm-run-all: ^4.1.5 postcss-pxtorem: ^6.0.0 @@ -3852,6 +3854,15 @@ __metadata: languageName: node linkType: hard +"detect-libc@npm:^1.0.3": + version: 1.0.3 + resolution: "detect-libc@npm:1.0.3" + bin: + detect-libc: ./bin/detect-libc.js + checksum: daaaed925ffa7889bd91d56e9624e6c8033911bb60f3a50a74a87500680652969dbaab9526d1e200a4c94acf80fc862a22131841145a0a8482d60a99c24f4a3e + languageName: node + linkType: hard + "detect-node@npm:^2.0.4, detect-node@npm:^2.1.0": version: 2.1.0 resolution: "detect-node@npm:2.1.0" @@ -6415,6 +6426,115 @@ fsevents@~2.3.2: languageName: node linkType: hard +"lightningcss-darwin-arm64@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-darwin-arm64@npm:1.22.0" + conditions: os=darwin & cpu=arm64 + languageName: node + linkType: hard + +"lightningcss-darwin-x64@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-darwin-x64@npm:1.22.0" + conditions: os=darwin & cpu=x64 + languageName: node + linkType: hard + +"lightningcss-freebsd-x64@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-freebsd-x64@npm:1.22.0" + conditions: os=freebsd & cpu=x64 + languageName: node + linkType: hard + +"lightningcss-linux-arm-gnueabihf@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-linux-arm-gnueabihf@npm:1.22.0" + conditions: os=linux & cpu=arm + languageName: node + linkType: hard + +"lightningcss-linux-arm64-gnu@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-linux-arm64-gnu@npm:1.22.0" + conditions: os=linux & cpu=arm64 & libc=glibc + languageName: node + linkType: hard + +"lightningcss-linux-arm64-musl@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-linux-arm64-musl@npm:1.22.0" + conditions: os=linux & cpu=arm64 & libc=musl + languageName: node + linkType: hard + +"lightningcss-linux-x64-gnu@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-linux-x64-gnu@npm:1.22.0" + conditions: os=linux & cpu=x64 & libc=glibc + languageName: node + linkType: hard + +"lightningcss-linux-x64-musl@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-linux-x64-musl@npm:1.22.0" + conditions: os=linux & cpu=x64 & libc=musl + languageName: node + linkType: hard + +"lightningcss-plugins@npm:^0.0.1": + version: 0.0.1 + resolution: "lightningcss-plugins@npm:0.0.1" + peerDependencies: + lightningcss: ">1.22.0" + checksum: 899f8d137ae80019da111e1f9fef8d88ce34ce58a9886d6c8ac501246fe4c93b8f2988d7eddbe003217a92ca176c151f7ddd1b0b4d48e542f8ea2a0817a6953e + languageName: node + linkType: hard + +"lightningcss-win32-x64-msvc@npm:1.22.0": + version: 1.22.0 + resolution: "lightningcss-win32-x64-msvc@npm:1.22.0" + conditions: os=win32 & cpu=x64 + languageName: node + linkType: hard + +"lightningcss@npm:^1.22.0": + version: 1.22.0 + resolution: "lightningcss@npm:1.22.0" + dependencies: + detect-libc: ^1.0.3 + lightningcss-darwin-arm64: 1.22.0 + lightningcss-darwin-x64: 1.22.0 + lightningcss-freebsd-x64: 1.22.0 + lightningcss-linux-arm-gnueabihf: 1.22.0 + lightningcss-linux-arm64-gnu: 1.22.0 + lightningcss-linux-arm64-musl: 1.22.0 + lightningcss-linux-x64-gnu: 1.22.0 + lightningcss-linux-x64-musl: 1.22.0 + lightningcss-win32-x64-msvc: 1.22.0 + dependenciesMeta: + lightningcss-darwin-arm64: + optional: true + lightningcss-darwin-x64: + optional: true + lightningcss-freebsd-x64: + optional: true + lightningcss-linux-arm-gnueabihf: + optional: true + lightningcss-linux-arm64-gnu: + optional: true + lightningcss-linux-arm64-musl: + optional: true + lightningcss-linux-x64-gnu: + optional: true + lightningcss-linux-x64-musl: + optional: true + lightningcss-win32-x64-msvc: + optional: true + checksum: 6b9a04846243a2161ac12ee098f9c2143a1a06fb683228ef0433473257751a709b0bafa195efa8d3d8f1556ca60c54f5434caeb172874a8daced552dedcbed93 + languageName: node + linkType: hard + "lilconfig@npm:^2.0.5": version: 2.1.0 resolution: "lilconfig@npm:2.1.0"