narwhal_core/capabilities.rs
1use serde::{Deserialize, Serialize};
2
3/// Static description of features a driver supports.
4///
5/// The UI inspects [`Capabilities`] to enable or disable commands without
6/// hard-coding driver names. New flags are added by extending this struct;
7/// existing drivers default to `false` for unknown features.
8#[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Serialize, Deserialize)]
9#[non_exhaustive]
10pub struct Capabilities {
11 /// Driver supports explicit transactions (`BEGIN`/`COMMIT`/`ROLLBACK`).
12 pub transactions: bool,
13 /// Driver can request asynchronous cancellation of an in-flight query.
14 pub cancellation: bool,
15 /// Driver exposes more than one logical schema/namespace.
16 pub multiple_schemas: bool,
17 /// Driver supports server-side prepared statements with parameter binding.
18 pub prepared_statements: bool,
19 /// Driver supports nested transactions via savepoints.
20 pub savepoints: bool,
21 /// Driver can report row counts for `UPDATE`/`DELETE` statements.
22 pub rows_affected: bool,
23 /// Driver returns rows progressively from [`crate::Connection::stream`] —
24 /// i.e. the stream yields rows as the server produces them, without
25 /// materialising the entire result set in memory first.
26 ///
27 /// Drivers that currently buffer the full result before exposing the
28 /// stream (notably `MySQL`, which is awaiting a real `stream_and_drop`
29 /// implementation) must leave this `false` so the UI can warn the
30 /// user and refuse to launch open-ended streams over large tables.
31 pub streaming: bool,
32 /// Driver supports row-level DML through the standard
33 /// `INSERT`/`UPDATE`/`DELETE` grammar that
34 /// [`crate::Connection::execute`] accepts.
35 ///
36 /// Most engines do; the notable exception is `ClickHouse`, where
37 /// row-level changes have to go through `ALTER TABLE ... UPDATE`
38 /// or `ALTER TABLE ... DELETE` async mutations. The pending-changes
39 /// pipeline gates `o`/`O`/`d`/cell-edit on this flag so it never
40 /// emits a statement the driver cannot consume. Defaults to
41 /// `false`; drivers opt in explicitly via
42 /// [`Self::with_row_level_dml`].
43 pub row_level_dml: bool,
44}
45
46impl Capabilities {
47 /// Builder-style mutation used by drivers to assemble their capability set.
48 #[must_use]
49 pub const fn with_transactions(mut self, value: bool) -> Self {
50 self.transactions = value;
51 self
52 }
53
54 #[must_use]
55 pub const fn with_cancellation(mut self, value: bool) -> Self {
56 self.cancellation = value;
57 self
58 }
59
60 #[must_use]
61 pub const fn with_multiple_schemas(mut self, value: bool) -> Self {
62 self.multiple_schemas = value;
63 self
64 }
65
66 #[must_use]
67 pub const fn with_prepared_statements(mut self, value: bool) -> Self {
68 self.prepared_statements = value;
69 self
70 }
71
72 #[must_use]
73 pub const fn with_savepoints(mut self, value: bool) -> Self {
74 self.savepoints = value;
75 self
76 }
77
78 #[must_use]
79 pub const fn with_rows_affected(mut self, value: bool) -> Self {
80 self.rows_affected = value;
81 self
82 }
83
84 #[must_use]
85 pub const fn with_streaming(mut self, value: bool) -> Self {
86 self.streaming = value;
87 self
88 }
89
90 #[must_use]
91 pub const fn with_row_level_dml(mut self, value: bool) -> Self {
92 self.row_level_dml = value;
93 self
94 }
95}