Skip to content

Tracing Errors in JS #386

Closed
Closed
@apexys

Description

@apexys

I'm currently trying to use rquickjs to run the JS parts of https://github.com/pyodide/pyodide to be able to statically embed a python interpreter into a rust executable.

This is of course a very large codebase, but I'm trying an iterative approach, where I just patch in enough support so that I get the correct calls to the WebAssembly objects.

However, I often get stuck when some JS Exception occurs.

Is there a way to, when ctx.eval returns an error, to get a stack trace or the line of code that caused the problem?

This is especially a problem with Promises, since a failed Promise often only returns "WouldBlock", although the underlying problem is an exception that happened somewhere along the way (usually a missing import or a function not being defined yet).

My attempt at logging an error is as follows:

fn run_js(ctx: &Context, script: &str) {
    ctx.with(|ctx| {
        let res: Result<Value, rquickjs::Error> = ctx.eval(script);
        match res {
            Err(e) => {
                if e.is_exception() {
                    let exc = ctx.catch();
                    eprintln!("Exception during script evaluation: {exc:?}");
                } else {
                    eprintln!("Error evaluating script: {:?}", e)
                }
            }
            Ok(value) => {
                if value.is_promise() {
                    let p = value.into_promise().unwrap();
                    let v: Result<Value, rquickjs::Error> = p.finish();
                    if let Err(e) = v{
                        if e.is_exception() {
                            let exc = ctx.catch();
                            eprintln!("Exception during promise execution: {exc:?}");
                        } else {
                            eprintln!("Error during promise execution: {e:?} {p:?}");
                            let p = p.into_inner();
                            eprintln!("Promise inner: {:?}", p);
                            let p = p.into_inner();
                            eprintln!("Promise object inner: {:?}", p);
                            let prom = p.as_promise().unwrap();
                            let res: Result<Value, rquickjs::Error> = prom.finish();
                            eprintln!("Inner promise error: {res:?}");
                        }
                    } else {
                        eprintln!("Script evaluated with promise resulting in {:?}", v);
                    }
                } else {
                    eprintln!("Script evaluated with value {:?}", value);
                }
            }
        }
    });
}

This then prints something like

Error during promise execution: WouldBlock Promise(Object(Promise(0x62b51d48ce10)))
Promise inner: Object(Promise(0x62b51d48ce10))
Promise object inner: Promise(0x62b51d48ce10)
Inner promise error: Err(WouldBlock)

Thank you in advance!

Metadata

Metadata

Assignees

No one assigned

    Labels

    kind:questionUnclear usage of the library

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions