How Wand‑Enhancer Injects the Remote Panel Bridge into the Wand Electron App

Wand‑Enhancer injects the remote panel bridge by compiling TypeScript sources into a CommonJS bundle, embedding the output into the Electron ASAR archive, and patching the main process entry point to initialize the IPC bridge at application startup.

The k1tbyte/Wand-Enhancer repository provides a runtime modification system that augments the original Wand Electron binary with a remote control interface. This injection pipeline embeds a web‑based panel and a TypeScript bridge that connects the UI to Wand’s native services without requiring changes to the original source code.

Build the Bridge and Renderer Scripts

The injection process begins by compiling the TypeScript sources located in web-panel/bridge/src/ into a production‑ready bundle.

Running pnpm run build (or specifically pnpm run build:bridge) triggers the build pipeline. This process compiles the bridge logic into a single CommonJS file at web-panel/dist/bridge.cjs. Simultaneously, the build generates default renderer scripts and places them under web-panel/dist/renderer-scripts/, as documented in web-panel/scripts/custom/README.md.

These compiled assets serve as the runtime payload that the enhancer later embeds into the target application.

Embed Assets into the ASAR Archive

Once the bridge is built, Wand‑Enhancer modifies the Electron application bundle to include these assets permanently.

In WandEnhancer/Core/Enhancer.cs, the tool extracts the original resources/app.asar (along with its unpacked counterpart) from the Wand installation directory. It creates a new folder named remote-panel inside the extracted tree and copies the entire web-panel/dist directory into remote-panel/. This places bridge.cjs and the renderer scripts at remote-panel/dist/bridge.cjs within the ASAR structure.

The configuration constants defining these paths are declared in the source:

  • RemotePanelDirectoryName = "remote-panel"
  • EmbeddedRemotePanelDistPrefix = "remote-panel/dist/"

After copying, the tool repackages the ASAR, ensuring the bridge code becomes part of the Electron runtime environment.

Patch the Main Process Entry Point

The core injection logic resides in WandEnhancer/Core/EnhancerConfig.cs, which generates a runtime patch replacing the application's entry point.

When the patched app launches, the generated code wraps the original startup routine with a whenReady handler that loads the embedded bridge:

${app}.whenReady().then(() => {
    try {
        const path = require("node:path");
        require(path.join(__dirname, "remote-panel", "bridge.cjs"))
            .installWandRuntime(require("electron"));
    } catch (e) {
        const fs = require("node:fs"),
              os = require("node:os"),
              p  = require("node:path");
        fs.appendFileSync(
            p.join(os.tmpdir(), "wand-remote-bridge.log"),
            `[${new Date().toISOString()}] [boot-error] ${e && e.stack || e}\n`);
    }
    return run();
});

This snippet executes three critical actions:

  1. Resolves the path to remote-panel/bridge.cjs inside the ASAR.
  2. Invokes installWandRuntime exported by the bridge bundle, passing the Electron module.
  3. Implements error logging to a temporary log file at wand-remote-bridge.log for debugging boot failures.

Initialize the IPC Bridge at Runtime

The installWandRuntime function, implemented in web-panel/bridge/src/wand/runtime.ts, establishes the communication layer between the remote UI and Wand’s backend services.

// web-panel/bridge/src/wand/runtime.ts
export function installWandRuntime(electron: ElectronPort, options: BridgeOptions = {}) {
    const { ipcRenderer: c } = electron;
    const send = (channel: string, payload?: any) => {
        try { return c.invoke(channel, payload && JSON.parse(JSON.stringify(payload))); }
        catch (e) { /* ignore */ }
    };
    return {
        sync: (s) => send("wand-remote-sync", s),
        valueChanged: (s) => send("wand-remote-value-changed", s),
        setHandler: (h) => {
            if ((globalThis as any).__wandRemoteBridgeBound) return;
            (globalThis as any).__wandRemoteBridgeBound = true;
            c.invoke("wand-remote-set-handler-bind");
            c.on("wand-remote-set-value", (_e, req) => h(req));
        },
    };
}

This function creates createBridgeRuntime and ensureBridge internal utilities, then registers IPC methods including sync, valueChanged, and setHandler. It exposes a global __wandRemoteBridge object on the renderer window, enabling the remote panel to send commands and receive game‑status updates through Electron’s ipcRenderer channels.

Renderer-Side Hook Installation

After the main process initializes the bridge, a secondary injection targets the renderer process to complete the circuit.

The patch generated by EnhancerConfig.cs inserts a script that instantiates the __wandRemoteBridge object and binds incoming remote‑panel actions to Wand’s trainer services. This ensures that UI commands—such as launching games or modifying cheat values—forward correctly to the native Wand runtime.

The renderer scripts located in web-panel/dist/renderer-scripts/ (and documented in the custom scripts README) provide cleanup utilities like remote-popup-cleanup.js, which removes tooltip and QR‑code artifacts, demonstrating the bridge’s runtime impact on the UI layer.

Summary

  • Build Phase: TypeScript sources in web-panel/bridge/src/ compile into web-panel/dist/bridge.cjs via pnpm run build.
  • Embedding Phase: WandEnhancer/Core/Enhancer.cs extracts app.asar, creates a remote-panel directory, copies the dist folder, and repackages the archive.
  • Injection Phase: WandEnhancer/Core/EnhancerConfig.cs patches the main process entry point to require bridge.cjs inside a whenReady hook.
  • Runtime Phase: The installWandRuntime function in web-panel/bridge/src/wand/runtime.ts initializes IPC channels and exposes the global __wandRemoteBridge API.
  • Error Handling: Boot failures log to the system temp directory at wand-remote-bridge.log for diagnostics.

Frequently Asked Questions

How does Wand‑Enhancer modify the Electron ASAR without corrupting the application?

WandEnhancer/Core/Enhancer.cs performs a surgical extraction of resources/app.asar, inserts the remote-panel directory containing the compiled bridge assets, and repackages the archive using standard Electron ASAR tooling. This preserves the original file structure while adding the new runtime components, ensuring the app remains fully functional.

What is the purpose of the bridge.cjs file in the injection process?

bridge.cjs is the compiled output of the TypeScript bridge source located at web-panel/bridge/src/wand/runtime.ts. It exports the installWandRuntime function, which establishes the IPC communication layer between the remote panel UI and Wand’s native services. The main process loader invokes this function at startup to activate the bridge.

How does the remote panel communicate with Wand's trainer services?

The remote panel uses the global __wandRemoteBridge object exposed by the bridge. This object provides methods like sync, valueChanged, and setHandler that wrap Electron’s ipcRenderer.invoke calls. When the UI triggers an action, it calls these methods, which transmit messages through the IPC bridge to handlers registered in the main process.

Where does Wand‑Enhancer store logs if the bridge fails to initialize?

If the bridge fails to load during the whenReady hook, the catch block in the generated patch writes error details to wand-remote-bridge.log in the system temporary directory (retrieved via os.tmpdir()). This log includes timestamps and stack traces to facilitate debugging injection failures.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →