DelSkayn / rquickjs

High level bindings to the quickjs javascript engine
MIT License
504 stars 63 forks source link

Gracefully handle errors/exceptions/panics in ctx.spawn? #173

Closed richarddd closed 1 year ago

richarddd commented 1 year ago

Hi,

How can I gracefully catch errors/exceptions/panics that occurs inside a ctx.spawn closure?

ctx.spawn(async move {
        println!("Before!");
        tokio::time::sleep(Duration::from_secs(1)).await;
        println!("After!");
        cb.call::<(), ()>(()).unwrap()
    });

This code will panic if there is an error in the callback. Is there a way to gracefully handle this error since rt.idle().await; does not return a result or the async function in spawn does not expect a result?

DelSkayn commented 1 year ago

Instead of calling spawn you could create a future with Promise and if you turn that into a javascript value via IntoJs it will drive the future like spawn does but it will also allow you to return errors from the future which will be handled like other errors handled from promises.

I agree this is a bit clunky an I will have a look at improving this part of error handling once I finished redesigning the class system.

richarddd commented 1 year ago

I can't return a promise since i wan't the JS code to accept a callback, like setTimeout(() => {}), which should return an integer id that can later be cancelable.

DelSkayn commented 1 year ago

You don't have to return it, just turning a future wrapped in Promise into a JavaScript value is enough to schedule the future to be executed as a job.

You can also do this manually by creating a promise with Ctx::promise and then spawning the future, calling the reject function with the error if the function rejects. Errors will then be handled like any other promises with or without a rejection handler.

Again, this is a temporary solution I will have another pass at how errors are handled with futures and promises.