Documentation ¶
Overview ¶
Package ast represents SQL code hierarchy.
Index ¶
- func ColumnName(n Node) string
- func Copy[T Node](n T) T
- func EndLine[T Node](n T) T
- func Indent[T Node](n T, i string) T
- func IndentAfter[T Node](before lexer.Token, n T, i string) (T, lexer.Token)
- func IndentFrom[T Node](new T, old Node) T
- func OneSpace[T Node](n T) T
- func SpaceFrom[T Node](new T, old Node) T
- func SpaceFromItem[T Node](new T, grouping Grouping, pos int) T
- func SwapWhitespaces[T1 Node, T2 Node](first T1, second T2) (T1, T2)
- func TableName(expr Node) string
- func TrimNewLine[T Node](n T) T
- type Alias
- type Between
- type CTE
- type Call
- type Case
- type Clause
- type Column
- type Columns
- type ConnectBy
- type Cycle
- type Fetch
- type From
- func (from *From) Append(table Node)
- func (from From) Contains(table string) bool
- func (from From) Index(table string) int
- func (from From) IsJoin(table string) bool
- func (from From) IsZero() bool
- func (from From) Names() (names []string)
- func (from *From) Replace(table string, expr Node)
- func (from From) Sort(names ...string) (sorted []string)
- func (from From) Tokens() []lexer.Token
- func (from From) TransformEnd(f Transformer[lexer.Token]) Node
- func (from From) TransformStart(f Transformer[lexer.Token]) Node
- func (from From) Visit(f Transformer[Node]) Node
- type GroupBy
- type Grouping
- func (g *Grouping) Append(n Node)
- func (g *Grouping) Delete(pos int) (expr Node)
- func (g *Grouping) Insert(pos int, n Node)
- func (g Grouping) Tokens() []lexer.Token
- func (g Grouping) TransformEnd(f Transformer[lexer.Token]) Node
- func (g Grouping) TransformStart(f Transformer[lexer.Token]) Node
- func (g Grouping) Visit(f Transformer[Node]) Node
- type Having
- type Infix
- type Join
- type Leaf
- func (a Leaf) In(s ...any) bool
- func (a Leaf) IsIdentifier() bool
- func (a Leaf) String() string
- func (a Leaf) Tokens() []lexer.Token
- func (a Leaf) TransformEnd(f Transformer[lexer.Token]) Node
- func (a Leaf) TransformStart(f Transformer[lexer.Token]) Node
- func (a Leaf) Visit(f Transformer[Node]) Node
- type Limit
- type LiteralCast
- type Node
- type Offset
- type OrderBy
- type OrderCriterium
- type Postfix
- func (p Postfix) Is(s string) bool
- func (p Postfix) RemoveOperator() Postfix
- func (p Postfix) SetOperator(t lexer.Token) Postfix
- func (p Postfix) Tokens() []lexer.Token
- func (p Postfix) TransformEnd(f Transformer[lexer.Token]) Node
- func (p Postfix) TransformStart(f Transformer[lexer.Token]) Node
- func (p Postfix) Visit(f Transformer[Node]) Node
- type Prefix
- func (i Prefix) Is(s string) bool
- func (p Prefix) IsZero() bool
- func (p Prefix) RemoveOperator() Prefix
- func (p Prefix) SetOperator(t lexer.Token) Prefix
- func (p Prefix) Tokens() []lexer.Token
- func (p Prefix) TransformEnd(f Transformer[lexer.Token]) Node
- func (p Prefix) TransformStart(f Transformer[lexer.Token]) Node
- func (p Prefix) Visit(f Transformer[Node]) Node
- type Search
- type Select
- type StartWith
- type Statement
- type Statements
- type Transformer
- type When
- type Where
- func (w *Where) And(condition Node)
- func (w *Where) Append(items ...Prefix)
- func (w *Where) Delete(index int) (condition Node)
- func (w Where) IsZero() bool
- func (w Where) Tokens() []lexer.Token
- func (w Where) TransformEnd(f Transformer[lexer.Token]) Node
- func (w Where) TransformStart(f Transformer[lexer.Token]) Node
- func (w Where) Visit(f Transformer[Node]) Node
- type With
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func ColumnName ¶
ColumnName returns the identifier of a column expression.
e.g. "col0" for "a AS col0", "t1.col0", etc.
func Copy ¶
func Copy[T Node](n T) T
Copy recursively a node.
Token lists are duplicated, but tokens are not.
func Indent ¶
Indent a whole tree.
Replace node indentation with given string. Indentation is recursive. Follows Simon Holywell style guide.
func IndentAfter ¶
IndentAfter indent node after a token.
Handle spacing between token and node like parenthesis, new line or regular keyword.
func IndentFrom ¶
IndentFrom copies indentation from a node to another.
If old does not begins line, indent is removed.
func OneSpace ¶
func OneSpace[T Node](n T) T
OneSpace prefixes node with a single space.
Use it when moving an expression after a keyword. Removes leading comment.
func SpaceFrom ¶
SpaceFrom apply spacings from a node to another.
Preserves whitespace, indentation and comments from old node.
func SpaceFromItem ¶
SpaceFromItem apply spacings from an item in a grouping.
It's used when replacing a list with a plain syntax like decode() with CASE. Since comma will be lost, spacings around comma are moved to the new node.
func SwapWhitespaces ¶
SwapWhitespaces apply spacings from a node to another and vice versa.
Preserves comments. Useful when you swap two nodes.
func TableName ¶
TableName guess table expression name in FROM clause.
Accepts <table>, schema.<table> and expr AS <table>, ... JOIN <table>.
func TrimNewLine ¶
func TrimNewLine[T Node](n T) T
TrimNewLine removes final new line from node.
Use it when wrapping a node in another.
Types ¶
type Alias ¶
type Alias struct { Expression Node // As may be Void if AS keyword is omitted. As lexer.Token // Name is the new name, an identifier. Name lexer.Token }
Alias renames an expression with or without AS keyword.
func AliasTo ¶
AliasTo ensure expr has a name.
If expr is an alias, it renames it. If expr is not an alias, it creates a new alias with the given name.
func (Alias) TransformEnd ¶
func (a Alias) TransformEnd(f Transformer[lexer.Token]) Node
func (Alias) TransformStart ¶
func (a Alias) TransformStart(f Transformer[lexer.Token]) Node
type Between ¶
Between holds BETWEEN or NOT BETWEEN expression.
func (Between) TransformEnd ¶
func (b Between) TransformEnd(f Transformer[lexer.Token]) Node
func (Between) TransformStart ¶
func (b Between) TransformStart(f Transformer[lexer.Token]) Node
type CTE ¶
type CTE struct { Name lexer.Token Columns Columns // May be zero. As lexer.Token Materialized []lexer.Token // May be nil Open lexer.Token Query Node Close lexer.Token Search Node // May be nil Cycle Node // May be nil Comma lexer.Token // May be zero }
CTE holds a single Common Table Expression.
Example:
cte_name [( column_name [, ...] )] AS ( query ) [SEARCH] [CYCLE]
Holds the final comma separing from the next CTE.
cf. https://www.postgresql.org/docs/current/queries-with.html#QUERIES-WITH
func (CTE) TransformEnd ¶
func (c CTE) TransformEnd(f Transformer[lexer.Token]) Node
func (CTE) TransformStart ¶
func (c CTE) TransformStart(f Transformer[lexer.Token]) Node
type Call ¶
type Call struct { Function Node // Identifier or qualified name Args Grouping // The grouping containing arguments }
Call holds a function call.
func (Call) Is ¶
Is reports whether the function name matches the given strings.
Accepts one or two strings. If two strings are given, the first one is the package/schema name and the second one is the function name.
func (Call) TransformEnd ¶
func (c Call) TransformEnd(f Transformer[lexer.Token]) Node
func (Call) TransformStart ¶
func (c Call) TransformStart(f Transformer[lexer.Token]) Node
type Case ¶
type Case struct { Case lexer.Token Expression Node // nil if CASE is used for simple WHEN/THEN. Cases []When Else Prefix // Use Prefix.IsZero() to check for presence of ELSE. End lexer.Token }
Case is a SQL CASE statement.
func (Case) TransformEnd ¶
func (c Case) TransformEnd(f Transformer[lexer.Token]) Node
func (Case) TransformStart ¶
func (c Case) TransformStart(f Transformer[lexer.Token]) Node
type Clause ¶
Clause holds keywords prefixing an expression.
For example, PARTITION BY, DISTINCT ON, etc.
func (Clause) TransformEnd ¶
func (c Clause) TransformEnd(f Transformer[lexer.Token]) Node
func (Clause) TransformStart ¶
func (c Clause) TransformStart(f Transformer[lexer.Token]) Node
type Column ¶
Column is an item in a Columns list.
func (Column) TransformEnd ¶
func (c Column) TransformEnd(f Transformer[lexer.Token]) Node
func (Column) TransformStart ¶
func (c Column) TransformStart(f Transformer[lexer.Token]) Node
type Columns ¶
Columns holds a list of columns names.
This is plain column name, without typing like in CREATE TABLE.
Parens can be zero.
func (Columns) TransformEnd ¶
func (c Columns) TransformEnd(f Transformer[lexer.Token]) Node
func (Columns) TransformStart ¶
func (c Columns) TransformStart(f Transformer[lexer.Token]) Node
type ConnectBy ¶
ConnectBy holds CONNECT BY clause of SELECT statement.
func (ConnectBy) TransformEnd ¶
func (c ConnectBy) TransformEnd(f Transformer[lexer.Token]) Node
func (ConnectBy) TransformStart ¶
func (c ConnectBy) TransformStart(f Transformer[lexer.Token]) Node
type Cycle ¶
type Cycle struct { Cycle lexer.Token Columns Columns Set lexer.Token Target lexer.Token // May be zeros To lexer.Token Value lexer.Token Default lexer.Token DefaultValue lexer.Token // Required. Using lexer.Token Path lexer.Token }
Cycle holds CYCLE clause of CTE.
func (Cycle) TransformEnd ¶
func (c Cycle) TransformEnd(f Transformer[lexer.Token]) Node
func (Cycle) TransformStart ¶
func (c Cycle) TransformStart(f Transformer[lexer.Token]) Node
type Fetch ¶
type Fetch struct { Fetch []lexer.Token // FETCH { FIRST | NEXT } Count Node Tail []lexer.Token //{ ROW | ROWS } { ONLY | WITH TIES } Offset Node // PostgreSQL accepts OFFSET after FETCH }
Fetch holds FETCH FIRST or FETCH NEXT.
func (Fetch) TransformEnd ¶
func (f Fetch) TransformEnd(g Transformer[lexer.Token]) Node
func (Fetch) TransformStart ¶
func (f Fetch) TransformStart(g Transformer[lexer.Token]) Node
type From ¶
From holds the FROM clause of a SELECT query.
func (*From) Append ¶
Append a table expression to FROM clause.
Ensures FROM keyword is set. Indents JOIN with FROM and tables with previous table. Ensures JOIN is on its own line.
func (From) IsJoin ¶
IsJoin reports whether a table expression is a JOIN.
table is the name of the table in the FROM clause.
func (From) Names ¶
Names of all table expression in FROM clause.
Returns anonymous expression as empty string.
func (From) Sort ¶
Sort table names in the order they appear in FROM clause.
Panics if a name is not in FROM.
func (From) TransformEnd ¶
func (from From) TransformEnd(f Transformer[lexer.Token]) Node
func (From) TransformStart ¶
func (from From) TransformStart(f Transformer[lexer.Token]) Node
type GroupBy ¶
type GroupBy struct { GroupBy []lexer.Token // May contains SIBLINGS Expressions Grouping Having Node }
GroupBy holds a GROUP BY clause.
func (GroupBy) TransformEnd ¶
func (g GroupBy) TransformEnd(f Transformer[lexer.Token]) Node
func (GroupBy) TransformStart ¶
func (g GroupBy) TransformStart(f Transformer[lexer.Token]) Node
type Grouping ¶
Grouping holds comma separated expressions, eventually braced by parenthesis.
e.g. a.id, a.name or (1, 2) or [3, 4]
Open and Close can be Void for SELECT list, FROM clause. All Items are Postfix node with separator as postfix operator. Last Item has void operator because SQL does not allow trailing comma.
Used for function call arguments, sub-queries, function signature, etc.
func (*Grouping) Insert ¶
Insert adds a new item to the grouping at the given position.
Panics if position is out of range.
func (Grouping) TransformEnd ¶
func (g Grouping) TransformEnd(f Transformer[lexer.Token]) Node
func (Grouping) TransformStart ¶
func (g Grouping) TransformStart(f Transformer[lexer.Token]) Node
type Having ¶
type Having struct { Having lexer.Token Condition Node // Oracle accepts HAVING before GROUP BY. // See. https://docs.oracle.com/cd/E11882_01/server.112/e41084/statements_10002.htm#i2065777 GroupBy Node }
Having holds a HAVING SQL statement.
func (Having) TransformEnd ¶
func (h Having) TransformEnd(f Transformer[lexer.Token]) Node
func (Having) TransformStart ¶
func (h Having) TransformStart(f Transformer[lexer.Token]) Node
type Infix ¶
Infix is a node with an operator with left and right operands. e.g. 1 + 2, 3 OR 4
func (Infix) Rebalance ¶
Rebalance ensure tip of Infix chain of same operator starts with first item. Assumes that Left is the chain of previous items.
func (Infix) TransformEnd ¶
func (i Infix) TransformEnd(f Transformer[lexer.Token]) Node
func (Infix) TransformStart ¶
func (i Infix) TransformStart(f Transformer[lexer.Token]) Node
type Join ¶
type Join struct { // Left table is previous table in From. Join []lexer.Token Right Node // Right table, not join direction. Condition Node // nil or an [ast.Where] clause with ON or USING keyword. }
Join holds an explicit JOIN clause.
func (Join) TransformEnd ¶
func (j Join) TransformEnd(f Transformer[lexer.Token]) Node
func (Join) TransformStart ¶
func (j Join) TransformStart(f Transformer[lexer.Token]) Node
type Leaf ¶
Leaf is a single token node without children.
func (Leaf) IsIdentifier ¶
IsIdentifier reports whether the token is an identifier.
func (Leaf) TransformEnd ¶
func (a Leaf) TransformEnd(f Transformer[lexer.Token]) Node
func (Leaf) TransformStart ¶
func (a Leaf) TransformStart(f Transformer[lexer.Token]) Node
type Limit ¶
Limit holds a LIMIT clause.
func (Limit) TransformEnd ¶
func (l Limit) TransformEnd(f Transformer[lexer.Token]) Node
func (Limit) TransformStart ¶
func (l Limit) TransformStart(f Transformer[lexer.Token]) Node
type LiteralCast ¶
LiteralCast is a node with a type and a string literal. e.g. date '2020-01-01' or interval '1 day'
func (LiteralCast) Tokens ¶
func (c LiteralCast) Tokens() []lexer.Token
func (LiteralCast) TransformEnd ¶
func (c LiteralCast) TransformEnd(f Transformer[lexer.Token]) Node
func (LiteralCast) TransformStart ¶
func (c LiteralCast) TransformStart(f Transformer[lexer.Token]) Node
func (LiteralCast) Visit ¶
func (c LiteralCast) Visit(f Transformer[Node]) Node
type Node ¶
type Node interface { lexer.Tokener // Transform first token of the node. TransformStart(Transformer[lexer.Token]) Node // Transform last token of the node. TransformEnd(Transformer[lexer.Token]) Node // Depth-first traversal of the AST applying a transformation function. // Used to rewrite expressions. Visit(Transformer[Node]) Node }
Node is the base interface for all nodes in the AST.
func TransformColumnRef ¶
func TransformColumnRef(n Node, f Transformer[Node]) Node
TransformColumnRef applies a transformation to all column names in the WHERE clause.
Node passed to f is guaranteed to be a Leaf with an identifier token or an Infix with qualified column ref.
Example: <col> = 1, <t1.col> = <t2.col>, COALESCE(<column>)
type Offset ¶
Offset holds OFFSET clause of LIMIT.
func (Offset) TransformEnd ¶
func (o Offset) TransformEnd(f Transformer[lexer.Token]) Node
func (Offset) TransformStart ¶
func (o Offset) TransformStart(f Transformer[lexer.Token]) Node
type OrderBy ¶
func (OrderBy) TransformEnd ¶
func (o OrderBy) TransformEnd(f Transformer[lexer.Token]) Node
func (OrderBy) TransformStart ¶
func (o OrderBy) TransformStart(f Transformer[lexer.Token]) Node
type OrderCriterium ¶
type OrderCriterium struct { Expression Node // { ASC | DESC | USING operator } [ NULLS { FIRST | LAST } ] Tail []lexer.Token }
func (OrderCriterium) Tokens ¶
func (o OrderCriterium) Tokens() []lexer.Token
func (OrderCriterium) TransformEnd ¶
func (o OrderCriterium) TransformEnd(f Transformer[lexer.Token]) Node
func (OrderCriterium) TransformStart ¶
func (o OrderCriterium) TransformStart(f Transformer[lexer.Token]) Node
func (OrderCriterium) Visit ¶
func (o OrderCriterium) Visit(f Transformer[Node]) Node
type Postfix ¶
Postfix is a node with a single operator and a left operand. e.g. mytable.column(+)
Also used as an item of comma separated list. The comma is stored in the Token field.
func (Postfix) RemoveOperator ¶
RemoveOperator removes the operator of the postfix node.
Move spacings before operator.
func (Postfix) SetOperator ¶
SetOperator sets the operator of the postfix node.
Move spacings after operator.
func (Postfix) TransformEnd ¶
func (p Postfix) TransformEnd(f Transformer[lexer.Token]) Node
func (Postfix) TransformStart ¶
func (p Postfix) TransformStart(f Transformer[lexer.Token]) Node
type Prefix ¶
Prefix is a node with an operator with a single operand after. e.g. NOT 1, -2
Prefix is used to hold item of AND list in ast.Where.
func (Prefix) RemoveOperator ¶
RemoveOperator removes the operator of the prefix node.
Move operator prefix to expression.
func (Prefix) SetOperator ¶
SetOperator sets the operator of the prefix node.
Move spacings before operator.
func (Prefix) TransformEnd ¶
func (p Prefix) TransformEnd(f Transformer[lexer.Token]) Node
func (Prefix) TransformStart ¶
func (p Prefix) TransformStart(f Transformer[lexer.Token]) Node
type Search ¶
Search holds the SEARCH clause of CTE.
func (Search) TransformEnd ¶
func (s Search) TransformEnd(f Transformer[lexer.Token]) Node
func (Search) TransformStart ¶
func (s Search) TransformStart(f Transformer[lexer.Token]) Node
type Select ¶
type Select struct { With With Select []lexer.Token Distinct Clause // List is a Grouping only for more than one column. // This way, SELECT * or SELECT <scalar> have simpler tree. // It's easier to not have to check for Grouping in rules. List Node From From Where Where Hierarchy Node // May be an [ast.ConnectBy] or [ast.StartWith] GroupBy Node // May be an [ast.Having] for Oracle HAVING before GROUP BY. OrderBy Node Limit Node // May be [ast.Limit], [ast.Offset] or [ast.Fetch] }
Select holds a SELECT query.
func (Select) ColumnNames ¶
ColumnNames lists the names of the columns in the SELECT clause.
func (Select) IsStar ¶
IsStar reports whether SELECT returns *.
It's use to determine whether the FROM order is important.
func (Select) TransformEnd ¶
func (s Select) TransformEnd(f Transformer[lexer.Token]) Node
func (Select) TransformStart ¶
func (s Select) TransformStart(f Transformer[lexer.Token]) Node
type StartWith ¶
func (StartWith) TransformEnd ¶
func (s StartWith) TransformEnd(f Transformer[lexer.Token]) Node
func (StartWith) TransformStart ¶
func (s StartWith) TransformStart(f Transformer[lexer.Token]) Node
type Statement ¶
Statement is a single expression followed by a semi-colon.
func (Statement) TransformEnd ¶
func (s Statement) TransformEnd(f Transformer[lexer.Token]) Node
func (Statement) TransformStart ¶
func (s Statement) TransformStart(f Transformer[lexer.Token]) Node
type Statements ¶
Statements is a list of statements until EOF.
func (Statements) Tokens ¶
func (s Statements) Tokens() []lexer.Token
func (Statements) TransformEnd ¶
func (s Statements) TransformEnd(f Transformer[lexer.Token]) Node
func (Statements) TransformStart ¶
func (s Statements) TransformStart(f Transformer[lexer.Token]) Node
TransformStart applies a transformation to the first token of the node.
func (Statements) Visit ¶
func (s Statements) Visit(f Transformer[Node]) Node
type Transformer ¶
type Transformer[T any] func(T) T
Transformer is a function that transforms a value into another.
type When ¶
When is the WHEN-THEN clause of a CASE statement.
func (When) TransformEnd ¶
func (w When) TransformEnd(f Transformer[lexer.Token]) Node
func (When) TransformStart ¶
func (w When) TransformStart(f Transformer[lexer.Token]) Node
type Where ¶
Where is a SQL WHERE clause.
func (*Where) Append ¶
Append adds an existing WHERE item.
Handles whether AND operator must be added or removed. Preserves spacings.
func (Where) TransformEnd ¶
func (w Where) TransformEnd(f Transformer[lexer.Token]) Node
func (Where) TransformStart ¶
func (w Where) TransformStart(f Transformer[lexer.Token]) Node
type With ¶
With holds Common Table Expressions.
func (With) TransformEnd ¶
func (w With) TransformEnd(f Transformer[lexer.Token]) Node
func (With) TransformStart ¶
func (w With) TransformStart(f Transformer[lexer.Token]) Node