I think this is not possible, based on https://doc.rust-lang.org/edition-guide/rust-2018/error-handling-and-panics/the-question-mark-operator-for-easier-error-handling.html:
One current restriction is that you cannot use
?
for both in the same function, as the return type needs to match the type you use?
on. In the future, this restriction will be lifted.
But to be sure, I'm asking here...
I have a function that returns Option<Result<T, E>>
. It is an implementation of Iterator
, but that doesn't matter for now. It calls a function that might fail, and thus returns Result<T, E>
. Something like:
fn helper() -> Result<T, E> {
// ...
}
fn next() -> Option<Result<T, E>> {
helper();
}
Now, I want next()
to fail with Some(Err(E))
if helper()
returns Err(E)
. Of course I can do this the long way:
if let Err(e) = helper() {
return Some(Err(e));
}
But I'd like to do this using the ?
operator. But if I do this raw, the compiler complains (obviously):
error[E0277]: `?` couldn't convert the error to `std::option::NoneError`
--> src/lib.rs:9:13
|
8 | fn next() -> Option<Result<(), ()>> {
| ---------------------- expected `std::option::NoneError` because of this
9 | helper()?;
| ^ the trait `std::convert::From<()>` is not implemented for `std::option::NoneError`
|
= note: the question mark operation (`?`) implicitly performs a conversion on the error value using the `From` trait
= note: required by `std::convert::From::from`
help: consider converting the `Result<T, _>` into an `Option<T>` using `Result::ok`
|
9 | helper().ok()?;
| ^^^^^
I can use .ok()
, but then the error E
is discarded:
helper().ok()?; // Err(e) becomes None instead of Some(Err(e))
I can also wrap it with Some(...)
, but then the ?
operator applies to the Some(...)
never returns from the function:
Some(helper())?; // The ? operator sees Some(...) and never returns
I thought about implementing std::ops::Try
, but:
- Couldn't figure out how to do this properly.
- I think it's not possible since it's cross-crate
impl
.
Is this possible (I'm not afraid of using nightly Rust)?
Thanks in advance.