Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: CLI event hook flags #4457

Merged
merged 14 commits into from May 5, 2022
8 changes: 8 additions & 0 deletions cli/run/watch-cli.ts
Expand Up @@ -15,6 +15,7 @@ import loadAndParseConfigFile from './loadConfigFile';
import loadConfigFromCommand from './loadConfigFromCommand';
import { getResetScreen } from './resetScreen';
import { printTimings } from './timings';
import { createWatchHooks } from './watchHooks';

export async function watch(command: Record<string, any>): Promise<void> {
process.env.ROLLUP_WATCH = 'true';
Expand All @@ -24,6 +25,7 @@ export async function watch(command: Record<string, any>): Promise<void> {
let configWatcher: FSWatcher;
let resetScreen: (heading: string) => void;
const configFile = command.config ? await getConfigPath(command.config) : null;
const runWatchHook = createWatchHooks(command);

onExit(close);
process.on('uncaughtException', close);
Expand Down Expand Up @@ -84,6 +86,7 @@ export async function watch(command: Record<string, any>): Promise<void> {
case 'ERROR':
warnings.flush();
handleError(event.error, true);
runWatchHook('onError');
break;

case 'START':
Expand All @@ -93,6 +96,8 @@ export async function watch(command: Record<string, any>): Promise<void> {
}
resetScreen(underline(`rollup v${rollup.VERSION}`));
}
runWatchHook('onStart');

break;

case 'BUNDLE_START':
Expand All @@ -107,6 +112,7 @@ export async function watch(command: Record<string, any>): Promise<void> {
cyan(`bundles ${bold(input)} → ${bold(event.output.map(relativeId).join(', '))}...`)
);
}
runWatchHook('onBundleStart');
break;

case 'BUNDLE_END':
Expand All @@ -119,12 +125,14 @@ export async function watch(command: Record<string, any>): Promise<void> {
)}`
)
);
runWatchHook('onBundleEnd');
if (event.result && event.result.getTimings) {
printTimings(event.result.getTimings());
}
break;

case 'END':
runWatchHook('onEnd');
if (!silent && isTTY) {
stderr(`\n[${dateTime()}] waiting for changes...`);
}
Expand Down
34 changes: 34 additions & 0 deletions cli/run/watchHooks.ts
@@ -0,0 +1,34 @@
import { execSync } from 'child_process';
import type { RollupWatchHooks } from '../../src/rollup/types';
import { bold, cyan } from '../../src/utils/colors';
import { stderr } from '../logging';

function extractWatchHooks(
command: Record<string, any>
): Partial<Record<RollupWatchHooks, string>> {
if (!Array.isArray(command.watch)) return {};

return command.watch
.filter(value => typeof value === 'object')
.reduce((acc, keyValueOption) => ({ ...acc, ...keyValueOption }), {});
}

export function createWatchHooks(command: Record<string, any>): (hook: RollupWatchHooks) => void {
const watchHooks = extractWatchHooks(command);

return function (hook: RollupWatchHooks): void {
if (watchHooks[hook]) {
const cmd = watchHooks[hook]!;

if (!command.silent) {
stderr(cyan(`watch.${hook} ${bold(`$ ${cmd}`)}`));
}

try {
execSync(cmd, { stdio: command.silent ? 'ignore' : 'inherit' });
} catch (e) {
stderr((e as Error).message);
}
}
};
}
2 changes: 2 additions & 0 deletions src/rollup/types.d.ts
Expand Up @@ -868,6 +868,8 @@ export interface ChokidarOptions {
usePolling?: boolean;
}

export type RollupWatchHooks = 'onError' | 'onStart' | 'onBundleStart' | 'onBundleEnd' | 'onEnd';

export interface WatcherOptions {
buildDelay?: number;
chokidar?: ChokidarOptions;
Expand Down