1use std::any::Any;
16
17use common_error::ext::ErrorExt;
18use common_error::status_code::StatusCode;
19use common_macro::stack_trace_debug;
20use datafusion_common::ScalarValue;
21use datatypes::arrow;
22use datatypes::prelude::Value;
23use snafu::{Location, Snafu};
24use store_api::storage::RegionId;
25use table::metadata::TableId;
26
27use crate::expr::PartitionExpr;
28
29#[derive(Snafu)]
30#[snafu(visibility(pub))]
31#[stack_trace_debug]
32pub enum Error {
33 #[snafu(display("Failed to find table route: {}", table_id))]
34 TableRouteNotFound {
35 table_id: TableId,
36 #[snafu(implicit)]
37 location: Location,
38 },
39
40 #[snafu(display("Table route manager error"))]
41 TableRouteManager {
42 source: common_meta::error::Error,
43 #[snafu(implicit)]
44 location: Location,
45 },
46
47 #[snafu(display("Failed to get meta info from cache, error: {}", err_msg))]
48 GetCache {
49 err_msg: String,
50 #[snafu(implicit)]
51 location: Location,
52 },
53
54 #[snafu(display("Failed to find table routes for table id {}", table_id))]
55 FindTableRoutes {
56 table_id: TableId,
57 #[snafu(implicit)]
58 location: Location,
59 },
60
61 #[snafu(display(
62 "Failed to find region routes for table {}, region id: {}",
63 table_id,
64 region_id
65 ))]
66 FindRegionRoutes {
67 table_id: TableId,
68 region_id: u64,
69 #[snafu(implicit)]
70 location: Location,
71 },
72
73 #[snafu(display("Failed to serialize value to json"))]
74 SerializeJson {
75 #[snafu(source)]
76 error: serde_json::Error,
77 #[snafu(implicit)]
78 location: Location,
79 },
80
81 #[snafu(display("Failed to deserialize value from json"))]
82 DeserializeJson {
83 #[snafu(source)]
84 error: serde_json::Error,
85 #[snafu(implicit)]
86 location: Location,
87 },
88
89 #[snafu(display("Expect {} region keys, actual {}", expect, actual))]
90 RegionKeysSize {
91 expect: usize,
92 actual: usize,
93 #[snafu(implicit)]
94 location: Location,
95 },
96
97 #[snafu(display("Invalid InsertRequest, reason: {}", reason))]
98 InvalidInsertRequest {
99 reason: String,
100 #[snafu(implicit)]
101 location: Location,
102 },
103
104 #[snafu(display("Invalid DeleteRequest, reason: {}", reason))]
105 InvalidDeleteRequest {
106 reason: String,
107 #[snafu(implicit)]
108 location: Location,
109 },
110
111 #[snafu(display("Invalid table route data, table id: {}, msg: {}", table_id, err_msg))]
112 InvalidTableRouteData {
113 table_id: TableId,
114 err_msg: String,
115 #[snafu(implicit)]
116 location: Location,
117 },
118
119 #[snafu(display("Failed to convert DataFusion's ScalarValue: {:?}", value))]
120 ConvertScalarValue {
121 value: ScalarValue,
122 #[snafu(implicit)]
123 location: Location,
124 source: datatypes::error::Error,
125 },
126
127 #[snafu(display("Failed to find leader of table id {} region {}", table_id, region_id))]
128 FindLeader {
129 table_id: TableId,
130 region_id: RegionId,
131 #[snafu(implicit)]
132 location: Location,
133 },
134
135 #[snafu(display("Unexpected table route type: {}", err_msg))]
136 UnexpectedLogicalRouteTable {
137 #[snafu(implicit)]
138 location: Location,
139 err_msg: String,
140 source: common_meta::error::Error,
141 },
142
143 #[snafu(display("Conjunct expr with non-expr is invalid"))]
144 ConjunctExprWithNonExpr {
145 expr: PartitionExpr,
146 #[snafu(implicit)]
147 location: Location,
148 },
149
150 #[snafu(display("Unclosed value {} on column {}", value, column))]
151 UnclosedValue {
152 value: String,
153 column: String,
154 #[snafu(implicit)]
155 location: Location,
156 },
157
158 #[snafu(display("Invalid partition expr: {:?}", expr))]
159 InvalidExpr {
160 expr: PartitionExpr,
161 #[snafu(implicit)]
162 location: Location,
163 },
164
165 #[snafu(display("Undefined column: {}", column))]
166 UndefinedColumn {
167 column: String,
168 #[snafu(implicit)]
169 location: Location,
170 },
171
172 #[snafu(display("Unexpected: {err_msg}"))]
173 Unexpected {
174 err_msg: String,
175 #[snafu(implicit)]
176 location: Location,
177 },
178
179 #[snafu(display("Failed to convert to vector"))]
180 ConvertToVector {
181 source: datatypes::error::Error,
182 #[snafu(implicit)]
183 location: Location,
184 },
185
186 #[snafu(display("Failed to evaluate record batch"))]
187 EvaluateRecordBatch {
188 #[snafu(source)]
189 error: datafusion_common::error::DataFusionError,
190 #[snafu(implicit)]
191 location: Location,
192 },
193
194 #[snafu(display("Failed to compute arrow kernel"))]
195 ComputeArrowKernel {
196 #[snafu(source)]
197 error: arrow::error::ArrowError,
198 #[snafu(implicit)]
199 location: Location,
200 },
201
202 #[snafu(display("Unexpected evaluation result column type: {}", data_type))]
203 UnexpectedColumnType {
204 data_type: arrow::datatypes::DataType,
205 #[snafu(implicit)]
206 location: Location,
207 },
208
209 #[snafu(display("Failed to convert to DataFusion's Schema"))]
210 ToDFSchema {
211 #[snafu(source)]
212 error: datafusion_common::error::DataFusionError,
213 #[snafu(implicit)]
214 location: Location,
215 },
216
217 #[snafu(display("Failed to create physical expression"))]
218 CreatePhysicalExpr {
219 #[snafu(source)]
220 error: datafusion_common::error::DataFusionError,
221 #[snafu(implicit)]
222 location: Location,
223 },
224
225 #[snafu(display("Partition expr value is not supported: {:?}", value))]
226 UnsupportedPartitionExprValue {
227 value: Value,
228 #[snafu(implicit)]
229 location: Location,
230 },
231}
232
233impl ErrorExt for Error {
234 fn status_code(&self) -> StatusCode {
235 match self {
236 Error::GetCache { .. } => StatusCode::StorageUnavailable,
237 Error::FindLeader { .. } => StatusCode::TableUnavailable,
238
239 Error::ConjunctExprWithNonExpr { .. }
240 | Error::UnclosedValue { .. }
241 | Error::InvalidExpr { .. }
242 | Error::UndefinedColumn { .. } => StatusCode::InvalidArguments,
243
244 Error::RegionKeysSize { .. }
245 | Error::InvalidInsertRequest { .. }
246 | Error::InvalidDeleteRequest { .. } => StatusCode::InvalidArguments,
247
248 Error::ConvertScalarValue { .. }
249 | Error::SerializeJson { .. }
250 | Error::DeserializeJson { .. } => StatusCode::Internal,
251
252 Error::Unexpected { .. }
253 | Error::InvalidTableRouteData { .. }
254 | Error::FindTableRoutes { .. }
255 | Error::FindRegionRoutes { .. } => StatusCode::Unexpected,
256 Error::TableRouteNotFound { .. } => StatusCode::TableNotFound,
257 Error::TableRouteManager { source, .. } => source.status_code(),
258 Error::UnexpectedLogicalRouteTable { source, .. } => source.status_code(),
259 Error::ConvertToVector { source, .. } => source.status_code(),
260 Error::EvaluateRecordBatch { .. } => StatusCode::Internal,
261 Error::ComputeArrowKernel { .. } => StatusCode::Internal,
262 Error::UnexpectedColumnType { .. } => StatusCode::Internal,
263 Error::ToDFSchema { .. } => StatusCode::Internal,
264 Error::CreatePhysicalExpr { .. } => StatusCode::Internal,
265 Error::UnsupportedPartitionExprValue { .. } => StatusCode::InvalidArguments,
266 }
267 }
268
269 fn as_any(&self) -> &dyn Any {
270 self
271 }
272}
273
274pub type Result<T> = std::result::Result<T, Error>;