build: refactor build script
parent
8d95184abe
commit
607a3c8719
142
build.js
142
build.js
|
|
@ -1,5 +1,30 @@
|
|||
import * as esbuild from 'esbuild';
|
||||
import { cp, mkdir } from 'fs/promises';
|
||||
import { cpSync, rmSync, existsSync, mkdirSync, watch } from 'node:fs';
|
||||
import { createRequire } from 'node:module';
|
||||
import { execSync } from 'child_process';
|
||||
|
||||
const require = createRequire(import.meta.url);
|
||||
const pkg = require('./package.json');
|
||||
const isProd = process.env.NODE_ENV === 'production';
|
||||
|
||||
let _commitHash = null;
|
||||
const getCommitHash = () => {
|
||||
if (_commitHash) return _commitHash;
|
||||
try {
|
||||
_commitHash = execSync('git rev-parse --short HEAD').toString().trim();
|
||||
} catch {
|
||||
_commitHash = 'unknown';
|
||||
}
|
||||
return _commitHash;
|
||||
};
|
||||
|
||||
const jsBanner = `/*!
|
||||
* ${pkg.name} v${pkg.version}+${getCommitHash()}
|
||||
* ${pkg.description}
|
||||
* (c) ${new Date().getFullYear()} ${pkg.author}
|
||||
* ${pkg.repository.url?.replace(/\.git$/, '')}
|
||||
* Released under the ${pkg.license} License.
|
||||
*/`;
|
||||
|
||||
const userscriptBanner = `// ==UserScript==
|
||||
// @name Gemini NanoBanana Watermark Remover
|
||||
|
|
@ -20,51 +45,82 @@ const userscriptBanner = `// ==UserScript==
|
|||
// ==/UserScript==
|
||||
`;
|
||||
|
||||
async function build() {
|
||||
console.log(`Start Build... ${process.env.NODE_ENV === 'production' ? 'production' : 'development'}\r\n`);
|
||||
const copyAssetsPlugin = {
|
||||
name: 'copy-assets',
|
||||
setup(build) {
|
||||
build.onEnd(() => {
|
||||
console.log('📂 Syncing static assets...');
|
||||
try {
|
||||
if (!existsSync('dist/i18n')) mkdirSync('dist/i18n', { recursive: true });
|
||||
cpSync('src/i18n', 'dist/i18n', { recursive: true });
|
||||
cpSync('public', 'dist', { recursive: true });
|
||||
} catch (err) {
|
||||
console.error('❌ Asset copy failed:', err);
|
||||
}
|
||||
});
|
||||
},
|
||||
};
|
||||
|
||||
// Build website - app.js
|
||||
console.log('Building: dist/app.js');
|
||||
await esbuild.build({
|
||||
entryPoints: ['src/app.js'],
|
||||
bundle: true,
|
||||
format: 'esm',
|
||||
outfile: 'dist/app.js',
|
||||
loader: { '.png': 'dataurl' },
|
||||
publicPath: '/',
|
||||
minify: process.env.NODE_ENV === 'production'
|
||||
});
|
||||
const commonConfig = {
|
||||
bundle: true,
|
||||
loader: { '.png': 'dataurl' },
|
||||
minify: isProd,
|
||||
logLevel: 'info',
|
||||
};
|
||||
|
||||
// Build website - i18n.js
|
||||
console.log('Building: dist/i18n.js');
|
||||
await esbuild.build({
|
||||
entryPoints: ['src/i18n.js'],
|
||||
bundle: true,
|
||||
format: 'esm',
|
||||
outfile: 'dist/i18n.js',
|
||||
minify: process.env.NODE_ENV === 'production'
|
||||
});
|
||||
// Build website - app.js
|
||||
const websiteCtx = await esbuild.context({
|
||||
...commonConfig,
|
||||
entryPoints: ['src/app.js'],
|
||||
outfile: 'dist/app.js',
|
||||
platform: 'browser',
|
||||
target: ['es2020'],
|
||||
banner: { js: jsBanner },
|
||||
sourcemap: !isProd,
|
||||
plugins: [copyAssetsPlugin],
|
||||
});
|
||||
|
||||
// Build userscript
|
||||
console.log('Building: dist/userscript/gemini-watermark-remover.user.js');
|
||||
await mkdir('dist/userscript', { recursive: true });
|
||||
await esbuild.build({
|
||||
entryPoints: ['src/userscript/index.js'],
|
||||
bundle: true,
|
||||
format: 'iife',
|
||||
outfile: 'dist/userscript/gemini-watermark-remover.user.js',
|
||||
banner: { js: userscriptBanner },
|
||||
loader: { '.png': 'dataurl' },
|
||||
minify: false
|
||||
});
|
||||
// Build userscript
|
||||
const userscriptCtx = await esbuild.context({
|
||||
...commonConfig,
|
||||
entryPoints: ['src/userscript/index.js'],
|
||||
format: 'iife',
|
||||
outfile: 'dist/userscript/gemini-watermark-remover.user.js',
|
||||
banner: { js: userscriptBanner },
|
||||
minify: false
|
||||
});
|
||||
|
||||
// Copy static files
|
||||
console.log('Copying: src/i18n -> dist/i18n');
|
||||
await cp('src/i18n', 'dist/i18n', { recursive: true });
|
||||
console.log('Copying: public -> dist');
|
||||
await cp('public', 'dist', { recursive: true });
|
||||
console.log(`🚀 Starting build process... [${isProd ? 'PRODUCTION' : 'DEVELOPMENT'}]`);
|
||||
|
||||
console.log('\r\n✓ Build complete');
|
||||
if (existsSync('dist')) rmSync('dist', { recursive: true });
|
||||
mkdirSync('dist/userscript', { recursive: true });
|
||||
|
||||
if (isProd) {
|
||||
await Promise.all([websiteCtx.rebuild(), userscriptCtx.rebuild()]);
|
||||
console.log('✅ Build complete!');
|
||||
process.exit(0);
|
||||
} else {
|
||||
await Promise.all([websiteCtx.watch(), userscriptCtx.watch()]);
|
||||
|
||||
const watchDir = (dir, dest) => {
|
||||
let debounceTimer = null;
|
||||
|
||||
watch(dir, { recursive: true }, (eventType, filename) => {
|
||||
if (!filename) return;
|
||||
if (debounceTimer) clearTimeout(debounceTimer);
|
||||
|
||||
debounceTimer = setTimeout(() => {
|
||||
console.log(`📂 Asset changed: ${filename}`);
|
||||
try {
|
||||
cpSync(dir, dest, { recursive: true });
|
||||
} catch (e) {
|
||||
console.error('Sync failed:', e);
|
||||
}
|
||||
}, 100);
|
||||
});
|
||||
};
|
||||
watchDir('src/i18n', 'dist/i18n');
|
||||
watchDir('public', 'dist');
|
||||
|
||||
console.log('👀 Watching for changes...');
|
||||
}
|
||||
|
||||
build().catch(console.error);
|
||||
|
|
|
|||
|
|
@ -1,6 +1,13 @@
|
|||
{
|
||||
"name": "gemini-watermark-remover",
|
||||
"description": "Automatically removes watermarks from Gemini AI generated images",
|
||||
"version": "1.0.0",
|
||||
"author": "journey-ad",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/journey-ad/gemini-watermark-remover.git"
|
||||
},
|
||||
"license": "MIT",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"dev": "node build.js",
|
||||
|
|
|
|||
Loading…
Reference in New Issue