charon_error/lib.rs
1#![forbid(unsafe_code)]
2#![deny(clippy::all)]
3//! # Charon Error
4//!
5//! Structured error handling for Rust with rich error reports, data sensitivity
6//! labels, panic capture, and GitLab issue integration.
7//!
8//! Named after Charon, the Greek ferryman of the dead across the river Styx —
9//! this crate ferries your program from a running state to a graceful death,
10//! collecting every detail along the way.
11//!
12//! ## Features
13//!
14//! - **Error chains**: Stack multiple errors with [`ErrorReport`] to preserve the full context
15//! - **Panic hooks**: Capture panics and display human-readable reports with
16//! [`setup_panic!`] and [`setup_panic_simple!`]
17//! - **Issue submission**: Generate pre-filled GitLab issue URLs from errors via
18//! [`GitLabErrorReport`] or [`SimpleErrorReport`]
19//! - **Sensitivity labels**: Tag data as [`Public`](ErrorSensitivityLabel::Public),
20//! [`Private`](ErrorSensitivityLabel::Private), [`Internal`](ErrorSensitivityLabel::Internal),
21//! or [`Confidential`](ErrorSensitivityLabel::Confidential) to control what gets shared
22//! - **Tracing integration**: Works with the `tracing` crate - use `#[instrument]`
23//! and `tracing::error!()` alongside `ErrorReport`
24//! - **Flexible formatting**: Configure output detail with [`ErrorFmtSettings`]
25//!
26//! ## Quick Start
27//!
28//! ```rust,no_run
29//! use charon_error::prelude::*;
30//!
31//! #[derive(Debug, thiserror::Error)]
32//! enum AppError {
33//! #[error("failed to load config")]
34//! ConfigLoad,
35//! }
36//!
37//! fn load_config() -> ResultER<String> {
38//! std::fs::read_to_string("config.toml")
39//! .change_context(AppError::ConfigLoad)?;
40//! Ok("loaded".to_owned())
41//! }
42//! ```
43//!
44//! ## Using `ResultER<T>`
45//!
46//! [`ResultER<T>`] is a type alias for `Result<T, ErrorReport>`. Use it as your
47//! return type and the [`ResultExt`] trait methods become available on any
48//! `Result` or `Option`:
49//!
50//! ```rust,no_run
51//! use charon_error::prelude::*;
52//!
53//! fn example() -> ResultER<()> {
54//! let value: i32 = "not_a_number"
55//! .parse::<i32>()
56//! .change_context(StringError::new("parsing failed"))?;
57//! Ok(())
58//! }
59//! ```
60
61mod errors;
62#[macro_use]
63mod panic_hook;
64mod error_formating;
65/// Prelude module for convenient imports.
66///
67/// Import everything with `use charon_error::prelude::*;`
68pub mod prelude;
69mod report;
70mod result_ext;
71mod settings;
72mod submit;
73mod utils;
74
75pub use error_formating::*;
76pub use errors::*;
77pub use report::{ErrorAttachment, ErrorFrame, ErrorReport, ErrorSensitivityLabel};
78pub use result_ext::ResultExt;
79pub use settings::er_global_settings::{ERGlobalSettings, check_known_error_types_default};
80pub use settings::global_settings::{GlobalSettings, GlobalSettingsError};
81pub use submit::{
82 GitLabERGlobalSettings, GitLabErrorReport, SimpleERGlobalSettings, SimpleErrorReport,
83 SubmitErrorReport,
84};
85pub use utils::{LinkDebugIde, SourceLocation};
86
87/// Convenience type alias for `Result<T, ErrorReport>`.
88///
89/// ER stands for ErrorReport. Use this as the return type for functions
90/// that can fail with structured error reports.
91///
92/// # Example
93///
94/// ```rust,no_run
95/// use charon_error::prelude::*;
96///
97/// fn do_work() -> ResultER<String> {
98/// Ok("done".to_owned())
99/// }
100/// ```
101pub type ResultER<T> = Result<T, ErrorReport>;