How to catch all errors in rust?

Viewed 890

I am new to rust and I have wrote a function which returns a Result with Box dyn Error.

use std::error::Error;

fn func<T>(val: T) -> Result<(), Box<dyn Error>>
where
    T: std::fmt::Debug,
{
    println!("{:?}", val);    
    Ok(())
}

fn main() {
    func("hello world");
}

Here I am not writing any error logic in the function func but it still works. Does the above code automatically catches all errors? similar to python's

try:
  # Run the code
except:
  # Catch all the errors

Is there any universal error catching way in rust?

1 Answers

If you run cargo clippy on this you will get the following warning:

warning: unused `std::result::Result` that must be used
  --> src/main.rs:12:5
   |
12 |     func("hello world");
   |     ^^^^^^^^^^^^^^^^^^^^
   |

this is telling you that although func returns a Result which could be an error, you are not doing anything with it.

You need to handle the error - the simplest way to do this is to just change main to return an error:

fn main() -> Result<(), Box<dyn Error>> {
    func("hello world")?; // If this fails, the `?` makes main return it
    Ok(())
}

Now is func fails, main will fail too.

To see this in action we need an error type - which is a bit tedious to implement (for example see here for details). Instead, I'll just convert to using anyhow for errors.

use anyhow::{anyhow, Result};

fn func<T>(val: T) -> Result<()>
where
    T: std::fmt::Debug,
{
    println!("{:?}", val);    
    Err(anyhow!("BANG"))
}

fn main() -> Result<()> {
    func("hello world")?;
    Ok(())
}

Now func returns an error, and running the binary outputs:

"hello world"
Error: BANG

If you don't want your application to exit on error, or don't want it to exit in this way, then you need to handle the result from func yourself

use anyhow::{anyhow, Result};

fn func<T>(val: T) -> Result<()>
where
    T: std::fmt::Debug,
{
    println!("{:?}", val);    
    Err(anyhow!("BANG"))
}

fn main() {
    match func("hello world") {
      Err(e) => println!("an error: {:?}", e), //<= error handling
      Ok(_) => println!("func was OK"),
    }
}

which will output:

"hello world"
an error: BANG
Related