Closed stevedonovan closed 4 years ago
There's an experimental implementation at https://github.com/stevedonovan/rhai, runtime-errors branch. Seems to work fine, although I wonder if raise
is not a better word than throw
:)
But I won't immediately submit a PR since this is something that needs to be discussed first.
I can take a whack at it. Probably simple to extend the return
functionality.
Turns out it is quite easy to add. Already did.
My implementation takes the easy way out by requiring throw
to always throw nothing or throw a string, which then gets mapped to EvalAltResult::ErrorRuntime(reason, position)
with reason
capturing the thrown string. Throwing anything other than a string will lose the value.
Not having error handling (other than panicking) is a problem when integrating non-trivial Rust code with Rhai. This proposal basically adds unchecked exceptions so that functions can terminate script execution with a clean error.
First,
EvalAltResult
gets a new variant,ErrorRuntime(String)
. A user-defined function may 'throw' a Rhai exception by returning aResult<T,EvalAltResult>
; a Rhai function may call a predefinedthrow
function.Implementation is fairly straightforward. We keep a map of type ids for all
Result<T,EvalAltResult>
of interest, providing a closure that can match this for each specificT
and return aResult<Box<Any>,EvalAltResult>
which Rhai passes on. These closures are created inregister_type
(finally, no longer a no-op!)There will be some overhead with doing a hash lookup on all returned values, and with re-boxing 'exception' values.
This is implementable now, as an incremental step towards either Rust-style explicit result handling or catchable exceptions.