sinelaw/fresh · error

Failed to set up global API

Error message

Failed to set up global API: {}

What it means

The closure that evaluates bootstrap scripts and installs the global API (console shim, editor shims, promise bootstrap) into a context failed. Any rquickjs::Error from those steps is converted to this error.

Solutions

  1. Rebuild/reinstall the host to ensure shim scripts match the binary
  2. Identify which setup step failed via the wrapped rquickjs error
  3. Check for syntax issues if you modified the shims locally
  4. Verify context memory limits are not exhausted
Defensive patterns

Strategy: try-catch

Try / catch

if let Err(e) = backend.setup_global_api() {
    let msg = e.to_string();
    if msg.contains("Failed to set up global API") {
        eprintln!("plugin API bootstrap failed: {e:#}");
        // surface at startup rather than mid-execution
    }
}

Prevention

When it happens

Trigger: One of the embedded setup scripts fails to eval (syntax error in a shipped shim, e.g. EDITOR_ON_OFF_SHIM or EDITOR_PROMISE_BOOTSTRAP), install_console throws, or a registered global binding fails at runtime.

Common situations: Version mismatch between the host binary and embedded shim scripts; corrupted build artifacts; a context API setup step throwing because of engine limits.

Related errors


AI-assisted analysis of sinelaw/fresh@67894ca546 (2026-09-13). Data as JSON: /api/errors/d78f11746375cd58. Report an issue: GitHub.

Appendix: source

Thrown at crates/fresh-plugin-runtime/src/backend/quickjs_backend.rs:9038

                // values) and export it as a global.
                let editor = rquickjs::Class::<JsEditorApi>::instance(
                    ctx.clone(),
                    self.build_editor_api(plugin_name),
                )?;
                globals.set("editor", editor)?;

                // Bootstrap, in order: the getEditor()/registerHandler()
                // globals, the closure-friendly editor.on/off shim, a console
                // that forwards to tracing, then the Promise/async-wrapper
                // infrastructure.
                ctx.eval::<(), _>(EDITOR_GLOBALS_BOOTSTRAP)?;
                ctx.eval::<(), _>(EDITOR_ON_OFF_SHIM)?;
                install_console(&ctx, &globals)?;
                ctx.eval::<(), _>(EDITOR_PROMISE_BOOTSTRAP.as_bytes())?;

                Ok::<_, rquickjs::Error>(())
            })
            .map_err(|e| anyhow!("Failed to set up global API: {}", e))?;

        Ok(())
    }

    /// Load and execute a TypeScript/JavaScript plugin from a file path
    pub async fn load_module_with_source(
        &mut self,
        path: &str,
        _plugin_source: &str,
    ) -> Result<()> {
        let path_buf = PathBuf::from(path);
        let source = std::fs::read_to_string(&path_buf)
            .map_err(|e| anyhow!("Failed to read plugin {}: {}", path, e))?;

        let filename = path_buf
            .file_name()
            .and_then(|s| s.to_str())
            .unwrap_or("plugin.ts");

View on GitHub (pinned to 67894ca546)