Files
Desktop/scripts/esbuild.js
automated-signal 5fb2d59449 Simplify esbuild script
Co-authored-by: Fedor Indutny <79877362+indutny-signal@users.noreply.github.com>
2026-03-24 14:01:06 -07:00

212 lines
5.4 KiB
JavaScript

// Copyright 2022 Signal Messenger, LLC
// SPDX-License-Identifier: AGPL-3.0-only
const esbuild = require('esbuild');
const path = require('node:path');
const fs = require('node:fs');
const fastGlob = require('fast-glob');
const ROOT_DIR = path.join(__dirname, '..');
const BUNDLES_DIR = 'bundles';
const NODE_MODULES_DIR = path.join(ROOT_DIR, 'node_modules');
const watch = process.argv.some(argv => argv === '-w' || argv === '--watch');
const isProd = process.argv.some(argv => argv === '-prod' || argv === '--prod');
const noBundle = process.argv.some(argv => argv === '--no-bundle');
const noScripts = process.argv.some(argv => argv === '--no-scripts');
const nodeDefaults = {
platform: 'node',
target: 'es2023',
// Disabled even in dev because the debugger is broken
sourcemap: false,
logLevel: 'info',
plugins: [
{
name: 'resolve-ts',
setup(b) {
b.onResolve({ filter: /\.js$/ }, args => {
if (!args.path.startsWith('.')) {
return undefined;
}
const targetPath = path.join(args.resolveDir, args.path);
if (targetPath.startsWith(NODE_MODULES_DIR)) {
return undefined;
}
const tsPath = targetPath.replace(/\.js$/, '.ts');
const tsxPath = targetPath.replace(/\.js$/, '.tsx');
if (fs.existsSync(tsPath)) {
return { path: tsPath };
}
if (fs.existsSync(tsxPath)) {
return { path: tsxPath };
}
return undefined;
});
},
},
],
};
const bundleDefaults = {
...nodeDefaults,
define: {
'process.env.NODE_ENV': isProd ? '"production"' : '"development"',
},
bundle: true,
minify: isProd,
external: [
// Native libraries
'@signalapp/libsignal-client',
'@signalapp/libsignal-client/zkgroup',
'@signalapp/ringrtc',
'@signalapp/sqlcipher',
'@signalapp/mute-state-change',
'@indutny/mac-screen-share',
'electron',
'fs-xattr',
'fsevents',
'mac-screen-capture-permissions',
'sass',
// Things that don't bundle well
'got',
'node-fetch',
'pino',
'proxy-agent',
// Large libraries (3.7mb total)
// See: https://esbuild.github.io/api/#analyze
'emoji-datasource',
'fabric',
'google-libphonenumber',
'moment',
'quill',
// Imported, but not used in production builds
'mocha',
// Uses fast-glob and dynamic requires
'./preload_test.preload.js',
],
};
const sandboxedPreloadDefaults = {
...nodeDefaults,
define: {
'process.env.NODE_ENV': isProd ? '"production"' : '"development"',
},
external: ['electron'],
bundle: true,
minify: isProd,
};
const sandboxedBrowserDefaults = {
...sandboxedPreloadDefaults,
chunkNames: 'chunks/[name]-[hash]',
format: 'esm',
outdir: path.join(ROOT_DIR, BUNDLES_DIR),
platform: 'browser',
splitting: true,
};
async function build(config) {
const instance = await esbuild.context(config);
if (watch) {
await instance.watch();
} else {
await instance.rebuild();
await instance.dispose();
}
}
async function main() {
await Promise.all([
!noScripts &&
build({
...nodeDefaults,
format: 'cjs',
mainFields: ['browser', 'main'],
entryPoints: [
'preload.wrapper.ts',
...fastGlob
.sync('{app,ts,build}/**/*.{ts,tsx}', {
onlyFiles: true,
cwd: ROOT_DIR,
})
.filter(file => !file.endsWith('.d.ts')),
],
outdir: path.join(ROOT_DIR),
}),
!noBundle &&
build({
...bundleDefaults,
mainFields: ['browser', 'main'],
entryPoints: [
path.join(ROOT_DIR, 'ts', 'windows', 'main', 'preload.preload.ts'),
],
outfile: path.join(ROOT_DIR, 'preload.bundle.js'),
}),
!noBundle &&
build({
...sandboxedBrowserDefaults,
mainFields: ['browser', 'main'],
entryPoints: [
path.join(ROOT_DIR, 'ts', 'windows', 'about', 'app.dom.tsx'),
path.join(ROOT_DIR, 'ts', 'windows', 'calldiagnostic', 'app.dom.tsx'),
path.join(ROOT_DIR, 'ts', 'windows', 'debuglog', 'app.dom.tsx'),
path.join(ROOT_DIR, 'ts', 'windows', 'loading', 'start.dom.ts'),
path.join(ROOT_DIR, 'ts', 'windows', 'permissions', 'app.dom.tsx'),
path.join(ROOT_DIR, 'ts', 'windows', 'screenShare', 'app.dom.tsx'),
],
}),
!noBundle &&
build({
...sandboxedPreloadDefaults,
mainFields: ['browser', 'main'],
entryPoints: [
path.join(ROOT_DIR, 'ts', 'windows', 'about', 'preload.preload.ts'),
path.join(
ROOT_DIR,
'ts',
'windows',
'calldiagnostic',
'preload.preload.ts'
),
path.join(
ROOT_DIR,
'ts',
'windows',
'debuglog',
'preload.preload.ts'
),
path.join(ROOT_DIR, 'ts', 'windows', 'loading', 'preload.preload.ts'),
path.join(
ROOT_DIR,
'ts',
'windows',
'permissions',
'preload.preload.ts'
),
path.join(
ROOT_DIR,
'ts',
'windows',
'screenShare',
'preload.preload.ts'
),
],
format: 'cjs',
outdir: 'bundles',
}),
]);
}
main().catch(error => {
console.error(error.stack);
process.exit(1);
});