meta_srv/
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 common_error::define_into_tonic_status;
16use common_error::ext::{BoxedError, ErrorExt};
17use common_error::status_code::StatusCode;
18use common_macro::stack_trace_debug;
19use common_meta::DatanodeId;
20use common_runtime::JoinError;
21use snafu::{Location, Snafu};
22use store_api::storage::RegionId;
23use table::metadata::TableId;
24use tokio::sync::mpsc::error::SendError;
25use tonic::codegen::http;
26
27use crate::metasrv::SelectTarget;
28use crate::pubsub::Message;
29use crate::service::mailbox::Channel;
30
31#[derive(Snafu)]
32#[snafu(visibility(pub))]
33#[stack_trace_debug]
34pub enum Error {
35    #[snafu(display("Failed to choose items"))]
36    ChooseItems {
37        #[snafu(implicit)]
38        location: Location,
39        #[snafu(source)]
40        error: rand::distr::weighted::Error,
41    },
42
43    #[snafu(display("Exceeded deadline, operation: {}", operation))]
44    ExceededDeadline {
45        #[snafu(implicit)]
46        location: Location,
47        operation: String,
48    },
49
50    #[snafu(display("The target peer is unavailable temporally: {}", peer_id))]
51    PeerUnavailable {
52        #[snafu(implicit)]
53        location: Location,
54        peer_id: u64,
55    },
56
57    #[snafu(display("Failed to lookup peer: {}", peer_id))]
58    LookupPeer {
59        #[snafu(implicit)]
60        location: Location,
61        source: common_meta::error::Error,
62        peer_id: u64,
63    },
64
65    #[snafu(display("Another migration procedure is running for region: {}", region_id))]
66    MigrationRunning {
67        #[snafu(implicit)]
68        location: Location,
69        region_id: RegionId,
70    },
71
72    #[snafu(display("The region migration procedure aborted, reason: {}", reason))]
73    MigrationAbort {
74        #[snafu(implicit)]
75        location: Location,
76        reason: String,
77    },
78
79    #[snafu(display(
80        "Another procedure is opening the region: {} on peer: {}",
81        region_id,
82        peer_id
83    ))]
84    RegionOpeningRace {
85        #[snafu(implicit)]
86        location: Location,
87        peer_id: DatanodeId,
88        region_id: RegionId,
89    },
90
91    #[snafu(display("Failed to init ddl manager"))]
92    InitDdlManager {
93        #[snafu(implicit)]
94        location: Location,
95        source: common_meta::error::Error,
96    },
97
98    #[snafu(display("Failed to create default catalog and schema"))]
99    InitMetadata {
100        #[snafu(implicit)]
101        location: Location,
102        source: common_meta::error::Error,
103    },
104
105    #[snafu(display("Failed to allocate next sequence number"))]
106    NextSequence {
107        #[snafu(implicit)]
108        location: Location,
109        source: common_meta::error::Error,
110    },
111
112    #[snafu(display("Failed to start telemetry task"))]
113    StartTelemetryTask {
114        #[snafu(implicit)]
115        location: Location,
116        source: common_runtime::error::Error,
117    },
118
119    #[snafu(display("Failed to submit ddl task"))]
120    SubmitDdlTask {
121        #[snafu(implicit)]
122        location: Location,
123        source: common_meta::error::Error,
124    },
125
126    #[snafu(display("Failed to invalidate table cache"))]
127    InvalidateTableCache {
128        #[snafu(implicit)]
129        location: Location,
130        source: common_meta::error::Error,
131    },
132
133    #[snafu(display("Failed to list catalogs"))]
134    ListCatalogs {
135        #[snafu(implicit)]
136        location: Location,
137        source: BoxedError,
138    },
139
140    #[snafu(display("Failed to list {}'s schemas", catalog))]
141    ListSchemas {
142        #[snafu(implicit)]
143        location: Location,
144        catalog: String,
145        source: BoxedError,
146    },
147
148    #[snafu(display("Failed to list {}.{}'s tables", catalog, schema))]
149    ListTables {
150        #[snafu(implicit)]
151        location: Location,
152        catalog: String,
153        schema: String,
154        source: BoxedError,
155    },
156
157    #[snafu(display("Failed to join a future"))]
158    Join {
159        #[snafu(implicit)]
160        location: Location,
161        #[snafu(source)]
162        error: JoinError,
163    },
164
165    #[snafu(display(
166        "Failed to request {}, required: {}, but only {} available",
167        select_target,
168        required,
169        available
170    ))]
171    NoEnoughAvailableNode {
172        #[snafu(implicit)]
173        location: Location,
174        required: usize,
175        available: usize,
176        select_target: SelectTarget,
177    },
178
179    #[snafu(display("Failed to send shutdown signal"))]
180    SendShutdownSignal {
181        #[snafu(source)]
182        error: SendError<()>,
183    },
184
185    #[snafu(display("Failed to shutdown {} server", server))]
186    ShutdownServer {
187        #[snafu(implicit)]
188        location: Location,
189        source: servers::error::Error,
190        server: String,
191    },
192
193    #[snafu(display("Empty key is not allowed"))]
194    EmptyKey {
195        #[snafu(implicit)]
196        location: Location,
197    },
198
199    #[snafu(display("Failed to execute via Etcd"))]
200    EtcdFailed {
201        #[snafu(source)]
202        error: etcd_client::Error,
203        #[snafu(implicit)]
204        location: Location,
205    },
206
207    #[snafu(display("Failed to connect to Etcd"))]
208    ConnectEtcd {
209        #[snafu(source)]
210        error: etcd_client::Error,
211        #[snafu(implicit)]
212        location: Location,
213    },
214
215    #[snafu(display("Failed to bind address {}", addr))]
216    TcpBind {
217        addr: String,
218        #[snafu(source)]
219        error: std::io::Error,
220        #[snafu(implicit)]
221        location: Location,
222    },
223
224    #[snafu(display("Failed to convert to TcpIncoming"))]
225    TcpIncoming {
226        #[snafu(source)]
227        error: Box<dyn std::error::Error + Send + Sync>,
228    },
229
230    #[snafu(display("Failed to start gRPC server"))]
231    StartGrpc {
232        #[snafu(source)]
233        error: tonic::transport::Error,
234        #[snafu(implicit)]
235        location: Location,
236    },
237
238    #[snafu(display("Failed to start http server"))]
239    StartHttp {
240        #[snafu(implicit)]
241        location: Location,
242        source: servers::error::Error,
243    },
244
245    #[snafu(display("Failed to init export metrics task"))]
246    InitExportMetricsTask {
247        #[snafu(implicit)]
248        location: Location,
249        source: servers::error::Error,
250    },
251
252    #[snafu(display("Failed to parse address {}", addr))]
253    ParseAddr {
254        addr: String,
255        #[snafu(source)]
256        error: std::net::AddrParseError,
257    },
258
259    #[snafu(display("Invalid lease key: {}", key))]
260    InvalidLeaseKey {
261        key: String,
262        #[snafu(implicit)]
263        location: Location,
264    },
265
266    #[snafu(display("Invalid datanode stat key: {}", key))]
267    InvalidStatKey {
268        key: String,
269        #[snafu(implicit)]
270        location: Location,
271    },
272
273    #[snafu(display("Invalid inactive region key: {}", key))]
274    InvalidInactiveRegionKey {
275        key: String,
276        #[snafu(implicit)]
277        location: Location,
278    },
279
280    #[snafu(display("Failed to parse lease key from utf8"))]
281    LeaseKeyFromUtf8 {
282        #[snafu(source)]
283        error: std::string::FromUtf8Error,
284        #[snafu(implicit)]
285        location: Location,
286    },
287
288    #[snafu(display("Failed to parse lease value from utf8"))]
289    LeaseValueFromUtf8 {
290        #[snafu(source)]
291        error: std::string::FromUtf8Error,
292        #[snafu(implicit)]
293        location: Location,
294    },
295
296    #[snafu(display("Failed to parse invalid region key from utf8"))]
297    InvalidRegionKeyFromUtf8 {
298        #[snafu(source)]
299        error: std::string::FromUtf8Error,
300        #[snafu(implicit)]
301        location: Location,
302    },
303
304    #[snafu(display("Failed to serialize to json: {}", input))]
305    SerializeToJson {
306        input: String,
307        #[snafu(source)]
308        error: serde_json::error::Error,
309        #[snafu(implicit)]
310        location: Location,
311    },
312
313    #[snafu(display("Failed to deserialize from json: {}", input))]
314    DeserializeFromJson {
315        input: String,
316        #[snafu(source)]
317        error: serde_json::error::Error,
318        #[snafu(implicit)]
319        location: Location,
320    },
321
322    #[snafu(display("Failed to parse number: {}", err_msg))]
323    ParseNum {
324        err_msg: String,
325        #[snafu(source)]
326        error: std::num::ParseIntError,
327        #[snafu(implicit)]
328        location: Location,
329    },
330
331    #[snafu(display("Failed to parse bool: {}", err_msg))]
332    ParseBool {
333        err_msg: String,
334        #[snafu(source)]
335        error: std::str::ParseBoolError,
336        #[snafu(implicit)]
337        location: Location,
338    },
339
340    #[snafu(display("Failed to downgrade region leader, region: {}", region_id))]
341    DowngradeLeader {
342        region_id: RegionId,
343        #[snafu(implicit)]
344        location: Location,
345        #[snafu(source)]
346        source: BoxedError,
347    },
348
349    #[snafu(display("Region's leader peer changed: {}", msg))]
350    LeaderPeerChanged {
351        msg: String,
352        #[snafu(implicit)]
353        location: Location,
354    },
355
356    #[snafu(display("Invalid arguments: {}", err_msg))]
357    InvalidArguments {
358        err_msg: String,
359        #[snafu(implicit)]
360        location: Location,
361    },
362
363    #[cfg(feature = "mysql_kvbackend")]
364    #[snafu(display("Failed to parse mysql url: {}", mysql_url))]
365    ParseMySqlUrl {
366        #[snafu(source)]
367        error: sqlx::error::Error,
368        mysql_url: String,
369        #[snafu(implicit)]
370        location: Location,
371    },
372
373    #[snafu(display("Failed to find table route for {table_id}"))]
374    TableRouteNotFound {
375        table_id: TableId,
376        #[snafu(implicit)]
377        location: Location,
378    },
379
380    #[snafu(display("Failed to find table route for {region_id}"))]
381    RegionRouteNotFound {
382        region_id: RegionId,
383        #[snafu(implicit)]
384        location: Location,
385    },
386
387    #[snafu(display("Table info not found: {}", table_id))]
388    TableInfoNotFound {
389        table_id: TableId,
390        #[snafu(implicit)]
391        location: Location,
392    },
393
394    #[snafu(display("Datanode table not found: {}, datanode: {}", table_id, datanode_id))]
395    DatanodeTableNotFound {
396        table_id: TableId,
397        datanode_id: DatanodeId,
398        #[snafu(implicit)]
399        location: Location,
400    },
401
402    #[snafu(display("Metasrv has no leader at this moment"))]
403    NoLeader {
404        #[snafu(implicit)]
405        location: Location,
406    },
407
408    #[snafu(display("Table {} not found", name))]
409    TableNotFound {
410        name: String,
411        #[snafu(implicit)]
412        location: Location,
413    },
414
415    #[snafu(display("Unsupported selector type, {}", selector_type))]
416    UnsupportedSelectorType {
417        selector_type: String,
418        #[snafu(implicit)]
419        location: Location,
420    },
421
422    #[snafu(display("Unexpected, violated: {violated}"))]
423    Unexpected {
424        violated: String,
425        #[snafu(implicit)]
426        location: Location,
427    },
428
429    #[snafu(display("Failed to create gRPC channel"))]
430    CreateChannel {
431        #[snafu(implicit)]
432        location: Location,
433        source: common_grpc::error::Error,
434    },
435
436    #[snafu(display("Failed to batch get KVs from leader's in_memory kv store"))]
437    BatchGet {
438        #[snafu(source)]
439        error: tonic::Status,
440        #[snafu(implicit)]
441        location: Location,
442    },
443
444    #[snafu(display("Failed to batch range KVs from leader's in_memory kv store"))]
445    Range {
446        #[snafu(source)]
447        error: tonic::Status,
448        #[snafu(implicit)]
449        location: Location,
450    },
451
452    #[snafu(display("Response header not found"))]
453    ResponseHeaderNotFound {
454        #[snafu(implicit)]
455        location: Location,
456    },
457
458    #[snafu(display("The requested meta node is not leader, node addr: {}", node_addr))]
459    IsNotLeader {
460        node_addr: String,
461        #[snafu(implicit)]
462        location: Location,
463    },
464
465    #[snafu(display("Invalid http body"))]
466    InvalidHttpBody {
467        #[snafu(source)]
468        error: http::Error,
469        #[snafu(implicit)]
470        location: Location,
471    },
472
473    #[snafu(display(
474        "The number of retries for the grpc call {} exceeded the limit, {}",
475        func_name,
476        retry_num
477    ))]
478    ExceededRetryLimit {
479        func_name: String,
480        retry_num: usize,
481        #[snafu(implicit)]
482        location: Location,
483    },
484
485    #[snafu(display("Invalid utf-8 value"))]
486    InvalidUtf8Value {
487        #[snafu(source)]
488        error: std::string::FromUtf8Error,
489        #[snafu(implicit)]
490        location: Location,
491    },
492
493    #[snafu(display("Missing required parameter, param: {:?}", param))]
494    MissingRequiredParameter { param: String },
495
496    #[snafu(display("Failed to start procedure manager"))]
497    StartProcedureManager {
498        #[snafu(implicit)]
499        location: Location,
500        source: common_procedure::Error,
501    },
502
503    #[snafu(display("Failed to stop procedure manager"))]
504    StopProcedureManager {
505        #[snafu(implicit)]
506        location: Location,
507        source: common_procedure::Error,
508    },
509
510    #[snafu(display("Failed to wait procedure done"))]
511    WaitProcedure {
512        #[snafu(implicit)]
513        location: Location,
514        source: common_procedure::Error,
515    },
516
517    #[snafu(display("Failed to query procedure state"))]
518    QueryProcedure {
519        #[snafu(implicit)]
520        location: Location,
521        source: common_procedure::Error,
522    },
523
524    #[snafu(display("Procedure not found: {pid}"))]
525    ProcedureNotFound {
526        #[snafu(implicit)]
527        location: Location,
528        pid: String,
529    },
530
531    #[snafu(display("Failed to submit procedure"))]
532    SubmitProcedure {
533        #[snafu(implicit)]
534        location: Location,
535        source: common_procedure::Error,
536    },
537
538    #[snafu(display("A prune task for topic {} is already running", topic))]
539    PruneTaskAlreadyRunning {
540        topic: String,
541        #[snafu(implicit)]
542        location: Location,
543    },
544
545    #[snafu(display("Schema already exists, name: {schema_name}"))]
546    SchemaAlreadyExists {
547        schema_name: String,
548        #[snafu(implicit)]
549        location: Location,
550    },
551
552    #[snafu(display("Table already exists: {table_name}"))]
553    TableAlreadyExists {
554        table_name: String,
555        #[snafu(implicit)]
556        location: Location,
557    },
558
559    #[snafu(display("Pusher not found: {pusher_id}"))]
560    PusherNotFound {
561        pusher_id: String,
562        #[snafu(implicit)]
563        location: Location,
564    },
565
566    #[snafu(display("Failed to push message: {err_msg}"))]
567    PushMessage {
568        err_msg: String,
569        #[snafu(implicit)]
570        location: Location,
571    },
572
573    #[snafu(display("Mailbox already closed: {id}"))]
574    MailboxClosed {
575        id: u64,
576        #[snafu(implicit)]
577        location: Location,
578    },
579
580    #[snafu(display("Mailbox timeout: {id}"))]
581    MailboxTimeout {
582        id: u64,
583        #[snafu(implicit)]
584        location: Location,
585    },
586
587    #[snafu(display("Mailbox receiver got an error: {id}, {err_msg}"))]
588    MailboxReceiver {
589        id: u64,
590        err_msg: String,
591        #[snafu(implicit)]
592        location: Location,
593    },
594
595    #[snafu(display("Mailbox channel closed: {channel}"))]
596    MailboxChannelClosed {
597        channel: Channel,
598        #[snafu(implicit)]
599        location: Location,
600    },
601
602    #[snafu(display("Missing request header"))]
603    MissingRequestHeader {
604        #[snafu(implicit)]
605        location: Location,
606    },
607
608    #[snafu(display("Failed to register procedure loader, type name: {}", type_name))]
609    RegisterProcedureLoader {
610        type_name: String,
611        #[snafu(implicit)]
612        location: Location,
613        source: common_procedure::error::Error,
614    },
615
616    #[snafu(display(
617        "Received unexpected instruction reply, mailbox message: {}, reason: {}",
618        mailbox_message,
619        reason
620    ))]
621    UnexpectedInstructionReply {
622        mailbox_message: String,
623        reason: String,
624        #[snafu(implicit)]
625        location: Location,
626    },
627
628    #[snafu(display("Expected to retry later, reason: {}", reason))]
629    RetryLater {
630        reason: String,
631        #[snafu(implicit)]
632        location: Location,
633    },
634
635    #[snafu(display("Expected to retry later, reason: {}", reason))]
636    RetryLaterWithSource {
637        reason: String,
638        #[snafu(implicit)]
639        location: Location,
640        source: BoxedError,
641    },
642
643    #[snafu(display("Failed to convert proto data"))]
644    ConvertProtoData {
645        #[snafu(implicit)]
646        location: Location,
647        source: common_meta::error::Error,
648    },
649
650    // this error is used for custom error mapping
651    // please do not delete it
652    #[snafu(display("Other error"))]
653    Other {
654        source: BoxedError,
655        #[snafu(implicit)]
656        location: Location,
657    },
658
659    #[snafu(display("Table metadata manager error"))]
660    TableMetadataManager {
661        source: common_meta::error::Error,
662        #[snafu(implicit)]
663        location: Location,
664    },
665
666    #[snafu(display("Maintenance mode manager error"))]
667    MaintenanceModeManager {
668        source: common_meta::error::Error,
669        #[snafu(implicit)]
670        location: Location,
671    },
672
673    #[snafu(display("Keyvalue backend error"))]
674    KvBackend {
675        source: common_meta::error::Error,
676        #[snafu(implicit)]
677        location: Location,
678    },
679
680    #[snafu(display("Failed to publish message"))]
681    PublishMessage {
682        #[snafu(source)]
683        error: SendError<Message>,
684        #[snafu(implicit)]
685        location: Location,
686    },
687
688    #[snafu(display("Too many partitions"))]
689    TooManyPartitions {
690        #[snafu(implicit)]
691        location: Location,
692    },
693
694    #[snafu(display("Unsupported operation {}", operation))]
695    Unsupported {
696        operation: String,
697        #[snafu(implicit)]
698        location: Location,
699    },
700
701    #[snafu(display("Unexpected table route type: {}", err_msg))]
702    UnexpectedLogicalRouteTable {
703        #[snafu(implicit)]
704        location: Location,
705        err_msg: String,
706        source: common_meta::error::Error,
707    },
708
709    #[snafu(display("Failed to save cluster info"))]
710    SaveClusterInfo {
711        #[snafu(implicit)]
712        location: Location,
713        source: common_meta::error::Error,
714    },
715
716    #[snafu(display("Invalid cluster info format"))]
717    InvalidClusterInfoFormat {
718        #[snafu(implicit)]
719        location: Location,
720        source: common_meta::error::Error,
721    },
722
723    #[snafu(display("Invalid datanode stat format"))]
724    InvalidDatanodeStatFormat {
725        #[snafu(implicit)]
726        location: Location,
727        source: common_meta::error::Error,
728    },
729
730    #[snafu(display("Failed to serialize options to TOML"))]
731    TomlFormat {
732        #[snafu(implicit)]
733        location: Location,
734        #[snafu(source(from(common_config::error::Error, Box::new)))]
735        source: Box<common_config::error::Error>,
736    },
737
738    #[cfg(feature = "pg_kvbackend")]
739    #[snafu(display("Failed to execute via postgres"))]
740    PostgresExecution {
741        #[snafu(source)]
742        error: tokio_postgres::Error,
743        #[snafu(implicit)]
744        location: Location,
745    },
746
747    #[cfg(feature = "pg_kvbackend")]
748    #[snafu(display("Failed to connect to Postgres"))]
749    ConnectPostgres {
750        #[snafu(source)]
751        error: tokio_postgres::Error,
752        #[snafu(implicit)]
753        location: Location,
754    },
755
756    #[cfg(feature = "pg_kvbackend")]
757    #[snafu(display("Failed to create connection pool for Postgres"))]
758    CreatePostgresPool {
759        #[snafu(source)]
760        error: deadpool_postgres::CreatePoolError,
761        #[snafu(implicit)]
762        location: Location,
763    },
764
765    #[cfg(feature = "pg_kvbackend")]
766    #[snafu(display("Failed to get connection from Postgres pool: {}", reason))]
767    GetPostgresConnection {
768        reason: String,
769        #[snafu(implicit)]
770        location: Location,
771    },
772
773    #[cfg(feature = "mysql_kvbackend")]
774    #[snafu(display("Failed to execute via mysql, sql: {}", sql))]
775    MySqlExecution {
776        #[snafu(source)]
777        error: sqlx::Error,
778        #[snafu(implicit)]
779        location: Location,
780        sql: String,
781    },
782
783    #[cfg(feature = "mysql_kvbackend")]
784    #[snafu(display("Failed to create mysql pool"))]
785    CreateMySqlPool {
786        #[snafu(source)]
787        error: sqlx::Error,
788        #[snafu(implicit)]
789        location: Location,
790    },
791
792    #[cfg(feature = "mysql_kvbackend")]
793    #[snafu(display("Failed to connect to mysql"))]
794    ConnectMySql {
795        #[snafu(source)]
796        error: sqlx::Error,
797        #[snafu(implicit)]
798        location: Location,
799    },
800
801    #[snafu(display("Handler not found: {}", name))]
802    HandlerNotFound {
803        name: String,
804        #[snafu(implicit)]
805        location: Location,
806    },
807
808    #[snafu(display("Flow state handler error"))]
809    FlowStateHandler {
810        #[snafu(implicit)]
811        location: Location,
812        source: common_meta::error::Error,
813    },
814
815    #[snafu(display("Failed to build wal options allocator"))]
816    BuildWalOptionsAllocator {
817        #[snafu(implicit)]
818        location: Location,
819        source: common_meta::error::Error,
820    },
821
822    #[snafu(display("Failed to build kafka client."))]
823    BuildKafkaClient {
824        #[snafu(implicit)]
825        location: Location,
826        #[snafu(source)]
827        error: common_meta::error::Error,
828    },
829
830    #[snafu(display(
831        "Failed to build a Kafka partition client, topic: {}, partition: {}",
832        topic,
833        partition
834    ))]
835    BuildPartitionClient {
836        topic: String,
837        partition: i32,
838        #[snafu(implicit)]
839        location: Location,
840        #[snafu(source)]
841        error: rskafka::client::error::Error,
842    },
843
844    #[snafu(display(
845        "Failed to delete records from Kafka, topic: {}, partition: {}, offset: {}",
846        topic,
847        partition,
848        offset
849    ))]
850    DeleteRecords {
851        #[snafu(implicit)]
852        location: Location,
853        #[snafu(source)]
854        error: rskafka::client::error::Error,
855        topic: String,
856        partition: i32,
857        offset: u64,
858    },
859
860    #[snafu(display("Failed to update the TopicNameValue in kvbackend, topic: {}", topic))]
861    UpdateTopicNameValue {
862        topic: String,
863        #[snafu(implicit)]
864        location: Location,
865        #[snafu(source)]
866        source: common_meta::error::Error,
867    },
868}
869
870impl Error {
871    /// Returns `true` if the error is retryable.
872    pub fn is_retryable(&self) -> bool {
873        matches!(self, Error::RetryLater { .. })
874            || matches!(self, Error::RetryLaterWithSource { .. })
875    }
876}
877
878pub type Result<T> = std::result::Result<T, Error>;
879
880define_into_tonic_status!(Error);
881
882impl ErrorExt for Error {
883    fn status_code(&self) -> StatusCode {
884        match self {
885            Error::EtcdFailed { .. }
886            | Error::ConnectEtcd { .. }
887            | Error::TcpBind { .. }
888            | Error::TcpIncoming { .. }
889            | Error::SerializeToJson { .. }
890            | Error::DeserializeFromJson { .. }
891            | Error::NoLeader { .. }
892            | Error::CreateChannel { .. }
893            | Error::BatchGet { .. }
894            | Error::Range { .. }
895            | Error::ResponseHeaderNotFound { .. }
896            | Error::IsNotLeader { .. }
897            | Error::InvalidHttpBody { .. }
898            | Error::ExceededRetryLimit { .. }
899            | Error::SendShutdownSignal { .. }
900            | Error::PusherNotFound { .. }
901            | Error::PushMessage { .. }
902            | Error::MailboxClosed { .. }
903            | Error::MailboxTimeout { .. }
904            | Error::MailboxReceiver { .. }
905            | Error::MailboxChannelClosed { .. }
906            | Error::RetryLater { .. }
907            | Error::RetryLaterWithSource { .. }
908            | Error::StartGrpc { .. }
909            | Error::NoEnoughAvailableNode { .. }
910            | Error::PublishMessage { .. }
911            | Error::Join { .. }
912            | Error::PeerUnavailable { .. }
913            | Error::ExceededDeadline { .. }
914            | Error::ChooseItems { .. }
915            | Error::FlowStateHandler { .. }
916            | Error::BuildWalOptionsAllocator { .. }
917            | Error::BuildPartitionClient { .. }
918            | Error::BuildKafkaClient { .. }
919            | Error::DeleteRecords { .. }
920            | Error::PruneTaskAlreadyRunning { .. } => StatusCode::Internal,
921
922            Error::Unsupported { .. } => StatusCode::Unsupported,
923
924            Error::SchemaAlreadyExists { .. } => StatusCode::DatabaseAlreadyExists,
925
926            Error::TableAlreadyExists { .. } => StatusCode::TableAlreadyExists,
927            Error::EmptyKey { .. }
928            | Error::MissingRequiredParameter { .. }
929            | Error::MissingRequestHeader { .. }
930            | Error::InvalidLeaseKey { .. }
931            | Error::InvalidStatKey { .. }
932            | Error::InvalidInactiveRegionKey { .. }
933            | Error::ParseNum { .. }
934            | Error::ParseBool { .. }
935            | Error::ParseAddr { .. }
936            | Error::UnsupportedSelectorType { .. }
937            | Error::InvalidArguments { .. }
938            | Error::InitExportMetricsTask { .. }
939            | Error::ProcedureNotFound { .. }
940            | Error::TooManyPartitions { .. }
941            | Error::TomlFormat { .. }
942            | Error::HandlerNotFound { .. }
943            | Error::LeaderPeerChanged { .. } => StatusCode::InvalidArguments,
944            Error::LeaseKeyFromUtf8 { .. }
945            | Error::LeaseValueFromUtf8 { .. }
946            | Error::InvalidRegionKeyFromUtf8 { .. }
947            | Error::TableRouteNotFound { .. }
948            | Error::TableInfoNotFound { .. }
949            | Error::DatanodeTableNotFound { .. }
950            | Error::InvalidUtf8Value { .. }
951            | Error::UnexpectedInstructionReply { .. }
952            | Error::Unexpected { .. }
953            | Error::RegionOpeningRace { .. }
954            | Error::RegionRouteNotFound { .. }
955            | Error::MigrationAbort { .. }
956            | Error::MigrationRunning { .. } => StatusCode::Unexpected,
957            Error::TableNotFound { .. } => StatusCode::TableNotFound,
958            Error::SaveClusterInfo { source, .. }
959            | Error::InvalidClusterInfoFormat { source, .. }
960            | Error::InvalidDatanodeStatFormat { source, .. } => source.status_code(),
961            Error::InvalidateTableCache { source, .. } => source.status_code(),
962            Error::SubmitProcedure { source, .. }
963            | Error::WaitProcedure { source, .. }
964            | Error::QueryProcedure { source, .. } => source.status_code(),
965            Error::ShutdownServer { source, .. } | Error::StartHttp { source, .. } => {
966                source.status_code()
967            }
968            Error::StartProcedureManager { source, .. }
969            | Error::StopProcedureManager { source, .. } => source.status_code(),
970
971            Error::ListCatalogs { source, .. }
972            | Error::ListSchemas { source, .. }
973            | Error::ListTables { source, .. } => source.status_code(),
974            Error::StartTelemetryTask { source, .. } => source.status_code(),
975
976            Error::NextSequence { source, .. } => source.status_code(),
977            Error::DowngradeLeader { source, .. } => source.status_code(),
978            Error::RegisterProcedureLoader { source, .. } => source.status_code(),
979            Error::SubmitDdlTask { source, .. } => source.status_code(),
980            Error::ConvertProtoData { source, .. }
981            | Error::TableMetadataManager { source, .. }
982            | Error::MaintenanceModeManager { source, .. }
983            | Error::KvBackend { source, .. }
984            | Error::UnexpectedLogicalRouteTable { source, .. }
985            | Error::UpdateTopicNameValue { source, .. } => source.status_code(),
986
987            Error::InitMetadata { source, .. } | Error::InitDdlManager { source, .. } => {
988                source.status_code()
989            }
990
991            Error::Other { source, .. } => source.status_code(),
992            Error::LookupPeer { source, .. } => source.status_code(),
993            #[cfg(feature = "pg_kvbackend")]
994            Error::CreatePostgresPool { .. }
995            | Error::GetPostgresConnection { .. }
996            | Error::PostgresExecution { .. }
997            | Error::ConnectPostgres { .. } => StatusCode::Internal,
998            #[cfg(feature = "mysql_kvbackend")]
999            Error::MySqlExecution { .. }
1000            | Error::CreateMySqlPool { .. }
1001            | Error::ConnectMySql { .. }
1002            | Error::ParseMySqlUrl { .. } => StatusCode::Internal,
1003        }
1004    }
1005
1006    fn as_any(&self) -> &dyn std::any::Any {
1007        self
1008    }
1009}
1010
1011// for form tonic
1012pub(crate) fn match_for_io_error(err_status: &tonic::Status) -> Option<&std::io::Error> {
1013    let mut err: &(dyn std::error::Error + 'static) = err_status;
1014
1015    loop {
1016        if let Some(io_err) = err.downcast_ref::<std::io::Error>() {
1017            return Some(io_err);
1018        }
1019
1020        // h2::Error do not expose std::io::Error with `source()`
1021        // https://github.com/hyperium/h2/pull/462
1022        if let Some(h2_err) = err.downcast_ref::<h2::Error>() {
1023            if let Some(io_err) = h2_err.get_io() {
1024                return Some(io_err);
1025            }
1026        }
1027
1028        err = err.source()?;
1029    }
1030}