index/inverted_index/
error.rs

1// Copyright 2023 Greptime Team
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//     http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15use std::any::Any;
16use std::io::Error as IoError;
17
18use common_error::ext::{BoxedError, ErrorExt};
19use common_error::status_code::StatusCode;
20use common_macro::stack_trace_debug;
21use snafu::{Location, Snafu};
22
23use crate::inverted_index::search::predicate::Predicate;
24
25#[derive(Snafu)]
26#[snafu(visibility(pub))]
27#[stack_trace_debug]
28pub enum Error {
29    #[snafu(display("Failed to read"))]
30    Read {
31        #[snafu(source)]
32        error: IoError,
33        #[snafu(implicit)]
34        location: Location,
35    },
36
37    #[snafu(display("Failed to write"))]
38    Write {
39        #[snafu(source)]
40        error: IoError,
41        #[snafu(implicit)]
42        location: Location,
43    },
44
45    #[snafu(display("Failed to flush"))]
46    Flush {
47        #[snafu(source)]
48        error: IoError,
49        #[snafu(implicit)]
50        location: Location,
51    },
52
53    #[snafu(display("Failed to close"))]
54    Close {
55        #[snafu(source)]
56        error: IoError,
57        #[snafu(implicit)]
58        location: Location,
59    },
60
61    #[snafu(display(
62        "Unexpected inverted index blob size, min: {min_blob_size}, actual: {actual_blob_size}"
63    ))]
64    UnexpectedBlobSize {
65        min_blob_size: u64,
66        actual_blob_size: u64,
67        #[snafu(implicit)]
68        location: Location,
69    },
70
71    #[snafu(display("Blob size too small"))]
72    BlobSizeTooSmall {
73        #[snafu(implicit)]
74        location: Location,
75    },
76
77    #[snafu(display("Invalid footer payload size"))]
78    InvalidFooterPayloadSize {
79        #[snafu(implicit)]
80        location: Location,
81    },
82
83    #[snafu(display(
84        "Unexpected inverted index footer payload size, max: {max_payload_size}, actual: {actual_payload_size}"
85    ))]
86    UnexpectedFooterPayloadSize {
87        max_payload_size: u64,
88        actual_payload_size: u64,
89        #[snafu(implicit)]
90        location: Location,
91    },
92
93    #[snafu(display(
94        "Unexpected inverted index offset size, offset: {offset}, size: {size}, blob_size: {blob_size}, payload_size: {payload_size}"
95    ))]
96    UnexpectedOffsetSize {
97        offset: u64,
98        size: u64,
99        blob_size: u64,
100        payload_size: u64,
101    },
102
103    #[snafu(display("Unexpected zero segment row count"))]
104    UnexpectedZeroSegmentRowCount {
105        #[snafu(implicit)]
106        location: Location,
107    },
108
109    #[snafu(display("Failed to decode fst"))]
110    DecodeFst {
111        #[snafu(source)]
112        error: fst::Error,
113        #[snafu(implicit)]
114        location: Location,
115    },
116
117    #[snafu(display("Failed to decode bitmap"))]
118    DecodeBitmap {
119        #[snafu(source)]
120        error: IoError,
121        #[snafu(implicit)]
122        location: Location,
123    },
124
125    #[snafu(display("Failed to decode protobuf"))]
126    DecodeProto {
127        #[snafu(source)]
128        error: prost::DecodeError,
129        #[snafu(implicit)]
130        location: Location,
131    },
132
133    #[snafu(display("Failed to parse regex pattern: {pattern}"))]
134    ParseRegex {
135        #[snafu(source)]
136        error: regex::Error,
137        pattern: String,
138        #[snafu(implicit)]
139        location: Location,
140    },
141
142    #[snafu(display("Failed to parse regex DFA"))]
143    ParseDFA {
144        #[snafu(source)]
145        error: Box<regex_automata::dfa::dense::BuildError>,
146        #[snafu(implicit)]
147        location: Location,
148    },
149
150    #[snafu(display("Unexpected empty predicates to construct fst applier"))]
151    EmptyPredicates {
152        #[snafu(implicit)]
153        location: Location,
154    },
155
156    #[snafu(display("Failed to construct intersection fst applier with InList predicate"))]
157    IntersectionApplierWithInList {
158        #[snafu(implicit)]
159        location: Location,
160    },
161
162    #[snafu(display("Failed to construct keys fst applier without InList predicate"))]
163    KeysApplierWithoutInList {
164        #[snafu(implicit)]
165        location: Location,
166    },
167
168    #[snafu(display(
169        "Failed to construct keys fst applier with unexpected predicates: {predicates:?}"
170    ))]
171    KeysApplierUnexpectedPredicates {
172        #[snafu(implicit)]
173        location: Location,
174        predicates: Vec<Predicate>,
175    },
176
177    #[snafu(display("index not found, name: {name}"))]
178    IndexNotFound {
179        name: String,
180        #[snafu(implicit)]
181        location: Location,
182    },
183
184    #[snafu(display("Failed to insert value to FST"))]
185    FstInsert {
186        #[snafu(source)]
187        error: fst::Error,
188        #[snafu(implicit)]
189        location: Location,
190    },
191
192    #[snafu(display("Failed to compile FST"))]
193    FstCompile {
194        #[snafu(source)]
195        error: fst::Error,
196        #[snafu(implicit)]
197        location: Location,
198    },
199
200    #[snafu(display("Failed to perform IO operation"))]
201    CommonIo {
202        #[snafu(source)]
203        error: IoError,
204        #[snafu(implicit)]
205        location: Location,
206    },
207
208    #[snafu(display("Unknown intermediate codec magic: {magic:?}"))]
209    UnknownIntermediateCodecMagic {
210        magic: [u8; 4],
211        #[snafu(implicit)]
212        location: Location,
213    },
214
215    #[snafu(display(
216        "Inconsistent row count, index_name: {index_name}, total_row_count: {total_row_count}, expected: {expected_row_count}"
217    ))]
218    InconsistentRowCount {
219        index_name: String,
220        total_row_count: usize,
221        expected_row_count: usize,
222    },
223
224    #[snafu(display("External error"))]
225    External {
226        source: BoxedError,
227        #[snafu(implicit)]
228        location: Location,
229    },
230
231    #[snafu(display("Intermediate error"))]
232    Intermediate {
233        source: crate::error::Error,
234        #[snafu(implicit)]
235        location: Location,
236    },
237}
238
239impl ErrorExt for Error {
240    fn status_code(&self) -> StatusCode {
241        use Error::*;
242        match self {
243            Read { .. }
244            | Write { .. }
245            | Flush { .. }
246            | Close { .. }
247            | UnexpectedFooterPayloadSize { .. }
248            | UnexpectedZeroSegmentRowCount { .. }
249            | UnexpectedOffsetSize { .. }
250            | UnexpectedBlobSize { .. }
251            | DecodeProto { .. }
252            | DecodeFst { .. }
253            | KeysApplierUnexpectedPredicates { .. }
254            | CommonIo { .. }
255            | UnknownIntermediateCodecMagic { .. }
256            | FstCompile { .. }
257            | DecodeBitmap { .. }
258            | InvalidFooterPayloadSize { .. }
259            | BlobSizeTooSmall { .. } => StatusCode::Unexpected,
260
261            ParseRegex { .. }
262            | ParseDFA { .. }
263            | KeysApplierWithoutInList { .. }
264            | IntersectionApplierWithInList { .. }
265            | EmptyPredicates { .. }
266            | FstInsert { .. }
267            | InconsistentRowCount { .. }
268            | IndexNotFound { .. } => StatusCode::InvalidArguments,
269
270            Intermediate { source, .. } => source.status_code(),
271            External { source, .. } => source.status_code(),
272        }
273    }
274
275    fn as_any(&self) -> &dyn Any {
276        self
277    }
278}
279
280pub type Result<T> = std::result::Result<T, Error>;