Skip to content

fix: replace broken bun:bundle shim with source pre-processing#657

Merged
kevincodex1 merged 2 commits into
Gitlawb:mainfrom
Flo5k5:fix/feature-flag-build-system
Apr 13, 2026
Merged

fix: replace broken bun:bundle shim with source pre-processing#657
kevincodex1 merged 2 commits into
Gitlawb:mainfrom
Flo5k5:fix/feature-flag-build-system

Conversation

@Flo5k5
Copy link
Copy Markdown
Contributor

@Flo5k5 Flo5k5 commented Apr 13, 2026

Summary

The onResolve/onLoad plugin shim for import { feature } from 'bun:bundle' was silently ineffective in Bun v1.3.9+. The bun: namespace is resolved by Bun's native C++ resolver before the JS plugin phase runs, so the onResolve callback was never called. This meant ALL feature() flags evaluated to false regardless of the featureFlags map — including MONITOR_TOOL: true which was already enabled.

Root cause

Bun handles bun:bundle as a compile-time macro via its internal resolver, not as a regular module. Plugins cannot intercept bun: namespace resolution.

Fix — source pre-processing

Replace the broken shim with a build-time source transformation:

  1. Before Bun.build(): walk src/, strip import { feature } from 'bun:bundle', replace feature('FLAG') calls with boolean literals from the featureFlags map
  2. After Bun.build(): restore original source files in a finally block (safe even if the build throws)
  3. Extended scanner: detect require() and dynamic import() calls (not just static import ... from) since modules behind feature() gates become resolvable when flags are enabled

Impact

Before/After

Before (broken shim) After (pre-processing)
feature('MONITOR_TOOL') with MONITOR_TOOL: true false at runtime true (constant-folded)
feature() calls in bundle 2+ (runtime function) 0 (all replaced)
Source files after build Unchanged Restored in finally

Test plan

  • bun run build — compiles successfully (206 files pre-processed, all restored)
  • bun run smoke — smoke tests pass
  • 0 feature() calls in compiled bundle
  • Source files verified intact after build (bun:bundle imports present)
  • Enable a flag (e.g. COORDINATOR_MODE: true), verify the feature code is included in the bundle

The `onResolve`/`onLoad` plugin shim for `bun:bundle` was silently
ineffective in Bun v1.3.9+ — the `bun:` namespace is resolved by
Bun's native C++ resolver before the JS plugin phase runs. This meant
ALL `feature()` flags evaluated to `false` regardless of the
`featureFlags` map in build.ts (including `MONITOR_TOOL: true`).

Replace the shim with a source pre-processing step that:
1. Strips `import { feature } from 'bun:bundle'` from .ts/.tsx files
2. Replaces `feature('FLAG')` calls with boolean literals
3. Restores original files in a `finally` block after Bun.build()

Also extend the missing-module scanner to detect `require()` and
dynamic `import()` calls — not just static `import ... from` — since
modules behind feature() gates become resolvable when flags are enabled.
Copilot AI review requested due to automatic review settings April 13, 2026 08:18
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR fixes open-build feature flags by replacing the broken bun:bundle plugin shim (no longer interceptable in Bun v1.3.9+) with a build-time source pre-processing step that rewrites feature('FLAG') calls to boolean literals and restores sources afterward.

Changes:

  • Add a pre-build pass over src/ to remove bun:bundle feature imports and inline feature() calls from the featureFlags map.
  • Remove the ineffective onResolve/onLoad shim for bun:bundle.
  • Extend the missing-import scanner to also detect require() and dynamic import() usage (in addition to static import ... from ...).

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread scripts/build.ts
Comment thread scripts/build.ts
- Add SIGINT/SIGTERM handlers to restore pre-processed source files
  on abrupt termination (Ctrl+C, kill)
- Replace process.exit(1) with process.exitCode = 1 so the finally
  block runs on build failure
@kevincodex1
Copy link
Copy Markdown
Contributor

bro @Vasanthdev2004 please have look when you have time

@kevincodex1 kevincodex1 merged commit adbe391 into Gitlawb:main Apr 13, 2026
1 check passed
C1ph3r404 pushed a commit to C1ph3r404/openclaude that referenced this pull request Apr 29, 2026
…wb#657)

* fix: replace broken bun:bundle shim with source pre-processing

The `onResolve`/`onLoad` plugin shim for `bun:bundle` was silently
ineffective in Bun v1.3.9+ — the `bun:` namespace is resolved by
Bun's native C++ resolver before the JS plugin phase runs. This meant
ALL `feature()` flags evaluated to `false` regardless of the
`featureFlags` map in build.ts (including `MONITOR_TOOL: true`).

Replace the shim with a source pre-processing step that:
1. Strips `import { feature } from 'bun:bundle'` from .ts/.tsx files
2. Replaces `feature('FLAG')` calls with boolean literals
3. Restores original files in a `finally` block after Bun.build()

Also extend the missing-module scanner to detect `require()` and
dynamic `import()` calls — not just static `import ... from` — since
modules behind feature() gates become resolvable when flags are enabled.

* fix: ensure source files are always restored after build

- Add SIGINT/SIGTERM handlers to restore pre-processed source files
  on abrupt termination (Ctrl+C, kill)
- Replace process.exit(1) with process.exitCode = 1 so the finally
  block runs on build failure
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.

4 participants