qubit_budget/resource/error/limit_exceeded_error.rs
1// =============================================================================
2// Copyright (c) 2025 - 2026 Haixing Hu.
3//
4// SPDX-License-Identifier: Apache-2.0
5//
6// Licensed under the Apache License, Version 2.0.
7// =============================================================================
8//! Defines point-limit failures for finite resource constraints.
9
10use std::fmt::Debug;
11
12use thiserror::Error;
13
14use crate::resource::Observation;
15
16/// Structured facts for a point measurement that exceeded its maximum.
17///
18/// # Type Parameters
19///
20/// * `R` - Caller-defined resource value retained for diagnostics.
21/// * `Q` - Copyable measurement value used by the failed constraint.
22///
23/// # Examples
24///
25/// ```
26/// use qubit_budget::LimitExceededError;
27/// use qubit_budget::Observation;
28///
29/// let error = LimitExceededError::exact("depth", 3_u64, 2);
30/// assert_eq!(error.observation(), Observation::Exact(3));
31/// assert_eq!(error.maximum(), 2);
32/// ```
33#[must_use]
34#[derive(Debug, Error, Clone, PartialEq, Eq)]
35#[error("resource {resource:?} measured {observed}, exceeding the maximum of {maximum:?}")]
36pub struct LimitExceededError<R, Q = u64>
37where
38 Q: Copy + Debug,
39{
40 /// Resource associated with the failed point check.
41 pub resource: R,
42 /// Observed point measurement or safe lower bound.
43 pub observed: Observation<Q>,
44 /// Configured inclusive point maximum.
45 pub maximum: Q,
46}
47
48impl<R, Q> LimitExceededError<R, Q>
49where
50 Q: Copy + Debug,
51{
52 /// Creates a failure from an exact point measurement.
53 ///
54 /// # Parameters
55 ///
56 /// * `resource` - Resource associated with the failed point check.
57 /// * `observed` - Exact measurement that exceeded `maximum`.
58 /// * `maximum` - Configured inclusive point maximum.
59 ///
60 /// # Returns
61 ///
62 /// A structured failure containing an [`Observation::Exact`] measurement.
63 #[inline(always)]
64 pub const fn exact(resource: R, observed: Q, maximum: Q) -> Self {
65 Self {
66 resource,
67 observed: Observation::Exact(observed),
68 maximum,
69 }
70 }
71
72 /// Creates a failure from a safe lower bound for a point measurement.
73 ///
74 /// # Parameters
75 ///
76 /// * `resource` - Resource associated with the failed point check.
77 /// * `lower_bound` - Proven lower bound that exceeded `maximum`.
78 /// * `maximum` - Configured inclusive point maximum.
79 ///
80 /// # Returns
81 ///
82 /// A structured failure containing an [`Observation::AtLeast`]
83 /// measurement.
84 #[inline(always)]
85 pub const fn at_least(resource: R, lower_bound: Q, maximum: Q) -> Self {
86 Self {
87 resource,
88 observed: Observation::AtLeast(lower_bound),
89 maximum,
90 }
91 }
92
93 /// Returns the resource associated with this failure.
94 ///
95 /// # Returns
96 ///
97 /// Returns the resource associated with this failure.
98 #[must_use]
99 #[inline(always)]
100 pub const fn resource(&self) -> &R {
101 &self.resource
102 }
103
104 /// Consumes this error and returns its associated resource.
105 ///
106 /// # Returns
107 ///
108 /// Consumes this error and returns its associated resource.
109 #[must_use]
110 #[inline(always)]
111 pub fn into_resource(self) -> R {
112 self.resource
113 }
114
115 /// Returns the observed point measurement or safe lower bound.
116 ///
117 /// # Returns
118 ///
119 /// Returns the observed point measurement or safe lower bound.
120 #[must_use]
121 #[inline(always)]
122 pub const fn observation(&self) -> Observation<Q> {
123 self.observed
124 }
125
126 /// Returns the exact point measurement when the observation is exact.
127 ///
128 /// # Returns
129 ///
130 /// Returns the exact point measurement when the observation is exact.
131 ///
132 /// `None` indicates that the observation is only a lower bound.
133 #[must_use]
134 #[inline(always)]
135 pub const fn exact_observed(&self) -> Option<Q> {
136 match self.observed {
137 Observation::Exact(value) => Some(value),
138 Observation::AtLeast(_) => None,
139 }
140 }
141
142 /// Returns the safe lower bound of the observed point measurement.
143 ///
144 /// # Returns
145 ///
146 /// Returns the safe lower bound of the observed point measurement.
147 #[must_use]
148 #[inline(always)]
149 pub const fn observed_lower_bound(&self) -> Q {
150 self.observed.lower_bound()
151 }
152
153 /// Returns the configured inclusive point maximum.
154 ///
155 /// # Returns
156 ///
157 /// Returns the configured inclusive point maximum.
158 #[must_use]
159 #[inline(always)]
160 pub const fn maximum(&self) -> Q {
161 self.maximum
162 }
163}