Skip to content

fix: dev-loop hygiene and the electron named exports - #19

Merged
ipfizz merged 3 commits into
chore/comment-and-test-cleanupfrom
feat/dev-loop-hygiene
Aug 29, 2026
Merged

ipfizz merged 3 commits into
chore/comment-and-test-cleanupfrom
feat/dev-loop-hygiene

Conversation

@ipfizz

@ipfizz ipfizz commented Aug 29, 2026

Copy link
Copy Markdown
Owner

Stacks on #18. Phase 2a of the dev-loop plan — the cheap, high-payoff half. Does not yet add a renderer build step (that is 2b, and it is what finally kills the React-restart problem).

What was wrong

Seven root causes were traced for the two reported symptoms. This PR closes four of them.

fix
RC2 no-op saves restart the app content-hash filter in the watcher: a metadata-only touch or a formatter rewriting identical bytes no longer fires. First sight of a path still passes (no baseline to compare against) — the filter earns its keep from the second save onward.
RC3 dist ignored, build output watched dist removed from the ignore list, so a rebuilt renderer bundle finally reaches the window. build/out/coverage and any *.app / *.AppDir segment ignored instead, because bunmaska build defaults its output to the project root.
RC5 preload edits reload a stale script the preload is read and bundled once in the BrowserWindow constructor, so reload() re-injects the old source forever. A preload.* change now restarts, which is the honest action. Verified end to end: editing the preload used to print PRELOAD-V1 after the reload; it now prints PRELOAD-V2.
RC7 restart races, and reloads at a dead child kill() only delivers a signal, so respawning immediately left two live apps racing for the window and the single-instance lock. The restart now awaits the old child's exit. The supervisor also tracks liveness: after the user quits, a renderer edit says app is not running instead of printing reloaded at a corpse.

Also: the watcher classifies before hashing, so node_modules churn never costs a file read.

Engine pin

bunmaska dev and bunmaska run never read config.engine.webkit — only build and doctor did — so a dev launch silently resolved to the system WebKit, which on Windows means no engine at all. Both now pass BUNMASKA_WEBKIT_ID to the child.

The electron shim

import { app, BrowserWindow } from "bunmaska/electron" — the exact line in migrating-from-electron.md:23, for the flagship drop-in feature — threw SyntaxError: Export named 'app' not found. The module had only a default export. Adding export * from './index' fixes the documented path; the default export's Proxy still turns a property access on an unimplemented module into the actionable message, which I checked both ways.

Tests

Every new behaviour was mutation-checked — I reverted each fix in turn and confirmed a test goes red, rather than assuming coverage:

  • drop the await on child exit → the restart-race test fails
  • drop the liveness guard → the dead-child test fails
  • stop restarting on preload → the preload classification test fails
  • drop the env wiring → the engine-pin test fails
  • remove the named re-exports → the shim test fails

bun run validate EXIT=0 (1515 pass / 74 skip / 0 fail).

Still open, deliberately

RC1 (.tsx classified as a main source) and RC4 (no renderer build step anywhere) are 2b. They need bunmaska to own the renderer build, and the binding constraint is that file:// blocks ES modules while bun build ./index.html emits type="module" — so the IIFE recipe in .admin/RENDERER-BUILD.md is the target, not Bun's HTML entry. RC6 (window state across restart) is blocked on macOS getBounds() returning a cached rect that lies once the window moves.

@ipfizz
ipfizz merged commit bdab0e2 into chore/comment-and-test-cleanup Aug 29, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant