|
6 | 6 | import sqlglot.dialects.bigquery |
7 | 7 | import sqlglot.dialects.duckdb |
8 | 8 | import sqlglot.dialects.postgres |
9 | | -from sqlglot import Expression, exp, select |
10 | | -from sqlglot.helper import seq_get |
| 9 | +from sqlglot import exp, select, alias |
| 10 | +from sqlglot.expressions import Array, array |
11 | 11 |
|
12 | 12 | # Apply transformation monkey patches |
13 | 13 | # these modules are imported for their side effects |
@@ -47,6 +47,26 @@ def transpile_query(query: str, source_dialect: str="bigquery", destination_dial |
47 | 47 | quoted=False |
48 | 48 | ) |
49 | 49 |
|
| 50 | + # HACK: sqlglot has a GenerateSeries transpilation in v25.13.0, |
| 51 | + # which is inserted during the parse of BigQuery. However, it looks |
| 52 | + # incorrect for postgres (at least), as it swaps GENERATE_ARRAY for GENERATE_SERIES. |
| 53 | + # BigQuery's GENERATE_ARRAY outputs an array, but GENERATE_SERIES outputs exploded rows. |
| 54 | + # We will manually replace the GENERATE_SERIES call with an anonymous function, so our |
| 55 | + # custom transpile code can do the correct conversion for postgres. |
| 56 | + if (source_dialect == 'bigquery') and (destination_dialect == 'postgres'): |
| 57 | + for gs_function in sql_parsed.find_all(exp.GenerateSeries): |
| 58 | + # rename to our anonymous generate array function, so the |
| 59 | + # later loop will catch it |
| 60 | + gs_function.replace( |
| 61 | + exp.Anonymous( |
| 62 | + this='GENERATE_ARRAY', |
| 63 | + expressions=[ |
| 64 | + gs_function.args['start'], |
| 65 | + gs_function.args['end'] |
| 66 | + ] |
| 67 | + ) |
| 68 | + ) |
| 69 | + |
50 | 70 | # BigQuery has a few functions which are not in sqlglot, so we have |
51 | 71 | # created classes for them, and this loop replaces the anonymous functions |
52 | 72 | # with the named functions |
|
0 commit comments