From 7e4b29cdc88bd26d77fd37a718ce80c1d22415d1 Mon Sep 17 00:00:00 2001 From: Kevin Buffardi Date: Thu, 5 Nov 2026 20:59:02 -0800 Subject: [PATCH] fix: order compiler restart status before prompt Reset terminal prompt state while the replacement compiler loads so readiness is displayed before accepting commands. --- scripts/e2e-terminal-stop.test.mjs | 33 ++++++++++++++++++++++++++++-- src/ui/app.js | 1 + src/ui/terminal.js | 12 +++++++++++ src/ui/toolbar.js | 2 +- 4 files changed, 45 insertions(+), 3 deletions(-) diff --git a/scripts/e2e-terminal-stop.test.mjs b/scripts/e2e-terminal-stop.test.mjs index 559ca71..ed29d67 100644 --- a/scripts/e2e-terminal-stop.test.mjs +++ b/scripts/e2e-terminal-stop.test.mjs @@ -8,6 +8,7 @@ import { clearTerminal, onRunStart, onRunResult, + prepareCompilerRestart, printInfo, resetTerminalSession, showInitialPrompt, @@ -69,7 +70,7 @@ function ctrlCEvent() { test('e2e: compiler ready status prints before the first terminal prompt', () => { const ctx = setupTerminalHarness(); - const status = 'Clang WASM compiler loaded. Ready to compile C++20.'; + const status = 'Clang WASM compiler loaded, ready to compile C++ in browser'; printInfo(status); showInitialPrompt(); @@ -116,7 +117,7 @@ test('e2e: clearing during startup does not reveal the initial prompt early', () const ctx = setupTerminalHarness(); clearTerminal(); - printInfo('Clang WASM compiler loaded. Ready to compile C++20.'); + printInfo('Clang WASM compiler loaded, ready to compile C++ in browser'); showInitialPrompt(); const output = ctx.writes.join(''); @@ -186,6 +187,34 @@ test('e2e: STOP discards stdout queued after a stopped run', async () => { assert.ok(!ctx.writes.join('').includes('Process interrupted.')); }); +test('e2e: compiler restart waits to restore the prompt until the worker is ready', async () => { + const ctx = setupTerminalHarness(); + const status = 'Clang WASM compiler loaded, ready to compile C++ in browser'; + + showInitialPrompt(); + assert.equal(await startRun(), true); + onRunStart({ stdinMode: 'interactive' }); + assert.equal(stopRun(), true); + + const clearCallsBeforeRestart = ctx.clearCalls.length; + const writesBeforeRestart = ctx.writes.length; + prepareCompilerRestart(); + assert.equal(ctx.clearCalls.length, clearCallsBeforeRestart + 1); + assert.equal(__getTerminalStateForTesting().busy, true); + const writesBeforeInput = ctx.writes.length; + __handleTerminalKeyForTesting('x', { key: 'x', ctrlKey: false, altKey: false }); + assert.equal(ctx.writes.length, writesBeforeInput); + + printInfo(status); + showInitialPrompt(); + + const output = ctx.writes.slice(writesBeforeRestart).join(''); + assert.equal(__getTerminalStateForTesting().busy, false); + assert.ok(output.indexOf(status) < output.indexOf('browser.cpp')); + assert.equal(output.match(/browser\.cpp/g)?.length, 1); + assert.ok(!output.includes(`browser.cpp:~$ ${status}`)); +}); + test('e2e: STOP ignores a late nonzero run result', async () => { const ctx = setupTerminalHarness(); diff --git a/src/ui/app.js b/src/ui/app.js index ab1fa3d..09e88f5 100644 --- a/src/ui/app.js +++ b/src/ui/app.js @@ -96,6 +96,7 @@ window.addEventListener('DOMContentLoaded', async () => { onStdinData: (message) => worker.postMessage(message), onStdinEOF: (message) => worker.postMessage(message), onStopRun: () => { + terminalAPI.prepareCompilerRestart(); worker.terminate(); worker = createCompilerWorker(); toolbarController?.setWorker(worker); diff --git a/src/ui/terminal.js b/src/ui/terminal.js index 00f67df..d1c0d49 100644 --- a/src/ui/terminal.js +++ b/src/ui/terminal.js @@ -621,6 +621,18 @@ export function stopRun() { return true; } +/** + * Clear the stopped-run prompt while a replacement compiler worker loads. + * The next compiler-ready or compiler-error event restores the prompt. + */ +export function prepareCompilerRestart() { + clearScreen(); + initialPromptShown = false; + inputBuffer = ''; + historyIdx = -1; + busy = true; +} + // ── Output helpers called by toolbar.js / app.js ───────────────────────────── /** Write stdout text from the running program. */ diff --git a/src/ui/toolbar.js b/src/ui/toolbar.js index 0aec64f..e9e459b 100644 --- a/src/ui/toolbar.js +++ b/src/ui/toolbar.js @@ -254,7 +254,7 @@ async function handleWorkerMessage(data) { } updateStatusBar('compiler', 'ready', 'Compiler ready'); updateCompileButtons(); - _terminalAPI.printInfo('Clang WASM compiler loaded. Ready to compile C++20.'); + _terminalAPI.printInfo('Clang WASM compiler loaded, ready to compile C++ in browser'); _terminalAPI.showInitialPrompt?.(); break;