Skip to content

Commit 43d9965

Browse files
authored
Fix 99 format roundtrip tests (#53)
1 parent eaf72c3 commit 43d9965

File tree

102 files changed

+1197
-103
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

102 files changed

+1197
-103
lines changed

internal/format/expressions.go

Lines changed: 251 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,44 @@ func Expression(sb *strings.Builder, expr ast.Expression) {
3030
formatAsterisk(sb, e)
3131
case *ast.AliasedExpr:
3232
formatAliasedExpr(sb, e)
33+
case *ast.Subquery:
34+
formatSubquery(sb, e)
35+
case *ast.LikeExpr:
36+
formatLikeExpr(sb, e)
37+
case *ast.CaseExpr:
38+
formatCaseExpr(sb, e)
39+
case *ast.CastExpr:
40+
formatCastExpr(sb, e)
41+
case *ast.InExpr:
42+
formatInExpr(sb, e)
43+
case *ast.BetweenExpr:
44+
formatBetweenExpr(sb, e)
45+
case *ast.IsNullExpr:
46+
formatIsNullExpr(sb, e)
47+
case *ast.TernaryExpr:
48+
formatTernaryExpr(sb, e)
49+
case *ast.ArrayAccess:
50+
formatArrayAccess(sb, e)
51+
case *ast.TupleAccess:
52+
formatTupleAccess(sb, e)
53+
case *ast.IntervalExpr:
54+
formatIntervalExpr(sb, e)
55+
case *ast.ExtractExpr:
56+
formatExtractExpr(sb, e)
57+
case *ast.Lambda:
58+
formatLambda(sb, e)
59+
case *ast.ColumnsMatcher:
60+
formatColumnsMatcher(sb, e)
61+
case *ast.WithElement:
62+
formatWithElement(sb, e)
63+
case *ast.ExistsExpr:
64+
formatExistsExpr(sb, e)
65+
case *ast.DataType:
66+
formatDataType(sb, e)
67+
case *ast.NameTypePair:
68+
formatNameTypePair(sb, e)
69+
case *ast.Parameter:
70+
formatParameter(sb, e)
3371
default:
3472
// Fallback for unhandled expressions
3573
sb.WriteString(fmt.Sprintf("%v", expr))
@@ -164,3 +202,216 @@ func formatAliasedExpr(sb *strings.Builder, a *ast.AliasedExpr) {
164202
sb.WriteString(" AS ")
165203
sb.WriteString(a.Alias)
166204
}
205+
206+
// formatSubquery formats a subquery expression.
207+
func formatSubquery(sb *strings.Builder, s *ast.Subquery) {
208+
sb.WriteString("(")
209+
Statement(sb, s.Query)
210+
sb.WriteString(")")
211+
}
212+
213+
// formatLikeExpr formats a LIKE expression.
214+
func formatLikeExpr(sb *strings.Builder, l *ast.LikeExpr) {
215+
Expression(sb, l.Expr)
216+
if l.Not {
217+
sb.WriteString(" NOT")
218+
}
219+
if l.CaseInsensitive {
220+
sb.WriteString(" ILIKE ")
221+
} else {
222+
sb.WriteString(" LIKE ")
223+
}
224+
Expression(sb, l.Pattern)
225+
}
226+
227+
// formatCaseExpr formats a CASE expression.
228+
func formatCaseExpr(sb *strings.Builder, c *ast.CaseExpr) {
229+
sb.WriteString("CASE")
230+
if c.Operand != nil {
231+
sb.WriteString(" ")
232+
Expression(sb, c.Operand)
233+
}
234+
for _, when := range c.Whens {
235+
sb.WriteString(" WHEN ")
236+
Expression(sb, when.Condition)
237+
sb.WriteString(" THEN ")
238+
Expression(sb, when.Result)
239+
}
240+
if c.Else != nil {
241+
sb.WriteString(" ELSE ")
242+
Expression(sb, c.Else)
243+
}
244+
sb.WriteString(" END")
245+
}
246+
247+
// formatCastExpr formats a CAST expression.
248+
func formatCastExpr(sb *strings.Builder, c *ast.CastExpr) {
249+
if c.OperatorSyntax {
250+
Expression(sb, c.Expr)
251+
sb.WriteString("::")
252+
formatDataType(sb, c.Type)
253+
} else {
254+
sb.WriteString("CAST(")
255+
Expression(sb, c.Expr)
256+
if c.UsedASSyntax {
257+
sb.WriteString(" AS ")
258+
formatDataType(sb, c.Type)
259+
} else if c.TypeExpr != nil {
260+
sb.WriteString(", ")
261+
Expression(sb, c.TypeExpr)
262+
} else if c.Type != nil {
263+
sb.WriteString(", '")
264+
sb.WriteString(c.Type.Name)
265+
sb.WriteString("'")
266+
}
267+
sb.WriteString(")")
268+
}
269+
}
270+
271+
// formatInExpr formats an IN expression.
272+
func formatInExpr(sb *strings.Builder, i *ast.InExpr) {
273+
Expression(sb, i.Expr)
274+
if i.Global {
275+
sb.WriteString(" GLOBAL")
276+
}
277+
if i.Not {
278+
sb.WriteString(" NOT IN ")
279+
} else {
280+
sb.WriteString(" IN ")
281+
}
282+
if i.Query != nil {
283+
sb.WriteString("(")
284+
Statement(sb, i.Query)
285+
sb.WriteString(")")
286+
} else {
287+
sb.WriteString("(")
288+
for j, e := range i.List {
289+
if j > 0 {
290+
sb.WriteString(", ")
291+
}
292+
Expression(sb, e)
293+
}
294+
sb.WriteString(")")
295+
}
296+
}
297+
298+
// formatBetweenExpr formats a BETWEEN expression.
299+
func formatBetweenExpr(sb *strings.Builder, b *ast.BetweenExpr) {
300+
Expression(sb, b.Expr)
301+
if b.Not {
302+
sb.WriteString(" NOT BETWEEN ")
303+
} else {
304+
sb.WriteString(" BETWEEN ")
305+
}
306+
Expression(sb, b.Low)
307+
sb.WriteString(" AND ")
308+
Expression(sb, b.High)
309+
}
310+
311+
// formatIsNullExpr formats an IS NULL expression.
312+
func formatIsNullExpr(sb *strings.Builder, i *ast.IsNullExpr) {
313+
Expression(sb, i.Expr)
314+
if i.Not {
315+
sb.WriteString(" IS NOT NULL")
316+
} else {
317+
sb.WriteString(" IS NULL")
318+
}
319+
}
320+
321+
// formatTernaryExpr formats a ternary expression.
322+
func formatTernaryExpr(sb *strings.Builder, t *ast.TernaryExpr) {
323+
Expression(sb, t.Condition)
324+
sb.WriteString(" ? ")
325+
Expression(sb, t.Then)
326+
sb.WriteString(" : ")
327+
Expression(sb, t.Else)
328+
}
329+
330+
// formatArrayAccess formats an array access expression.
331+
func formatArrayAccess(sb *strings.Builder, a *ast.ArrayAccess) {
332+
Expression(sb, a.Array)
333+
sb.WriteString("[")
334+
Expression(sb, a.Index)
335+
sb.WriteString("]")
336+
}
337+
338+
// formatTupleAccess formats a tuple access expression.
339+
func formatTupleAccess(sb *strings.Builder, t *ast.TupleAccess) {
340+
Expression(sb, t.Tuple)
341+
sb.WriteString(".")
342+
Expression(sb, t.Index)
343+
}
344+
345+
// formatIntervalExpr formats an INTERVAL expression.
346+
func formatIntervalExpr(sb *strings.Builder, i *ast.IntervalExpr) {
347+
sb.WriteString("INTERVAL ")
348+
Expression(sb, i.Value)
349+
sb.WriteString(" ")
350+
sb.WriteString(i.Unit)
351+
}
352+
353+
// formatExtractExpr formats an EXTRACT expression.
354+
func formatExtractExpr(sb *strings.Builder, e *ast.ExtractExpr) {
355+
sb.WriteString("EXTRACT(")
356+
sb.WriteString(e.Field)
357+
sb.WriteString(" FROM ")
358+
Expression(sb, e.From)
359+
sb.WriteString(")")
360+
}
361+
362+
// formatLambda formats a lambda expression.
363+
func formatLambda(sb *strings.Builder, l *ast.Lambda) {
364+
if len(l.Parameters) == 1 {
365+
sb.WriteString(l.Parameters[0])
366+
} else {
367+
sb.WriteString("(")
368+
for i, p := range l.Parameters {
369+
if i > 0 {
370+
sb.WriteString(", ")
371+
}
372+
sb.WriteString(p)
373+
}
374+
sb.WriteString(")")
375+
}
376+
sb.WriteString(" -> ")
377+
Expression(sb, l.Body)
378+
}
379+
380+
// formatColumnsMatcher formats a COLUMNS expression.
381+
func formatColumnsMatcher(sb *strings.Builder, c *ast.ColumnsMatcher) {
382+
sb.WriteString("COLUMNS('")
383+
sb.WriteString(c.Pattern)
384+
sb.WriteString("')")
385+
}
386+
387+
// formatWithElement formats a WITH element.
388+
func formatWithElement(sb *strings.Builder, w *ast.WithElement) {
389+
Expression(sb, w.Query)
390+
sb.WriteString(" AS ")
391+
sb.WriteString(w.Name)
392+
}
393+
394+
// formatExistsExpr formats an EXISTS expression.
395+
func formatExistsExpr(sb *strings.Builder, e *ast.ExistsExpr) {
396+
sb.WriteString("EXISTS (")
397+
Statement(sb, e.Query)
398+
sb.WriteString(")")
399+
}
400+
401+
// formatNameTypePair formats a name-type pair.
402+
func formatNameTypePair(sb *strings.Builder, n *ast.NameTypePair) {
403+
sb.WriteString(n.Name)
404+
sb.WriteString(" ")
405+
formatDataType(sb, n.Type)
406+
}
407+
408+
// formatParameter formats a parameter.
409+
func formatParameter(sb *strings.Builder, p *ast.Parameter) {
410+
sb.WriteString("{")
411+
sb.WriteString(p.Name)
412+
if p.Type != nil {
413+
sb.WriteString(":")
414+
formatDataType(sb, p.Type)
415+
}
416+
sb.WriteString("}")
417+
}

internal/format/format.go

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,39 @@ func Statement(sb *strings.Builder, stmt ast.Statement) {
3131
formatSelectWithUnionQuery(sb, s)
3232
case *ast.SelectQuery:
3333
formatSelectQuery(sb, s)
34+
case *ast.SelectIntersectExceptQuery:
35+
formatSelectIntersectExceptQuery(sb, s)
36+
case *ast.SetQuery:
37+
formatSetQuery(sb, s)
38+
case *ast.DropQuery:
39+
formatDropQuery(sb, s)
40+
case *ast.CreateQuery:
41+
formatCreateQuery(sb, s)
42+
case *ast.InsertQuery:
43+
formatInsertQuery(sb, s)
44+
case *ast.AlterQuery:
45+
formatAlterQuery(sb, s)
46+
case *ast.TruncateQuery:
47+
formatTruncateQuery(sb, s)
48+
case *ast.UseQuery:
49+
formatUseQuery(sb, s)
50+
case *ast.DescribeQuery:
51+
formatDescribeQuery(sb, s)
52+
case *ast.ShowQuery:
53+
formatShowQuery(sb, s)
54+
case *ast.ExplainQuery:
55+
formatExplainQuery(sb, s)
56+
case *ast.OptimizeQuery:
57+
formatOptimizeQuery(sb, s)
58+
case *ast.SystemQuery:
59+
formatSystemQuery(sb, s)
60+
case *ast.RenameQuery:
61+
formatRenameQuery(sb, s)
62+
case *ast.ExchangeQuery:
63+
formatExchangeQuery(sb, s)
64+
case *ast.ExistsQuery:
65+
formatExistsQueryStmt(sb, s)
3466
default:
35-
// For now, only handle SELECT statements
67+
// Fallback for unhandled statements
3668
}
3769
}

0 commit comments

Comments
 (0)