mirror of
https://github.com/SquidDev-CC/CC-Tweaked
synced 2025-11-14 20:17:11 +00:00
Small cleanup to our web build scripts
- Update to Rollup 4.x - Replace terser and postcss with swc and lightningcss. This is definitely more code for us to write (maybe I should turn them into proper plugins we can depend on), but both speedier and fewer dependencies. - Drop dependency on glob - we can get away with fs.readdir for what we needed it for.
This commit is contained in:
2597
package-lock.json
generated
2597
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@@ -13,17 +13,16 @@
|
|||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@rollup/plugin-node-resolve": "^15.2.1",
|
"@rollup/plugin-node-resolve": "^15.2.1",
|
||||||
"@rollup/plugin-terser": "^0.4.3",
|
|
||||||
"@rollup/plugin-typescript": "^11.0.0",
|
"@rollup/plugin-typescript": "^11.0.0",
|
||||||
"@rollup/plugin-url": "^8.0.1",
|
"@rollup/plugin-url": "^8.0.1",
|
||||||
"@types/glob": "^8.1.0",
|
"@swc/core": "^1.3.92",
|
||||||
"glob": "^10.3.4",
|
"@types/node": "^20.8.3",
|
||||||
|
"lightningcss": "^1.22.0",
|
||||||
"preact-render-to-string": "^6.2.1",
|
"preact-render-to-string": "^6.2.1",
|
||||||
"rehype": "^13.0.0",
|
"rehype": "^13.0.0",
|
||||||
"rehype-highlight": "^7.0.0",
|
"rehype-highlight": "^7.0.0",
|
||||||
"rehype-react": "^8.0.0",
|
"rehype-react": "^8.0.0",
|
||||||
"rollup": "^3.19.1",
|
"rollup": "^4.0.0",
|
||||||
"rollup-plugin-postcss": "^4.0.2",
|
|
||||||
"tsx": "^3.12.10",
|
"tsx": "^3.12.10",
|
||||||
"typescript": "^5.2.2"
|
"typescript": "^5.2.2"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,19 +4,109 @@
|
|||||||
|
|
||||||
import path from "path";
|
import path from "path";
|
||||||
|
|
||||||
import terser from "@rollup/plugin-terser";
|
|
||||||
import resolve from "@rollup/plugin-node-resolve";
|
import resolve from "@rollup/plugin-node-resolve";
|
||||||
import typescript from "@rollup/plugin-typescript";
|
import typescript from "@rollup/plugin-typescript";
|
||||||
import url from "@rollup/plugin-url";
|
import url from "@rollup/plugin-url";
|
||||||
import postcss from "rollup-plugin-postcss";
|
import { minify as minifyJavascript } from "@swc/core";
|
||||||
|
import { transform as transformCss } from "lightningcss";
|
||||||
|
|
||||||
const input = "src/frontend";
|
const inputDir = "src/frontend";
|
||||||
|
|
||||||
const minify = args => !args.configDebug;
|
/**
|
||||||
|
* Generate an ESM module from a list of {@code ligntingcss} exports.
|
||||||
|
*
|
||||||
|
* @param {string} filename The input file name.
|
||||||
|
* @param {string} input The input code.
|
||||||
|
* @param {boolean} minify Whether to minify the css.
|
||||||
|
* @returns {string} The ESM module, containing the list of exports.
|
||||||
|
*/
|
||||||
|
const compileCss = (filename, input, minify) => {
|
||||||
|
const { code, exports } = transformCss({
|
||||||
|
filename,
|
||||||
|
cssModules: filename.endsWith(".module.css"),
|
||||||
|
pattern: "[local]-[hash]",
|
||||||
|
code: Buffer.from(input),
|
||||||
|
minify,
|
||||||
|
});
|
||||||
|
|
||||||
|
let output = "";
|
||||||
|
let importId = 0;
|
||||||
|
for (const [name, symbol] of Object.entries(exports ?? {})) {
|
||||||
|
let className = JSON.stringify(symbol.name);
|
||||||
|
for (const dep of symbol.composes) {
|
||||||
|
if (dep.type == "dependency") {
|
||||||
|
output += `import { ${dep.name} as import_${++importId}$ } from ${JSON.stringify(dep.specifier)};\n`;
|
||||||
|
className += `+ " " + import_${importId}$`;
|
||||||
|
} else {
|
||||||
|
className += `+ " " + ${JSON.stringify(dep.name)}`;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
output += `export const ${name} = ${className};\n`;
|
||||||
|
}
|
||||||
|
|
||||||
|
return { js: output, css: new TextDecoder().decode(code) };
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Custom plugin for CC: Tweaked specific build logic.
|
||||||
|
*
|
||||||
|
* This handles:
|
||||||
|
* - Minifying JS using swc, which is faster than using terser.
|
||||||
|
* - Importing CSS files.
|
||||||
|
* - Importing plain text files from our "mount/" directory.
|
||||||
|
* - Resoving our TeaVM compiled classes and resources files.
|
||||||
|
*
|
||||||
|
* @param {boolean} minify Whether to minify our sources.
|
||||||
|
* @returns {@type import("rollup").Plugin} Our plugin.
|
||||||
|
*/
|
||||||
|
const ccTweaked = minify => {
|
||||||
|
let cssChunks = [];
|
||||||
|
return {
|
||||||
|
name: "cc-tweaked",
|
||||||
|
|
||||||
|
buildStart() {
|
||||||
|
cssChunks = [];
|
||||||
|
},
|
||||||
|
|
||||||
|
async renderChunk(code) {
|
||||||
|
// Use swc to minify our Javascript.
|
||||||
|
return minify ? (await minifyJavascript(code, { module: true })).code : code;
|
||||||
|
},
|
||||||
|
|
||||||
|
async transform(code, file) {
|
||||||
|
const ext = path.extname(file);
|
||||||
|
if (ext === ".css") {
|
||||||
|
// Compile our CSS file, emitting a JS module, and saving the CSS for later.
|
||||||
|
const { js, css } = compileCss(file, code, minify);
|
||||||
|
cssChunks.push(css);
|
||||||
|
return js;
|
||||||
|
} else if (ext != ".dfpwm" && path.dirname(file) === path.resolve(`${inputDir}/mount`)) {
|
||||||
|
// Bundle all mount files aside from our dfpwm.
|
||||||
|
return `export default ${JSON.stringify(code)};\n`
|
||||||
|
} else {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
async resolveId(source) {
|
||||||
|
if (source === "cct/classes") return path.resolve("build/teaVM/classes.js");
|
||||||
|
if (source === "cct/resources") return path.resolve("build/teaVM/resources.js");
|
||||||
|
return null;
|
||||||
|
},
|
||||||
|
|
||||||
|
generateBundle() {
|
||||||
|
this.emitFile({
|
||||||
|
type: 'asset',
|
||||||
|
fileName: "index.css",
|
||||||
|
source: cssChunks.join(),
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
/** @type import("rollup").RollupOptionsFunction */
|
/** @type import("rollup").RollupOptionsFunction */
|
||||||
export default args => ({
|
export default args => ({
|
||||||
input: [`${input}/index.tsx`],
|
input: [`${inputDir}/index.tsx`],
|
||||||
output: {
|
output: {
|
||||||
// Also defined in build.gradle.kts
|
// Also defined in build.gradle.kts
|
||||||
dir: "build/rollup/",
|
dir: "build/rollup/",
|
||||||
@@ -40,29 +130,6 @@ export default args => ({
|
|||||||
limit: 0,
|
limit: 0,
|
||||||
}),
|
}),
|
||||||
|
|
||||||
postcss({
|
ccTweaked(!args.configDebug),
|
||||||
namedExports: true,
|
|
||||||
minimize: minify(args),
|
|
||||||
extract: true,
|
|
||||||
}),
|
|
||||||
|
|
||||||
{
|
|
||||||
name: "cc-tweaked",
|
|
||||||
async transform(code, file) {
|
|
||||||
// Allow loading files in /mount.
|
|
||||||
const ext = path.extname(file);
|
|
||||||
return ext != ".dfpwm" && path.dirname(file) === path.resolve(`${input}/mount`)
|
|
||||||
? `export default ${JSON.stringify(code)};\n`
|
|
||||||
: null;
|
|
||||||
},
|
|
||||||
|
|
||||||
async resolveId(source) {
|
|
||||||
if (source === "cct/classes") return path.resolve("build/teaVM/classes.js");
|
|
||||||
if (source === "cct/resources") return path.resolve("build/teaVM/resources.js");
|
|
||||||
return null;
|
|
||||||
},
|
|
||||||
},
|
|
||||||
|
|
||||||
minify(args) && terser(),
|
|
||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -11,7 +11,6 @@
|
|||||||
* Yes, this would be so much nicer with next.js.
|
* Yes, this would be so much nicer with next.js.
|
||||||
*/
|
*/
|
||||||
import fs from "fs/promises";
|
import fs from "fs/promises";
|
||||||
import { glob } from "glob";
|
|
||||||
import path from "path";
|
import path from "path";
|
||||||
import { type JSX, h } from "preact";
|
import { type JSX, h } from "preact";
|
||||||
import renderToStaticMarkup from "preact-render-to-string";
|
import renderToStaticMarkup from "preact-render-to-string";
|
||||||
@@ -54,12 +53,15 @@ import { type DataExport, WithExport } from "./components/WithExport";
|
|||||||
|
|
||||||
const dataExport = JSON.parse(await fs.readFile(dataFile, "utf-8")) as DataExport;
|
const dataExport = JSON.parse(await fs.readFile(dataFile, "utf-8")) as DataExport;
|
||||||
|
|
||||||
for (const file of await glob(sourceDir + "/**/*.html")) {
|
for (const file of await fs.readdir(sourceDir, { withFileTypes: true, recursive: true })) {
|
||||||
const contents = await fs.readFile(file, "utf-8");
|
if(!file.isFile() || !file.name.endsWith(".html")) continue;
|
||||||
|
|
||||||
|
const sourcePath = path.join(file.path, file.name);
|
||||||
|
const contents = await fs.readFile(sourcePath, "utf-8");
|
||||||
|
|
||||||
const { result } = await processor.process(contents);
|
const { result } = await processor.process(contents);
|
||||||
|
|
||||||
const outputPath = path.resolve(outputDir, path.relative(sourceDir, file));
|
const outputPath = path.resolve(outputDir, path.relative(sourceDir, sourcePath));
|
||||||
await fs.mkdir(path.dirname(outputPath), { recursive: true });
|
await fs.mkdir(path.dirname(outputPath), { recursive: true });
|
||||||
await fs.writeFile(outputPath, "<!doctype HTML>" + renderToStaticMarkup(<WithExport data={dataExport}>{result}</WithExport>));
|
await fs.writeFile(outputPath, "<!doctype HTML>" + renderToStaticMarkup(<WithExport data={dataExport}>{result}</WithExport>));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -27,6 +27,7 @@
|
|||||||
"allowSyntheticDefaultImports": true,
|
"allowSyntheticDefaultImports": true,
|
||||||
},
|
},
|
||||||
"include": [
|
"include": [
|
||||||
"src",
|
"src/htmlTransform",
|
||||||
|
"src/frontend",
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user