1use std::collections::BTreeMap;
22use std::fmt;
23
24use enum_kinds::EnumKind;
25use serde::{Deserialize, Serialize};
26use smallvec::{SmallVec, smallvec};
27
28use crate::ast::display::{self, AstDisplay, AstFormatter, WithOptionName};
29use crate::ast::{
30 AstInfo, ColumnDef, ConnectionOption, ConnectionOptionName, ContinualTaskOption,
31 CreateConnectionOption, CreateConnectionType, CreateSinkConnection, CreateSourceConnection,
32 CreateSourceOption, CreateSourceOptionName, CteMutRecColumnDef, DeferredItemName, Expr, Format,
33 FormatSpecifier, IcebergSinkMode, Ident, IntervalValue, KeyConstraint, MaterializedViewOption,
34 Query, SelectItem, SinkEnvelope, SourceEnvelope, SourceIncludeMetadata, SubscribeOutput,
35 TableAlias, TableConstraint, TableWithJoins, UnresolvedDatabaseName, UnresolvedItemName,
36 UnresolvedObjectName, UnresolvedSchemaName, Value,
37};
38
39#[allow(clippy::large_enum_variant)]
41#[derive(Debug, Clone, PartialEq, Eq, Hash, EnumKind)]
42#[enum_kind(StatementKind, derive(Serialize, Deserialize))]
43pub enum Statement<T: AstInfo> {
44 Select(SelectStatement<T>),
45 Insert(InsertStatement<T>),
46 Copy(CopyStatement<T>),
47 Update(UpdateStatement<T>),
48 Delete(DeleteStatement<T>),
49 CreateConnection(CreateConnectionStatement<T>),
50 CreateDatabase(CreateDatabaseStatement),
51 CreateSchema(CreateSchemaStatement),
52 CreateWebhookSource(CreateWebhookSourceStatement<T>),
53 CreateSource(CreateSourceStatement<T>),
54 CreateSubsource(CreateSubsourceStatement<T>),
55 CreateSink(CreateSinkStatement<T>),
56 CreateView(CreateViewStatement<T>),
57 CreateMaterializedView(CreateMaterializedViewStatement<T>),
58 CreateContinualTask(CreateContinualTaskStatement<T>),
59 CreateTable(CreateTableStatement<T>),
60 CreateTableFromSource(CreateTableFromSourceStatement<T>),
61 CreateIndex(CreateIndexStatement<T>),
62 CreateType(CreateTypeStatement<T>),
63 CreateRole(CreateRoleStatement),
64 CreateCluster(CreateClusterStatement<T>),
65 CreateClusterReplica(CreateClusterReplicaStatement<T>),
66 CreateSecret(CreateSecretStatement<T>),
67 CreateNetworkPolicy(CreateNetworkPolicyStatement<T>),
68 AlterCluster(AlterClusterStatement<T>),
69 AlterOwner(AlterOwnerStatement<T>),
70 AlterObjectRename(AlterObjectRenameStatement),
71 AlterObjectSwap(AlterObjectSwapStatement),
72 AlterRetainHistory(AlterRetainHistoryStatement<T>),
73 AlterIndex(AlterIndexStatement<T>),
74 AlterSecret(AlterSecretStatement<T>),
75 AlterSetCluster(AlterSetClusterStatement<T>),
76 AlterSink(AlterSinkStatement<T>),
77 AlterSource(AlterSourceStatement<T>),
78 AlterSystemSet(AlterSystemSetStatement),
79 AlterSystemReset(AlterSystemResetStatement),
80 AlterSystemResetAll(AlterSystemResetAllStatement),
81 AlterConnection(AlterConnectionStatement<T>),
82 AlterNetworkPolicy(AlterNetworkPolicyStatement<T>),
83 AlterRole(AlterRoleStatement<T>),
84 AlterTableAddColumn(AlterTableAddColumnStatement<T>),
85 AlterMaterializedViewApplyReplacement(AlterMaterializedViewApplyReplacementStatement),
86 Discard(DiscardStatement),
87 DropObjects(DropObjectsStatement),
88 DropOwned(DropOwnedStatement<T>),
89 SetVariable(SetVariableStatement),
90 ResetVariable(ResetVariableStatement),
91 Show(ShowStatement<T>),
92 StartTransaction(StartTransactionStatement),
93 SetTransaction(SetTransactionStatement),
94 Commit(CommitStatement),
95 Rollback(RollbackStatement),
96 Subscribe(SubscribeStatement<T>),
97 ExplainPlan(ExplainPlanStatement<T>),
98 ExplainPushdown(ExplainPushdownStatement<T>),
99 ExplainTimestamp(ExplainTimestampStatement<T>),
100 ExplainSinkSchema(ExplainSinkSchemaStatement<T>),
101 ExplainAnalyzeObject(ExplainAnalyzeObjectStatement<T>),
102 ExplainAnalyzeCluster(ExplainAnalyzeClusterStatement),
103 Declare(DeclareStatement<T>),
104 Fetch(FetchStatement<T>),
105 Close(CloseStatement),
106 Prepare(PrepareStatement<T>),
107 Execute(ExecuteStatement<T>),
108 Deallocate(DeallocateStatement),
109 Raise(RaiseStatement),
110 GrantRole(GrantRoleStatement<T>),
111 RevokeRole(RevokeRoleStatement<T>),
112 GrantPrivileges(GrantPrivilegesStatement<T>),
113 RevokePrivileges(RevokePrivilegesStatement<T>),
114 AlterDefaultPrivileges(AlterDefaultPrivilegesStatement<T>),
115 ReassignOwned(ReassignOwnedStatement<T>),
116 ValidateConnection(ValidateConnectionStatement<T>),
117 Comment(CommentStatement<T>),
118}
119
120impl<T: AstInfo> AstDisplay for Statement<T> {
121 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
122 match self {
123 Statement::Select(stmt) => f.write_node(stmt),
124 Statement::Insert(stmt) => f.write_node(stmt),
125 Statement::Copy(stmt) => f.write_node(stmt),
126 Statement::Update(stmt) => f.write_node(stmt),
127 Statement::Delete(stmt) => f.write_node(stmt),
128 Statement::CreateConnection(stmt) => f.write_node(stmt),
129 Statement::CreateDatabase(stmt) => f.write_node(stmt),
130 Statement::CreateSchema(stmt) => f.write_node(stmt),
131 Statement::CreateWebhookSource(stmt) => f.write_node(stmt),
132 Statement::CreateSource(stmt) => f.write_node(stmt),
133 Statement::CreateSubsource(stmt) => f.write_node(stmt),
134 Statement::CreateSink(stmt) => f.write_node(stmt),
135 Statement::CreateView(stmt) => f.write_node(stmt),
136 Statement::CreateMaterializedView(stmt) => f.write_node(stmt),
137 Statement::CreateContinualTask(stmt) => f.write_node(stmt),
138 Statement::CreateTable(stmt) => f.write_node(stmt),
139 Statement::CreateTableFromSource(stmt) => f.write_node(stmt),
140 Statement::CreateIndex(stmt) => f.write_node(stmt),
141 Statement::CreateRole(stmt) => f.write_node(stmt),
142 Statement::CreateSecret(stmt) => f.write_node(stmt),
143 Statement::CreateType(stmt) => f.write_node(stmt),
144 Statement::CreateCluster(stmt) => f.write_node(stmt),
145 Statement::CreateClusterReplica(stmt) => f.write_node(stmt),
146 Statement::CreateNetworkPolicy(stmt) => f.write_node(stmt),
147 Statement::AlterCluster(stmt) => f.write_node(stmt),
148 Statement::AlterNetworkPolicy(stmt) => f.write_node(stmt),
149 Statement::AlterOwner(stmt) => f.write_node(stmt),
150 Statement::AlterObjectRename(stmt) => f.write_node(stmt),
151 Statement::AlterRetainHistory(stmt) => f.write_node(stmt),
152 Statement::AlterObjectSwap(stmt) => f.write_node(stmt),
153 Statement::AlterIndex(stmt) => f.write_node(stmt),
154 Statement::AlterSetCluster(stmt) => f.write_node(stmt),
155 Statement::AlterSecret(stmt) => f.write_node(stmt),
156 Statement::AlterSink(stmt) => f.write_node(stmt),
157 Statement::AlterSource(stmt) => f.write_node(stmt),
158 Statement::AlterSystemSet(stmt) => f.write_node(stmt),
159 Statement::AlterSystemReset(stmt) => f.write_node(stmt),
160 Statement::AlterSystemResetAll(stmt) => f.write_node(stmt),
161 Statement::AlterConnection(stmt) => f.write_node(stmt),
162 Statement::AlterRole(stmt) => f.write_node(stmt),
163 Statement::AlterTableAddColumn(stmt) => f.write_node(stmt),
164 Statement::AlterMaterializedViewApplyReplacement(stmt) => f.write_node(stmt),
165 Statement::Discard(stmt) => f.write_node(stmt),
166 Statement::DropObjects(stmt) => f.write_node(stmt),
167 Statement::DropOwned(stmt) => f.write_node(stmt),
168 Statement::SetVariable(stmt) => f.write_node(stmt),
169 Statement::ResetVariable(stmt) => f.write_node(stmt),
170 Statement::Show(stmt) => f.write_node(stmt),
171 Statement::StartTransaction(stmt) => f.write_node(stmt),
172 Statement::SetTransaction(stmt) => f.write_node(stmt),
173 Statement::Commit(stmt) => f.write_node(stmt),
174 Statement::Rollback(stmt) => f.write_node(stmt),
175 Statement::Subscribe(stmt) => f.write_node(stmt),
176 Statement::ExplainPlan(stmt) => f.write_node(stmt),
177 Statement::ExplainPushdown(stmt) => f.write_node(stmt),
178 Statement::ExplainAnalyzeObject(stmt) => f.write_node(stmt),
179 Statement::ExplainAnalyzeCluster(stmt) => f.write_node(stmt),
180 Statement::ExplainTimestamp(stmt) => f.write_node(stmt),
181 Statement::ExplainSinkSchema(stmt) => f.write_node(stmt),
182 Statement::Declare(stmt) => f.write_node(stmt),
183 Statement::Close(stmt) => f.write_node(stmt),
184 Statement::Fetch(stmt) => f.write_node(stmt),
185 Statement::Prepare(stmt) => f.write_node(stmt),
186 Statement::Execute(stmt) => f.write_node(stmt),
187 Statement::Deallocate(stmt) => f.write_node(stmt),
188 Statement::Raise(stmt) => f.write_node(stmt),
189 Statement::GrantRole(stmt) => f.write_node(stmt),
190 Statement::RevokeRole(stmt) => f.write_node(stmt),
191 Statement::GrantPrivileges(stmt) => f.write_node(stmt),
192 Statement::RevokePrivileges(stmt) => f.write_node(stmt),
193 Statement::AlterDefaultPrivileges(stmt) => f.write_node(stmt),
194 Statement::ReassignOwned(stmt) => f.write_node(stmt),
195 Statement::ValidateConnection(stmt) => f.write_node(stmt),
196 Statement::Comment(stmt) => f.write_node(stmt),
197 }
198 }
199}
200impl_display_t!(Statement);
201
202pub fn statement_kind_label_value(kind: StatementKind) -> &'static str {
204 match kind {
205 StatementKind::Select => "select",
206 StatementKind::Insert => "insert",
207 StatementKind::Copy => "copy",
208 StatementKind::Update => "update",
209 StatementKind::Delete => "delete",
210 StatementKind::CreateConnection => "create_connection",
211 StatementKind::CreateDatabase => "create_database",
212 StatementKind::CreateSchema => "create_schema",
213 StatementKind::CreateWebhookSource => "create_webhook",
214 StatementKind::CreateSource => "create_source",
215 StatementKind::CreateSubsource => "create_subsource",
216 StatementKind::CreateSink => "create_sink",
217 StatementKind::CreateView => "create_view",
218 StatementKind::CreateMaterializedView => "create_materialized_view",
219 StatementKind::CreateContinualTask => "create_continual_task",
220 StatementKind::CreateTable => "create_table",
221 StatementKind::CreateTableFromSource => "create_table_from_source",
222 StatementKind::CreateIndex => "create_index",
223 StatementKind::CreateType => "create_type",
224 StatementKind::CreateRole => "create_role",
225 StatementKind::CreateCluster => "create_cluster",
226 StatementKind::CreateClusterReplica => "create_cluster_replica",
227 StatementKind::CreateSecret => "create_secret",
228 StatementKind::CreateNetworkPolicy => "create_network_policy",
229 StatementKind::AlterCluster => "alter_cluster",
230 StatementKind::AlterObjectRename => "alter_object_rename",
231 StatementKind::AlterRetainHistory => "alter_retain_history",
232 StatementKind::AlterObjectSwap => "alter_object_swap",
233 StatementKind::AlterIndex => "alter_index",
234 StatementKind::AlterNetworkPolicy => "alter_network_policy",
235 StatementKind::AlterRole => "alter_role",
236 StatementKind::AlterSecret => "alter_secret",
237 StatementKind::AlterSetCluster => "alter_set_cluster",
238 StatementKind::AlterSink => "alter_sink",
239 StatementKind::AlterSource => "alter_source",
240 StatementKind::AlterSystemSet => "alter_system_set",
241 StatementKind::AlterSystemReset => "alter_system_reset",
242 StatementKind::AlterSystemResetAll => "alter_system_reset_all",
243 StatementKind::AlterOwner => "alter_owner",
244 StatementKind::AlterConnection => "alter_connection",
245 StatementKind::AlterTableAddColumn => "alter_table",
246 StatementKind::AlterMaterializedViewApplyReplacement => {
247 "alter_materialized_view_apply_replacement"
248 }
249 StatementKind::Discard => "discard",
250 StatementKind::DropObjects => "drop_objects",
251 StatementKind::DropOwned => "drop_owned",
252 StatementKind::SetVariable => "set_variable",
253 StatementKind::ResetVariable => "reset_variable",
254 StatementKind::Show => "show",
255 StatementKind::StartTransaction => "start_transaction",
256 StatementKind::SetTransaction => "set_transaction",
257 StatementKind::Commit => "commit",
258 StatementKind::Rollback => "rollback",
259 StatementKind::Subscribe => "subscribe",
260 StatementKind::ExplainPlan => "explain_plan",
261 StatementKind::ExplainPushdown => "explain_pushdown",
262 StatementKind::ExplainAnalyzeObject => "explain_analyze_object",
263 StatementKind::ExplainAnalyzeCluster => "explain_analyze_cluster",
264 StatementKind::ExplainTimestamp => "explain_timestamp",
265 StatementKind::ExplainSinkSchema => "explain_sink_schema",
266 StatementKind::Declare => "declare",
267 StatementKind::Fetch => "fetch",
268 StatementKind::Close => "close",
269 StatementKind::Prepare => "prepare",
270 StatementKind::Execute => "execute",
271 StatementKind::Deallocate => "deallocate",
272 StatementKind::Raise => "raise",
273 StatementKind::GrantRole => "grant_role",
274 StatementKind::RevokeRole => "revoke_role",
275 StatementKind::GrantPrivileges => "grant_privileges",
276 StatementKind::RevokePrivileges => "revoke_privileges",
277 StatementKind::AlterDefaultPrivileges => "alter_default_privileges",
278 StatementKind::ReassignOwned => "reassign_owned",
279 StatementKind::ValidateConnection => "validate_connection",
280 StatementKind::Comment => "comment",
281 }
282}
283
284#[derive(Debug, Clone, PartialEq, Eq, Hash)]
286pub struct SelectStatement<T: AstInfo> {
287 pub query: Query<T>,
288 pub as_of: Option<AsOf<T>>,
289}
290
291impl<T: AstInfo> AstDisplay for SelectStatement<T> {
292 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
293 f.write_node(&self.query);
294 if let Some(as_of) = &self.as_of {
295 f.write_str(" ");
296 f.write_node(as_of);
297 }
298 }
299}
300impl_display_t!(SelectStatement);
301
302#[derive(Debug, Clone, PartialEq, Eq, Hash)]
304pub struct InsertStatement<T: AstInfo> {
305 pub table_name: T::ItemName,
307 pub columns: Vec<Ident>,
309 pub source: InsertSource<T>,
311 pub returning: Vec<SelectItem<T>>,
313}
314
315impl<T: AstInfo> AstDisplay for InsertStatement<T> {
316 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
317 f.write_str("INSERT INTO ");
318 f.write_node(&self.table_name);
319 if !self.columns.is_empty() {
320 f.write_str(" (");
321 f.write_node(&display::comma_separated(&self.columns));
322 f.write_str(")");
323 }
324 f.write_str(" ");
325 f.write_node(&self.source);
326 if !self.returning.is_empty() {
327 f.write_str(" RETURNING ");
328 f.write_node(&display::comma_separated(&self.returning));
329 }
330 }
331}
332impl_display_t!(InsertStatement);
333
334#[derive(Debug, Clone, PartialEq, Eq, Hash)]
335pub enum CopyRelation<T: AstInfo> {
336 Named {
337 name: T::ItemName,
338 columns: Vec<Ident>,
339 },
340 Select(SelectStatement<T>),
341 Subscribe(SubscribeStatement<T>),
342}
343
344#[derive(Debug, Clone, PartialEq, Eq, Hash)]
345pub enum CopyDirection {
346 To,
347 From,
348}
349
350impl AstDisplay for CopyDirection {
351 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
352 f.write_str(match self {
353 CopyDirection::To => "TO",
354 CopyDirection::From => "FROM",
355 })
356 }
357}
358impl_display!(CopyDirection);
359
360#[derive(Debug, Clone, PartialEq, Eq, Hash)]
361pub enum CopyTarget<T: AstInfo> {
362 Stdin,
363 Stdout,
364 Expr(Expr<T>),
365}
366
367impl<T: AstInfo> AstDisplay for CopyTarget<T> {
368 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
369 match self {
370 CopyTarget::Stdin => f.write_str("STDIN"),
371 CopyTarget::Stdout => f.write_str("STDOUT"),
372 CopyTarget::Expr(expr) => f.write_node(expr),
373 }
374 }
375}
376impl_display_t!(CopyTarget);
377
378#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
379pub enum CopyOptionName {
380 Format,
381 Delimiter,
382 Null,
383 Escape,
384 Quote,
385 Header,
386 AwsConnection,
387 MaxFileSize,
388 Files,
389 Pattern,
390}
391
392impl AstDisplay for CopyOptionName {
393 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
394 f.write_str(match self {
395 CopyOptionName::Format => "FORMAT",
396 CopyOptionName::Delimiter => "DELIMITER",
397 CopyOptionName::Null => "NULL",
398 CopyOptionName::Escape => "ESCAPE",
399 CopyOptionName::Quote => "QUOTE",
400 CopyOptionName::Header => "HEADER",
401 CopyOptionName::AwsConnection => "AWS CONNECTION",
402 CopyOptionName::MaxFileSize => "MAX FILE SIZE",
403 CopyOptionName::Files => "FILES",
404 CopyOptionName::Pattern => "PATTERN",
405 })
406 }
407}
408
409impl WithOptionName for CopyOptionName {
410 fn redact_value(&self) -> bool {
416 match self {
417 CopyOptionName::Format
418 | CopyOptionName::Delimiter
419 | CopyOptionName::Null
420 | CopyOptionName::Escape
421 | CopyOptionName::Quote
422 | CopyOptionName::Header
423 | CopyOptionName::AwsConnection
424 | CopyOptionName::MaxFileSize => false,
425 CopyOptionName::Files | CopyOptionName::Pattern => true,
426 }
427 }
428}
429
430#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
431pub struct CopyOption<T: AstInfo> {
432 pub name: CopyOptionName,
433 pub value: Option<WithOptionValue<T>>,
434}
435impl_display_for_with_option!(CopyOption);
436
437#[derive(Debug, Clone, PartialEq, Eq, Hash)]
439pub struct CopyStatement<T: AstInfo> {
440 pub relation: CopyRelation<T>,
442 pub direction: CopyDirection,
444 pub target: CopyTarget<T>,
446 pub options: Vec<CopyOption<T>>,
448}
449
450impl<T: AstInfo> AstDisplay for CopyStatement<T> {
451 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
452 f.write_str("COPY ");
453 match &self.relation {
454 CopyRelation::Named { name, columns } => {
455 f.write_node(name);
456 if !columns.is_empty() {
457 f.write_str("(");
458 f.write_node(&display::comma_separated(columns));
459 f.write_str(")");
460 }
461 }
462 CopyRelation::Select(query) => {
463 f.write_str("(");
464 f.write_node(query);
465 f.write_str(")");
466 }
467 CopyRelation::Subscribe(query) => {
468 f.write_str("(");
469 f.write_node(query);
470 f.write_str(")");
471 }
472 };
473 f.write_str(" ");
474 f.write_node(&self.direction);
475 f.write_str(" ");
476 f.write_node(&self.target);
477 if !self.options.is_empty() {
478 f.write_str(" WITH (");
479 f.write_node(&display::comma_separated(&self.options));
480 f.write_str(")");
481 }
482 }
483}
484impl_display_t!(CopyStatement);
485
486#[derive(Debug, Clone, PartialEq, Eq, Hash)]
488pub struct UpdateStatement<T: AstInfo> {
489 pub table_name: T::ItemName,
491 pub alias: Option<TableAlias>,
492 pub assignments: Vec<Assignment<T>>,
494 pub selection: Option<Expr<T>>,
496}
497
498impl<T: AstInfo> AstDisplay for UpdateStatement<T> {
499 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
500 f.write_str("UPDATE ");
501 f.write_node(&self.table_name);
502 if let Some(alias) = &self.alias {
503 f.write_str(" AS ");
504 f.write_node(alias);
505 }
506 if !self.assignments.is_empty() {
507 f.write_str(" SET ");
508 f.write_node(&display::comma_separated(&self.assignments));
509 }
510 if let Some(selection) = &self.selection {
511 f.write_str(" WHERE ");
512 f.write_node(selection);
513 }
514 }
515}
516impl_display_t!(UpdateStatement);
517
518#[derive(Debug, Clone, PartialEq, Eq, Hash)]
520pub struct DeleteStatement<T: AstInfo> {
521 pub table_name: T::ItemName,
523 pub alias: Option<TableAlias>,
525 pub using: Vec<TableWithJoins<T>>,
527 pub selection: Option<Expr<T>>,
529}
530
531impl<T: AstInfo> AstDisplay for DeleteStatement<T> {
532 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
533 f.write_str("DELETE FROM ");
534 f.write_node(&self.table_name);
535 if let Some(alias) = &self.alias {
536 f.write_str(" AS ");
537 f.write_node(alias);
538 }
539 if !self.using.is_empty() {
540 f.write_str(" USING ");
541 f.write_node(&display::comma_separated(&self.using));
542 }
543 if let Some(selection) = &self.selection {
544 f.write_str(" WHERE ");
545 f.write_node(selection);
546 }
547 }
548}
549impl_display_t!(DeleteStatement);
550
551#[derive(Debug, Clone, PartialEq, Eq, Hash)]
553pub struct CreateDatabaseStatement {
554 pub name: UnresolvedDatabaseName,
555 pub if_not_exists: bool,
556}
557
558impl AstDisplay for CreateDatabaseStatement {
559 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
560 f.write_str("CREATE DATABASE ");
561 if self.if_not_exists {
562 f.write_str("IF NOT EXISTS ");
563 }
564 f.write_node(&self.name);
565 }
566}
567impl_display!(CreateDatabaseStatement);
568
569#[derive(Debug, Clone, PartialEq, Eq, Hash)]
571pub struct CreateSchemaStatement {
572 pub name: UnresolvedSchemaName,
573 pub if_not_exists: bool,
574}
575
576impl AstDisplay for CreateSchemaStatement {
577 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
578 f.write_str("CREATE SCHEMA ");
579 if self.if_not_exists {
580 f.write_str("IF NOT EXISTS ");
581 }
582 f.write_node(&self.name);
583 }
584}
585impl_display!(CreateSchemaStatement);
586
587#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
588pub struct ConnectionDefaultAwsPrivatelink<T: AstInfo> {
589 pub connection: T::ItemName,
590 pub port: Option<u16>,
592}
593
594impl<T: AstInfo> AstDisplay for ConnectionDefaultAwsPrivatelink<T> {
595 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
596 f.write_node(&self.connection);
597 if let Some(port) = self.port {
598 f.write_str(" (PORT ");
599 f.write_node(&display::escape_single_quote_string(&port.to_string()));
600 f.write_str(")");
601 }
602 }
603}
604impl_display_t!(ConnectionDefaultAwsPrivatelink);
605
606#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
607pub struct KafkaBroker<T: AstInfo> {
608 pub address: String,
609 pub tunnel: KafkaBrokerTunnel<T>,
610}
611
612impl<T: AstInfo> AstDisplay for KafkaBroker<T> {
613 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
614 f.write_str("'");
615 f.write_node(&display::escape_single_quote_string(&self.address));
616 f.write_str("'");
617 f.write_node(&self.tunnel);
618 }
619}
620
621impl_display_t!(KafkaBroker);
622
623#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
624pub enum KafkaBrokerTunnel<T: AstInfo> {
625 Direct,
626 AwsPrivatelink(KafkaBrokerAwsPrivatelink<T>),
627 SshTunnel(T::ItemName),
628}
629
630impl<T: AstInfo> AstDisplay for KafkaBrokerTunnel<T> {
631 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
632 use KafkaBrokerTunnel::*;
633 match self {
634 Direct => {}
635 AwsPrivatelink(aws) => {
636 f.write_str(" ");
637 f.write_node(aws);
638 }
639 Self::SshTunnel(connection) => {
640 f.write_str("USING SSH TUNNEL ");
641 f.write_node(connection);
642 }
643 }
644 }
645}
646
647impl_display_t!(KafkaBrokerTunnel);
648
649#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
650pub enum KafkaBrokerAwsPrivatelinkOptionName {
651 AvailabilityZone,
652 Port,
653}
654
655impl AstDisplay for KafkaBrokerAwsPrivatelinkOptionName {
656 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
657 match self {
658 Self::AvailabilityZone => f.write_str("AVAILABILITY ZONE"),
659 Self::Port => f.write_str("PORT"),
660 }
661 }
662}
663impl_display!(KafkaBrokerAwsPrivatelinkOptionName);
664
665impl WithOptionName for KafkaBrokerAwsPrivatelinkOptionName {
666 fn redact_value(&self) -> bool {
672 match self {
673 Self::AvailabilityZone | Self::Port => false,
674 }
675 }
676}
677
678#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
679pub struct KafkaBrokerAwsPrivatelinkOption<T: AstInfo> {
680 pub name: KafkaBrokerAwsPrivatelinkOptionName,
681 pub value: Option<WithOptionValue<T>>,
682}
683impl_display_for_with_option!(KafkaBrokerAwsPrivatelinkOption);
684impl_display_t!(KafkaBrokerAwsPrivatelinkOption);
685
686#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
687pub struct KafkaBrokerAwsPrivatelink<T: AstInfo> {
688 pub connection: T::ItemName,
689 pub options: Vec<KafkaBrokerAwsPrivatelinkOption<T>>,
690}
691
692impl<T: AstInfo> AstDisplay for KafkaBrokerAwsPrivatelink<T> {
693 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
694 f.write_str("USING AWS PRIVATELINK ");
695 f.write_node(&self.connection);
696 if !self.options.is_empty() {
697 f.write_str(" (");
698 f.write_node(&display::comma_separated(&self.options));
699 f.write_str(")");
700 }
701 }
702}
703impl_display_t!(KafkaBrokerAwsPrivatelink);
704
705#[derive(Debug, Clone, PartialEq, Eq, Hash)]
707pub struct CreateConnectionStatement<T: AstInfo> {
708 pub name: UnresolvedItemName,
709 pub connection_type: CreateConnectionType,
710 pub if_not_exists: bool,
711 pub values: Vec<ConnectionOption<T>>,
712 pub with_options: Vec<CreateConnectionOption<T>>,
713}
714
715impl<T: AstInfo> AstDisplay for CreateConnectionStatement<T> {
716 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
717 f.write_str("CREATE CONNECTION ");
718 if self.if_not_exists {
719 f.write_str("IF NOT EXISTS ");
720 }
721 f.write_node(&self.name);
722 f.write_str(" TO ");
723 self.connection_type.fmt(f);
724 f.write_str(" (");
725 f.write_node(&display::comma_separated(&self.values));
726 f.write_str(")");
727
728 if !self.with_options.is_empty() {
729 f.write_str(" WITH (");
730 f.write_node(&display::comma_separated(&self.with_options));
731 f.write_str(")");
732 }
733 }
734}
735impl_display_t!(CreateConnectionStatement);
736
737#[derive(Debug, Clone, PartialEq, Eq, Hash)]
739pub struct ValidateConnectionStatement<T: AstInfo> {
740 pub name: T::ItemName,
742}
743
744impl<T: AstInfo> AstDisplay for ValidateConnectionStatement<T> {
745 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
746 f.write_str("VALIDATE CONNECTION ");
747 f.write_node(&self.name);
748 }
749}
750impl_display_t!(ValidateConnectionStatement);
751
752#[derive(Debug, Clone, PartialEq, Eq, Hash)]
754pub struct CreateWebhookSourceStatement<T: AstInfo> {
755 pub name: UnresolvedItemName,
756 pub is_table: bool,
757 pub if_not_exists: bool,
758 pub body_format: Format<T>,
759 pub include_headers: CreateWebhookSourceIncludeHeaders,
760 pub validate_using: Option<CreateWebhookSourceCheck<T>>,
761 pub in_cluster: Option<T::ClusterName>,
762}
763
764impl<T: AstInfo> AstDisplay for CreateWebhookSourceStatement<T> {
765 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
766 f.write_str("CREATE ");
767
768 if self.is_table {
769 f.write_str("TABLE ");
770 } else {
771 f.write_str("SOURCE ");
772 }
773
774 if self.if_not_exists {
775 f.write_str("IF NOT EXISTS ");
776 }
777 f.write_node(&self.name);
778
779 if !self.is_table {
781 if let Some(cluster_name) = &self.in_cluster {
782 f.write_str(" IN CLUSTER ");
783 f.write_node(cluster_name);
784 }
785 }
786
787 f.write_str(" FROM WEBHOOK ");
788
789 f.write_str("BODY FORMAT ");
790 f.write_node(&self.body_format);
791
792 f.write_node(&self.include_headers);
793
794 if let Some(validate) = &self.validate_using {
795 f.write_str(" ");
796 f.write_node(validate);
797 }
798 }
799}
800
801impl_display_t!(CreateWebhookSourceStatement);
802
803#[derive(Debug, Clone, PartialEq, Eq, Hash)]
805pub struct CreateWebhookSourceCheck<T: AstInfo> {
806 pub options: Option<CreateWebhookSourceCheckOptions<T>>,
807 pub using: Expr<T>,
808}
809
810impl<T: AstInfo> AstDisplay for CreateWebhookSourceCheck<T> {
811 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
812 f.write_str("CHECK (");
813
814 if let Some(options) = &self.options {
815 f.write_node(options);
816 f.write_str(" ");
817 }
818
819 f.write_node(&self.using);
820 f.write_str(")");
821 }
822}
823
824impl_display_t!(CreateWebhookSourceCheck);
825
826#[derive(Debug, Clone, PartialEq, Eq, Hash)]
828pub struct CreateWebhookSourceCheckOptions<T: AstInfo> {
829 pub secrets: Vec<CreateWebhookSourceSecret<T>>,
830 pub headers: Vec<CreateWebhookSourceHeader>,
831 pub bodies: Vec<CreateWebhookSourceBody>,
832}
833
834impl<T: AstInfo> AstDisplay for CreateWebhookSourceCheckOptions<T> {
835 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
836 f.write_str("WITH (");
837
838 let mut delim = "";
839 if !self.headers.is_empty() {
840 f.write_node(&display::comma_separated(&self.headers[..]));
841 delim = ", ";
842 }
843 if !self.bodies.is_empty() {
844 f.write_str(delim);
845 f.write_node(&display::comma_separated(&self.bodies[..]));
846 delim = ", ";
847 }
848 if !self.secrets.is_empty() {
849 f.write_str(delim);
850 f.write_node(&display::comma_separated(&self.secrets[..]));
851 }
852
853 f.write_str(")");
854 }
855}
856
857impl_display_t!(CreateWebhookSourceCheckOptions);
858
859#[derive(Debug, Clone, PartialEq, Eq, Hash)]
861pub struct CreateWebhookSourceSecret<T: AstInfo> {
862 pub secret: T::ItemName,
863 pub alias: Option<Ident>,
864 pub use_bytes: bool,
865}
866
867impl<T: AstInfo> AstDisplay for CreateWebhookSourceSecret<T> {
868 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
869 f.write_str("SECRET ");
870 f.write_node(&self.secret);
871
872 if let Some(alias) = &self.alias {
873 f.write_str(" AS ");
874 f.write_node(alias);
875 }
876
877 if self.use_bytes {
878 f.write_str(" BYTES");
879 }
880 }
881}
882
883impl_display_t!(CreateWebhookSourceSecret);
884
885#[derive(Debug, Clone, PartialEq, Eq, Hash)]
887pub struct CreateWebhookSourceHeader {
888 pub alias: Option<Ident>,
889 pub use_bytes: bool,
890}
891
892impl AstDisplay for CreateWebhookSourceHeader {
893 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
894 f.write_str("HEADERS");
895
896 if let Some(alias) = &self.alias {
897 f.write_str(" AS ");
898 f.write_node(alias);
899 }
900
901 if self.use_bytes {
902 f.write_str(" BYTES");
903 }
904 }
905}
906
907impl_display!(CreateWebhookSourceHeader);
908
909#[derive(Debug, Clone, PartialEq, Eq, Hash)]
911pub struct CreateWebhookSourceBody {
912 pub alias: Option<Ident>,
913 pub use_bytes: bool,
914}
915
916impl AstDisplay for CreateWebhookSourceBody {
917 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
918 f.write_str("BODY");
919
920 if let Some(alias) = &self.alias {
921 f.write_str(" AS ");
922 f.write_node(alias);
923 }
924
925 if self.use_bytes {
926 f.write_str(" BYTES");
927 }
928 }
929}
930
931impl_display!(CreateWebhookSourceBody);
932
933#[derive(Default, Debug, Clone, PartialEq, Eq, Hash)]
935pub struct CreateWebhookSourceIncludeHeaders {
936 pub mappings: Vec<CreateWebhookSourceMapHeader>,
938 pub column: Option<Vec<CreateWebhookSourceFilterHeader>>,
940}
941
942impl AstDisplay for CreateWebhookSourceIncludeHeaders {
943 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
944 if !self.mappings.is_empty() {
945 f.write_str(" ");
946 }
947 f.write_node(&display::separated(&self.mappings[..], " "));
948
949 if let Some(column) = &self.column {
950 f.write_str(" INCLUDE HEADERS");
951
952 if !column.is_empty() {
953 f.write_str(" ");
954 f.write_str("(");
955 f.write_node(&display::comma_separated(&column[..]));
956 f.write_str(")");
957 }
958 }
959 }
960}
961
962impl_display!(CreateWebhookSourceIncludeHeaders);
963
964#[derive(Debug, Clone, PartialEq, Eq, Hash)]
965pub struct CreateWebhookSourceFilterHeader {
966 pub block: bool,
967 pub header_name: String,
968}
969
970impl AstDisplay for CreateWebhookSourceFilterHeader {
971 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
972 if self.block {
973 f.write_str("NOT ");
974 }
975 f.write_node(&display::escaped_string_literal(&self.header_name));
976 }
977}
978
979impl_display!(CreateWebhookSourceFilterHeader);
980
981#[derive(Debug, Clone, PartialEq, Eq, Hash)]
983pub struct CreateWebhookSourceMapHeader {
984 pub header_name: String,
985 pub column_name: Ident,
986 pub use_bytes: bool,
987}
988
989impl AstDisplay for CreateWebhookSourceMapHeader {
990 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
991 f.write_str("INCLUDE HEADER ");
992
993 f.write_node(&display::escaped_string_literal(&self.header_name));
994
995 f.write_str(" AS ");
996 f.write_node(&self.column_name);
997
998 if self.use_bytes {
999 f.write_str(" BYTES");
1000 }
1001 }
1002}
1003
1004impl_display!(CreateWebhookSourceMapHeader);
1005
1006#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1008pub struct CreateSourceStatement<T: AstInfo> {
1009 pub name: UnresolvedItemName,
1010 pub in_cluster: Option<T::ClusterName>,
1011 pub col_names: Vec<Ident>,
1012 pub connection: CreateSourceConnection<T>,
1013 pub include_metadata: Vec<SourceIncludeMetadata>,
1014 pub format: Option<FormatSpecifier<T>>,
1015 pub envelope: Option<SourceEnvelope>,
1016 pub if_not_exists: bool,
1017 pub key_constraint: Option<KeyConstraint>,
1018 pub with_options: Vec<CreateSourceOption<T>>,
1019 pub external_references: Option<ExternalReferences>,
1020 pub progress_subsource: Option<DeferredItemName<T>>,
1021}
1022
1023impl<T: AstInfo> AstDisplay for CreateSourceStatement<T> {
1024 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1025 f.write_str("CREATE SOURCE ");
1026 if self.if_not_exists {
1027 f.write_str("IF NOT EXISTS ");
1028 }
1029 f.write_node(&self.name);
1030 if !self.col_names.is_empty() {
1031 f.write_str(" (");
1032 f.write_node(&display::comma_separated(&self.col_names));
1033 if self.key_constraint.is_some() {
1034 f.write_str(", ");
1035 f.write_node(self.key_constraint.as_ref().unwrap());
1036 }
1037 f.write_str(")");
1038 } else if self.key_constraint.is_some() {
1039 f.write_str(" (");
1040 f.write_node(self.key_constraint.as_ref().unwrap());
1041 f.write_str(")")
1042 }
1043 if let Some(cluster) = &self.in_cluster {
1044 f.write_str(" IN CLUSTER ");
1045 f.write_node(cluster);
1046 }
1047 f.write_str(" FROM ");
1048 f.write_node(&self.connection);
1049 if let Some(format) = &self.format {
1050 f.write_str(" ");
1051 f.write_node(format);
1052 }
1053 if !self.include_metadata.is_empty() {
1054 f.write_str(" INCLUDE ");
1055 f.write_node(&display::comma_separated(&self.include_metadata));
1056 }
1057
1058 if let Some(envelope) = &self.envelope {
1059 f.write_str(" ENVELOPE ");
1060 f.write_node(envelope);
1061 }
1062
1063 if let Some(subsources) = &self.external_references {
1064 f.write_str(" ");
1065 f.write_node(subsources);
1066 }
1067
1068 if let Some(progress) = &self.progress_subsource {
1069 f.write_str(" EXPOSE PROGRESS AS ");
1070 f.write_node(progress);
1071 }
1072
1073 if !self.with_options.is_empty() {
1074 f.write_str(" WITH (");
1075 f.write_node(&display::comma_separated(&self.with_options));
1076 f.write_str(")");
1077 }
1078 }
1079}
1080impl_display_t!(CreateSourceStatement);
1081
1082#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
1084pub struct ExternalReferenceExport {
1085 pub reference: UnresolvedItemName,
1086 pub alias: Option<UnresolvedItemName>,
1087}
1088
1089impl AstDisplay for ExternalReferenceExport {
1090 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1091 f.write_node(&self.reference);
1092 if let Some(alias) = &self.alias {
1093 f.write_str(" AS ");
1094 f.write_node(alias);
1095 }
1096 }
1097}
1098impl_display!(ExternalReferenceExport);
1099
1100#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1103pub enum ExternalReferences {
1104 SubsetTables(Vec<ExternalReferenceExport>),
1106 SubsetSchemas(Vec<Ident>),
1108 All,
1110}
1111
1112impl AstDisplay for ExternalReferences {
1113 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1114 match self {
1115 Self::SubsetTables(tables) => {
1116 f.write_str("FOR TABLES (");
1117 f.write_node(&display::comma_separated(tables));
1118 f.write_str(")");
1119 }
1120 Self::SubsetSchemas(schemas) => {
1121 f.write_str("FOR SCHEMAS (");
1122 f.write_node(&display::comma_separated(schemas));
1123 f.write_str(")");
1124 }
1125 Self::All => f.write_str("FOR ALL TABLES"),
1126 }
1127 }
1128}
1129impl_display!(ExternalReferences);
1130
1131#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1133pub enum CreateSubsourceOptionName {
1134 Progress,
1135 ExternalReference,
1137 RetainHistory,
1139 TextColumns,
1141 ExcludeColumns,
1143 Details,
1146}
1147
1148impl AstDisplay for CreateSubsourceOptionName {
1149 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1150 f.write_str(match self {
1151 CreateSubsourceOptionName::Progress => "PROGRESS",
1152 CreateSubsourceOptionName::ExternalReference => "EXTERNAL REFERENCE",
1153 CreateSubsourceOptionName::RetainHistory => "RETAIN HISTORY",
1154 CreateSubsourceOptionName::TextColumns => "TEXT COLUMNS",
1155 CreateSubsourceOptionName::ExcludeColumns => "EXCLUDE COLUMNS",
1156 CreateSubsourceOptionName::Details => "DETAILS",
1157 })
1158 }
1159}
1160
1161impl WithOptionName for CreateSubsourceOptionName {
1162 fn redact_value(&self) -> bool {
1168 match self {
1169 CreateSubsourceOptionName::Progress
1170 | CreateSubsourceOptionName::ExternalReference
1171 | CreateSubsourceOptionName::RetainHistory
1172 | CreateSubsourceOptionName::Details
1173 | CreateSubsourceOptionName::TextColumns
1174 | CreateSubsourceOptionName::ExcludeColumns => false,
1175 }
1176 }
1177}
1178
1179#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1180pub struct CreateSubsourceOption<T: AstInfo> {
1181 pub name: CreateSubsourceOptionName,
1182 pub value: Option<WithOptionValue<T>>,
1183}
1184impl_display_for_with_option!(CreateSubsourceOption);
1185
1186#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1188pub struct CreateSubsourceStatement<T: AstInfo> {
1189 pub name: UnresolvedItemName,
1190 pub columns: Vec<ColumnDef<T>>,
1191 pub of_source: Option<T::ItemName>,
1194 pub constraints: Vec<TableConstraint<T>>,
1195 pub if_not_exists: bool,
1196 pub with_options: Vec<CreateSubsourceOption<T>>,
1197}
1198
1199impl<T: AstInfo> AstDisplay for CreateSubsourceStatement<T> {
1200 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1201 f.write_str("CREATE SUBSOURCE ");
1202 if self.if_not_exists {
1203 f.write_str("IF NOT EXISTS ");
1204 }
1205
1206 f.write_node(&self.name);
1207 f.write_str(" (");
1208 f.write_node(&display::comma_separated(&self.columns));
1209 if !self.constraints.is_empty() {
1210 f.write_str(", ");
1211 f.write_node(&display::comma_separated(&self.constraints));
1212 }
1213 f.write_str(")");
1214
1215 if let Some(of_source) = &self.of_source {
1216 f.write_str(" OF SOURCE ");
1217 f.write_node(of_source);
1218 }
1219
1220 if !self.with_options.is_empty() {
1221 f.write_str(" WITH (");
1222 f.write_node(&display::comma_separated(&self.with_options));
1223 f.write_str(")");
1224 }
1225 }
1226}
1227impl_display_t!(CreateSubsourceStatement);
1228
1229#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1231pub enum CreateSinkOptionName {
1232 Snapshot,
1233 Version,
1234 PartitionStrategy,
1235 CommitInterval,
1236}
1237
1238impl AstDisplay for CreateSinkOptionName {
1239 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1240 match self {
1241 CreateSinkOptionName::Snapshot => {
1242 f.write_str("SNAPSHOT");
1243 }
1244 CreateSinkOptionName::Version => {
1245 f.write_str("VERSION");
1246 }
1247 CreateSinkOptionName::PartitionStrategy => {
1248 f.write_str("PARTITION STRATEGY");
1249 }
1250 CreateSinkOptionName::CommitInterval => {
1251 f.write_str("COMMIT INTERVAL");
1252 }
1253 }
1254 }
1255}
1256
1257impl WithOptionName for CreateSinkOptionName {
1258 fn redact_value(&self) -> bool {
1264 match self {
1265 CreateSinkOptionName::Snapshot => false,
1266 CreateSinkOptionName::Version => false,
1267 CreateSinkOptionName::PartitionStrategy => false,
1268 CreateSinkOptionName::CommitInterval => false,
1269 }
1270 }
1271}
1272
1273#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1274pub struct CreateSinkOption<T: AstInfo> {
1275 pub name: CreateSinkOptionName,
1276 pub value: Option<WithOptionValue<T>>,
1277}
1278impl_display_for_with_option!(CreateSinkOption);
1279
1280#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1282pub struct CreateSinkStatement<T: AstInfo> {
1283 pub name: Option<UnresolvedItemName>,
1284 pub in_cluster: Option<T::ClusterName>,
1285 pub if_not_exists: bool,
1286 pub from: T::ItemName,
1287 pub connection: CreateSinkConnection<T>,
1288 pub format: Option<FormatSpecifier<T>>,
1289 pub envelope: Option<SinkEnvelope>,
1290 pub mode: Option<IcebergSinkMode>,
1291 pub with_options: Vec<CreateSinkOption<T>>,
1292}
1293
1294impl<T: AstInfo> AstDisplay for CreateSinkStatement<T> {
1295 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1296 f.write_str("CREATE SINK ");
1297 if self.if_not_exists {
1298 f.write_str("IF NOT EXISTS ");
1299 }
1300 if let Some(name) = &self.name {
1301 f.write_node(&name);
1302 f.write_str(" ");
1303 }
1304 if let Some(cluster) = &self.in_cluster {
1305 f.write_str("IN CLUSTER ");
1306 f.write_node(cluster);
1307 f.write_str(" ");
1308 }
1309 f.write_str("FROM ");
1310 f.write_node(&self.from);
1311 f.write_str(" INTO ");
1312 f.write_node(&self.connection);
1313 if let Some(format) = &self.format {
1314 f.write_str(" ");
1315 f.write_node(format);
1316 }
1317 if let Some(envelope) = &self.envelope {
1318 f.write_str(" ENVELOPE ");
1319 f.write_node(envelope);
1320 }
1321 if let Some(mode) = &self.mode {
1322 f.write_str(" MODE ");
1323 f.write_node(mode);
1324 }
1325
1326 if !self.with_options.is_empty() {
1327 f.write_str(" WITH (");
1328 f.write_node(&display::comma_separated(&self.with_options));
1329 f.write_str(")");
1330 }
1331 }
1332}
1333impl_display_t!(CreateSinkStatement);
1334
1335#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1336pub struct ViewDefinition<T: AstInfo> {
1337 pub name: UnresolvedItemName,
1339 pub columns: Vec<Ident>,
1340 pub query: Query<T>,
1341}
1342
1343impl<T: AstInfo> AstDisplay for ViewDefinition<T> {
1344 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1345 f.write_node(&self.name);
1346
1347 if !self.columns.is_empty() {
1348 f.write_str(" (");
1349 f.write_node(&display::comma_separated(&self.columns));
1350 f.write_str(")");
1351 }
1352
1353 f.write_str(" AS ");
1354 f.write_node(&self.query);
1355 }
1356}
1357impl_display_t!(ViewDefinition);
1358
1359#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1361pub struct CreateViewStatement<T: AstInfo> {
1362 pub if_exists: IfExistsBehavior,
1363 pub temporary: bool,
1364 pub definition: ViewDefinition<T>,
1365}
1366
1367impl<T: AstInfo> AstDisplay for CreateViewStatement<T> {
1368 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1369 f.write_str("CREATE");
1370 if self.if_exists == IfExistsBehavior::Replace {
1371 f.write_str(" OR REPLACE");
1372 }
1373 if self.temporary {
1374 f.write_str(" TEMPORARY");
1375 }
1376
1377 f.write_str(" VIEW");
1378
1379 if self.if_exists == IfExistsBehavior::Skip {
1380 f.write_str(" IF NOT EXISTS");
1381 }
1382
1383 f.write_str(" ");
1384 f.write_node(&self.definition);
1385 }
1386}
1387impl_display_t!(CreateViewStatement);
1388
1389#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1391pub struct CreateMaterializedViewStatement<T: AstInfo> {
1392 pub if_exists: IfExistsBehavior,
1393 pub name: UnresolvedItemName,
1394 pub columns: Vec<Ident>,
1395 pub replacement_for: Option<T::ItemName>,
1396 pub in_cluster: Option<T::ClusterName>,
1397 pub query: Query<T>,
1398 pub as_of: Option<u64>,
1399 pub with_options: Vec<MaterializedViewOption<T>>,
1400}
1401
1402impl<T: AstInfo> AstDisplay for CreateMaterializedViewStatement<T> {
1403 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1404 f.write_str("CREATE");
1405 if self.if_exists == IfExistsBehavior::Replace {
1406 f.write_str(" OR REPLACE");
1407 }
1408 if self.replacement_for.is_some() {
1409 f.write_str(" REPLACEMENT");
1410 }
1411
1412 f.write_str(" MATERIALIZED VIEW");
1413
1414 if self.if_exists == IfExistsBehavior::Skip {
1415 f.write_str(" IF NOT EXISTS");
1416 }
1417
1418 f.write_str(" ");
1419 f.write_node(&self.name);
1420
1421 if !self.columns.is_empty() {
1422 f.write_str(" (");
1423 f.write_node(&display::comma_separated(&self.columns));
1424 f.write_str(")");
1425 }
1426
1427 if let Some(target) = &self.replacement_for {
1428 f.write_str(" FOR ");
1429 f.write_node(target);
1430 }
1431
1432 if let Some(cluster) = &self.in_cluster {
1433 f.write_str(" IN CLUSTER ");
1434 f.write_node(cluster);
1435 }
1436
1437 if !self.with_options.is_empty() {
1438 f.write_str(" WITH (");
1439 f.write_node(&display::comma_separated(&self.with_options));
1440 f.write_str(")");
1441 }
1442
1443 f.write_str(" AS ");
1444 f.write_node(&self.query);
1445
1446 if let Some(time) = &self.as_of {
1447 f.write_str(" AS OF ");
1448 f.write_str(time);
1449 }
1450 }
1451}
1452impl_display_t!(CreateMaterializedViewStatement);
1453
1454#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1456pub struct CreateContinualTaskStatement<T: AstInfo> {
1457 pub name: T::ItemName,
1458 pub columns: Option<Vec<CteMutRecColumnDef<T>>>,
1459 pub in_cluster: Option<T::ClusterName>,
1460 pub as_of: Option<u64>,
1461 pub with_options: Vec<ContinualTaskOption<T>>,
1462
1463 pub input: T::ItemName,
1465
1466 pub stmts: Vec<ContinualTaskStmt<T>>,
1468
1469 pub sugar: Option<CreateContinualTaskSugar<T>>,
1470}
1471
1472#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1473pub enum ContinualTaskStmt<T: AstInfo> {
1474 Delete(DeleteStatement<T>),
1475 Insert(InsertStatement<T>),
1476}
1477
1478impl<T: AstInfo> AstDisplay for ContinualTaskStmt<T> {
1479 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1480 match self {
1481 ContinualTaskStmt::Delete(stmt) => f.write_node(stmt),
1482 ContinualTaskStmt::Insert(stmt) => f.write_node(stmt),
1483 }
1484 }
1485}
1486
1487#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1488pub enum CreateContinualTaskSugar<T: AstInfo> {
1489 Transform { transform: Query<T> },
1490 Retain { retain: Expr<T> },
1491}
1492
1493impl<T: AstInfo> AstDisplay for CreateContinualTaskStatement<T> {
1494 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1495 f.write_str("CREATE CONTINUAL TASK ");
1496 f.write_node(&self.name);
1497 if let Some(columns) = &self.columns {
1498 f.write_str(" (");
1499 f.write_node(&display::comma_separated(columns));
1500 f.write_str(")");
1501 }
1502
1503 if let Some(cluster) = &self.in_cluster {
1504 f.write_str(" IN CLUSTER ");
1505 f.write_node(cluster);
1506 }
1507
1508 if !self.with_options.is_empty() {
1509 f.write_str(" WITH (");
1510 f.write_node(&display::comma_separated(&self.with_options));
1511 f.write_str(")");
1512 }
1513
1514 match &self.sugar {
1515 Some(CreateContinualTaskSugar::Transform { transform }) => {
1516 f.write_str(" FROM TRANSFORM ");
1517 f.write_node(&self.input);
1518 f.write_str(" USING ");
1519 f.write_str("(");
1520 f.write_node(transform);
1521 f.write_str(")");
1522 }
1523 Some(CreateContinualTaskSugar::Retain { retain }) => {
1524 f.write_str(" FROM RETAIN ");
1525 f.write_node(&self.input);
1526 f.write_str(" WHILE ");
1527 f.write_str("(");
1528 f.write_node(retain);
1529 f.write_str(")");
1530 }
1531 None => {
1532 f.write_str(" ON INPUT ");
1533 f.write_node(&self.input);
1534 f.write_str(" AS (");
1535 for (idx, stmt) in self.stmts.iter().enumerate() {
1536 if idx > 0 {
1537 f.write_str("; ");
1538 }
1539 f.write_node(stmt);
1540 }
1541 f.write_str(")");
1542 }
1543 }
1544
1545 if let Some(time) = &self.as_of {
1546 f.write_str(" AS OF ");
1547 f.write_str(time);
1548 }
1549 }
1550}
1551impl_display_t!(CreateContinualTaskStatement);
1552
1553#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1555pub struct AlterSetClusterStatement<T: AstInfo> {
1556 pub if_exists: bool,
1557 pub name: UnresolvedItemName,
1558 pub object_type: ObjectType,
1559 pub set_cluster: T::ClusterName,
1560}
1561
1562impl<T: AstInfo> AstDisplay for AlterSetClusterStatement<T> {
1563 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1564 f.write_str("ALTER ");
1565 f.write_node(&self.object_type);
1566
1567 if self.if_exists {
1568 f.write_str(" IF EXISTS");
1569 }
1570
1571 f.write_str(" ");
1572 f.write_node(&self.name);
1573
1574 f.write_str(" SET CLUSTER ");
1575 f.write_node(&self.set_cluster);
1576 }
1577}
1578impl_display_t!(AlterSetClusterStatement);
1579
1580#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1582pub struct CreateTableStatement<T: AstInfo> {
1583 pub name: UnresolvedItemName,
1585 pub columns: Vec<ColumnDef<T>>,
1587 pub constraints: Vec<TableConstraint<T>>,
1588 pub if_not_exists: bool,
1589 pub temporary: bool,
1590 pub with_options: Vec<TableOption<T>>,
1591}
1592
1593impl<T: AstInfo> AstDisplay for CreateTableStatement<T> {
1594 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1595 let Self {
1596 name,
1597 columns,
1598 constraints,
1599 if_not_exists,
1600 temporary,
1601 with_options,
1602 } = self;
1603 f.write_str("CREATE ");
1604 if *temporary {
1605 f.write_str("TEMPORARY ");
1606 }
1607 f.write_str("TABLE ");
1608 if *if_not_exists {
1609 f.write_str("IF NOT EXISTS ");
1610 }
1611 f.write_node(name);
1612 f.write_str(" (");
1613 f.write_node(&display::comma_separated(columns));
1614 if !self.constraints.is_empty() {
1615 f.write_str(", ");
1616 f.write_node(&display::comma_separated(constraints));
1617 }
1618 f.write_str(")");
1619 if !with_options.is_empty() {
1620 f.write_str(" WITH (");
1621 f.write_node(&display::comma_separated(&self.with_options));
1622 f.write_str(")");
1623 }
1624 }
1625}
1626impl_display_t!(CreateTableStatement);
1627
1628#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1629pub enum TableOptionName {
1630 PartitionBy,
1632 RetainHistory,
1634 RedactedTest,
1636}
1637
1638impl AstDisplay for TableOptionName {
1639 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1640 match self {
1641 TableOptionName::PartitionBy => {
1642 f.write_str("PARTITION BY");
1643 }
1644 TableOptionName::RetainHistory => {
1645 f.write_str("RETAIN HISTORY");
1646 }
1647 TableOptionName::RedactedTest => {
1648 f.write_str("REDACTED");
1649 }
1650 }
1651 }
1652}
1653
1654impl WithOptionName for TableOptionName {
1655 fn redact_value(&self) -> bool {
1661 match self {
1662 TableOptionName::PartitionBy => false,
1663 TableOptionName::RetainHistory => false,
1664 TableOptionName::RedactedTest => true,
1665 }
1666 }
1667}
1668
1669#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1670pub struct TableOption<T: AstInfo> {
1671 pub name: TableOptionName,
1672 pub value: Option<WithOptionValue<T>>,
1673}
1674impl_display_for_with_option!(TableOption);
1675
1676#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1677pub enum TableFromSourceOptionName {
1678 TextColumns,
1680 ExcludeColumns,
1682 Details,
1686 PartitionBy,
1688 RetainHistory,
1690}
1691
1692impl AstDisplay for TableFromSourceOptionName {
1693 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1694 f.write_str(match self {
1695 TableFromSourceOptionName::TextColumns => "TEXT COLUMNS",
1696 TableFromSourceOptionName::ExcludeColumns => "EXCLUDE COLUMNS",
1697 TableFromSourceOptionName::Details => "DETAILS",
1698 TableFromSourceOptionName::PartitionBy => "PARTITION BY",
1699 TableFromSourceOptionName::RetainHistory => "RETAIN HISTORY",
1700 })
1701 }
1702}
1703impl_display!(TableFromSourceOptionName);
1704
1705impl WithOptionName for TableFromSourceOptionName {
1706 fn redact_value(&self) -> bool {
1712 match self {
1713 TableFromSourceOptionName::Details
1714 | TableFromSourceOptionName::TextColumns
1715 | TableFromSourceOptionName::ExcludeColumns
1716 | TableFromSourceOptionName::RetainHistory
1717 | TableFromSourceOptionName::PartitionBy => false,
1718 }
1719 }
1720}
1721
1722#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1723pub struct TableFromSourceOption<T: AstInfo> {
1724 pub name: TableFromSourceOptionName,
1725 pub value: Option<WithOptionValue<T>>,
1726}
1727impl_display_for_with_option!(TableFromSourceOption);
1728
1729#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1738pub enum TableFromSourceColumns<T: AstInfo> {
1739 NotSpecified,
1741 Named(Vec<Ident>),
1744 Defined(Vec<ColumnDef<T>>),
1746}
1747
1748#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1750pub struct CreateTableFromSourceStatement<T: AstInfo> {
1751 pub name: UnresolvedItemName,
1752 pub columns: TableFromSourceColumns<T>,
1753 pub constraints: Vec<TableConstraint<T>>,
1754 pub if_not_exists: bool,
1755 pub source: T::ItemName,
1756 pub external_reference: Option<UnresolvedItemName>,
1757 pub with_options: Vec<TableFromSourceOption<T>>,
1758 pub include_metadata: Vec<SourceIncludeMetadata>,
1759 pub format: Option<FormatSpecifier<T>>,
1760 pub envelope: Option<SourceEnvelope>,
1761}
1762
1763impl<T: AstInfo> AstDisplay for CreateTableFromSourceStatement<T> {
1764 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1765 let Self {
1766 name,
1767 columns,
1768 constraints,
1769 source,
1770 external_reference,
1771 if_not_exists,
1772 with_options,
1773 include_metadata,
1774 format,
1775 envelope,
1776 } = self;
1777 f.write_str("CREATE TABLE ");
1778 if *if_not_exists {
1779 f.write_str("IF NOT EXISTS ");
1780 }
1781 f.write_node(name);
1782 if !matches!(columns, TableFromSourceColumns::NotSpecified) || !constraints.is_empty() {
1783 f.write_str(" (");
1784
1785 match columns {
1786 TableFromSourceColumns::NotSpecified => unreachable!(),
1787 TableFromSourceColumns::Named(columns) => {
1788 f.write_node(&display::comma_separated(columns))
1789 }
1790 TableFromSourceColumns::Defined(columns) => {
1791 f.write_node(&display::comma_separated(columns))
1792 }
1793 };
1794 if !constraints.is_empty() {
1795 f.write_str(", ");
1796 f.write_node(&display::comma_separated(constraints));
1797 }
1798 f.write_str(")");
1799 }
1800 f.write_str(" FROM SOURCE ");
1801 f.write_node(source);
1802 if let Some(external_reference) = external_reference {
1803 f.write_str(" (REFERENCE = ");
1804 f.write_node(external_reference);
1805 f.write_str(")");
1806 }
1807
1808 if let Some(format) = &format {
1809 f.write_str(" ");
1810 f.write_node(format);
1811 }
1812 if !include_metadata.is_empty() {
1813 f.write_str(" INCLUDE ");
1814 f.write_node(&display::comma_separated(include_metadata));
1815 }
1816 if let Some(envelope) = &envelope {
1817 f.write_str(" ENVELOPE ");
1818 f.write_node(envelope);
1819 }
1820 if !with_options.is_empty() {
1821 f.write_str(" WITH (");
1822 f.write_node(&display::comma_separated(with_options));
1823 f.write_str(")");
1824 }
1825 }
1826}
1827impl_display_t!(CreateTableFromSourceStatement);
1828
1829#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1831pub struct CreateIndexStatement<T: AstInfo> {
1832 pub name: Option<Ident>,
1834 pub in_cluster: Option<T::ClusterName>,
1835 pub on_name: T::ItemName,
1837 pub key_parts: Option<Vec<Expr<T>>>,
1840 pub with_options: Vec<IndexOption<T>>,
1841 pub if_not_exists: bool,
1842}
1843
1844impl<T: AstInfo> AstDisplay for CreateIndexStatement<T> {
1845 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1846 f.write_str("CREATE ");
1847 if self.key_parts.is_none() {
1848 f.write_str("DEFAULT ");
1849 }
1850 f.write_str("INDEX ");
1851 if self.if_not_exists {
1852 f.write_str("IF NOT EXISTS ");
1853 }
1854 if let Some(name) = &self.name {
1855 f.write_node(name);
1856 f.write_str(" ");
1857 }
1858 if let Some(cluster) = &self.in_cluster {
1859 f.write_str("IN CLUSTER ");
1860 f.write_node(cluster);
1861 f.write_str(" ");
1862 }
1863 f.write_str("ON ");
1864 f.write_node(&self.on_name);
1865 if let Some(key_parts) = &self.key_parts {
1866 f.write_str(" (");
1867 f.write_node(&display::comma_separated(key_parts));
1868 f.write_str(")");
1869 }
1870 if !self.with_options.is_empty() {
1871 f.write_str(" WITH (");
1872 f.write_node(&display::comma_separated(&self.with_options));
1873 f.write_str(")");
1874 }
1875 }
1876}
1877impl_display_t!(CreateIndexStatement);
1878
1879#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
1881pub enum IndexOptionName {
1882 RetainHistory,
1884}
1885
1886impl AstDisplay for IndexOptionName {
1887 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1888 match self {
1889 IndexOptionName::RetainHistory => {
1890 f.write_str("RETAIN HISTORY");
1891 }
1892 }
1893 }
1894}
1895
1896impl WithOptionName for IndexOptionName {
1897 fn redact_value(&self) -> bool {
1903 match self {
1904 IndexOptionName::RetainHistory => false,
1905 }
1906 }
1907}
1908
1909#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1910pub struct IndexOption<T: AstInfo> {
1911 pub name: IndexOptionName,
1912 pub value: Option<WithOptionValue<T>>,
1913}
1914impl_display_for_with_option!(IndexOption);
1915
1916#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1918pub struct CreateRoleStatement {
1919 pub name: Ident,
1921 pub options: Vec<RoleAttribute>,
1923}
1924
1925impl AstDisplay for CreateRoleStatement {
1926 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1927 f.write_str("CREATE ");
1928 f.write_str("ROLE ");
1929 f.write_node(&self.name);
1930 for option in &self.options {
1931 f.write_str(" ");
1932 option.fmt(f)
1933 }
1934 }
1935}
1936impl_display!(CreateRoleStatement);
1937
1938#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1940pub enum RoleAttribute {
1941 Inherit,
1943 NoInherit,
1945 Password(Option<String>),
1947 Login,
1949 NoLogin,
1950 SuperUser,
1951 NoSuperUser,
1952 CreateCluster,
1953 NoCreateCluster,
1954 CreateDB,
1955 NoCreateDB,
1956 CreateRole,
1957 NoCreateRole,
1958}
1959
1960impl AstDisplay for RoleAttribute {
1961 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1962 match self {
1963 RoleAttribute::SuperUser => f.write_str("SUPERUSER"),
1964 RoleAttribute::NoSuperUser => f.write_str("NOSUPERUSER"),
1965 RoleAttribute::Login => f.write_str("LOGIN"),
1966 RoleAttribute::NoLogin => f.write_str("NOLOGIN"),
1967 RoleAttribute::Inherit => f.write_str("INHERIT"),
1968 RoleAttribute::NoInherit => f.write_str("NOINHERIT"),
1969 RoleAttribute::CreateCluster => f.write_str("CREATECLUSTER"),
1970 RoleAttribute::NoCreateCluster => f.write_str("NOCREATECLUSTER"),
1971 RoleAttribute::CreateDB => f.write_str("CREATEDB"),
1972 RoleAttribute::NoCreateDB => f.write_str("NOCREATEDB"),
1973 RoleAttribute::CreateRole => f.write_str("CREATEROLE"),
1974 RoleAttribute::NoCreateRole => f.write_str("NOCREATEROLE"),
1975 RoleAttribute::Password(_) => f.write_str("PASSWORD"),
1976 }
1977 }
1978}
1979impl_display!(RoleAttribute);
1980
1981#[derive(Debug, Clone, PartialEq, Eq, Hash)]
1983pub enum SetRoleVar {
1984 Set { name: Ident, value: SetVariableTo },
1986 Reset { name: Ident },
1988}
1989
1990impl AstDisplay for SetRoleVar {
1991 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
1992 match self {
1993 SetRoleVar::Set { name, value } => {
1994 f.write_str("SET ");
1995 f.write_node(name);
1996 f.write_str(" = ");
1997 f.write_node(value);
1998 }
1999 SetRoleVar::Reset { name } => {
2000 f.write_str("RESET ");
2001 f.write_node(name);
2002 }
2003 }
2004 }
2005}
2006impl_display!(SetRoleVar);
2007
2008#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2010pub struct AlterNetworkPolicyStatement<T: AstInfo> {
2011 pub name: Ident,
2013 pub options: Vec<NetworkPolicyOption<T>>,
2015}
2016
2017impl<T: AstInfo> AstDisplay for AlterNetworkPolicyStatement<T> {
2018 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2019 f.write_str("ALTER ");
2020 f.write_str("NETWORK POLICY ");
2021 f.write_node(&self.name);
2022 f.write_str(" SET (");
2023 f.write_node(&display::comma_separated(&self.options));
2024 f.write_str(" )");
2025 }
2026}
2027impl_display_t!(AlterNetworkPolicyStatement);
2028
2029#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2031pub struct CreateNetworkPolicyStatement<T: AstInfo> {
2032 pub name: Ident,
2034 pub options: Vec<NetworkPolicyOption<T>>,
2036}
2037
2038impl<T: AstInfo> AstDisplay for CreateNetworkPolicyStatement<T> {
2039 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2040 f.write_str("CREATE ");
2041 f.write_str("NETWORK POLICY ");
2042 f.write_node(&self.name);
2043 f.write_str(" (");
2044 f.write_node(&display::comma_separated(&self.options));
2045 f.write_str(" )");
2046 }
2047}
2048impl_display_t!(CreateNetworkPolicyStatement);
2049
2050#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2051pub struct NetworkPolicyOption<T: AstInfo> {
2052 pub name: NetworkPolicyOptionName,
2053 pub value: Option<WithOptionValue<T>>,
2054}
2055
2056#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2057pub enum NetworkPolicyOptionName {
2058 Rules,
2059}
2060
2061impl WithOptionName for NetworkPolicyOptionName {
2062 fn redact_value(&self) -> bool {
2068 match self {
2069 NetworkPolicyOptionName::Rules => false,
2070 }
2071 }
2072}
2073
2074impl AstDisplay for NetworkPolicyOptionName {
2075 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2076 match self {
2077 NetworkPolicyOptionName::Rules => f.write_str("RULES"),
2078 }
2079 }
2080}
2081impl_display_for_with_option!(NetworkPolicyOption);
2082
2083#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2084pub struct NetworkPolicyRuleDefinition<T: AstInfo> {
2085 pub name: Ident,
2086 pub options: Vec<NetworkPolicyRuleOption<T>>,
2087}
2088
2089impl<T: AstInfo> AstDisplay for NetworkPolicyRuleDefinition<T> {
2090 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2091 f.write_node(&self.name);
2092 f.write_str(" (");
2093 f.write_node(&display::comma_separated(&self.options));
2094 f.write_str(" )");
2095 }
2096}
2097
2098#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2099pub struct NetworkPolicyRuleOption<T: AstInfo> {
2100 pub name: NetworkPolicyRuleOptionName,
2101 pub value: Option<WithOptionValue<T>>,
2102}
2103
2104#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2105pub enum NetworkPolicyRuleOptionName {
2106 Direction,
2107 Action,
2108 Address,
2109}
2110
2111impl WithOptionName for NetworkPolicyRuleOptionName {
2112 fn redact_value(&self) -> bool {
2118 match self {
2119 NetworkPolicyRuleOptionName::Direction
2120 | NetworkPolicyRuleOptionName::Action
2121 | NetworkPolicyRuleOptionName::Address => false,
2122 }
2123 }
2124}
2125
2126impl AstDisplay for NetworkPolicyRuleOptionName {
2127 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2128 match self {
2129 NetworkPolicyRuleOptionName::Direction => f.write_str("DIRECTION"),
2130 NetworkPolicyRuleOptionName::Action => f.write_str("ACTION"),
2131 NetworkPolicyRuleOptionName::Address => f.write_str("ADDRESS"),
2132 }
2133 }
2134}
2135
2136impl_display_for_with_option!(NetworkPolicyRuleOption);
2137
2138#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2140pub struct CreateSecretStatement<T: AstInfo> {
2141 pub name: UnresolvedItemName,
2142 pub if_not_exists: bool,
2143 pub value: Expr<T>,
2144}
2145
2146impl<T: AstInfo> AstDisplay for CreateSecretStatement<T> {
2147 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2148 f.write_str("CREATE SECRET ");
2149 if self.if_not_exists {
2150 f.write_str("IF NOT EXISTS ");
2151 }
2152 f.write_node(&self.name);
2153 f.write_str(" AS ");
2154
2155 if f.redacted() {
2156 f.write_str("'<REDACTED>'");
2157 } else {
2158 f.write_node(&self.value);
2159 }
2160 }
2161}
2162impl_display_t!(CreateSecretStatement);
2163
2164#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2166pub struct CreateTypeStatement<T: AstInfo> {
2167 pub name: UnresolvedItemName,
2169 pub as_type: CreateTypeAs<T>,
2171}
2172
2173impl<T: AstInfo> AstDisplay for CreateTypeStatement<T> {
2174 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2175 f.write_str("CREATE TYPE ");
2176 f.write_node(&self.name);
2177 f.write_str(" AS ");
2178 match &self.as_type {
2179 CreateTypeAs::List { options } => {
2180 f.write_str(&self.as_type);
2181 f.write_str("(");
2182 if !options.is_empty() {
2183 f.write_node(&display::comma_separated(options));
2184 }
2185 f.write_str(")");
2186 }
2187 CreateTypeAs::Map { options } => {
2188 f.write_str(&self.as_type);
2189 f.write_str("(");
2190 if !options.is_empty() {
2191 f.write_node(&display::comma_separated(options));
2192 }
2193 f.write_str(")");
2194 }
2195 CreateTypeAs::Record { column_defs } => {
2196 f.write_str("(");
2197 if !column_defs.is_empty() {
2198 f.write_node(&display::comma_separated(column_defs));
2199 }
2200 f.write_str(")");
2201 }
2202 };
2203 }
2204}
2205impl_display_t!(CreateTypeStatement);
2206
2207#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2208pub enum ClusterOptionName {
2209 AvailabilityZones,
2211 Disk,
2213 IntrospectionInterval,
2215 IntrospectionDebugging,
2217 Managed,
2219 Replicas,
2221 ReplicationFactor,
2223 Size,
2225 Schedule,
2227 WorkloadClass,
2229}
2230
2231impl AstDisplay for ClusterOptionName {
2232 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2233 match self {
2234 ClusterOptionName::AvailabilityZones => f.write_str("AVAILABILITY ZONES"),
2235 ClusterOptionName::Disk => f.write_str("DISK"),
2236 ClusterOptionName::IntrospectionDebugging => f.write_str("INTROSPECTION DEBUGGING"),
2237 ClusterOptionName::IntrospectionInterval => f.write_str("INTROSPECTION INTERVAL"),
2238 ClusterOptionName::Managed => f.write_str("MANAGED"),
2239 ClusterOptionName::Replicas => f.write_str("REPLICAS"),
2240 ClusterOptionName::ReplicationFactor => f.write_str("REPLICATION FACTOR"),
2241 ClusterOptionName::Size => f.write_str("SIZE"),
2242 ClusterOptionName::Schedule => f.write_str("SCHEDULE"),
2243 ClusterOptionName::WorkloadClass => f.write_str("WORKLOAD CLASS"),
2244 }
2245 }
2246}
2247
2248impl WithOptionName for ClusterOptionName {
2249 fn redact_value(&self) -> bool {
2255 match self {
2256 ClusterOptionName::AvailabilityZones
2257 | ClusterOptionName::Disk
2258 | ClusterOptionName::IntrospectionDebugging
2259 | ClusterOptionName::IntrospectionInterval
2260 | ClusterOptionName::Managed
2261 | ClusterOptionName::Replicas
2262 | ClusterOptionName::ReplicationFactor
2263 | ClusterOptionName::Size
2264 | ClusterOptionName::Schedule
2265 | ClusterOptionName::WorkloadClass => false,
2266 }
2267 }
2268}
2269
2270#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2271pub struct ClusterOption<T: AstInfo> {
2273 pub name: ClusterOptionName,
2274 pub value: Option<WithOptionValue<T>>,
2275}
2276impl_display_for_with_option!(ClusterOption);
2277
2278#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2279pub enum ClusterAlterUntilReadyOptionName {
2280 Timeout,
2281 OnTimeout,
2282}
2283
2284impl AstDisplay for ClusterAlterUntilReadyOptionName {
2285 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2286 match self {
2287 Self::Timeout => f.write_str("TIMEOUT"),
2288 Self::OnTimeout => f.write_str("ON TIMEOUT"),
2289 }
2290 }
2291}
2292
2293impl WithOptionName for ClusterAlterUntilReadyOptionName {
2294 fn redact_value(&self) -> bool {
2300 match self {
2301 ClusterAlterUntilReadyOptionName::Timeout
2302 | ClusterAlterUntilReadyOptionName::OnTimeout => false,
2303 }
2304 }
2305}
2306
2307#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2308pub struct ClusterAlterUntilReadyOption<T: AstInfo> {
2309 pub name: ClusterAlterUntilReadyOptionName,
2310 pub value: Option<WithOptionValue<T>>,
2311}
2312impl_display_for_with_option!(ClusterAlterUntilReadyOption);
2313
2314#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2315pub enum ClusterAlterOptionName {
2316 Wait,
2317}
2318
2319impl AstDisplay for ClusterAlterOptionName {
2320 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2321 match self {
2322 ClusterAlterOptionName::Wait => f.write_str("WAIT"),
2323 }
2324 }
2325}
2326
2327impl WithOptionName for ClusterAlterOptionName {
2328 fn redact_value(&self) -> bool {
2334 match self {
2335 ClusterAlterOptionName::Wait => false,
2336 }
2337 }
2338}
2339
2340#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2341pub enum ClusterAlterOptionValue<T: AstInfo> {
2342 For(Value),
2343 UntilReady(Vec<ClusterAlterUntilReadyOption<T>>),
2344}
2345
2346impl<T: AstInfo> AstDisplay for ClusterAlterOptionValue<T> {
2347 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2348 match self {
2349 ClusterAlterOptionValue::For(duration) => {
2350 f.write_str("FOR ");
2351 f.write_node(duration);
2352 }
2353 ClusterAlterOptionValue::UntilReady(options) => {
2354 f.write_str("UNTIL READY (");
2355 f.write_node(&display::comma_separated(options));
2356 f.write_str(")");
2357 }
2358 }
2359 }
2360}
2361
2362#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2363pub struct ClusterAlterOption<T: AstInfo> {
2365 pub name: ClusterAlterOptionName,
2366 pub value: Option<WithOptionValue<T>>,
2367}
2368
2369impl_display_for_with_option!(ClusterAlterOption);
2370
2371#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2374pub enum ClusterFeatureName {
2375 ReoptimizeImportedViews,
2376 EnableNewOuterJoinLowering,
2377 EnableEagerDeltaJoins,
2378 EnableVariadicLeftJoinLowering,
2379 EnableLetrecFixpointAnalysis,
2380 EnableJoinPrioritizeArranged,
2381 EnableProjectionPushdownAfterRelationCse,
2382}
2383
2384impl WithOptionName for ClusterFeatureName {
2385 fn redact_value(&self) -> bool {
2391 match self {
2392 Self::ReoptimizeImportedViews
2393 | Self::EnableNewOuterJoinLowering
2394 | Self::EnableEagerDeltaJoins
2395 | Self::EnableVariadicLeftJoinLowering
2396 | Self::EnableLetrecFixpointAnalysis
2397 | Self::EnableJoinPrioritizeArranged
2398 | Self::EnableProjectionPushdownAfterRelationCse => false,
2399 }
2400 }
2401}
2402
2403#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2404pub struct ClusterFeature<T: AstInfo> {
2405 pub name: ClusterFeatureName,
2406 pub value: Option<WithOptionValue<T>>,
2407}
2408impl_display_for_with_option!(ClusterFeature);
2409
2410#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2412pub struct CreateClusterStatement<T: AstInfo> {
2413 pub name: Ident,
2415 pub options: Vec<ClusterOption<T>>,
2417 pub features: Vec<ClusterFeature<T>>,
2419}
2420
2421impl<T: AstInfo> AstDisplay for CreateClusterStatement<T> {
2422 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2423 f.write_str("CREATE CLUSTER ");
2424 f.write_node(&self.name);
2425 if !self.options.is_empty() {
2426 f.write_str(" (");
2427 f.write_node(&display::comma_separated(&self.options));
2428 f.write_str(")");
2429 }
2430 if !self.features.is_empty() {
2431 f.write_str(" FEATURES (");
2432 f.write_node(&display::comma_separated(&self.features));
2433 f.write_str(")");
2434 }
2435 }
2436}
2437impl_display_t!(CreateClusterStatement);
2438
2439#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2440pub struct ReplicaDefinition<T: AstInfo> {
2441 pub name: Ident,
2443 pub options: Vec<ReplicaOption<T>>,
2445}
2446
2447impl<T: AstInfo> AstDisplay for ReplicaDefinition<T> {
2450 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2451 f.write_node(&self.name);
2452 f.write_str(" (");
2453 f.write_node(&display::comma_separated(&self.options));
2454 f.write_str(")");
2455 }
2456}
2457impl_display_t!(ReplicaDefinition);
2458
2459#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2460pub enum AlterClusterAction<T: AstInfo> {
2461 SetOptions {
2462 options: Vec<ClusterOption<T>>,
2463 with_options: Vec<ClusterAlterOption<T>>,
2464 },
2465 ResetOptions(Vec<ClusterOptionName>),
2466}
2467
2468#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2470pub struct AlterClusterStatement<T: AstInfo> {
2471 pub if_exists: bool,
2473 pub name: Ident,
2475 pub action: AlterClusterAction<T>,
2477}
2478
2479impl<T: AstInfo> AstDisplay for AlterClusterStatement<T> {
2480 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2481 f.write_str("ALTER CLUSTER ");
2482 if self.if_exists {
2483 f.write_str("IF EXISTS ");
2484 }
2485 f.write_node(&self.name);
2486 f.write_str(" ");
2487 match &self.action {
2488 AlterClusterAction::SetOptions {
2489 options,
2490 with_options,
2491 } => {
2492 f.write_str("SET (");
2493 f.write_node(&display::comma_separated(options));
2494 f.write_str(")");
2495 if !with_options.is_empty() {
2496 f.write_str(" WITH (");
2497 f.write_node(&display::comma_separated(with_options));
2498 f.write_str(")");
2499 }
2500 }
2501 AlterClusterAction::ResetOptions(options) => {
2502 f.write_str("RESET (");
2503 f.write_node(&display::comma_separated(options));
2504 f.write_str(")");
2505 }
2506 }
2507 }
2508}
2509impl_display_t!(AlterClusterStatement);
2510
2511#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2513pub struct CreateClusterReplicaStatement<T: AstInfo> {
2514 pub of_cluster: Ident,
2516 pub definition: ReplicaDefinition<T>,
2518}
2519
2520impl<T: AstInfo> AstDisplay for CreateClusterReplicaStatement<T> {
2521 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2522 f.write_str("CREATE CLUSTER REPLICA ");
2523 f.write_node(&self.of_cluster);
2524 f.write_str(".");
2525 f.write_node(&self.definition.name);
2526 f.write_str(" (");
2527 f.write_node(&display::comma_separated(&self.definition.options));
2528 f.write_str(")");
2529 }
2530}
2531impl_display_t!(CreateClusterReplicaStatement);
2532
2533#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2534pub enum ReplicaOptionName {
2535 BilledAs,
2537 Size,
2539 AvailabilityZone,
2541 StorageAddresses,
2543 StoragectlAddresses,
2545 ComputectlAddresses,
2547 ComputeAddresses,
2549 Workers,
2551 Internal,
2553 IntrospectionInterval,
2555 IntrospectionDebugging,
2557 Disk,
2559}
2560
2561impl AstDisplay for ReplicaOptionName {
2562 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2563 match self {
2564 ReplicaOptionName::BilledAs => f.write_str("BILLED AS"),
2565 ReplicaOptionName::Size => f.write_str("SIZE"),
2566 ReplicaOptionName::AvailabilityZone => f.write_str("AVAILABILITY ZONE"),
2567 ReplicaOptionName::StorageAddresses => f.write_str("STORAGE ADDRESSES"),
2568 ReplicaOptionName::StoragectlAddresses => f.write_str("STORAGECTL ADDRESSES"),
2569 ReplicaOptionName::ComputectlAddresses => f.write_str("COMPUTECTL ADDRESSES"),
2570 ReplicaOptionName::ComputeAddresses => f.write_str("COMPUTE ADDRESSES"),
2571 ReplicaOptionName::Workers => f.write_str("WORKERS"),
2572 ReplicaOptionName::Internal => f.write_str("INTERNAL"),
2573 ReplicaOptionName::IntrospectionInterval => f.write_str("INTROSPECTION INTERVAL"),
2574 ReplicaOptionName::IntrospectionDebugging => f.write_str("INTROSPECTION DEBUGGING"),
2575 ReplicaOptionName::Disk => f.write_str("DISK"),
2576 }
2577 }
2578}
2579
2580impl WithOptionName for ReplicaOptionName {
2581 fn redact_value(&self) -> bool {
2587 match self {
2588 ReplicaOptionName::BilledAs
2589 | ReplicaOptionName::Size
2590 | ReplicaOptionName::AvailabilityZone
2591 | ReplicaOptionName::StorageAddresses
2592 | ReplicaOptionName::StoragectlAddresses
2593 | ReplicaOptionName::ComputectlAddresses
2594 | ReplicaOptionName::ComputeAddresses
2595 | ReplicaOptionName::Workers
2596 | ReplicaOptionName::Internal
2597 | ReplicaOptionName::IntrospectionInterval
2598 | ReplicaOptionName::IntrospectionDebugging
2599 | ReplicaOptionName::Disk => false,
2600 }
2601 }
2602}
2603
2604#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
2605pub struct ReplicaOption<T: AstInfo> {
2607 pub name: ReplicaOptionName,
2608 pub value: Option<WithOptionValue<T>>,
2609}
2610impl_display_for_with_option!(ReplicaOption);
2611
2612#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2614pub enum CreateTypeAs<T: AstInfo> {
2615 List {
2616 options: Vec<CreateTypeListOption<T>>,
2617 },
2618 Map {
2619 options: Vec<CreateTypeMapOption<T>>,
2620 },
2621 Record {
2622 column_defs: Vec<ColumnDef<T>>,
2623 },
2624}
2625
2626impl<T: AstInfo> AstDisplay for CreateTypeAs<T> {
2627 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2628 match self {
2629 CreateTypeAs::List { .. } => f.write_str("LIST "),
2630 CreateTypeAs::Map { .. } => f.write_str("MAP "),
2631 CreateTypeAs::Record { .. } => f.write_str("RECORD "),
2632 }
2633 }
2634}
2635impl_display_t!(CreateTypeAs);
2636
2637#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2638pub enum CreateTypeListOptionName {
2639 ElementType,
2640}
2641
2642impl AstDisplay for CreateTypeListOptionName {
2643 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2644 f.write_str(match self {
2645 CreateTypeListOptionName::ElementType => "ELEMENT TYPE",
2646 })
2647 }
2648}
2649
2650impl WithOptionName for CreateTypeListOptionName {
2651 fn redact_value(&self) -> bool {
2657 match self {
2658 CreateTypeListOptionName::ElementType => false,
2659 }
2660 }
2661}
2662
2663#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2664pub struct CreateTypeListOption<T: AstInfo> {
2665 pub name: CreateTypeListOptionName,
2666 pub value: Option<WithOptionValue<T>>,
2667}
2668impl_display_for_with_option!(CreateTypeListOption);
2669
2670#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2671pub enum CreateTypeMapOptionName {
2672 KeyType,
2673 ValueType,
2674}
2675
2676impl AstDisplay for CreateTypeMapOptionName {
2677 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2678 f.write_str(match self {
2679 CreateTypeMapOptionName::KeyType => "KEY TYPE",
2680 CreateTypeMapOptionName::ValueType => "VALUE TYPE",
2681 })
2682 }
2683}
2684
2685impl WithOptionName for CreateTypeMapOptionName {
2686 fn redact_value(&self) -> bool {
2692 match self {
2693 CreateTypeMapOptionName::KeyType | CreateTypeMapOptionName::ValueType => false,
2694 }
2695 }
2696}
2697
2698#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2699pub struct CreateTypeMapOption<T: AstInfo> {
2700 pub name: CreateTypeMapOptionName,
2701 pub value: Option<WithOptionValue<T>>,
2702}
2703impl_display_for_with_option!(CreateTypeMapOption);
2704
2705#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2707pub struct AlterOwnerStatement<T: AstInfo> {
2708 pub object_type: ObjectType,
2709 pub if_exists: bool,
2710 pub name: UnresolvedObjectName,
2711 pub new_owner: T::RoleName,
2712}
2713
2714impl<T: AstInfo> AstDisplay for AlterOwnerStatement<T> {
2715 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2716 f.write_str("ALTER ");
2717 f.write_node(&self.object_type);
2718 f.write_str(" ");
2719 if self.if_exists {
2720 f.write_str("IF EXISTS ");
2721 }
2722 f.write_node(&self.name);
2723 f.write_str(" OWNER TO ");
2724 f.write_node(&self.new_owner);
2725 }
2726}
2727impl_display_t!(AlterOwnerStatement);
2728
2729#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2731pub struct AlterObjectRenameStatement {
2732 pub object_type: ObjectType,
2733 pub if_exists: bool,
2734 pub name: UnresolvedObjectName,
2735 pub to_item_name: Ident,
2736}
2737
2738impl AstDisplay for AlterObjectRenameStatement {
2739 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2740 f.write_str("ALTER ");
2741 f.write_node(&self.object_type);
2742 f.write_str(" ");
2743 if self.if_exists {
2744 f.write_str("IF EXISTS ");
2745 }
2746 f.write_node(&self.name);
2747 f.write_str(" RENAME TO ");
2748 f.write_node(&self.to_item_name);
2749 }
2750}
2751impl_display!(AlterObjectRenameStatement);
2752
2753#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2755pub struct AlterRetainHistoryStatement<T: AstInfo> {
2756 pub object_type: ObjectType,
2757 pub if_exists: bool,
2758 pub name: UnresolvedObjectName,
2759 pub history: Option<WithOptionValue<T>>,
2760}
2761
2762impl<T: AstInfo> AstDisplay for AlterRetainHistoryStatement<T> {
2763 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2764 f.write_str("ALTER ");
2765 f.write_node(&self.object_type);
2766 f.write_str(" ");
2767 if self.if_exists {
2768 f.write_str("IF EXISTS ");
2769 }
2770 f.write_node(&self.name);
2771 if let Some(history) = &self.history {
2772 f.write_str(" SET (RETAIN HISTORY ");
2773 f.write_node(history);
2774 } else {
2775 f.write_str(" RESET (RETAIN HISTORY");
2776 }
2777 f.write_str(")");
2778 }
2779}
2780impl_display_t!(AlterRetainHistoryStatement);
2781
2782#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2784pub struct AlterObjectSwapStatement {
2785 pub object_type: ObjectType,
2786 pub name_a: UnresolvedObjectName,
2787 pub name_b: Ident,
2788}
2789
2790impl AstDisplay for AlterObjectSwapStatement {
2791 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2792 f.write_str("ALTER ");
2793
2794 f.write_node(&self.object_type);
2795 f.write_str(" ");
2796 f.write_node(&self.name_a);
2797
2798 f.write_str(" SWAP WITH ");
2799 f.write_node(&self.name_b);
2800 }
2801}
2802impl_display!(AlterObjectSwapStatement);
2803
2804#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2805pub enum AlterIndexAction<T: AstInfo> {
2806 SetOptions(Vec<IndexOption<T>>),
2807 ResetOptions(Vec<IndexOptionName>),
2808}
2809
2810#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2812pub struct AlterIndexStatement<T: AstInfo> {
2813 pub index_name: UnresolvedItemName,
2814 pub if_exists: bool,
2815 pub action: AlterIndexAction<T>,
2816}
2817
2818impl<T: AstInfo> AstDisplay for AlterIndexStatement<T> {
2819 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2820 f.write_str("ALTER INDEX ");
2821 if self.if_exists {
2822 f.write_str("IF EXISTS ");
2823 }
2824 f.write_node(&self.index_name);
2825 f.write_str(" ");
2826
2827 match &self.action {
2828 AlterIndexAction::SetOptions(options) => {
2829 f.write_str("SET (");
2830 f.write_node(&display::comma_separated(options));
2831 f.write_str(")");
2832 }
2833 AlterIndexAction::ResetOptions(options) => {
2834 f.write_str("RESET (");
2835 f.write_node(&display::comma_separated(options));
2836 f.write_str(")");
2837 }
2838 }
2839 }
2840}
2841
2842impl_display_t!(AlterIndexStatement);
2843
2844#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2845pub enum AlterSinkAction<T: AstInfo> {
2846 SetOptions(Vec<CreateSinkOption<T>>),
2847 ResetOptions(Vec<CreateSinkOptionName>),
2848 ChangeRelation(T::ItemName),
2849}
2850
2851#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2852pub struct AlterSinkStatement<T: AstInfo> {
2853 pub sink_name: UnresolvedItemName,
2854 pub if_exists: bool,
2855 pub action: AlterSinkAction<T>,
2856}
2857
2858impl<T: AstInfo> AstDisplay for AlterSinkStatement<T> {
2859 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2860 f.write_str("ALTER SINK ");
2861 if self.if_exists {
2862 f.write_str("IF EXISTS ");
2863 }
2864 f.write_node(&self.sink_name);
2865 f.write_str(" ");
2866
2867 match &self.action {
2868 AlterSinkAction::ChangeRelation(from) => {
2869 f.write_str("SET FROM ");
2870 f.write_node(from);
2871 }
2872 AlterSinkAction::SetOptions(options) => {
2873 f.write_str("SET (");
2874 f.write_node(&display::comma_separated(options));
2875 f.write_str(")");
2876 }
2877 AlterSinkAction::ResetOptions(options) => {
2878 f.write_str("RESET (");
2879 f.write_node(&display::comma_separated(options));
2880 f.write_str(")");
2881 }
2882 }
2883 }
2884}
2885
2886#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2887pub enum AlterSourceAddSubsourceOptionName {
2888 TextColumns,
2890 ExcludeColumns,
2892 Details,
2897}
2898
2899impl AstDisplay for AlterSourceAddSubsourceOptionName {
2900 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
2901 f.write_str(match self {
2902 AlterSourceAddSubsourceOptionName::TextColumns => "TEXT COLUMNS",
2903 AlterSourceAddSubsourceOptionName::ExcludeColumns => "EXCLUDE COLUMNS",
2904 AlterSourceAddSubsourceOptionName::Details => "DETAILS",
2905 })
2906 }
2907}
2908impl_display!(AlterSourceAddSubsourceOptionName);
2909
2910impl WithOptionName for AlterSourceAddSubsourceOptionName {
2911 fn redact_value(&self) -> bool {
2917 match self {
2918 AlterSourceAddSubsourceOptionName::Details
2919 | AlterSourceAddSubsourceOptionName::TextColumns
2920 | AlterSourceAddSubsourceOptionName::ExcludeColumns => false,
2921 }
2922 }
2923}
2924
2925#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
2926pub struct AlterSourceAddSubsourceOption<T: AstInfo> {
2928 pub name: AlterSourceAddSubsourceOptionName,
2929 pub value: Option<WithOptionValue<T>>,
2930}
2931impl_display_for_with_option!(AlterSourceAddSubsourceOption);
2932impl_display_t!(AlterSourceAddSubsourceOption);
2933
2934#[derive(Debug, Clone, PartialEq, Eq, Hash)]
2935pub enum AlterSourceAction<T: AstInfo> {
2936 SetOptions(Vec<CreateSourceOption<T>>),
2937 ResetOptions(Vec<CreateSourceOptionName>),
2938 AddSubsources {
2939 external_references: Vec<ExternalReferenceExport>,
2940 options: Vec<AlterSourceAddSubsourceOption<T>>,
2941 },
2942 DropSubsources {
2943 if_exists: bool,
2944 cascade: bool,
2945 names: Vec<UnresolvedItemName>,
2946 },
2947 RefreshReferences,
2948}
2949
2950impl<T: AstInfo> AstDisplay for AlterSourceAction<T> {
2951 fn fmt<W>(&self, f: &mut AstFormatter<W>)
2952 where
2953 W: fmt::Write,
2954 {
2955 match &self {
2956 AlterSourceAction::SetOptions(options) => {
2957 f.write_str("SET (");
2958 f.write_node(&display::comma_separated(options));
2959 f.write_str(")");
2960 }
2961 AlterSourceAction::ResetOptions(options) => {
2962 f.write_str("RESET (");
2963 f.write_node(&display::comma_separated(options));
2964 f.write_str(")");
2965 }
2966 AlterSourceAction::DropSubsources {
2967 if_exists,
2968 cascade,
2969 names,
2970 } => {
2971 f.write_str("DROP SUBSOURCE ");
2972 if *if_exists {
2973 f.write_str("IF EXISTS ");
2974 }
2975
2976 f.write_node(&display::comma_separated(names));
2977
2978 if *cascade {
2979 f.write_str(" CASCADE");
2980 }
2981 }
2982 AlterSourceAction::AddSubsources {
2983 external_references: subsources,
2984 options,
2985 } => {
2986 f.write_str("ADD SUBSOURCE ");
2987
2988 f.write_node(&display::comma_separated(subsources));
2989
2990 if !options.is_empty() {
2991 f.write_str(" WITH (");
2992 f.write_node(&display::comma_separated(options));
2993 f.write_str(")");
2994 }
2995 }
2996 AlterSourceAction::RefreshReferences => {
2997 f.write_str("REFRESH REFERENCES");
2998 }
2999 }
3000 }
3001}
3002
3003#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3004pub struct AlterSourceStatement<T: AstInfo> {
3005 pub source_name: UnresolvedItemName,
3006 pub if_exists: bool,
3007 pub action: AlterSourceAction<T>,
3008}
3009
3010impl<T: AstInfo> AstDisplay for AlterSourceStatement<T> {
3011 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3012 f.write_str("ALTER SOURCE ");
3013 if self.if_exists {
3014 f.write_str("IF EXISTS ");
3015 }
3016 f.write_node(&self.source_name);
3017 f.write_str(" ");
3018 f.write_node(&self.action)
3019 }
3020}
3021
3022impl_display_t!(AlterSourceStatement);
3023
3024#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3026pub struct AlterSecretStatement<T: AstInfo> {
3027 pub name: UnresolvedItemName,
3028 pub if_exists: bool,
3029 pub value: Expr<T>,
3030}
3031
3032impl<T: AstInfo> AstDisplay for AlterSecretStatement<T> {
3033 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3034 f.write_str("ALTER SECRET ");
3035 if self.if_exists {
3036 f.write_str("IF EXISTS ");
3037 }
3038 f.write_node(&self.name);
3039 f.write_str(" AS ");
3040
3041 if f.redacted() {
3042 f.write_str("'<REDACTED>'");
3043 } else {
3044 f.write_node(&self.value);
3045 }
3046 }
3047}
3048
3049impl_display_t!(AlterSecretStatement);
3050
3051#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3052pub enum AlterConnectionAction<T: AstInfo> {
3053 RotateKeys,
3054 SetOption(ConnectionOption<T>),
3055 DropOption(ConnectionOptionName),
3056}
3057
3058impl<T: AstInfo> AstDisplay for AlterConnectionAction<T> {
3059 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3060 match self {
3061 AlterConnectionAction::RotateKeys => f.write_str("ROTATE KEYS"),
3062 AlterConnectionAction::SetOption(option) => {
3063 f.write_str("SET (");
3064 f.write_node(option);
3065 f.write_str(")");
3066 }
3067 AlterConnectionAction::DropOption(option) => {
3068 f.write_str("DROP (");
3069 f.write_node(option);
3070 f.write_str(")");
3071 }
3072 }
3073 }
3074}
3075impl_display_t!(AlterConnectionAction);
3076
3077#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
3078pub enum AlterConnectionOptionName {
3079 Validate,
3080}
3081
3082impl AstDisplay for AlterConnectionOptionName {
3083 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3084 f.write_str(match self {
3085 AlterConnectionOptionName::Validate => "VALIDATE",
3086 })
3087 }
3088}
3089impl_display!(AlterConnectionOptionName);
3090
3091impl WithOptionName for AlterConnectionOptionName {
3092 fn redact_value(&self) -> bool {
3098 match self {
3099 AlterConnectionOptionName::Validate => false,
3100 }
3101 }
3102}
3103
3104#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
3105pub struct AlterConnectionOption<T: AstInfo> {
3107 pub name: AlterConnectionOptionName,
3108 pub value: Option<WithOptionValue<T>>,
3109}
3110impl_display_for_with_option!(AlterConnectionOption);
3111impl_display_t!(AlterConnectionOption);
3112
3113#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3115pub struct AlterConnectionStatement<T: AstInfo> {
3116 pub name: UnresolvedItemName,
3117 pub if_exists: bool,
3118 pub actions: Vec<AlterConnectionAction<T>>,
3119 pub with_options: Vec<AlterConnectionOption<T>>,
3120}
3121
3122impl<T: AstInfo> AstDisplay for AlterConnectionStatement<T> {
3123 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3124 f.write_str("ALTER CONNECTION ");
3125 if self.if_exists {
3126 f.write_str("IF EXISTS ");
3127 }
3128 f.write_node(&self.name);
3129 f.write_str(" ");
3130 f.write_node(&display::comma_separated(&self.actions));
3131
3132 if !self.with_options.is_empty() {
3133 f.write_str(" WITH (");
3134 f.write_node(&display::comma_separated(&self.with_options));
3135 f.write_str(")");
3136 }
3137 }
3138}
3139
3140impl_display_t!(AlterConnectionStatement);
3141
3142#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3144pub struct AlterRoleStatement<T: AstInfo> {
3145 pub name: T::RoleName,
3147 pub option: AlterRoleOption,
3149}
3150
3151impl<T: AstInfo> AstDisplay for AlterRoleStatement<T> {
3152 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3153 f.write_str("ALTER ROLE ");
3154 f.write_node(&self.name);
3155 f.write_node(&self.option);
3156 }
3157}
3158impl_display_t!(AlterRoleStatement);
3159
3160#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3162pub enum AlterRoleOption {
3163 Attributes(Vec<RoleAttribute>),
3165 Variable(SetRoleVar),
3167}
3168
3169impl AstDisplay for AlterRoleOption {
3170 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3171 match self {
3172 AlterRoleOption::Attributes(attrs) => {
3173 for attr in attrs {
3174 f.write_str(" ");
3175 attr.fmt(f)
3176 }
3177 }
3178 AlterRoleOption::Variable(var) => {
3179 f.write_str(" ");
3180 f.write_node(var);
3181 }
3182 }
3183 }
3184}
3185impl_display!(AlterRoleOption);
3186
3187#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3189pub struct AlterTableAddColumnStatement<T: AstInfo> {
3190 pub if_exists: bool,
3191 pub name: UnresolvedItemName,
3192 pub if_col_not_exist: bool,
3193 pub column_name: Ident,
3194 pub data_type: T::DataType,
3195}
3196
3197impl<T: AstInfo> AstDisplay for AlterTableAddColumnStatement<T> {
3198 fn fmt<W>(&self, f: &mut AstFormatter<W>)
3199 where
3200 W: fmt::Write,
3201 {
3202 f.write_str("ALTER TABLE ");
3203 if self.if_exists {
3204 f.write_str("IF EXISTS ");
3205 }
3206 f.write_node(&self.name);
3207
3208 f.write_str(" ADD COLUMN ");
3209 if self.if_col_not_exist {
3210 f.write_str("IF NOT EXISTS ");
3211 }
3212
3213 f.write_node(&self.column_name);
3214 f.write_str(" ");
3215 f.write_node(&self.data_type);
3216 }
3217}
3218
3219impl_display_t!(AlterTableAddColumnStatement);
3220
3221#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3223pub struct AlterMaterializedViewApplyReplacementStatement {
3224 pub if_exists: bool,
3225 pub name: UnresolvedItemName,
3226 pub replacement_name: UnresolvedItemName,
3227}
3228
3229impl AstDisplay for AlterMaterializedViewApplyReplacementStatement {
3230 fn fmt<W>(&self, f: &mut AstFormatter<W>)
3231 where
3232 W: fmt::Write,
3233 {
3234 f.write_str("ALTER MATERIALIZED VIEW ");
3235 if self.if_exists {
3236 f.write_str("IF EXISTS ");
3237 }
3238 f.write_node(&self.name);
3239
3240 f.write_str(" APPLY REPLACEMENT ");
3241 f.write_node(&self.replacement_name);
3242 }
3243}
3244
3245impl_display!(AlterMaterializedViewApplyReplacementStatement);
3246
3247#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3248pub struct DiscardStatement {
3249 pub target: DiscardTarget,
3250}
3251
3252impl AstDisplay for DiscardStatement {
3253 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3254 f.write_str("DISCARD ");
3255 f.write_node(&self.target);
3256 }
3257}
3258impl_display!(DiscardStatement);
3259
3260#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3261pub enum DiscardTarget {
3262 Plans,
3263 Sequences,
3264 Temp,
3265 All,
3266}
3267
3268impl AstDisplay for DiscardTarget {
3269 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3270 match self {
3271 DiscardTarget::Plans => f.write_str("PLANS"),
3272 DiscardTarget::Sequences => f.write_str("SEQUENCES"),
3273 DiscardTarget::Temp => f.write_str("TEMP"),
3274 DiscardTarget::All => f.write_str("ALL"),
3275 }
3276 }
3277}
3278impl_display!(DiscardTarget);
3279
3280#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3282pub struct DropObjectsStatement {
3283 pub object_type: ObjectType,
3285 pub if_exists: bool,
3287 pub names: Vec<UnresolvedObjectName>,
3289 pub cascade: bool,
3292}
3293
3294impl AstDisplay for DropObjectsStatement {
3295 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3296 f.write_str("DROP ");
3297 f.write_node(&self.object_type);
3298 f.write_str(" ");
3299 if self.if_exists {
3300 f.write_str("IF EXISTS ");
3301 }
3302 f.write_node(&display::comma_separated(&self.names));
3303 if self.cascade && self.object_type != ObjectType::Database {
3304 f.write_str(" CASCADE");
3305 } else if !self.cascade && self.object_type == ObjectType::Database {
3306 f.write_str(" RESTRICT");
3307 }
3308 }
3309}
3310impl_display!(DropObjectsStatement);
3311
3312#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3314pub struct DropOwnedStatement<T: AstInfo> {
3315 pub role_names: Vec<T::RoleName>,
3317 pub cascade: Option<bool>,
3320}
3321
3322impl<T: AstInfo> DropOwnedStatement<T> {
3323 pub fn cascade(&self) -> bool {
3324 self.cascade == Some(true)
3325 }
3326}
3327
3328impl<T: AstInfo> AstDisplay for DropOwnedStatement<T> {
3329 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3330 f.write_str("DROP OWNED BY ");
3331 f.write_node(&display::comma_separated(&self.role_names));
3332 if let Some(true) = self.cascade {
3333 f.write_str(" CASCADE");
3334 } else if let Some(false) = self.cascade {
3335 f.write_str(" RESTRICT");
3336 }
3337 }
3338}
3339impl_display_t!(DropOwnedStatement);
3340
3341#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3342pub struct QualifiedReplica {
3343 pub cluster: Ident,
3344 pub replica: Ident,
3345}
3346
3347impl AstDisplay for QualifiedReplica {
3348 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3349 f.write_node(&self.cluster);
3350 f.write_str(".");
3351 f.write_node(&self.replica);
3352 }
3353}
3354impl_display!(QualifiedReplica);
3355
3356#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3362pub struct SetVariableStatement {
3363 pub local: bool,
3364 pub variable: Ident,
3365 pub to: SetVariableTo,
3366}
3367
3368impl AstDisplay for SetVariableStatement {
3369 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3370 f.write_str("SET ");
3371 if self.local {
3372 f.write_str("LOCAL ");
3373 }
3374 f.write_node(&self.variable);
3375 f.write_str(" = ");
3376 f.write_node(&self.to);
3377 }
3378}
3379impl_display!(SetVariableStatement);
3380
3381#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3386pub struct ResetVariableStatement {
3387 pub variable: Ident,
3388}
3389
3390impl AstDisplay for ResetVariableStatement {
3391 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3392 f.write_str("RESET ");
3393 f.write_node(&self.variable);
3394 }
3395}
3396impl_display!(ResetVariableStatement);
3397
3398#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3400pub struct ShowVariableStatement {
3401 pub variable: Ident,
3402}
3403
3404impl AstDisplay for ShowVariableStatement {
3405 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3406 f.write_str("SHOW ");
3407 f.write_node(&self.variable);
3408 }
3409}
3410impl_display!(ShowVariableStatement);
3411
3412#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3414pub struct InspectShardStatement {
3415 pub id: String,
3416}
3417
3418impl AstDisplay for InspectShardStatement {
3419 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3420 f.write_str("INSPECT SHARD ");
3421 f.write_str("'");
3422 f.write_node(&display::escape_single_quote_string(&self.id));
3423 f.write_str("'");
3424 }
3425}
3426impl_display!(InspectShardStatement);
3427
3428#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3429pub enum ShowObjectType<T: AstInfo> {
3430 MaterializedView {
3431 in_cluster: Option<T::ClusterName>,
3432 },
3433 Index {
3434 in_cluster: Option<T::ClusterName>,
3435 on_object: Option<T::ItemName>,
3436 },
3437 Table {
3438 on_source: Option<T::ItemName>,
3439 },
3440 View,
3441 Source {
3442 in_cluster: Option<T::ClusterName>,
3443 },
3444 Sink {
3445 in_cluster: Option<T::ClusterName>,
3446 },
3447 Type,
3448 Role,
3449 Cluster,
3450 ClusterReplica,
3451 Object,
3452 Secret,
3453 Connection,
3454 Database,
3455 Schema {
3456 from: Option<T::DatabaseName>,
3457 },
3458 Subsource {
3459 on_source: Option<T::ItemName>,
3460 },
3461 Privileges {
3462 object_type: Option<SystemObjectType>,
3463 role: Option<T::RoleName>,
3464 },
3465 DefaultPrivileges {
3466 object_type: Option<ObjectType>,
3467 role: Option<T::RoleName>,
3468 },
3469 RoleMembership {
3470 role: Option<T::RoleName>,
3471 },
3472 ContinualTask {
3473 in_cluster: Option<T::ClusterName>,
3474 },
3475 NetworkPolicy,
3476}
3477#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3486pub struct ShowObjectsStatement<T: AstInfo> {
3487 pub object_type: ShowObjectType<T>,
3488 pub from: Option<T::SchemaName>,
3489 pub filter: Option<ShowStatementFilter<T>>,
3490}
3491
3492impl<T: AstInfo> AstDisplay for ShowObjectsStatement<T> {
3493 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3494 f.write_str("SHOW");
3495 f.write_str(" ");
3496
3497 f.write_str(match &self.object_type {
3498 ShowObjectType::Table { .. } => "TABLES",
3499 ShowObjectType::View => "VIEWS",
3500 ShowObjectType::Source { .. } => "SOURCES",
3501 ShowObjectType::Sink { .. } => "SINKS",
3502 ShowObjectType::Type => "TYPES",
3503 ShowObjectType::Role => "ROLES",
3504 ShowObjectType::Cluster => "CLUSTERS",
3505 ShowObjectType::ClusterReplica => "CLUSTER REPLICAS",
3506 ShowObjectType::Object => "OBJECTS",
3507 ShowObjectType::Secret => "SECRETS",
3508 ShowObjectType::Connection => "CONNECTIONS",
3509 ShowObjectType::MaterializedView { .. } => "MATERIALIZED VIEWS",
3510 ShowObjectType::Index { .. } => "INDEXES",
3511 ShowObjectType::Database => "DATABASES",
3512 ShowObjectType::Schema { .. } => "SCHEMAS",
3513 ShowObjectType::Subsource { .. } => "SUBSOURCES",
3514 ShowObjectType::Privileges { .. } => "PRIVILEGES",
3515 ShowObjectType::DefaultPrivileges { .. } => "DEFAULT PRIVILEGES",
3516 ShowObjectType::RoleMembership { .. } => "ROLE MEMBERSHIP",
3517 ShowObjectType::ContinualTask { .. } => "CONTINUAL TASKS",
3518 ShowObjectType::NetworkPolicy => "NETWORK POLICIES",
3519 });
3520
3521 if let ShowObjectType::Index { on_object, .. } = &self.object_type {
3522 if let Some(on_object) = on_object {
3523 f.write_str(" ON ");
3524 f.write_node(on_object);
3525 }
3526 }
3527
3528 if let ShowObjectType::Schema { from: Some(from) } = &self.object_type {
3529 f.write_str(" FROM ");
3530 f.write_node(from);
3531 }
3532
3533 if let Some(from) = &self.from {
3534 f.write_str(" FROM ");
3535 f.write_node(from);
3536 }
3537
3538 match &self.object_type {
3540 ShowObjectType::MaterializedView { in_cluster }
3541 | ShowObjectType::Index { in_cluster, .. }
3542 | ShowObjectType::Sink { in_cluster }
3543 | ShowObjectType::Source { in_cluster }
3544 | ShowObjectType::ContinualTask { in_cluster } => {
3545 if let Some(cluster) = in_cluster {
3546 f.write_str(" IN CLUSTER ");
3547 f.write_node(cluster);
3548 }
3549 }
3550 _ => (),
3551 }
3552
3553 if let ShowObjectType::Subsource { on_source } = &self.object_type {
3554 if let Some(on_source) = on_source {
3555 f.write_str(" ON ");
3556 f.write_node(on_source);
3557 }
3558 }
3559
3560 if let ShowObjectType::Table { on_source } = &self.object_type {
3561 if let Some(on_source) = on_source {
3562 f.write_str(" ON ");
3563 f.write_node(on_source);
3564 }
3565 }
3566
3567 if let ShowObjectType::Privileges { object_type, role } = &self.object_type {
3568 if let Some(object_type) = object_type {
3569 f.write_str(" ON ");
3570 f.write_node(object_type);
3571 if let SystemObjectType::Object(_) = object_type {
3572 f.write_str("S");
3573 }
3574 }
3575 if let Some(role) = role {
3576 f.write_str(" FOR ");
3577 f.write_node(role);
3578 }
3579 }
3580
3581 if let ShowObjectType::DefaultPrivileges { object_type, role } = &self.object_type {
3582 if let Some(object_type) = object_type {
3583 f.write_str(" ON ");
3584 f.write_node(object_type);
3585 f.write_str("S");
3586 }
3587 if let Some(role) = role {
3588 f.write_str(" FOR ");
3589 f.write_node(role);
3590 }
3591 }
3592
3593 if let ShowObjectType::RoleMembership {
3594 role: Some(role), ..
3595 } = &self.object_type
3596 {
3597 f.write_str(" FOR ");
3598 f.write_node(role);
3599 }
3600
3601 if let Some(filter) = &self.filter {
3602 f.write_str(" ");
3603 f.write_node(filter);
3604 }
3605 }
3606}
3607impl_display_t!(ShowObjectsStatement);
3608
3609#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3613pub struct ShowColumnsStatement<T: AstInfo> {
3614 pub table_name: T::ItemName,
3615 pub filter: Option<ShowStatementFilter<T>>,
3616}
3617
3618impl<T: AstInfo> AstDisplay for ShowColumnsStatement<T> {
3619 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3620 f.write_str("SHOW ");
3621 f.write_str("COLUMNS FROM ");
3622 f.write_node(&self.table_name);
3623 if let Some(filter) = &self.filter {
3624 f.write_str(" ");
3625 f.write_node(filter);
3626 }
3627 }
3628}
3629impl_display_t!(ShowColumnsStatement);
3630
3631#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3633pub struct ShowCreateViewStatement<T: AstInfo> {
3634 pub view_name: T::ItemName,
3635 pub redacted: bool,
3636}
3637
3638impl<T: AstInfo> AstDisplay for ShowCreateViewStatement<T> {
3639 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3640 f.write_str("SHOW ");
3641 if self.redacted {
3642 f.write_str("REDACTED ");
3643 }
3644 f.write_str("CREATE VIEW ");
3645 f.write_node(&self.view_name);
3646 }
3647}
3648impl_display_t!(ShowCreateViewStatement);
3649
3650#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3652pub struct ShowCreateMaterializedViewStatement<T: AstInfo> {
3653 pub materialized_view_name: T::ItemName,
3654 pub redacted: bool,
3655}
3656
3657impl<T: AstInfo> AstDisplay for ShowCreateMaterializedViewStatement<T> {
3658 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3659 f.write_str("SHOW ");
3660 if self.redacted {
3661 f.write_str("REDACTED ");
3662 }
3663 f.write_str("CREATE MATERIALIZED VIEW ");
3664 f.write_node(&self.materialized_view_name);
3665 }
3666}
3667impl_display_t!(ShowCreateMaterializedViewStatement);
3668
3669#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3671pub struct ShowCreateSourceStatement<T: AstInfo> {
3672 pub source_name: T::ItemName,
3673 pub redacted: bool,
3674}
3675
3676impl<T: AstInfo> AstDisplay for ShowCreateSourceStatement<T> {
3677 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3678 f.write_str("SHOW ");
3679 if self.redacted {
3680 f.write_str("REDACTED ");
3681 }
3682 f.write_str("CREATE SOURCE ");
3683 f.write_node(&self.source_name);
3684 }
3685}
3686impl_display_t!(ShowCreateSourceStatement);
3687
3688#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3690pub struct ShowCreateTableStatement<T: AstInfo> {
3691 pub table_name: T::ItemName,
3692 pub redacted: bool,
3693}
3694
3695impl<T: AstInfo> AstDisplay for ShowCreateTableStatement<T> {
3696 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3697 f.write_str("SHOW ");
3698 if self.redacted {
3699 f.write_str("REDACTED ");
3700 }
3701 f.write_str("CREATE TABLE ");
3702 f.write_node(&self.table_name);
3703 }
3704}
3705impl_display_t!(ShowCreateTableStatement);
3706
3707#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3709pub struct ShowCreateSinkStatement<T: AstInfo> {
3710 pub sink_name: T::ItemName,
3711 pub redacted: bool,
3712}
3713
3714impl<T: AstInfo> AstDisplay for ShowCreateSinkStatement<T> {
3715 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3716 f.write_str("SHOW ");
3717 if self.redacted {
3718 f.write_str("REDACTED ");
3719 }
3720 f.write_str("CREATE SINK ");
3721 f.write_node(&self.sink_name);
3722 }
3723}
3724impl_display_t!(ShowCreateSinkStatement);
3725
3726#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3728pub struct ShowCreateIndexStatement<T: AstInfo> {
3729 pub index_name: T::ItemName,
3730 pub redacted: bool,
3731}
3732
3733impl<T: AstInfo> AstDisplay for ShowCreateIndexStatement<T> {
3734 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3735 f.write_str("SHOW ");
3736 if self.redacted {
3737 f.write_str("REDACTED ");
3738 }
3739 f.write_str("CREATE INDEX ");
3740 f.write_node(&self.index_name);
3741 }
3742}
3743impl_display_t!(ShowCreateIndexStatement);
3744
3745#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3747pub struct ShowCreateConnectionStatement<T: AstInfo> {
3748 pub connection_name: T::ItemName,
3749 pub redacted: bool,
3750}
3751
3752impl<T: AstInfo> AstDisplay for ShowCreateConnectionStatement<T> {
3753 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3754 f.write_str("SHOW ");
3755 if self.redacted {
3756 f.write_str("REDACTED ");
3757 }
3758 f.write_str("CREATE CONNECTION ");
3759 f.write_node(&self.connection_name);
3760 }
3761}
3762
3763#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3764pub struct ShowCreateClusterStatement<T: AstInfo> {
3765 pub cluster_name: T::ClusterName,
3766}
3767
3768impl<T: AstInfo> AstDisplay for ShowCreateClusterStatement<T> {
3769 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3770 f.write_str("SHOW CREATE CLUSTER ");
3771 f.write_node(&self.cluster_name);
3772 }
3773}
3774
3775#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3777pub struct StartTransactionStatement {
3778 pub modes: Vec<TransactionMode>,
3779}
3780
3781impl AstDisplay for StartTransactionStatement {
3782 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3783 f.write_str("START TRANSACTION");
3784 if !self.modes.is_empty() {
3785 f.write_str(" ");
3786 f.write_node(&display::comma_separated(&self.modes));
3787 }
3788 }
3789}
3790impl_display!(StartTransactionStatement);
3791
3792#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3794pub struct ShowCreateTypeStatement<T: AstInfo> {
3795 pub type_name: T::DataType,
3796 pub redacted: bool,
3797}
3798
3799impl<T: AstInfo> AstDisplay for ShowCreateTypeStatement<T> {
3800 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3801 f.write_str("SHOW ");
3802 if self.redacted {
3803 f.write_str("REDACTED ");
3804 }
3805 f.write_str("CREATE TYPE ");
3806 f.write_node(&self.type_name);
3807 }
3808}
3809
3810#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3812pub struct SetTransactionStatement {
3813 pub local: bool,
3814 pub modes: Vec<TransactionMode>,
3815}
3816
3817impl AstDisplay for SetTransactionStatement {
3818 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3819 f.write_str("SET ");
3820 if !self.local {
3821 f.write_str("SESSION CHARACTERISTICS AS ");
3822 }
3823 f.write_str("TRANSACTION");
3824 if !self.modes.is_empty() {
3825 f.write_str(" ");
3826 f.write_node(&display::comma_separated(&self.modes));
3827 }
3828 }
3829}
3830impl_display!(SetTransactionStatement);
3831
3832#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3834pub struct CommitStatement {
3835 pub chain: bool,
3836}
3837
3838impl AstDisplay for CommitStatement {
3839 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3840 f.write_str("COMMIT");
3841 if self.chain {
3842 f.write_str(" AND CHAIN");
3843 }
3844 }
3845}
3846impl_display!(CommitStatement);
3847
3848#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3850pub struct RollbackStatement {
3851 pub chain: bool,
3852}
3853
3854impl AstDisplay for RollbackStatement {
3855 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3856 f.write_str("ROLLBACK");
3857 if self.chain {
3858 f.write_str(" AND CHAIN");
3859 }
3860 }
3861}
3862impl_display!(RollbackStatement);
3863
3864#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
3865pub enum SubscribeOptionName {
3866 Snapshot,
3867 Progress,
3868}
3869
3870impl AstDisplay for SubscribeOptionName {
3871 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3872 match self {
3873 SubscribeOptionName::Snapshot => f.write_str("SNAPSHOT"),
3874 SubscribeOptionName::Progress => f.write_str("PROGRESS"),
3875 }
3876 }
3877}
3878impl_display!(SubscribeOptionName);
3879
3880impl WithOptionName for SubscribeOptionName {
3881 fn redact_value(&self) -> bool {
3887 match self {
3888 SubscribeOptionName::Snapshot | SubscribeOptionName::Progress => false,
3889 }
3890 }
3891}
3892
3893#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3894pub struct SubscribeOption<T: AstInfo> {
3895 pub name: SubscribeOptionName,
3896 pub value: Option<WithOptionValue<T>>,
3897}
3898impl_display_for_with_option!(SubscribeOption);
3899impl_display_t!(SubscribeOption);
3900
3901#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3903pub struct SubscribeStatement<T: AstInfo> {
3904 pub relation: SubscribeRelation<T>,
3905 pub options: Vec<SubscribeOption<T>>,
3906 pub as_of: Option<AsOf<T>>,
3907 pub up_to: Option<Expr<T>>,
3908 pub output: SubscribeOutput<T>,
3909}
3910
3911impl<T: AstInfo> AstDisplay for SubscribeStatement<T> {
3912 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3913 f.write_str("SUBSCRIBE ");
3914 f.write_node(&self.relation);
3915 if !self.options.is_empty() {
3916 f.write_str(" WITH (");
3917 f.write_node(&display::comma_separated(&self.options));
3918 f.write_str(")");
3919 }
3920 if let Some(as_of) = &self.as_of {
3921 f.write_str(" ");
3922 f.write_node(as_of);
3923 }
3924 if let Some(up_to) = &self.up_to {
3925 f.write_str(" UP TO ");
3926 f.write_node(up_to);
3927 }
3928 f.write_str(&self.output);
3929 }
3930}
3931impl_display_t!(SubscribeStatement);
3932
3933#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3934pub enum SubscribeRelation<T: AstInfo> {
3935 Name(T::ItemName),
3936 Query(Query<T>),
3937}
3938
3939impl<T: AstInfo> AstDisplay for SubscribeRelation<T> {
3940 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3941 match self {
3942 SubscribeRelation::Name(name) => f.write_node(name),
3943 SubscribeRelation::Query(query) => {
3944 f.write_str("(");
3945 f.write_node(query);
3946 f.write_str(")");
3947 }
3948 }
3949 }
3950}
3951impl_display_t!(SubscribeRelation);
3952
3953#[derive(Debug, Clone, PartialEq, Eq, Hash)]
3954pub struct ExplainPlanStatement<T: AstInfo> {
3955 pub stage: Option<ExplainStage>,
3956 pub with_options: Vec<ExplainPlanOption<T>>,
3957 pub format: Option<ExplainFormat>,
3958 pub explainee: Explainee<T>,
3959}
3960
3961impl<T: AstInfo> ExplainPlanStatement<T> {
3962 pub fn stage(&self) -> ExplainStage {
3963 self.stage.unwrap_or(ExplainStage::PhysicalPlan)
3964 }
3965
3966 pub fn format(&self) -> ExplainFormat {
3967 self.format.unwrap_or(ExplainFormat::Text)
3968 }
3969}
3970
3971impl<T: AstInfo> AstDisplay for ExplainPlanStatement<T> {
3972 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
3973 f.write_str("EXPLAIN");
3974 if let Some(stage) = &self.stage {
3975 f.write_str(" ");
3976 f.write_node(stage);
3977 }
3978 if !self.with_options.is_empty() {
3979 f.write_str(" WITH (");
3980 f.write_node(&display::comma_separated(&self.with_options));
3981 f.write_str(")");
3982 }
3983 if let Some(format) = &self.format {
3984 f.write_str(" AS ");
3985 f.write_node(format);
3986 }
3987 if self.stage.is_some() {
3988 f.write_str(" FOR");
3989 }
3990 f.write_str(" ");
3991 f.write_node(&self.explainee);
3992 }
3993}
3994impl_display_t!(ExplainPlanStatement);
3995
3996#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
3999pub enum ExplainPlanOptionName {
4000 Arity,
4001 Cardinality,
4002 ColumnNames,
4003 FilterPushdown,
4004 HumanizedExpressions,
4005 JoinImplementations,
4006 Keys,
4007 LinearChains,
4008 NonNegative,
4009 NoFastPath,
4010 NoNotices,
4011 NodeIdentifiers,
4012 RawPlans,
4013 RawSyntax,
4014 Raw, Redacted,
4016 SubtreeSize,
4017 Timing,
4018 Types,
4019 Equivalences,
4020 ReoptimizeImportedViews,
4021 EnableNewOuterJoinLowering,
4022 EnableEagerDeltaJoins,
4023 EnableVariadicLeftJoinLowering,
4024 EnableLetrecFixpointAnalysis,
4025 EnableJoinPrioritizeArranged,
4026 EnableProjectionPushdownAfterRelationCse,
4027}
4028
4029impl WithOptionName for ExplainPlanOptionName {
4030 fn redact_value(&self) -> bool {
4036 match self {
4037 Self::Arity
4038 | Self::Cardinality
4039 | Self::ColumnNames
4040 | Self::FilterPushdown
4041 | Self::HumanizedExpressions
4042 | Self::JoinImplementations
4043 | Self::Keys
4044 | Self::LinearChains
4045 | Self::NonNegative
4046 | Self::NoFastPath
4047 | Self::NoNotices
4048 | Self::NodeIdentifiers
4049 | Self::RawPlans
4050 | Self::RawSyntax
4051 | Self::Raw
4052 | Self::Redacted
4053 | Self::SubtreeSize
4054 | Self::Timing
4055 | Self::Types
4056 | Self::Equivalences
4057 | Self::ReoptimizeImportedViews
4058 | Self::EnableNewOuterJoinLowering
4059 | Self::EnableEagerDeltaJoins
4060 | Self::EnableVariadicLeftJoinLowering
4061 | Self::EnableLetrecFixpointAnalysis
4062 | Self::EnableJoinPrioritizeArranged
4063 | Self::EnableProjectionPushdownAfterRelationCse => false,
4064 }
4065 }
4066}
4067
4068#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4069pub struct ExplainPlanOption<T: AstInfo> {
4070 pub name: ExplainPlanOptionName,
4071 pub value: Option<WithOptionValue<T>>,
4072}
4073impl_display_for_with_option!(ExplainPlanOption);
4074
4075#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4076pub enum ExplainSinkSchemaFor {
4077 Key,
4078 Value,
4079}
4080#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4081pub struct ExplainSinkSchemaStatement<T: AstInfo> {
4082 pub schema_for: ExplainSinkSchemaFor,
4083 pub format: Option<ExplainFormat>,
4084 pub statement: CreateSinkStatement<T>,
4085}
4086
4087impl<T: AstInfo> AstDisplay for ExplainSinkSchemaStatement<T> {
4088 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4089 f.write_str("EXPLAIN ");
4090 match &self.schema_for {
4091 ExplainSinkSchemaFor::Key => f.write_str("KEY"),
4092 ExplainSinkSchemaFor::Value => f.write_str("VALUE"),
4093 }
4094 f.write_str(" SCHEMA");
4095 if let Some(format) = &self.format {
4096 f.write_str(" AS ");
4097 f.write_node(format);
4098 }
4099 f.write_str(" FOR ");
4100 f.write_node(&self.statement);
4101 }
4102}
4103impl_display_t!(ExplainSinkSchemaStatement);
4104
4105#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4106pub struct ExplainPushdownStatement<T: AstInfo> {
4107 pub explainee: Explainee<T>,
4108}
4109
4110impl<T: AstInfo> AstDisplay for ExplainPushdownStatement<T> {
4111 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4112 f.write_str("EXPLAIN FILTER PUSHDOWN FOR ");
4113 f.write_node(&self.explainee);
4114 }
4115}
4116impl_display_t!(ExplainPushdownStatement);
4117
4118#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
4119pub enum ExplainAnalyzeComputationProperty {
4120 Cpu,
4121 Memory,
4122}
4123
4124#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4125pub enum ExplainAnalyzeProperty {
4126 Computation(ExplainAnalyzeComputationProperties),
4127 Hints,
4128}
4129
4130#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4131pub struct ExplainAnalyzeComputationProperties {
4132 pub properties: Vec<ExplainAnalyzeComputationProperty>,
4134 pub skew: bool,
4135}
4136#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4137pub struct ExplainAnalyzeObjectStatement<T: AstInfo> {
4138 pub properties: ExplainAnalyzeProperty,
4139 pub explainee: Explainee<T>,
4141 pub as_sql: bool,
4142}
4143
4144impl<T: AstInfo> AstDisplay for ExplainAnalyzeObjectStatement<T> {
4145 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4146 f.write_str("EXPLAIN ANALYZE");
4147 match &self.properties {
4148 ExplainAnalyzeProperty::Computation(ExplainAnalyzeComputationProperties {
4149 properties,
4150 skew,
4151 }) => {
4152 let mut first = true;
4153 for property in properties {
4154 if first {
4155 first = false;
4156 } else {
4157 f.write_str(",");
4158 }
4159 match property {
4160 ExplainAnalyzeComputationProperty::Cpu => f.write_str(" CPU"),
4161 ExplainAnalyzeComputationProperty::Memory => f.write_str(" MEMORY"),
4162 }
4163 }
4164 if *skew {
4165 f.write_str(" WITH SKEW");
4166 }
4167 }
4168 ExplainAnalyzeProperty::Hints => f.write_str(" HINTS"),
4169 }
4170 f.write_str(" FOR ");
4171 f.write_node(&self.explainee);
4172 if self.as_sql {
4173 f.write_str(" AS SQL");
4174 }
4175 }
4176}
4177impl_display_t!(ExplainAnalyzeObjectStatement);
4178
4179#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4180pub struct ExplainAnalyzeClusterStatement {
4181 pub properties: ExplainAnalyzeComputationProperties,
4182 pub as_sql: bool,
4183}
4184
4185impl AstDisplay for ExplainAnalyzeClusterStatement {
4186 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4187 f.write_str("EXPLAIN ANALYZE CLUSTER");
4188
4189 let mut first = true;
4190 for property in &self.properties.properties {
4191 if first {
4192 first = false;
4193 } else {
4194 f.write_str(",");
4195 }
4196 match property {
4197 ExplainAnalyzeComputationProperty::Cpu => f.write_str(" CPU"),
4198 ExplainAnalyzeComputationProperty::Memory => f.write_str(" MEMORY"),
4199 }
4200 }
4201
4202 if self.properties.skew {
4203 f.write_str(" WITH SKEW");
4204 }
4205 if self.as_sql {
4206 f.write_str(" AS SQL");
4207 }
4208 }
4209}
4210impl_display!(ExplainAnalyzeClusterStatement);
4211
4212#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4213pub struct ExplainTimestampStatement<T: AstInfo> {
4214 pub format: Option<ExplainFormat>,
4215 pub select: SelectStatement<T>,
4216}
4217
4218impl<T: AstInfo> ExplainTimestampStatement<T> {
4219 pub fn format(&self) -> ExplainFormat {
4220 self.format.unwrap_or(ExplainFormat::Text)
4221 }
4222}
4223
4224impl<T: AstInfo> AstDisplay for ExplainTimestampStatement<T> {
4225 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4226 f.write_str("EXPLAIN TIMESTAMP");
4227 if let Some(format) = &self.format {
4228 f.write_str(" AS ");
4229 f.write_node(format);
4230 }
4231 f.write_str(" FOR ");
4232 f.write_node(&self.select);
4233 }
4234}
4235impl_display_t!(ExplainTimestampStatement);
4236
4237#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4238pub enum InsertSource<T: AstInfo> {
4239 Query(Query<T>),
4240 DefaultValues,
4241}
4242
4243impl<T: AstInfo> AstDisplay for InsertSource<T> {
4244 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4245 match self {
4246 InsertSource::Query(query) => f.write_node(query),
4247 InsertSource::DefaultValues => f.write_str("DEFAULT VALUES"),
4248 }
4249 }
4250}
4251impl_display_t!(InsertSource);
4252
4253#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord, Copy)]
4254pub enum ObjectType {
4255 Table,
4256 View,
4257 MaterializedView,
4258 Source,
4259 Sink,
4260 Index,
4261 Type,
4262 Role,
4263 Cluster,
4264 ClusterReplica,
4265 Secret,
4266 Connection,
4267 Database,
4268 Schema,
4269 Func,
4270 Subsource,
4271 ContinualTask,
4272 NetworkPolicy,
4273}
4274
4275impl ObjectType {
4276 pub fn lives_in_schema(&self) -> bool {
4277 match self {
4278 ObjectType::Table
4279 | ObjectType::View
4280 | ObjectType::MaterializedView
4281 | ObjectType::Source
4282 | ObjectType::Sink
4283 | ObjectType::Index
4284 | ObjectType::Type
4285 | ObjectType::Secret
4286 | ObjectType::Connection
4287 | ObjectType::Func
4288 | ObjectType::Subsource
4289 | ObjectType::ContinualTask => true,
4290 ObjectType::Database
4291 | ObjectType::Schema
4292 | ObjectType::Cluster
4293 | ObjectType::ClusterReplica
4294 | ObjectType::Role
4295 | ObjectType::NetworkPolicy => false,
4296 }
4297 }
4298}
4299
4300impl AstDisplay for ObjectType {
4301 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4302 f.write_str(match self {
4303 ObjectType::Table => "TABLE",
4304 ObjectType::View => "VIEW",
4305 ObjectType::MaterializedView => "MATERIALIZED VIEW",
4306 ObjectType::Source => "SOURCE",
4307 ObjectType::Sink => "SINK",
4308 ObjectType::Index => "INDEX",
4309 ObjectType::Type => "TYPE",
4310 ObjectType::Role => "ROLE",
4311 ObjectType::Cluster => "CLUSTER",
4312 ObjectType::ClusterReplica => "CLUSTER REPLICA",
4313 ObjectType::Secret => "SECRET",
4314 ObjectType::Connection => "CONNECTION",
4315 ObjectType::Database => "DATABASE",
4316 ObjectType::Schema => "SCHEMA",
4317 ObjectType::Func => "FUNCTION",
4318 ObjectType::Subsource => "SUBSOURCE",
4319 ObjectType::ContinualTask => "CONTINUAL TASK",
4320 ObjectType::NetworkPolicy => "NETWORK POLICY",
4321 })
4322 }
4323}
4324impl_display!(ObjectType);
4325
4326#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord, Copy)]
4327pub enum SystemObjectType {
4328 System,
4329 Object(ObjectType),
4330}
4331
4332impl AstDisplay for SystemObjectType {
4333 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4334 match self {
4335 SystemObjectType::System => f.write_str("SYSTEM"),
4336 SystemObjectType::Object(object) => f.write_node(object),
4337 }
4338 }
4339}
4340impl_display!(SystemObjectType);
4341
4342#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4343pub enum ShowStatementFilter<T: AstInfo> {
4344 Like(String),
4345 Where(Expr<T>),
4346}
4347
4348impl<T: AstInfo> AstDisplay for ShowStatementFilter<T> {
4349 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4350 use ShowStatementFilter::*;
4351 match self {
4352 Like(pattern) => {
4353 f.write_str("LIKE '");
4354 f.write_node(&display::escape_single_quote_string(pattern));
4355 f.write_str("'");
4356 }
4357 Where(expr) => {
4358 f.write_str("WHERE ");
4359 f.write_node(expr);
4360 }
4361 }
4362 }
4363}
4364impl_display_t!(ShowStatementFilter);
4365
4366#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4367pub enum WithOptionValue<T: AstInfo> {
4368 Value(Value),
4369 DataType(T::DataType),
4370 Secret(T::ItemName),
4371 Item(T::ItemName),
4372 UnresolvedItemName(UnresolvedItemName),
4373 Ident(Ident),
4374 Sequence(Vec<WithOptionValue<T>>),
4375 Map(BTreeMap<String, WithOptionValue<T>>),
4376 Expr(Expr<T>),
4378 ClusterReplicas(Vec<ReplicaDefinition<T>>),
4379 ConnectionKafkaBroker(KafkaBroker<T>),
4380 ConnectionAwsPrivatelink(ConnectionDefaultAwsPrivatelink<T>),
4381 RetainHistoryFor(Value),
4382 Refresh(RefreshOptionValue<T>),
4383 ClusterScheduleOptionValue(ClusterScheduleOptionValue),
4384 ClusterAlterStrategy(ClusterAlterOptionValue<T>),
4385 NetworkPolicyRules(Vec<NetworkPolicyRuleDefinition<T>>),
4386}
4387
4388impl<T: AstInfo> AstDisplay for WithOptionValue<T> {
4389 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4390 if f.redacted() {
4391 match self {
4394 WithOptionValue::Value(_)
4395 | WithOptionValue::Sequence(_)
4396 | WithOptionValue::Map(_)
4397 | WithOptionValue::RetainHistoryFor(_)
4398 | WithOptionValue::Refresh(_)
4399 | WithOptionValue::Expr(_) => {
4400 }
4402 WithOptionValue::Secret(_) | WithOptionValue::ConnectionKafkaBroker(_) => {
4403 f.write_str("'<REDACTED>'");
4404 return;
4405 }
4406 WithOptionValue::DataType(_)
4407 | WithOptionValue::Item(_)
4408 | WithOptionValue::UnresolvedItemName(_)
4409 | WithOptionValue::Ident(_)
4410 | WithOptionValue::ConnectionAwsPrivatelink(_)
4411 | WithOptionValue::ClusterReplicas(_)
4412 | WithOptionValue::ClusterScheduleOptionValue(_)
4413 | WithOptionValue::ClusterAlterStrategy(_)
4414 | WithOptionValue::NetworkPolicyRules(_) => {
4415 }
4417 }
4418 }
4419 match self {
4420 WithOptionValue::Sequence(values) => {
4421 f.write_str("(");
4422 f.write_node(&display::comma_separated(values));
4423 f.write_str(")");
4424 }
4425 WithOptionValue::Map(values) => {
4426 f.write_str("MAP[");
4427 let len = values.len();
4428 for (i, (key, value)) in values.iter().enumerate() {
4429 f.write_str("'");
4430 f.write_node(&display::escape_single_quote_string(key));
4431 f.write_str("' => ");
4432 f.write_node(value);
4433 if i + 1 < len {
4434 f.write_str(", ");
4435 }
4436 }
4437 f.write_str("]");
4438 }
4439 WithOptionValue::Expr(e) => f.write_node(e),
4440 WithOptionValue::Value(value) => f.write_node(value),
4441 WithOptionValue::DataType(typ) => f.write_node(typ),
4442 WithOptionValue::Secret(name) => {
4443 f.write_str("SECRET ");
4444 f.write_node(name)
4445 }
4446 WithOptionValue::Item(obj) => f.write_node(obj),
4447 WithOptionValue::UnresolvedItemName(r) => f.write_node(r),
4448 WithOptionValue::Ident(r) => f.write_node(r),
4449 WithOptionValue::ClusterReplicas(replicas) => {
4450 f.write_str("(");
4451 f.write_node(&display::comma_separated(replicas));
4452 f.write_str(")");
4453 }
4454 WithOptionValue::NetworkPolicyRules(rules) => {
4455 f.write_str("(");
4456 f.write_node(&display::comma_separated(rules));
4457 f.write_str(")");
4458 }
4459 WithOptionValue::ConnectionAwsPrivatelink(aws_privatelink) => {
4460 f.write_node(aws_privatelink);
4461 }
4462 WithOptionValue::ConnectionKafkaBroker(broker) => {
4463 f.write_node(broker);
4464 }
4465 WithOptionValue::RetainHistoryFor(value) => {
4466 f.write_str("FOR ");
4467 f.write_node(value);
4468 }
4469 WithOptionValue::Refresh(opt) => f.write_node(opt),
4470 WithOptionValue::ClusterScheduleOptionValue(value) => f.write_node(value),
4471 WithOptionValue::ClusterAlterStrategy(value) => f.write_node(value),
4472 }
4473 }
4474}
4475impl_display_t!(WithOptionValue);
4476
4477#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4478pub enum RefreshOptionValue<T: AstInfo> {
4479 OnCommit,
4480 AtCreation,
4481 At(RefreshAtOptionValue<T>),
4482 Every(RefreshEveryOptionValue<T>),
4483}
4484
4485#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4486pub struct RefreshAtOptionValue<T: AstInfo> {
4487 pub time: Expr<T>,
4489}
4490
4491#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4492pub struct RefreshEveryOptionValue<T: AstInfo> {
4493 pub interval: IntervalValue,
4495 pub aligned_to: Option<Expr<T>>,
4497}
4498
4499impl<T: AstInfo> AstDisplay for RefreshOptionValue<T> {
4500 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4501 match self {
4502 RefreshOptionValue::OnCommit => {
4503 f.write_str("ON COMMIT");
4504 }
4505 RefreshOptionValue::AtCreation => {
4506 f.write_str("AT CREATION");
4507 }
4508 RefreshOptionValue::At(RefreshAtOptionValue { time }) => {
4509 f.write_str("AT ");
4510 f.write_node(time);
4511 }
4512 RefreshOptionValue::Every(RefreshEveryOptionValue {
4513 interval,
4514 aligned_to,
4515 }) => {
4516 f.write_str("EVERY '");
4517 f.write_node(interval);
4518 if let Some(aligned_to) = aligned_to {
4519 f.write_str(" ALIGNED TO ");
4520 f.write_node(aligned_to)
4521 }
4522 }
4523 }
4524 }
4525}
4526
4527#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord, Deserialize, Serialize)]
4528pub enum ClusterScheduleOptionValue {
4529 Manual,
4530 Refresh {
4531 hydration_time_estimate: Option<IntervalValue>,
4532 },
4533}
4534
4535impl Default for ClusterScheduleOptionValue {
4536 fn default() -> Self {
4537 ClusterScheduleOptionValue::Manual
4539 }
4540}
4541
4542impl AstDisplay for ClusterScheduleOptionValue {
4543 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4544 match self {
4545 ClusterScheduleOptionValue::Manual => {
4546 f.write_str("MANUAL");
4547 }
4548 ClusterScheduleOptionValue::Refresh {
4549 hydration_time_estimate,
4550 } => {
4551 f.write_str("ON REFRESH");
4552 if let Some(hydration_time_estimate) = hydration_time_estimate {
4553 f.write_str(" (HYDRATION TIME ESTIMATE = '");
4554 f.write_node(hydration_time_estimate);
4555 f.write_str(")");
4556 }
4557 }
4558 }
4559 }
4560}
4561
4562#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4563pub enum TransactionMode {
4564 AccessMode(TransactionAccessMode),
4565 IsolationLevel(TransactionIsolationLevel),
4566}
4567
4568impl AstDisplay for TransactionMode {
4569 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4570 use TransactionMode::*;
4571 match self {
4572 AccessMode(access_mode) => f.write_node(access_mode),
4573 IsolationLevel(iso_level) => {
4574 f.write_str("ISOLATION LEVEL ");
4575 f.write_node(iso_level);
4576 }
4577 }
4578 }
4579}
4580impl_display!(TransactionMode);
4581
4582#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
4583pub enum TransactionAccessMode {
4584 ReadOnly,
4585 ReadWrite,
4586}
4587
4588impl AstDisplay for TransactionAccessMode {
4589 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4590 use TransactionAccessMode::*;
4591 f.write_str(match self {
4592 ReadOnly => "READ ONLY",
4593 ReadWrite => "READ WRITE",
4594 })
4595 }
4596}
4597impl_display!(TransactionAccessMode);
4598
4599#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, PartialOrd, Ord)]
4600pub enum TransactionIsolationLevel {
4601 ReadUncommitted,
4602 ReadCommitted,
4603 RepeatableRead,
4604 Serializable,
4605 StrongSessionSerializable,
4606 StrictSerializable,
4607}
4608
4609impl AstDisplay for TransactionIsolationLevel {
4610 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4611 use TransactionIsolationLevel::*;
4612 f.write_str(match self {
4613 ReadUncommitted => "READ UNCOMMITTED",
4614 ReadCommitted => "READ COMMITTED",
4615 RepeatableRead => "REPEATABLE READ",
4616 Serializable => "SERIALIZABLE",
4617 StrongSessionSerializable => "STRONG SESSION SERIALIZABLE",
4618 StrictSerializable => "STRICT SERIALIZABLE",
4619 })
4620 }
4621}
4622impl_display!(TransactionIsolationLevel);
4623
4624#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4625pub enum SetVariableTo {
4626 Default,
4627 Values(Vec<SetVariableValue>),
4628}
4629
4630impl AstDisplay for SetVariableTo {
4631 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4632 use SetVariableTo::*;
4633 match self {
4634 Values(values) => f.write_node(&display::comma_separated(values)),
4635 Default => f.write_str("DEFAULT"),
4636 }
4637 }
4638}
4639impl_display!(SetVariableTo);
4640
4641#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4642pub enum SetVariableValue {
4643 Ident(Ident),
4644 Literal(Value),
4645}
4646
4647impl AstDisplay for SetVariableValue {
4648 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4649 use SetVariableValue::*;
4650 match self {
4651 Ident(ident) => f.write_node(ident),
4652 Literal(literal) => f.write_node(literal),
4653 }
4654 }
4655}
4656impl_display!(SetVariableValue);
4657
4658impl SetVariableValue {
4659 pub fn into_unquoted_value(self) -> String {
4661 match self {
4662 SetVariableValue::Literal(Value::String(s)) => s,
4665 SetVariableValue::Literal(lit) => lit.to_string(),
4666 SetVariableValue::Ident(ident) => ident.into_string(),
4667 }
4668 }
4669}
4670
4671#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4673pub struct Assignment<T: AstInfo> {
4674 pub id: Ident,
4675 pub value: Expr<T>,
4676}
4677
4678impl<T: AstInfo> AstDisplay for Assignment<T> {
4679 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4680 f.write_node(&self.id);
4681 f.write_str(" = ");
4682 f.write_node(&self.value);
4683 }
4684}
4685impl_display_t!(Assignment);
4686
4687#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
4689pub enum ExplainStage {
4690 RawPlan,
4692 DecorrelatedPlan,
4694 LocalPlan,
4696 GlobalPlan,
4698 PhysicalPlan,
4700 Trace,
4702 PlanInsights,
4704}
4705
4706impl ExplainStage {
4707 pub fn paths(&self) -> Option<SmallVec<[NamedPlan; 4]>> {
4709 use NamedPlan::*;
4710 match self {
4711 Self::RawPlan => Some(smallvec![Raw]),
4712 Self::DecorrelatedPlan => Some(smallvec![Decorrelated]),
4713 Self::LocalPlan => Some(smallvec![Local]),
4714 Self::GlobalPlan => Some(smallvec![Global]),
4715 Self::PhysicalPlan => Some(smallvec![Physical]),
4716 Self::Trace => None,
4717 Self::PlanInsights => Some(smallvec![Raw, Global, FastPath]),
4718 }
4719 }
4720
4721 pub fn show_fast_path(&self) -> bool {
4724 match self {
4725 Self::RawPlan => false,
4726 Self::DecorrelatedPlan => false,
4727 Self::LocalPlan => false,
4728 Self::GlobalPlan => true,
4729 Self::PhysicalPlan => true,
4730 Self::Trace => false,
4731 Self::PlanInsights => false,
4732 }
4733 }
4734}
4735
4736impl AstDisplay for ExplainStage {
4737 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4738 match self {
4739 Self::RawPlan => f.write_str("RAW PLAN"),
4740 Self::DecorrelatedPlan => f.write_str("DECORRELATED PLAN"),
4741 Self::LocalPlan => f.write_str("LOCALLY OPTIMIZED PLAN"),
4742 Self::GlobalPlan => f.write_str("OPTIMIZED PLAN"),
4743 Self::PhysicalPlan => f.write_str("PHYSICAL PLAN"),
4744 Self::Trace => f.write_str("OPTIMIZER TRACE"),
4745 Self::PlanInsights => f.write_str("PLAN INSIGHTS"),
4746 }
4747 }
4748}
4749impl_display!(ExplainStage);
4750
4751#[derive(Clone)]
4754pub enum NamedPlan {
4755 Raw,
4756 Decorrelated,
4757 Local,
4758 Global,
4759 Physical,
4760 FastPath,
4761}
4762
4763impl NamedPlan {
4764 pub fn of_path(value: &str) -> Option<Self> {
4766 match value {
4767 "optimize/raw" => Some(Self::Raw),
4768 "optimize/hir_to_mir" => Some(Self::Decorrelated),
4769 "optimize/local" => Some(Self::Local),
4770 "optimize/global" => Some(Self::Global),
4771 "optimize/finalize_dataflow" => Some(Self::Physical),
4772 "optimize/fast_path" => Some(Self::FastPath),
4773 _ => None,
4774 }
4775 }
4776
4777 pub fn path(&self) -> &'static str {
4780 match self {
4781 Self::Raw => "optimize/raw",
4782 Self::Decorrelated => "optimize/hir_to_mir",
4783 Self::Local => "optimize/local",
4784 Self::Global => "optimize/global",
4785 Self::Physical => "optimize/finalize_dataflow",
4786 Self::FastPath => "optimize/fast_path",
4787 }
4788 }
4789}
4790
4791#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4794pub enum Explainee<T: AstInfo> {
4795 View(T::ItemName),
4796 MaterializedView(T::ItemName),
4797 Index(T::ItemName),
4798 ReplanView(T::ItemName),
4799 ReplanMaterializedView(T::ItemName),
4800 ReplanIndex(T::ItemName),
4801 Select(Box<SelectStatement<T>>, bool),
4802 CreateView(Box<CreateViewStatement<T>>, bool),
4803 CreateMaterializedView(Box<CreateMaterializedViewStatement<T>>, bool),
4804 CreateIndex(Box<CreateIndexStatement<T>>, bool),
4805}
4806
4807impl<T: AstInfo> Explainee<T> {
4808 pub fn name(&self) -> Option<&T::ItemName> {
4809 match self {
4810 Self::View(name)
4811 | Self::ReplanView(name)
4812 | Self::MaterializedView(name)
4813 | Self::ReplanMaterializedView(name)
4814 | Self::Index(name)
4815 | Self::ReplanIndex(name) => Some(name),
4816 Self::Select(..)
4817 | Self::CreateView(..)
4818 | Self::CreateMaterializedView(..)
4819 | Self::CreateIndex(..) => None,
4820 }
4821 }
4822
4823 pub fn is_view(&self) -> bool {
4824 use Explainee::*;
4825 matches!(self, View(_) | ReplanView(_) | CreateView(_, _))
4826 }
4827}
4828
4829impl<T: AstInfo> AstDisplay for Explainee<T> {
4830 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4831 match self {
4832 Self::View(name) => {
4833 f.write_str("VIEW ");
4834 f.write_node(name);
4835 }
4836 Self::MaterializedView(name) => {
4837 f.write_str("MATERIALIZED VIEW ");
4838 f.write_node(name);
4839 }
4840 Self::Index(name) => {
4841 f.write_str("INDEX ");
4842 f.write_node(name);
4843 }
4844 Self::ReplanView(name) => {
4845 f.write_str("REPLAN VIEW ");
4846 f.write_node(name);
4847 }
4848 Self::ReplanMaterializedView(name) => {
4849 f.write_str("REPLAN MATERIALIZED VIEW ");
4850 f.write_node(name);
4851 }
4852 Self::ReplanIndex(name) => {
4853 f.write_str("REPLAN INDEX ");
4854 f.write_node(name);
4855 }
4856 Self::Select(select, broken) => {
4857 if *broken {
4858 f.write_str("BROKEN ");
4859 }
4860 f.write_node(select);
4861 }
4862 Self::CreateView(statement, broken) => {
4863 if *broken {
4864 f.write_str("BROKEN ");
4865 }
4866 f.write_node(statement);
4867 }
4868 Self::CreateMaterializedView(statement, broken) => {
4869 if *broken {
4870 f.write_str("BROKEN ");
4871 }
4872 f.write_node(statement);
4873 }
4874 Self::CreateIndex(statement, broken) => {
4875 if *broken {
4876 f.write_str("BROKEN ");
4877 }
4878 f.write_node(statement);
4879 }
4880 }
4881 }
4882}
4883impl_display_t!(Explainee);
4884
4885#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
4886pub enum ExplainFormat {
4887 Text,
4889 VerboseText,
4891 Json,
4893 Dot,
4895}
4896
4897impl AstDisplay for ExplainFormat {
4898 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4899 match self {
4900 Self::Text => f.write_str("TEXT"),
4901 Self::VerboseText => f.write_str("VERBOSE TEXT"),
4902 Self::Json => f.write_str("JSON"),
4903 Self::Dot => f.write_str("DOT"),
4904 }
4905 }
4906}
4907impl_display!(ExplainFormat);
4908
4909#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
4910pub enum IfExistsBehavior {
4911 Error,
4912 Skip,
4913 Replace,
4914}
4915
4916#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4918pub struct DeclareStatement<T: AstInfo> {
4919 pub name: Ident,
4920 pub stmt: Box<T::NestedStatement>,
4921 pub sql: String,
4922}
4923
4924impl<T: AstInfo> AstDisplay for DeclareStatement<T> {
4925 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4926 f.write_str("DECLARE ");
4927 f.write_node(&self.name);
4928 f.write_str(" CURSOR FOR ");
4929 f.write_node(&self.stmt);
4930 }
4931}
4932impl_display_t!(DeclareStatement);
4933
4934#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4936pub struct CloseStatement {
4937 pub name: Ident,
4938}
4939
4940impl AstDisplay for CloseStatement {
4941 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4942 f.write_str("CLOSE ");
4943 f.write_node(&self.name);
4944 }
4945}
4946impl_display!(CloseStatement);
4947
4948#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
4949pub enum FetchOptionName {
4950 Timeout,
4951}
4952
4953impl AstDisplay for FetchOptionName {
4954 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4955 f.write_str(match self {
4956 FetchOptionName::Timeout => "TIMEOUT",
4957 })
4958 }
4959}
4960
4961impl WithOptionName for FetchOptionName {
4962 fn redact_value(&self) -> bool {
4968 match self {
4969 FetchOptionName::Timeout => false,
4970 }
4971 }
4972}
4973
4974#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
4975pub struct FetchOption<T: AstInfo> {
4976 pub name: FetchOptionName,
4977 pub value: Option<WithOptionValue<T>>,
4978}
4979impl_display_for_with_option!(FetchOption);
4980
4981#[derive(Debug, Clone, PartialEq, Eq, Hash)]
4983pub struct FetchStatement<T: AstInfo> {
4984 pub name: Ident,
4985 pub count: Option<FetchDirection>,
4986 pub options: Vec<FetchOption<T>>,
4987}
4988
4989impl<T: AstInfo> AstDisplay for FetchStatement<T> {
4990 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
4991 f.write_str("FETCH ");
4992 if let Some(ref count) = self.count {
4993 f.write_str(format!("{} ", count));
4994 }
4995 f.write_node(&self.name);
4996 if !self.options.is_empty() {
4997 f.write_str(" WITH (");
4998 f.write_node(&display::comma_separated(&self.options));
4999 f.write_str(")");
5000 }
5001 }
5002}
5003impl_display_t!(FetchStatement);
5004
5005#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
5006pub enum FetchDirection {
5007 ForwardAll,
5008 ForwardCount(u64),
5009}
5010
5011impl AstDisplay for FetchDirection {
5012 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5013 match self {
5014 FetchDirection::ForwardAll => f.write_str("ALL"),
5015 FetchDirection::ForwardCount(count) => f.write_str(format!("{}", count)),
5016 }
5017 }
5018}
5019impl_display!(FetchDirection);
5020
5021#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5023pub struct PrepareStatement<T: AstInfo> {
5024 pub name: Ident,
5025 pub stmt: Box<T::NestedStatement>,
5026 pub sql: String,
5027}
5028
5029impl<T: AstInfo> AstDisplay for PrepareStatement<T> {
5030 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5031 f.write_str("PREPARE ");
5032 f.write_node(&self.name);
5033 f.write_str(" AS ");
5034 f.write_node(&self.stmt);
5035 }
5036}
5037impl_display_t!(PrepareStatement);
5038
5039#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5041pub struct ExecuteStatement<T: AstInfo> {
5042 pub name: Ident,
5043 pub params: Vec<Expr<T>>,
5044}
5045
5046impl<T: AstInfo> AstDisplay for ExecuteStatement<T> {
5047 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5048 f.write_str("EXECUTE ");
5049 f.write_node(&self.name);
5050 if !self.params.is_empty() {
5051 f.write_str(" (");
5052 f.write_node(&display::comma_separated(&self.params));
5053 f.write_str(")");
5054 }
5055 }
5056}
5057impl_display_t!(ExecuteStatement);
5058
5059#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5061pub struct DeallocateStatement {
5062 pub name: Option<Ident>,
5063}
5064
5065impl AstDisplay for DeallocateStatement {
5066 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5067 f.write_str("DEALLOCATE ");
5068 match &self.name {
5069 Some(name) => f.write_node(name),
5070 None => f.write_str("ALL"),
5071 };
5072 }
5073}
5074impl_display!(DeallocateStatement);
5075
5076#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5078pub struct RaiseStatement {
5079 pub severity: NoticeSeverity,
5080}
5081
5082impl AstDisplay for RaiseStatement {
5083 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5084 f.write_str("RAISE ");
5085 f.write_node(&self.severity);
5086 }
5087}
5088impl_display!(RaiseStatement);
5089
5090#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5091pub enum NoticeSeverity {
5092 Debug,
5093 Info,
5094 Log,
5095 Notice,
5096 Warning,
5097}
5098
5099impl AstDisplay for NoticeSeverity {
5100 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5101 f.write_str(match self {
5102 NoticeSeverity::Debug => "DEBUG",
5103 NoticeSeverity::Info => "INFO",
5104 NoticeSeverity::Log => "LOG",
5105 NoticeSeverity::Notice => "NOTICE",
5106 NoticeSeverity::Warning => "WARNING",
5107 })
5108 }
5109}
5110impl_display!(NoticeSeverity);
5111
5112#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5114pub struct AlterSystemSetStatement {
5115 pub name: Ident,
5116 pub to: SetVariableTo,
5117}
5118
5119impl AstDisplay for AlterSystemSetStatement {
5120 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5121 f.write_str("ALTER SYSTEM SET ");
5122 f.write_node(&self.name);
5123 f.write_str(" = ");
5124 f.write_node(&self.to);
5125 }
5126}
5127impl_display!(AlterSystemSetStatement);
5128
5129#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5131pub struct AlterSystemResetStatement {
5132 pub name: Ident,
5133}
5134
5135impl AstDisplay for AlterSystemResetStatement {
5136 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5137 f.write_str("ALTER SYSTEM RESET ");
5138 f.write_node(&self.name);
5139 }
5140}
5141impl_display!(AlterSystemResetStatement);
5142
5143#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5145pub struct AlterSystemResetAllStatement {}
5146
5147impl AstDisplay for AlterSystemResetAllStatement {
5148 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5149 f.write_str("ALTER SYSTEM RESET ALL");
5150 }
5151}
5152impl_display!(AlterSystemResetAllStatement);
5153
5154#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5155pub enum AsOf<T: AstInfo> {
5156 At(Expr<T>),
5157 AtLeast(Expr<T>),
5158}
5159
5160impl<T: AstInfo> AstDisplay for AsOf<T> {
5161 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5162 f.write_str("AS OF ");
5163 match self {
5164 AsOf::At(expr) => f.write_node(expr),
5165 AsOf::AtLeast(expr) => {
5166 f.write_str("AT LEAST ");
5167 f.write_node(expr);
5168 }
5169 }
5170 }
5171}
5172impl_display_t!(AsOf);
5173
5174#[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
5175pub enum ShowStatement<T: AstInfo> {
5176 ShowObjects(ShowObjectsStatement<T>),
5177 ShowColumns(ShowColumnsStatement<T>),
5178 ShowCreateView(ShowCreateViewStatement<T>),
5179 ShowCreateMaterializedView(ShowCreateMaterializedViewStatement<T>),
5180 ShowCreateSource(ShowCreateSourceStatement<T>),
5181 ShowCreateTable(ShowCreateTableStatement<T>),
5182 ShowCreateSink(ShowCreateSinkStatement<T>),
5183 ShowCreateIndex(ShowCreateIndexStatement<T>),
5184 ShowCreateConnection(ShowCreateConnectionStatement<T>),
5185 ShowCreateCluster(ShowCreateClusterStatement<T>),
5186 ShowCreateType(ShowCreateTypeStatement<T>),
5187 ShowVariable(ShowVariableStatement),
5188 InspectShard(InspectShardStatement),
5189}
5190
5191impl<T: AstInfo> AstDisplay for ShowStatement<T> {
5192 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5193 match self {
5194 ShowStatement::ShowObjects(stmt) => f.write_node(stmt),
5195 ShowStatement::ShowColumns(stmt) => f.write_node(stmt),
5196 ShowStatement::ShowCreateView(stmt) => f.write_node(stmt),
5197 ShowStatement::ShowCreateMaterializedView(stmt) => f.write_node(stmt),
5198 ShowStatement::ShowCreateSource(stmt) => f.write_node(stmt),
5199 ShowStatement::ShowCreateTable(stmt) => f.write_node(stmt),
5200 ShowStatement::ShowCreateSink(stmt) => f.write_node(stmt),
5201 ShowStatement::ShowCreateIndex(stmt) => f.write_node(stmt),
5202 ShowStatement::ShowCreateConnection(stmt) => f.write_node(stmt),
5203 ShowStatement::ShowCreateCluster(stmt) => f.write_node(stmt),
5204 ShowStatement::ShowCreateType(stmt) => f.write_node(stmt),
5205 ShowStatement::ShowVariable(stmt) => f.write_node(stmt),
5206 ShowStatement::InspectShard(stmt) => f.write_node(stmt),
5207 }
5208 }
5209}
5210impl_display_t!(ShowStatement);
5211
5212#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5214pub struct GrantRoleStatement<T: AstInfo> {
5215 pub role_names: Vec<T::RoleName>,
5217 pub member_names: Vec<T::RoleName>,
5219}
5220
5221impl<T: AstInfo> AstDisplay for GrantRoleStatement<T> {
5222 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5223 f.write_str("GRANT ");
5224 f.write_node(&display::comma_separated(&self.role_names));
5225 f.write_str(" TO ");
5226 f.write_node(&display::comma_separated(&self.member_names));
5227 }
5228}
5229impl_display_t!(GrantRoleStatement);
5230
5231#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5233pub struct RevokeRoleStatement<T: AstInfo> {
5234 pub role_names: Vec<T::RoleName>,
5236 pub member_names: Vec<T::RoleName>,
5238}
5239
5240impl<T: AstInfo> AstDisplay for RevokeRoleStatement<T> {
5241 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5242 f.write_str("REVOKE ");
5243 f.write_node(&display::comma_separated(&self.role_names));
5244 f.write_str(" FROM ");
5245 f.write_node(&display::comma_separated(&self.member_names));
5246 }
5247}
5248impl_display_t!(RevokeRoleStatement);
5249
5250#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5251pub enum Privilege {
5252 SELECT,
5253 INSERT,
5254 UPDATE,
5255 DELETE,
5256 USAGE,
5257 CREATE,
5258 CREATEROLE,
5259 CREATEDB,
5260 CREATECLUSTER,
5261 CREATENETWORKPOLICY,
5262}
5263
5264impl AstDisplay for Privilege {
5265 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5266 f.write_str(match self {
5267 Privilege::SELECT => "SELECT",
5268 Privilege::INSERT => "INSERT",
5269 Privilege::UPDATE => "UPDATE",
5270 Privilege::DELETE => "DELETE",
5271 Privilege::CREATE => "CREATE",
5272 Privilege::USAGE => "USAGE",
5273 Privilege::CREATEROLE => "CREATEROLE",
5274 Privilege::CREATEDB => "CREATEDB",
5275 Privilege::CREATECLUSTER => "CREATECLUSTER",
5276 Privilege::CREATENETWORKPOLICY => "CREATENETWORKPOLICY",
5277 });
5278 }
5279}
5280impl_display!(Privilege);
5281
5282#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5283pub enum PrivilegeSpecification {
5284 All,
5285 Privileges(Vec<Privilege>),
5286}
5287
5288impl AstDisplay for PrivilegeSpecification {
5289 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5290 match self {
5291 PrivilegeSpecification::All => f.write_str("ALL"),
5292 PrivilegeSpecification::Privileges(privileges) => {
5293 f.write_node(&display::comma_separated(privileges))
5294 }
5295 }
5296 }
5297}
5298impl_display!(PrivilegeSpecification);
5299
5300#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5301pub enum GrantTargetSpecification<T: AstInfo> {
5302 Object {
5303 object_type: ObjectType,
5307 object_spec_inner: GrantTargetSpecificationInner<T>,
5309 },
5310 System,
5311}
5312
5313#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5314pub enum GrantTargetSpecificationInner<T: AstInfo> {
5315 All(GrantTargetAllSpecification<T>),
5316 Objects { names: Vec<T::ObjectName> },
5317}
5318
5319#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5320pub enum GrantTargetAllSpecification<T: AstInfo> {
5321 All,
5322 AllDatabases { databases: Vec<T::DatabaseName> },
5323 AllSchemas { schemas: Vec<T::SchemaName> },
5324}
5325
5326impl<T: AstInfo> GrantTargetAllSpecification<T> {
5327 pub fn len(&self) -> usize {
5328 match self {
5329 GrantTargetAllSpecification::All => 1,
5330 GrantTargetAllSpecification::AllDatabases { databases } => databases.len(),
5331 GrantTargetAllSpecification::AllSchemas { schemas } => schemas.len(),
5332 }
5333 }
5334}
5335
5336impl<T: AstInfo> AstDisplay for GrantTargetSpecification<T> {
5337 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5338 match self {
5339 GrantTargetSpecification::Object {
5340 object_type,
5341 object_spec_inner,
5342 } => match object_spec_inner {
5343 GrantTargetSpecificationInner::All(all_spec) => match all_spec {
5344 GrantTargetAllSpecification::All => {
5345 f.write_str("ALL ");
5346 f.write_node(object_type);
5347 f.write_str("S");
5348 }
5349 GrantTargetAllSpecification::AllDatabases { databases } => {
5350 f.write_str("ALL ");
5351 f.write_node(object_type);
5352 f.write_str("S IN DATABASE ");
5353 f.write_node(&display::comma_separated(databases));
5354 }
5355 GrantTargetAllSpecification::AllSchemas { schemas } => {
5356 f.write_str("ALL ");
5357 f.write_node(object_type);
5358 f.write_str("S IN SCHEMA ");
5359 f.write_node(&display::comma_separated(schemas));
5360 }
5361 },
5362 GrantTargetSpecificationInner::Objects { names } => {
5363 f.write_node(object_type);
5364 f.write_str(" ");
5365 f.write_node(&display::comma_separated(names));
5366 }
5367 },
5368 GrantTargetSpecification::System => f.write_str("SYSTEM"),
5369 }
5370 }
5371}
5372impl_display_t!(GrantTargetSpecification);
5373
5374#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5376pub struct GrantPrivilegesStatement<T: AstInfo> {
5377 pub privileges: PrivilegeSpecification,
5379 pub target: GrantTargetSpecification<T>,
5381 pub roles: Vec<T::RoleName>,
5383}
5384
5385impl<T: AstInfo> AstDisplay for GrantPrivilegesStatement<T> {
5386 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5387 f.write_str("GRANT ");
5388 f.write_node(&self.privileges);
5389 f.write_str(" ON ");
5390 f.write_node(&self.target);
5391 f.write_str(" TO ");
5392 f.write_node(&display::comma_separated(&self.roles));
5393 }
5394}
5395impl_display_t!(GrantPrivilegesStatement);
5396
5397#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5399pub struct RevokePrivilegesStatement<T: AstInfo> {
5400 pub privileges: PrivilegeSpecification,
5402 pub target: GrantTargetSpecification<T>,
5404 pub roles: Vec<T::RoleName>,
5406}
5407
5408impl<T: AstInfo> AstDisplay for RevokePrivilegesStatement<T> {
5409 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5410 f.write_str("REVOKE ");
5411 f.write_node(&self.privileges);
5412 f.write_str(" ON ");
5413 f.write_node(&self.target);
5414 f.write_str(" FROM ");
5415 f.write_node(&display::comma_separated(&self.roles));
5416 }
5417}
5418impl_display_t!(RevokePrivilegesStatement);
5419
5420#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5421pub enum TargetRoleSpecification<T: AstInfo> {
5422 Roles(Vec<T::RoleName>),
5424 AllRoles,
5426}
5427
5428impl<T: AstInfo> AstDisplay for TargetRoleSpecification<T> {
5429 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5430 match self {
5431 TargetRoleSpecification::Roles(roles) => f.write_node(&display::comma_separated(roles)),
5432 TargetRoleSpecification::AllRoles => f.write_str("ALL ROLES"),
5433 }
5434 }
5435}
5436impl_display_t!(TargetRoleSpecification);
5437
5438#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5439pub struct AbbreviatedGrantStatement<T: AstInfo> {
5440 pub privileges: PrivilegeSpecification,
5442 pub object_type: ObjectType,
5446 pub grantees: Vec<T::RoleName>,
5448}
5449
5450impl<T: AstInfo> AstDisplay for AbbreviatedGrantStatement<T> {
5451 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5452 f.write_str("GRANT ");
5453 f.write_node(&self.privileges);
5454 f.write_str(" ON ");
5455 f.write_node(&self.object_type);
5456 f.write_str("S TO ");
5457 f.write_node(&display::comma_separated(&self.grantees));
5458 }
5459}
5460impl_display_t!(AbbreviatedGrantStatement);
5461
5462#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5463pub struct AbbreviatedRevokeStatement<T: AstInfo> {
5464 pub privileges: PrivilegeSpecification,
5466 pub object_type: ObjectType,
5470 pub revokees: Vec<T::RoleName>,
5472}
5473
5474impl<T: AstInfo> AstDisplay for AbbreviatedRevokeStatement<T> {
5475 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5476 f.write_str("REVOKE ");
5477 f.write_node(&self.privileges);
5478 f.write_str(" ON ");
5479 f.write_node(&self.object_type);
5480 f.write_str("S FROM ");
5481 f.write_node(&display::comma_separated(&self.revokees));
5482 }
5483}
5484impl_display_t!(AbbreviatedRevokeStatement);
5485
5486#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5487pub enum AbbreviatedGrantOrRevokeStatement<T: AstInfo> {
5488 Grant(AbbreviatedGrantStatement<T>),
5489 Revoke(AbbreviatedRevokeStatement<T>),
5490}
5491
5492impl<T: AstInfo> AbbreviatedGrantOrRevokeStatement<T> {
5493 pub fn privileges(&self) -> &PrivilegeSpecification {
5494 match self {
5495 AbbreviatedGrantOrRevokeStatement::Grant(grant) => &grant.privileges,
5496 AbbreviatedGrantOrRevokeStatement::Revoke(revoke) => &revoke.privileges,
5497 }
5498 }
5499
5500 pub fn object_type(&self) -> &ObjectType {
5501 match self {
5502 AbbreviatedGrantOrRevokeStatement::Grant(grant) => &grant.object_type,
5503 AbbreviatedGrantOrRevokeStatement::Revoke(revoke) => &revoke.object_type,
5504 }
5505 }
5506
5507 pub fn roles(&self) -> &Vec<T::RoleName> {
5508 match self {
5509 AbbreviatedGrantOrRevokeStatement::Grant(grant) => &grant.grantees,
5510 AbbreviatedGrantOrRevokeStatement::Revoke(revoke) => &revoke.revokees,
5511 }
5512 }
5513}
5514
5515impl<T: AstInfo> AstDisplay for AbbreviatedGrantOrRevokeStatement<T> {
5516 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5517 match self {
5518 AbbreviatedGrantOrRevokeStatement::Grant(grant) => f.write_node(grant),
5519 AbbreviatedGrantOrRevokeStatement::Revoke(revoke) => f.write_node(revoke),
5520 }
5521 }
5522}
5523impl_display_t!(AbbreviatedGrantOrRevokeStatement);
5524
5525#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5527pub struct AlterDefaultPrivilegesStatement<T: AstInfo> {
5528 pub target_roles: TargetRoleSpecification<T>,
5530 pub target_objects: GrantTargetAllSpecification<T>,
5532 pub grant_or_revoke: AbbreviatedGrantOrRevokeStatement<T>,
5534}
5535
5536impl<T: AstInfo> AstDisplay for AlterDefaultPrivilegesStatement<T> {
5537 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5538 f.write_str("ALTER DEFAULT PRIVILEGES");
5539 match &self.target_roles {
5540 TargetRoleSpecification::Roles(_) => {
5541 f.write_str(" FOR ROLE ");
5542 f.write_node(&self.target_roles);
5543 }
5544 TargetRoleSpecification::AllRoles => {
5545 f.write_str(" FOR ");
5546 f.write_node(&self.target_roles);
5547 }
5548 }
5549 match &self.target_objects {
5550 GrantTargetAllSpecification::All => {}
5551 GrantTargetAllSpecification::AllDatabases { databases } => {
5552 f.write_str(" IN DATABASE ");
5553 f.write_node(&display::comma_separated(databases));
5554 }
5555 GrantTargetAllSpecification::AllSchemas { schemas } => {
5556 f.write_str(" IN SCHEMA ");
5557 f.write_node(&display::comma_separated(schemas));
5558 }
5559 }
5560 f.write_str(" ");
5561 f.write_node(&self.grant_or_revoke);
5562 }
5563}
5564impl_display_t!(AlterDefaultPrivilegesStatement);
5565
5566#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5568pub struct ReassignOwnedStatement<T: AstInfo> {
5569 pub old_roles: Vec<T::RoleName>,
5571 pub new_role: T::RoleName,
5573}
5574
5575impl<T: AstInfo> AstDisplay for ReassignOwnedStatement<T> {
5576 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5577 f.write_str("REASSIGN OWNED BY ");
5578 f.write_node(&display::comma_separated(&self.old_roles));
5579 f.write_str(" TO ");
5580 f.write_node(&self.new_role);
5581 }
5582}
5583impl_display_t!(ReassignOwnedStatement);
5584
5585#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5587pub struct CommentStatement<T: AstInfo> {
5588 pub object: CommentObjectType<T>,
5589 pub comment: Option<String>,
5590}
5591
5592impl<T: AstInfo> AstDisplay for CommentStatement<T> {
5593 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5594 f.write_str("COMMENT ON ");
5595 f.write_node(&self.object);
5596
5597 f.write_str(" IS ");
5598 match &self.comment {
5599 Some(s) => {
5600 f.write_str("'");
5601 f.write_node(&display::escape_single_quote_string(s));
5602 f.write_str("'");
5603 }
5604 None => f.write_str("NULL"),
5605 }
5606 }
5607}
5608impl_display_t!(CommentStatement);
5609
5610#[derive(Debug, PartialEq, Eq, Hash, PartialOrd, Ord, Clone)]
5611pub struct ColumnName<T: AstInfo> {
5612 pub relation: T::ItemName,
5613 pub column: T::ColumnReference,
5614}
5615
5616impl<T: AstInfo> AstDisplay for ColumnName<T> {
5617 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5618 f.write_node(&self.relation);
5619 f.write_str(".");
5620 f.write_node(&self.column);
5621 }
5622}
5623impl_display_t!(ColumnName);
5624
5625#[derive(Debug, Clone, PartialEq, Eq, Hash)]
5626pub enum CommentObjectType<T: AstInfo> {
5627 Table { name: T::ItemName },
5628 View { name: T::ItemName },
5629 Column { name: ColumnName<T> },
5630 MaterializedView { name: T::ItemName },
5631 Source { name: T::ItemName },
5632 Sink { name: T::ItemName },
5633 Index { name: T::ItemName },
5634 Func { name: T::ItemName },
5635 Connection { name: T::ItemName },
5636 Type { ty: T::DataType },
5637 Secret { name: T::ItemName },
5638 Role { name: T::RoleName },
5639 Database { name: T::DatabaseName },
5640 Schema { name: T::SchemaName },
5641 Cluster { name: T::ClusterName },
5642 ClusterReplica { name: QualifiedReplica },
5643 ContinualTask { name: T::ItemName },
5644 NetworkPolicy { name: T::NetworkPolicyName },
5645}
5646
5647impl<T: AstInfo> AstDisplay for CommentObjectType<T> {
5648 fn fmt<W: fmt::Write>(&self, f: &mut AstFormatter<W>) {
5649 use CommentObjectType::*;
5650
5651 match self {
5652 Table { name } => {
5653 f.write_str("TABLE ");
5654 f.write_node(name);
5655 }
5656 View { name } => {
5657 f.write_str("VIEW ");
5658 f.write_node(name);
5659 }
5660 Column { name } => {
5661 f.write_str("COLUMN ");
5662 f.write_node(name);
5663 }
5664 MaterializedView { name } => {
5665 f.write_str("MATERIALIZED VIEW ");
5666 f.write_node(name);
5667 }
5668 Source { name } => {
5669 f.write_str("SOURCE ");
5670 f.write_node(name);
5671 }
5672 Sink { name } => {
5673 f.write_str("SINK ");
5674 f.write_node(name);
5675 }
5676 Index { name } => {
5677 f.write_str("INDEX ");
5678 f.write_node(name);
5679 }
5680 Func { name } => {
5681 f.write_str("FUNCTION ");
5682 f.write_node(name);
5683 }
5684 Connection { name } => {
5685 f.write_str("CONNECTION ");
5686 f.write_node(name);
5687 }
5688 Type { ty } => {
5689 f.write_str("TYPE ");
5690 f.write_node(ty);
5691 }
5692 Secret { name } => {
5693 f.write_str("SECRET ");
5694 f.write_node(name);
5695 }
5696 Role { name } => {
5697 f.write_str("ROLE ");
5698 f.write_node(name);
5699 }
5700 Database { name } => {
5701 f.write_str("DATABASE ");
5702 f.write_node(name);
5703 }
5704 Schema { name } => {
5705 f.write_str("SCHEMA ");
5706 f.write_node(name);
5707 }
5708 Cluster { name } => {
5709 f.write_str("CLUSTER ");
5710 f.write_node(name);
5711 }
5712 ClusterReplica { name } => {
5713 f.write_str("CLUSTER REPLICA ");
5714 f.write_node(name);
5715 }
5716 ContinualTask { name } => {
5717 f.write_str("CONTINUAL TASK ");
5718 f.write_node(name);
5719 }
5720 NetworkPolicy { name } => {
5721 f.write_str("NETWORK POLICY ");
5722 f.write_node(name);
5723 }
5724 }
5725 }
5726}
5727
5728impl_display_t!(CommentObjectType);
5729
5730include!(concat!(env!("OUT_DIR"), "/display.simple_options.rs"));