@@ -62,6 +62,9 @@ pub struct Query {
62
62
/// [ClickHouse](https://clickhouse.com/docs/en/sql-reference/statements/select/format)
63
63
/// (ClickHouse-specific)
64
64
pub format_clause : Option < FormatClause > ,
65
+
66
+ /// Pipe operator
67
+ pub pipe_operators : Vec < PipeOperator > ,
65
68
}
66
69
67
70
impl fmt:: Display for Query {
@@ -92,6 +95,9 @@ impl fmt::Display for Query {
92
95
if let Some ( ref format) = self . format_clause {
93
96
write ! ( f, " {}" , format) ?;
94
97
}
98
+ for pipe_operator in & self . pipe_operators {
99
+ write ! ( f, " |> {}" , pipe_operator) ?;
100
+ }
95
101
Ok ( ( ) )
96
102
}
97
103
}
@@ -1004,6 +1010,26 @@ impl fmt::Display for ExprWithAlias {
1004
1010
}
1005
1011
}
1006
1012
1013
+ /// An expression optionally followed by an alias and order by options.
1014
+ ///
1015
+ /// Example:
1016
+ /// ```sql
1017
+ /// 42 AS myint ASC
1018
+ /// ```
1019
+ #[ derive( Debug , Clone , PartialEq , PartialOrd , Eq , Ord , Hash ) ]
1020
+ #[ cfg_attr( feature = "serde" , derive( Serialize , Deserialize ) ) ]
1021
+ #[ cfg_attr( feature = "visitor" , derive( Visit , VisitMut ) ) ]
1022
+ pub struct ExprWithAliasAndOrderBy {
1023
+ pub expr : ExprWithAlias ,
1024
+ pub order_by : OrderByOptions ,
1025
+ }
1026
+
1027
+ impl fmt:: Display for ExprWithAliasAndOrderBy {
1028
+ fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
1029
+ write ! ( f, "{}{}" , self . expr, self . order_by)
1030
+ }
1031
+ }
1032
+
1007
1033
/// Arguments to a table-valued function
1008
1034
#[ derive( Debug , Clone , PartialEq , PartialOrd , Eq , Ord , Hash ) ]
1009
1035
#[ cfg_attr( feature = "serde" , derive( Serialize , Deserialize ) ) ]
@@ -2513,6 +2539,135 @@ impl fmt::Display for OffsetRows {
2513
2539
}
2514
2540
}
2515
2541
2542
+ /// Pipe syntax, first introduced in Google BigQuery.
2543
+ /// Example:
2544
+ ///
2545
+ /// ```sql
2546
+ /// FROM Produce
2547
+ /// |> WHERE sales > 0
2548
+ /// |> AGGREGATE SUM(sales) AS total_sales, COUNT(*) AS num_sales
2549
+ /// GROUP BY item;
2550
+ /// ```
2551
+ ///
2552
+ /// See <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#pipe_syntax>
2553
+ #[ derive( Debug , Clone , PartialEq , PartialOrd , Eq , Ord , Hash ) ]
2554
+ #[ cfg_attr( feature = "serde" , derive( Serialize , Deserialize ) ) ]
2555
+ #[ cfg_attr( feature = "visitor" , derive( Visit , VisitMut ) ) ]
2556
+ pub enum PipeOperator {
2557
+ /// Limits the number of rows to return in a query, with an optional OFFSET clause to skip over rows.
2558
+ ///
2559
+ /// Syntax: `|> LIMIT <n> [OFFSET <m>]`
2560
+ ///
2561
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#limit_pipe_operator>
2562
+ Limit { expr : Expr , offset : Option < Expr > } ,
2563
+ /// Filters the results of the input table.
2564
+ ///
2565
+ /// Syntax: `|> WHERE <condition>`
2566
+ ///
2567
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#where_pipe_operator>
2568
+ Where { expr : Expr } ,
2569
+ /// `ORDER BY <expr> [ASC|DESC], ...`
2570
+ OrderBy { exprs : Vec < OrderByExpr > } ,
2571
+ /// Produces a new table with the listed columns, similar to the outermost SELECT clause in a table subquery in standard syntax.
2572
+ ///
2573
+ /// Syntax `|> SELECT <expr> [[AS] alias], ...`
2574
+ ///
2575
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#select_pipe_operator>
2576
+ Select { exprs : Vec < SelectItem > } ,
2577
+ /// Propagates the existing table and adds computed columns, similar to SELECT *, new_column in standard syntax.
2578
+ ///
2579
+ /// Syntax: `|> EXTEND <expr> [[AS] alias], ...`
2580
+ ///
2581
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#extend_pipe_operator>
2582
+ Extend { exprs : Vec < SelectItem > } ,
2583
+ /// Replaces the value of a column in the current table, similar to SELECT * REPLACE (expression AS column) in standard syntax.
2584
+ ///
2585
+ /// Syntax: `|> SET <column> = <expression>, ...`
2586
+ ///
2587
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#set_pipe_operator>
2588
+ Set { assignments : Vec < Assignment > } ,
2589
+ /// Removes listed columns from the current table, similar to SELECT * EXCEPT (column) in standard syntax.
2590
+ ///
2591
+ /// Syntax: `|> DROP <column>, ...`
2592
+ ///
2593
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#drop_pipe_operator>
2594
+ Drop { columns : Vec < Ident > } ,
2595
+ /// Introduces a table alias for the input table, similar to applying the AS alias clause on a table subquery in standard syntax.
2596
+ ///
2597
+ /// Syntax: `|> AS <alias>`
2598
+ ///
2599
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#as_pipe_operator>
2600
+ As { alias : Ident } ,
2601
+ /// Performs aggregation on data across grouped rows or an entire table.
2602
+ ///
2603
+ /// Syntax: `|> AGGREGATE <agg_expr> [[AS] alias], ...`
2604
+ ///
2605
+ /// Syntax:
2606
+ /// ```norust
2607
+ /// |> AGGREGATE [<agg_expr> [[AS] alias], ...]
2608
+ /// GROUP BY <grouping_expr> [AS alias], ...
2609
+ /// ```
2610
+ ///
2611
+ /// See more at <https://cloud.google.com/bigquery/docs/reference/standard-sql/pipe-syntax#aggregate_pipe_operator>
2612
+ Aggregate {
2613
+ full_table_exprs : Vec < ExprWithAliasAndOrderBy > ,
2614
+ group_by_expr : Vec < ExprWithAliasAndOrderBy > ,
2615
+ } ,
2616
+ }
2617
+
2618
+ impl fmt:: Display for PipeOperator {
2619
+ fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
2620
+ match self {
2621
+ PipeOperator :: Select { exprs } => {
2622
+ write ! ( f, "SELECT {}" , display_comma_separated( exprs. as_slice( ) ) )
2623
+ }
2624
+ PipeOperator :: Extend { exprs } => {
2625
+ write ! ( f, "EXTEND {}" , display_comma_separated( exprs. as_slice( ) ) )
2626
+ }
2627
+ PipeOperator :: Set { assignments } => {
2628
+ write ! ( f, "SET {}" , display_comma_separated( assignments. as_slice( ) ) )
2629
+ }
2630
+ PipeOperator :: Drop { columns } => {
2631
+ write ! ( f, "DROP {}" , display_comma_separated( columns. as_slice( ) ) )
2632
+ }
2633
+ PipeOperator :: As { alias } => {
2634
+ write ! ( f, "AS {}" , alias)
2635
+ }
2636
+ PipeOperator :: Limit { expr, offset } => {
2637
+ write ! ( f, "LIMIT {}" , expr) ?;
2638
+ if let Some ( offset) = offset {
2639
+ write ! ( f, " OFFSET {}" , offset) ?;
2640
+ }
2641
+ Ok ( ( ) )
2642
+ }
2643
+ PipeOperator :: Aggregate {
2644
+ full_table_exprs,
2645
+ group_by_expr,
2646
+ } => {
2647
+ write ! ( f, "AGGREGATE" ) ?;
2648
+ if !full_table_exprs. is_empty ( ) {
2649
+ write ! (
2650
+ f,
2651
+ " {}" ,
2652
+ display_comma_separated( full_table_exprs. as_slice( ) )
2653
+ ) ?;
2654
+ }
2655
+ if !group_by_expr. is_empty ( ) {
2656
+ write ! ( f, " GROUP BY {}" , display_comma_separated( group_by_expr) ) ?;
2657
+ }
2658
+ Ok ( ( ) )
2659
+ }
2660
+
2661
+ PipeOperator :: Where { expr } => {
2662
+ write ! ( f, "WHERE {}" , expr)
2663
+ }
2664
+ PipeOperator :: OrderBy { exprs } => {
2665
+ write ! ( f, "ORDER BY {}" , display_comma_separated( exprs. as_slice( ) ) )
2666
+ }
2667
+ }
2668
+ }
2669
+ }
2670
+
2516
2671
#[ derive( Debug , Clone , PartialEq , PartialOrd , Eq , Ord , Hash ) ]
2517
2672
#[ cfg_attr( feature = "serde" , derive( Serialize , Deserialize ) ) ]
2518
2673
#[ cfg_attr( feature = "visitor" , derive( Visit , VisitMut ) ) ]
0 commit comments