1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
//! Unified error types for FraiseQL runtime crates.
//!
//! All runtime crates depend on this crate for error handling.
//!
//! # Two-Layer Error Design
//!
//! FraiseQL uses two distinct error layers with separate responsibilities:
//!
//! ## Layer 1 — Compile-time errors: [`FraiseQLError`] (in `core_error`)
//!
//! Returned by schema compilation, query planning, and the CLI. These are
//! **developer-facing errors** that occur before any user request is processed.
//! Library consumers building atop the `Executor` API will encounter this type.
//!
//! ```rust,ignore
//! use fraiseql_error::{FraiseQLError, Result};
//!
//! fn compile_schema(json: &str) -> Result<CompiledSchema> {
//! // Returns FraiseQLError::Parse if the JSON is malformed,
//! // FraiseQLError::Validation if the schema is semantically invalid.
//! todo!()
//! }
//! ```
//!
//! [`FraiseQLError`] variants: `Parse`, `Validation`, `Database`, `Compilation`,
//! `IO`, `Config`, `Unsupported`, `Auth`, `Timeout`, `NotFound`.
//!
//! ## Layer 2 — Runtime errors: [`RuntimeError`]
//!
//! Returned by the HTTP server and live request handlers. These map directly
//! to HTTP status codes and are safe to return to API clients (internal details
//! are stripped before the response is sent).
//!
//! Application code using the `Server` API will encounter this type.
//! Conversion from `FraiseQLError` to `RuntimeError` happens automatically inside
//! the request-handler middleware via `From<FraiseQLError> for RuntimeError`.
//!
//! ## Conversion rules
//!
//! `FraiseQLError` → `RuntimeError` mapping:
//! - `Validation`, `Parse` → `RuntimeError::Internal` (HTTP 400 via handler logic)
//! - `Database` → `RuntimeError::Database` (HTTP 500)
//! - `Auth` → `RuntimeError::Auth` (HTTP 401/403)
//! - `NotFound` → `RuntimeError::NotFound` (HTTP 404)
//! - Everything else → `RuntimeError::Internal` (HTTP 500)
//!
//! # `RuntimeError` → HTTP mapping
//!
//! | `RuntimeError` variant | HTTP status |
//! |-----------------------------------|------------------------------|
//! | `Auth(InsufficientPermissions)` | 403 Forbidden |
//! | `Auth(*)` | 401 Unauthorized |
//! | `Webhook(InvalidSignature)` | 401 Unauthorized |
//! | `RateLimited` | 429 Too Many Requests |
//! | `ServiceUnavailable` | 503 Service Unavailable |
//! | `NotFound` | 404 Not Found |
//! | `Database` | 500 Internal Server Error |
//! | `Config` / `Internal` | 500 Internal Server Error |
//!
//! # Security note
//!
//! All variants that might leak internal details (database messages, config values,
//! provider endpoints) return **generic** descriptions in the HTTP response body.
//! Raw error details are available only in structured server logs.
//!
//! See also: [`docs/architecture/error-hierarchy.md`](https://docs.fraiseql.dev/architecture/error-hierarchy)
pub use AuthError;
pub use ConfigError;
pub use ;
pub use FileError;
pub use ;
// Re-export for convenience — only available with the `axum-compat` feature
pub use ;
pub use IntegrationError;
pub use NotificationError;
pub use ObserverError;
pub use WebhookError;
/// Unified error type wrapping all domain errors.
///
/// `RuntimeError` aggregates every domain-level error that can surface during
/// request handling. It implements [`axum::response::IntoResponse`] so that
/// handlers can return `Result<_, RuntimeError>` directly; the conversion
/// produces an [`ErrorResponse`] JSON body with the appropriate HTTP status
/// code. Sensitive internal details (database messages, config values) are
/// stripped from the HTTP response and are only present in server-side logs.