#![feature(try_blocks)]
use eyre::{Ok, Result, eyre};
fn main() {
let res: Result<()> = try {
if true {
// Jump to the end of try block with Ok value assigned to res
return Ok(());
}
Err(eyre!("Unreachable"))?;
};
res.unwrap();
}
error[E0308]: mismatched types
--> src/main.rs:8:20
|
5 | fn main() {
| - expected `()` because of default return type
...
8 | return Ok(());
| ^^^^^^ expected `()`, found `Result<(), Report>`
|
= note: expected unit type `()`
found enum `Result<(), ErrReport>`
help: consider using `Result::expect` to unwrap the `Result<(), ErrReport>` value, panicking if the value is a `Result::Err`
|
8 | return Ok(()).expect("REASON");
| +++++++++++++++++
I don't think it was possible. IIRC, try blocks only interact with the question mark operator, it has not effect on return.
instead of a try block, I usually abuse Result::and_then() (or Option::and_then()) to create a inner scope for to use the question mark operator:
// sometimes, type annotation is needed
// alternative is to use eyre::Ok
let res = Ok::<(), eyre::Report>(()).and_then(|_| {
if true {
return Ok(());
}
Err(eyre!("unreachable"))?;
});
res.unwrap();
After some playing around, I wondered - why not labeled try? And the answer is Ok wrapping. It's unclear if a break to a labeled try block should do so or not.
it's a personal taste, I guess. I find myself use and_then() a lot when I want to access a chain of nested optional fields, similar to the ?. operator (I don't remember what it is called) in typescript:
I just personally prefer and_then(), for no particular reason.
granted, this pattern is not very common in hand written code, but may be used a lot in some machine generated data structures from some DSL model. those as_ref()s can be very annoying, but this is rust, I gotta unwrap my head around it.