snippetrustModeratepending
Rust error handling with thiserror and anyhow
Viewed 0 times
thiserroranyhowErrorcontextFromResult
Problem
Rust error handling requires defining error types and implementing std::error::Error, which is boilerplate-heavy.
Solution
Use thiserror for library errors, anyhow for application errors:
// Library code: use thiserror (typed errors)
use thiserror::Error;
#[derive(Error, Debug)]
enum AppError {
#[error("Database error: {0}")]
Database(#[from] sqlx::Error),
#[error("Not found: {entity} with id {id}")]
NotFound { entity: String, id: i64 },
#[error("Validation failed: {0}")]
Validation(String),
#[error("IO error")]
Io(#[from] std::io::Error),
}
// Automatic From implementations via #[from]
fn get_user(id: i64) -> Result<User, AppError> {
let user = db.query("...").await?; // sqlx::Error -> AppError::Database
Ok(user)
}
// Application code: use anyhow (any error)
use anyhow::{Context, Result};
fn main() -> Result<()> {
let config = read_config()
.context("Failed to read configuration")?;
let db = connect_db(&config.db_url)
.context("Failed to connect to database")?;
start_server(db).context("Server crashed")?;
Ok(())
}
// anyhow wraps any error and adds context chain
// Library code: use thiserror (typed errors)
use thiserror::Error;
#[derive(Error, Debug)]
enum AppError {
#[error("Database error: {0}")]
Database(#[from] sqlx::Error),
#[error("Not found: {entity} with id {id}")]
NotFound { entity: String, id: i64 },
#[error("Validation failed: {0}")]
Validation(String),
#[error("IO error")]
Io(#[from] std::io::Error),
}
// Automatic From implementations via #[from]
fn get_user(id: i64) -> Result<User, AppError> {
let user = db.query("...").await?; // sqlx::Error -> AppError::Database
Ok(user)
}
// Application code: use anyhow (any error)
use anyhow::{Context, Result};
fn main() -> Result<()> {
let config = read_config()
.context("Failed to read configuration")?;
let db = connect_db(&config.db_url)
.context("Failed to connect to database")?;
start_server(db).context("Server crashed")?;
Ok(())
}
// anyhow wraps any error and adds context chain
Why
thiserror generates Error trait implementations. anyhow erases error types for application code where you just want to propagate and add context.
Revisions (0)
No revisions yet.