From f1c2dbe3b17a0d5edffbb65b85b642d0bb2756c5 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Tue, 19 Dec 2023 12:01:55 +0100 Subject: Merging upstream version 20.3.0. Signed-off-by: Daniel Baumann --- docs/sqlglot/dialects/presto.html | 1810 +++++++++++++++++++------------------ 1 file changed, 929 insertions(+), 881 deletions(-) (limited to 'docs/sqlglot/dialects/presto.html') diff --git a/docs/sqlglot/dialects/presto.html b/docs/sqlglot/dialects/presto.html index 7ba1b99..b397d12 100644 --- a/docs/sqlglot/dialects/presto.html +++ b/docs/sqlglot/dialects/presto.html @@ -3,7 +3,7 @@ - + sqlglot.dialects.presto API documentation @@ -117,6 +117,9 @@
  • LIMIT_ONLY_LITERALS
  • +
  • + SUPPORTS_SINGLE_ARG_CONCAT +
  • PROPERTIES_LOCATION
  • @@ -421,285 +424,301 @@ 186 return "" 187 188 -189class Presto(Dialect): -190 INDEX_OFFSET = 1 -191 NULL_ORDERING = "nulls_are_last" -192 TIME_FORMAT = MySQL.TIME_FORMAT -193 TIME_MAPPING = MySQL.TIME_MAPPING -194 STRICT_STRING_CONCAT = True -195 SUPPORTS_SEMI_ANTI_JOIN = False -196 TYPED_DIVISION = True +189def _to_int(expression: exp.Expression) -> exp.Expression: +190 if not expression.type: +191 from sqlglot.optimizer.annotate_types import annotate_types +192 +193 annotate_types(expression) +194 if expression.type and expression.type.this not in exp.DataType.INTEGER_TYPES: +195 return exp.cast(expression, to=exp.DataType.Type.BIGINT) +196 return expression 197 -198 # https://github.com/trinodb/trino/issues/17 -199 # https://github.com/trinodb/trino/issues/12289 -200 # https://github.com/prestodb/presto/issues/2863 -201 NORMALIZATION_STRATEGY = NormalizationStrategy.CASE_INSENSITIVE -202 -203 class Tokenizer(tokens.Tokenizer): -204 KEYWORDS = { -205 **tokens.Tokenizer.KEYWORDS, -206 "START": TokenType.BEGIN, -207 "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE, -208 "ROW": TokenType.STRUCT, -209 "IPADDRESS": TokenType.IPADDRESS, -210 "IPPREFIX": TokenType.IPPREFIX, -211 } +198 +199class Presto(Dialect): +200 INDEX_OFFSET = 1 +201 NULL_ORDERING = "nulls_are_last" +202 TIME_FORMAT = MySQL.TIME_FORMAT +203 TIME_MAPPING = MySQL.TIME_MAPPING +204 STRICT_STRING_CONCAT = True +205 SUPPORTS_SEMI_ANTI_JOIN = False +206 TYPED_DIVISION = True +207 +208 # https://github.com/trinodb/trino/issues/17 +209 # https://github.com/trinodb/trino/issues/12289 +210 # https://github.com/prestodb/presto/issues/2863 +211 NORMALIZATION_STRATEGY = NormalizationStrategy.CASE_INSENSITIVE 212 -213 class Parser(parser.Parser): -214 FUNCTIONS = { -215 **parser.Parser.FUNCTIONS, -216 "ARBITRARY": exp.AnyValue.from_arg_list, -217 "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list, -218 "APPROX_PERCENTILE": _approx_percentile, -219 "BITWISE_AND": binary_from_function(exp.BitwiseAnd), -220 "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)), -221 "BITWISE_OR": binary_from_function(exp.BitwiseOr), -222 "BITWISE_XOR": binary_from_function(exp.BitwiseXor), -223 "CARDINALITY": exp.ArraySize.from_arg_list, -224 "CONTAINS": exp.ArrayContains.from_arg_list, -225 "DATE_ADD": lambda args: exp.DateAdd( -226 this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0) -227 ), -228 "DATE_DIFF": lambda args: exp.DateDiff( -229 this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0) -230 ), -231 "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"), -232 "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"), -233 "DATE_TRUNC": date_trunc_to_time, -234 "ELEMENT_AT": _parse_element_at, -235 "FROM_HEX": exp.Unhex.from_arg_list, -236 "FROM_UNIXTIME": _from_unixtime, -237 "FROM_UTF8": lambda args: exp.Decode( -238 this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8") -239 ), -240 "NOW": exp.CurrentTimestamp.from_arg_list, -241 "REGEXP_EXTRACT": lambda args: exp.RegexpExtract( -242 this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2) -243 ), -244 "REGEXP_REPLACE": lambda args: exp.RegexpReplace( -245 this=seq_get(args, 0), -246 expression=seq_get(args, 1), -247 replacement=seq_get(args, 2) or exp.Literal.string(""), -248 ), -249 "ROW": exp.Struct.from_arg_list, -250 "SEQUENCE": exp.GenerateSeries.from_arg_list, -251 "SET_AGG": exp.ArrayUniqueAgg.from_arg_list, -252 "SPLIT_TO_MAP": exp.StrToMap.from_arg_list, -253 "STRPOS": lambda args: exp.StrPosition( -254 this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2) -255 ), -256 "TO_UNIXTIME": exp.TimeToUnix.from_arg_list, -257 "TO_HEX": exp.Hex.from_arg_list, -258 "TO_UTF8": lambda args: exp.Encode( -259 this=seq_get(args, 0), charset=exp.Literal.string("utf-8") -260 ), -261 } -262 -263 FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy() -264 FUNCTION_PARSERS.pop("TRIM") -265 -266 class Generator(generator.Generator): -267 INTERVAL_ALLOWS_PLURAL_FORM = False -268 JOIN_HINTS = False -269 TABLE_HINTS = False -270 QUERY_HINTS = False -271 IS_BOOL_ALLOWED = False -272 TZ_TO_WITH_TIME_ZONE = True -273 NVL2_SUPPORTED = False -274 STRUCT_DELIMITER = ("(", ")") -275 LIMIT_ONLY_LITERALS = True -276 -277 PROPERTIES_LOCATION = { -278 **generator.Generator.PROPERTIES_LOCATION, -279 exp.LocationProperty: exp.Properties.Location.UNSUPPORTED, -280 exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED, -281 } -282 -283 TYPE_MAPPING = { -284 **generator.Generator.TYPE_MAPPING, -285 exp.DataType.Type.INT: "INTEGER", -286 exp.DataType.Type.FLOAT: "REAL", -287 exp.DataType.Type.BINARY: "VARBINARY", -288 exp.DataType.Type.TEXT: "VARCHAR", -289 exp.DataType.Type.TIMETZ: "TIME", -290 exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP", -291 exp.DataType.Type.STRUCT: "ROW", -292 exp.DataType.Type.DATETIME: "TIMESTAMP", -293 exp.DataType.Type.DATETIME64: "TIMESTAMP", -294 } -295 -296 TRANSFORMS = { -297 **generator.Generator.TRANSFORMS, -298 exp.AnyValue: rename_func("ARBITRARY"), -299 exp.ApproxDistinct: _approx_distinct_sql, -300 exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"), -301 exp.ArgMax: rename_func("MAX_BY"), -302 exp.ArgMin: rename_func("MIN_BY"), -303 exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]", -304 exp.ArrayConcat: rename_func("CONCAT"), -305 exp.ArrayContains: rename_func("CONTAINS"), -306 exp.ArraySize: rename_func("CARDINALITY"), -307 exp.ArrayUniqueAgg: rename_func("SET_AGG"), -308 exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})", -309 exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})", -310 exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})", -311 exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})", -312 exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})", -313 exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})", -314 exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]), -315 exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP", -316 exp.DateAdd: lambda self, e: self.func( -317 "DATE_ADD", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this -318 ), -319 exp.DateDiff: lambda self, e: self.func( -320 "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this -321 ), -322 exp.DateStrToDate: datestrtodate_sql, -323 exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)", -324 exp.DateSub: lambda self, e: self.func( -325 "DATE_ADD", -326 exp.Literal.string(e.text("unit") or "day"), -327 e.expression * -1, -328 e.this, -329 ), -330 exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"), -331 exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)", -332 exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"), -333 exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'", -334 exp.First: _first_last_sql, -335 exp.Group: transforms.preprocess([transforms.unalias_group]), -336 exp.GroupConcat: lambda self, e: self.func( -337 "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator") -338 ), -339 exp.Hex: rename_func("TO_HEX"), -340 exp.If: if_sql(), -341 exp.ILike: no_ilike_sql, -342 exp.Initcap: _initcap_sql, -343 exp.ParseJSON: rename_func("JSON_PARSE"), -344 exp.Last: _first_last_sql, -345 exp.Lateral: _explode_to_unnest_sql, -346 exp.Left: left_to_substring_sql, -347 exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"), -348 exp.LogicalAnd: rename_func("BOOL_AND"), -349 exp.LogicalOr: rename_func("BOOL_OR"), -350 exp.Pivot: no_pivot_sql, -351 exp.Quantile: _quantile_sql, -352 exp.RegexpExtract: regexp_extract_sql, -353 exp.Right: right_to_substring_sql, -354 exp.SafeDivide: no_safe_divide_sql, -355 exp.Schema: _schema_sql, -356 exp.Select: transforms.preprocess( -357 [ -358 transforms.eliminate_qualify, -359 transforms.eliminate_distinct_on, -360 transforms.explode_to_unnest(1), -361 transforms.eliminate_semi_and_anti_joins, -362 ] -363 ), -364 exp.SortArray: _no_sort_array, -365 exp.StrPosition: rename_func("STRPOS"), -366 exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)", -367 exp.StrToMap: rename_func("SPLIT_TO_MAP"), -368 exp.StrToTime: _str_to_time_sql, -369 exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))", -370 exp.StructExtract: struct_extract_sql, -371 exp.Table: transforms.preprocess([_unnest_sequence]), -372 exp.Timestamp: no_timestamp_sql, -373 exp.TimestampTrunc: timestamptrunc_sql, -374 exp.TimeStrToDate: timestrtotime_sql, -375 exp.TimeStrToTime: timestrtotime_sql, -376 exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))", -377 exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})", -378 exp.TimeToUnix: rename_func("TO_UNIXTIME"), -379 exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]), -380 exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)", -381 exp.TsOrDsAdd: _ts_or_ds_add_sql, -382 exp.TsOrDsDiff: _ts_or_ds_diff_sql, -383 exp.TsOrDsToDate: _ts_or_ds_to_date_sql, -384 exp.Unhex: rename_func("FROM_HEX"), -385 exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})", -386 exp.UnixToTime: _unix_to_time_sql, -387 exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)", -388 exp.VariancePop: rename_func("VAR_POP"), -389 exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]), -390 exp.WithinGroup: transforms.preprocess( -391 [transforms.remove_within_group_for_percentiles] -392 ), -393 exp.Xor: bool_xor_sql, -394 } -395 -396 def bracket_sql(self, expression: exp.Bracket) -> str: -397 if expression.args.get("safe"): -398 return self.func( -399 "ELEMENT_AT", -400 expression.this, -401 seq_get( -402 apply_index_offset( -403 expression.this, -404 expression.expressions, -405 1 - expression.args.get("offset", 0), -406 ), -407 0, -408 ), -409 ) -410 return super().bracket_sql(expression) +213 class Tokenizer(tokens.Tokenizer): +214 KEYWORDS = { +215 **tokens.Tokenizer.KEYWORDS, +216 "START": TokenType.BEGIN, +217 "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE, +218 "ROW": TokenType.STRUCT, +219 "IPADDRESS": TokenType.IPADDRESS, +220 "IPPREFIX": TokenType.IPPREFIX, +221 } +222 +223 class Parser(parser.Parser): +224 FUNCTIONS = { +225 **parser.Parser.FUNCTIONS, +226 "ARBITRARY": exp.AnyValue.from_arg_list, +227 "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list, +228 "APPROX_PERCENTILE": _approx_percentile, +229 "BITWISE_AND": binary_from_function(exp.BitwiseAnd), +230 "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)), +231 "BITWISE_OR": binary_from_function(exp.BitwiseOr), +232 "BITWISE_XOR": binary_from_function(exp.BitwiseXor), +233 "CARDINALITY": exp.ArraySize.from_arg_list, +234 "CONTAINS": exp.ArrayContains.from_arg_list, +235 "DATE_ADD": lambda args: exp.DateAdd( +236 this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0) +237 ), +238 "DATE_DIFF": lambda args: exp.DateDiff( +239 this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0) +240 ), +241 "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"), +242 "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"), +243 "DATE_TRUNC": date_trunc_to_time, +244 "ELEMENT_AT": _parse_element_at, +245 "FROM_HEX": exp.Unhex.from_arg_list, +246 "FROM_UNIXTIME": _from_unixtime, +247 "FROM_UTF8": lambda args: exp.Decode( +248 this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8") +249 ), +250 "NOW": exp.CurrentTimestamp.from_arg_list, +251 "REGEXP_EXTRACT": lambda args: exp.RegexpExtract( +252 this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2) +253 ), +254 "REGEXP_REPLACE": lambda args: exp.RegexpReplace( +255 this=seq_get(args, 0), +256 expression=seq_get(args, 1), +257 replacement=seq_get(args, 2) or exp.Literal.string(""), +258 ), +259 "ROW": exp.Struct.from_arg_list, +260 "SEQUENCE": exp.GenerateSeries.from_arg_list, +261 "SET_AGG": exp.ArrayUniqueAgg.from_arg_list, +262 "SPLIT_TO_MAP": exp.StrToMap.from_arg_list, +263 "STRPOS": lambda args: exp.StrPosition( +264 this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2) +265 ), +266 "TO_UNIXTIME": exp.TimeToUnix.from_arg_list, +267 "TO_HEX": exp.Hex.from_arg_list, +268 "TO_UTF8": lambda args: exp.Encode( +269 this=seq_get(args, 0), charset=exp.Literal.string("utf-8") +270 ), +271 } +272 +273 FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy() +274 FUNCTION_PARSERS.pop("TRIM") +275 +276 class Generator(generator.Generator): +277 INTERVAL_ALLOWS_PLURAL_FORM = False +278 JOIN_HINTS = False +279 TABLE_HINTS = False +280 QUERY_HINTS = False +281 IS_BOOL_ALLOWED = False +282 TZ_TO_WITH_TIME_ZONE = True +283 NVL2_SUPPORTED = False +284 STRUCT_DELIMITER = ("(", ")") +285 LIMIT_ONLY_LITERALS = True +286 SUPPORTS_SINGLE_ARG_CONCAT = False +287 +288 PROPERTIES_LOCATION = { +289 **generator.Generator.PROPERTIES_LOCATION, +290 exp.LocationProperty: exp.Properties.Location.UNSUPPORTED, +291 exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED, +292 } +293 +294 TYPE_MAPPING = { +295 **generator.Generator.TYPE_MAPPING, +296 exp.DataType.Type.INT: "INTEGER", +297 exp.DataType.Type.FLOAT: "REAL", +298 exp.DataType.Type.BINARY: "VARBINARY", +299 exp.DataType.Type.TEXT: "VARCHAR", +300 exp.DataType.Type.TIMETZ: "TIME", +301 exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP", +302 exp.DataType.Type.STRUCT: "ROW", +303 exp.DataType.Type.DATETIME: "TIMESTAMP", +304 exp.DataType.Type.DATETIME64: "TIMESTAMP", +305 } +306 +307 TRANSFORMS = { +308 **generator.Generator.TRANSFORMS, +309 exp.AnyValue: rename_func("ARBITRARY"), +310 exp.ApproxDistinct: _approx_distinct_sql, +311 exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"), +312 exp.ArgMax: rename_func("MAX_BY"), +313 exp.ArgMin: rename_func("MIN_BY"), +314 exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]", +315 exp.ArrayConcat: rename_func("CONCAT"), +316 exp.ArrayContains: rename_func("CONTAINS"), +317 exp.ArraySize: rename_func("CARDINALITY"), +318 exp.ArrayUniqueAgg: rename_func("SET_AGG"), +319 exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})", +320 exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})", +321 exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})", +322 exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})", +323 exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})", +324 exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})", +325 exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]), +326 exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP", +327 exp.DateAdd: lambda self, e: self.func( +328 "DATE_ADD", +329 exp.Literal.string(e.text("unit") or "day"), +330 _to_int( +331 e.expression, +332 ), +333 e.this, +334 ), +335 exp.DateDiff: lambda self, e: self.func( +336 "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this +337 ), +338 exp.DateStrToDate: datestrtodate_sql, +339 exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)", +340 exp.DateSub: lambda self, e: self.func( +341 "DATE_ADD", +342 exp.Literal.string(e.text("unit") or "day"), +343 _to_int(e.expression * -1), +344 e.this, +345 ), +346 exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"), +347 exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)", +348 exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"), +349 exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'", +350 exp.First: _first_last_sql, +351 exp.Group: transforms.preprocess([transforms.unalias_group]), +352 exp.GroupConcat: lambda self, e: self.func( +353 "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator") +354 ), +355 exp.Hex: rename_func("TO_HEX"), +356 exp.If: if_sql(), +357 exp.ILike: no_ilike_sql, +358 exp.Initcap: _initcap_sql, +359 exp.ParseJSON: rename_func("JSON_PARSE"), +360 exp.Last: _first_last_sql, +361 exp.Lateral: _explode_to_unnest_sql, +362 exp.Left: left_to_substring_sql, +363 exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"), +364 exp.LogicalAnd: rename_func("BOOL_AND"), +365 exp.LogicalOr: rename_func("BOOL_OR"), +366 exp.Pivot: no_pivot_sql, +367 exp.Quantile: _quantile_sql, +368 exp.RegexpExtract: regexp_extract_sql, +369 exp.Right: right_to_substring_sql, +370 exp.SafeDivide: no_safe_divide_sql, +371 exp.Schema: _schema_sql, +372 exp.Select: transforms.preprocess( +373 [ +374 transforms.eliminate_qualify, +375 transforms.eliminate_distinct_on, +376 transforms.explode_to_unnest(1), +377 transforms.eliminate_semi_and_anti_joins, +378 ] +379 ), +380 exp.SortArray: _no_sort_array, +381 exp.StrPosition: rename_func("STRPOS"), +382 exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)", +383 exp.StrToMap: rename_func("SPLIT_TO_MAP"), +384 exp.StrToTime: _str_to_time_sql, +385 exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))", +386 exp.StructExtract: struct_extract_sql, +387 exp.Table: transforms.preprocess([_unnest_sequence]), +388 exp.Timestamp: no_timestamp_sql, +389 exp.TimestampTrunc: timestamptrunc_sql, +390 exp.TimeStrToDate: timestrtotime_sql, +391 exp.TimeStrToTime: timestrtotime_sql, +392 exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))", +393 exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})", +394 exp.TimeToUnix: rename_func("TO_UNIXTIME"), +395 exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]), +396 exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)", +397 exp.TsOrDsAdd: _ts_or_ds_add_sql, +398 exp.TsOrDsDiff: _ts_or_ds_diff_sql, +399 exp.TsOrDsToDate: _ts_or_ds_to_date_sql, +400 exp.Unhex: rename_func("FROM_HEX"), +401 exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})", +402 exp.UnixToTime: _unix_to_time_sql, +403 exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)", +404 exp.VariancePop: rename_func("VAR_POP"), +405 exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]), +406 exp.WithinGroup: transforms.preprocess( +407 [transforms.remove_within_group_for_percentiles] +408 ), +409 exp.Xor: bool_xor_sql, +410 } 411 -412 def struct_sql(self, expression: exp.Struct) -> str: -413 if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions): -414 self.unsupported("Struct with key-value definitions is unsupported.") -415 return self.function_fallback_sql(expression) -416 -417 return rename_func("ROW")(self, expression) -418 -419 def interval_sql(self, expression: exp.Interval) -> str: -420 unit = self.sql(expression, "unit") -421 if expression.this and unit.lower().startswith("week"): -422 return f"({expression.this.name} * INTERVAL '7' day)" -423 return super().interval_sql(expression) -424 -425 def transaction_sql(self, expression: exp.Transaction) -> str: -426 modes = expression.args.get("modes") -427 modes = f" {', '.join(modes)}" if modes else "" -428 return f"START TRANSACTION{modes}" -429 -430 def generateseries_sql(self, expression: exp.GenerateSeries) -> str: -431 start = expression.args["start"] -432 end = expression.args["end"] -433 step = expression.args.get("step") +412 def bracket_sql(self, expression: exp.Bracket) -> str: +413 if expression.args.get("safe"): +414 return self.func( +415 "ELEMENT_AT", +416 expression.this, +417 seq_get( +418 apply_index_offset( +419 expression.this, +420 expression.expressions, +421 1 - expression.args.get("offset", 0), +422 ), +423 0, +424 ), +425 ) +426 return super().bracket_sql(expression) +427 +428 def struct_sql(self, expression: exp.Struct) -> str: +429 if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions): +430 self.unsupported("Struct with key-value definitions is unsupported.") +431 return self.function_fallback_sql(expression) +432 +433 return rename_func("ROW")(self, expression) 434 -435 if isinstance(start, exp.Cast): -436 target_type = start.to -437 elif isinstance(end, exp.Cast): -438 target_type = end.to -439 else: -440 target_type = None -441 -442 if target_type and target_type.is_type("timestamp"): -443 if target_type is start.to: -444 end = exp.cast(end, target_type) -445 else: -446 start = exp.cast(start, target_type) -447 -448 return self.func("SEQUENCE", start, end, step) -449 -450 def offset_limit_modifiers( -451 self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit] -452 ) -> t.List[str]: -453 return [ -454 self.sql(expression, "offset"), -455 self.sql(limit), -456 ] +435 def interval_sql(self, expression: exp.Interval) -> str: +436 unit = self.sql(expression, "unit") +437 if expression.this and unit.lower().startswith("week"): +438 return f"({expression.this.name} * INTERVAL '7' day)" +439 return super().interval_sql(expression) +440 +441 def transaction_sql(self, expression: exp.Transaction) -> str: +442 modes = expression.args.get("modes") +443 modes = f" {', '.join(modes)}" if modes else "" +444 return f"START TRANSACTION{modes}" +445 +446 def generateseries_sql(self, expression: exp.GenerateSeries) -> str: +447 start = expression.args["start"] +448 end = expression.args["end"] +449 step = expression.args.get("step") +450 +451 if isinstance(start, exp.Cast): +452 target_type = start.to +453 elif isinstance(end, exp.Cast): +454 target_type = end.to +455 else: +456 target_type = None 457 -458 def create_sql(self, expression: exp.Create) -> str: -459 """ -460 Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression), -461 so we need to remove them -462 """ -463 kind = expression.args["kind"] -464 schema = expression.this -465 if kind == "VIEW" and schema.expressions: -466 expression.this.set("expressions", None) -467 return super().create_sql(expression) +458 if target_type and target_type.is_type("timestamp"): +459 if target_type is start.to: +460 end = exp.cast(end, target_type) +461 else: +462 start = exp.cast(start, target_type) +463 +464 return self.func("SEQUENCE", start, end, step) +465 +466 def offset_limit_modifiers( +467 self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit] +468 ) -> t.List[str]: +469 return [ +470 self.sql(expression, "offset"), +471 self.sql(limit), +472 ] +473 +474 def create_sql(self, expression: exp.Create) -> str: +475 """ +476 Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression), +477 so we need to remove them +478 """ +479 kind = expression.args["kind"] +480 schema = expression.this +481 if kind == "VIEW" and schema.expressions: +482 expression.this.set("expressions", None) +483 return super().create_sql(expression) @@ -715,285 +734,291 @@ -
    190class Presto(Dialect):
    -191    INDEX_OFFSET = 1
    -192    NULL_ORDERING = "nulls_are_last"
    -193    TIME_FORMAT = MySQL.TIME_FORMAT
    -194    TIME_MAPPING = MySQL.TIME_MAPPING
    -195    STRICT_STRING_CONCAT = True
    -196    SUPPORTS_SEMI_ANTI_JOIN = False
    -197    TYPED_DIVISION = True
    -198
    -199    # https://github.com/trinodb/trino/issues/17
    -200    # https://github.com/trinodb/trino/issues/12289
    -201    # https://github.com/prestodb/presto/issues/2863
    -202    NORMALIZATION_STRATEGY = NormalizationStrategy.CASE_INSENSITIVE
    -203
    -204    class Tokenizer(tokens.Tokenizer):
    -205        KEYWORDS = {
    -206            **tokens.Tokenizer.KEYWORDS,
    -207            "START": TokenType.BEGIN,
    -208            "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE,
    -209            "ROW": TokenType.STRUCT,
    -210            "IPADDRESS": TokenType.IPADDRESS,
    -211            "IPPREFIX": TokenType.IPPREFIX,
    -212        }
    +            
    200class Presto(Dialect):
    +201    INDEX_OFFSET = 1
    +202    NULL_ORDERING = "nulls_are_last"
    +203    TIME_FORMAT = MySQL.TIME_FORMAT
    +204    TIME_MAPPING = MySQL.TIME_MAPPING
    +205    STRICT_STRING_CONCAT = True
    +206    SUPPORTS_SEMI_ANTI_JOIN = False
    +207    TYPED_DIVISION = True
    +208
    +209    # https://github.com/trinodb/trino/issues/17
    +210    # https://github.com/trinodb/trino/issues/12289
    +211    # https://github.com/prestodb/presto/issues/2863
    +212    NORMALIZATION_STRATEGY = NormalizationStrategy.CASE_INSENSITIVE
     213
    -214    class Parser(parser.Parser):
    -215        FUNCTIONS = {
    -216            **parser.Parser.FUNCTIONS,
    -217            "ARBITRARY": exp.AnyValue.from_arg_list,
    -218            "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list,
    -219            "APPROX_PERCENTILE": _approx_percentile,
    -220            "BITWISE_AND": binary_from_function(exp.BitwiseAnd),
    -221            "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)),
    -222            "BITWISE_OR": binary_from_function(exp.BitwiseOr),
    -223            "BITWISE_XOR": binary_from_function(exp.BitwiseXor),
    -224            "CARDINALITY": exp.ArraySize.from_arg_list,
    -225            "CONTAINS": exp.ArrayContains.from_arg_list,
    -226            "DATE_ADD": lambda args: exp.DateAdd(
    -227                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    -228            ),
    -229            "DATE_DIFF": lambda args: exp.DateDiff(
    -230                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    -231            ),
    -232            "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"),
    -233            "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"),
    -234            "DATE_TRUNC": date_trunc_to_time,
    -235            "ELEMENT_AT": _parse_element_at,
    -236            "FROM_HEX": exp.Unhex.from_arg_list,
    -237            "FROM_UNIXTIME": _from_unixtime,
    -238            "FROM_UTF8": lambda args: exp.Decode(
    -239                this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8")
    -240            ),
    -241            "NOW": exp.CurrentTimestamp.from_arg_list,
    -242            "REGEXP_EXTRACT": lambda args: exp.RegexpExtract(
    -243                this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2)
    -244            ),
    -245            "REGEXP_REPLACE": lambda args: exp.RegexpReplace(
    -246                this=seq_get(args, 0),
    -247                expression=seq_get(args, 1),
    -248                replacement=seq_get(args, 2) or exp.Literal.string(""),
    -249            ),
    -250            "ROW": exp.Struct.from_arg_list,
    -251            "SEQUENCE": exp.GenerateSeries.from_arg_list,
    -252            "SET_AGG": exp.ArrayUniqueAgg.from_arg_list,
    -253            "SPLIT_TO_MAP": exp.StrToMap.from_arg_list,
    -254            "STRPOS": lambda args: exp.StrPosition(
    -255                this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2)
    -256            ),
    -257            "TO_UNIXTIME": exp.TimeToUnix.from_arg_list,
    -258            "TO_HEX": exp.Hex.from_arg_list,
    -259            "TO_UTF8": lambda args: exp.Encode(
    -260                this=seq_get(args, 0), charset=exp.Literal.string("utf-8")
    -261            ),
    -262        }
    -263
    -264        FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy()
    -265        FUNCTION_PARSERS.pop("TRIM")
    -266
    -267    class Generator(generator.Generator):
    -268        INTERVAL_ALLOWS_PLURAL_FORM = False
    -269        JOIN_HINTS = False
    -270        TABLE_HINTS = False
    -271        QUERY_HINTS = False
    -272        IS_BOOL_ALLOWED = False
    -273        TZ_TO_WITH_TIME_ZONE = True
    -274        NVL2_SUPPORTED = False
    -275        STRUCT_DELIMITER = ("(", ")")
    -276        LIMIT_ONLY_LITERALS = True
    -277
    -278        PROPERTIES_LOCATION = {
    -279            **generator.Generator.PROPERTIES_LOCATION,
    -280            exp.LocationProperty: exp.Properties.Location.UNSUPPORTED,
    -281            exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED,
    -282        }
    -283
    -284        TYPE_MAPPING = {
    -285            **generator.Generator.TYPE_MAPPING,
    -286            exp.DataType.Type.INT: "INTEGER",
    -287            exp.DataType.Type.FLOAT: "REAL",
    -288            exp.DataType.Type.BINARY: "VARBINARY",
    -289            exp.DataType.Type.TEXT: "VARCHAR",
    -290            exp.DataType.Type.TIMETZ: "TIME",
    -291            exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP",
    -292            exp.DataType.Type.STRUCT: "ROW",
    -293            exp.DataType.Type.DATETIME: "TIMESTAMP",
    -294            exp.DataType.Type.DATETIME64: "TIMESTAMP",
    -295        }
    -296
    -297        TRANSFORMS = {
    -298            **generator.Generator.TRANSFORMS,
    -299            exp.AnyValue: rename_func("ARBITRARY"),
    -300            exp.ApproxDistinct: _approx_distinct_sql,
    -301            exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"),
    -302            exp.ArgMax: rename_func("MAX_BY"),
    -303            exp.ArgMin: rename_func("MIN_BY"),
    -304            exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]",
    -305            exp.ArrayConcat: rename_func("CONCAT"),
    -306            exp.ArrayContains: rename_func("CONTAINS"),
    -307            exp.ArraySize: rename_func("CARDINALITY"),
    -308            exp.ArrayUniqueAgg: rename_func("SET_AGG"),
    -309            exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -310            exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -311            exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})",
    -312            exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -313            exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -314            exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -315            exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    -316            exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP",
    -317            exp.DateAdd: lambda self, e: self.func(
    -318                "DATE_ADD", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    -319            ),
    -320            exp.DateDiff: lambda self, e: self.func(
    -321                "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    -322            ),
    -323            exp.DateStrToDate: datestrtodate_sql,
    -324            exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)",
    -325            exp.DateSub: lambda self, e: self.func(
    -326                "DATE_ADD",
    -327                exp.Literal.string(e.text("unit") or "day"),
    -328                e.expression * -1,
    -329                e.this,
    -330            ),
    -331            exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"),
    -332            exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)",
    -333            exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"),
    -334            exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'",
    -335            exp.First: _first_last_sql,
    -336            exp.Group: transforms.preprocess([transforms.unalias_group]),
    -337            exp.GroupConcat: lambda self, e: self.func(
    -338                "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator")
    -339            ),
    -340            exp.Hex: rename_func("TO_HEX"),
    -341            exp.If: if_sql(),
    -342            exp.ILike: no_ilike_sql,
    -343            exp.Initcap: _initcap_sql,
    -344            exp.ParseJSON: rename_func("JSON_PARSE"),
    -345            exp.Last: _first_last_sql,
    -346            exp.Lateral: _explode_to_unnest_sql,
    -347            exp.Left: left_to_substring_sql,
    -348            exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"),
    -349            exp.LogicalAnd: rename_func("BOOL_AND"),
    -350            exp.LogicalOr: rename_func("BOOL_OR"),
    -351            exp.Pivot: no_pivot_sql,
    -352            exp.Quantile: _quantile_sql,
    -353            exp.RegexpExtract: regexp_extract_sql,
    -354            exp.Right: right_to_substring_sql,
    -355            exp.SafeDivide: no_safe_divide_sql,
    -356            exp.Schema: _schema_sql,
    -357            exp.Select: transforms.preprocess(
    -358                [
    -359                    transforms.eliminate_qualify,
    -360                    transforms.eliminate_distinct_on,
    -361                    transforms.explode_to_unnest(1),
    -362                    transforms.eliminate_semi_and_anti_joins,
    -363                ]
    -364            ),
    -365            exp.SortArray: _no_sort_array,
    -366            exp.StrPosition: rename_func("STRPOS"),
    -367            exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)",
    -368            exp.StrToMap: rename_func("SPLIT_TO_MAP"),
    -369            exp.StrToTime: _str_to_time_sql,
    -370            exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))",
    -371            exp.StructExtract: struct_extract_sql,
    -372            exp.Table: transforms.preprocess([_unnest_sequence]),
    -373            exp.Timestamp: no_timestamp_sql,
    -374            exp.TimestampTrunc: timestamptrunc_sql,
    -375            exp.TimeStrToDate: timestrtotime_sql,
    -376            exp.TimeStrToTime: timestrtotime_sql,
    -377            exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))",
    -378            exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})",
    -379            exp.TimeToUnix: rename_func("TO_UNIXTIME"),
    -380            exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    -381            exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)",
    -382            exp.TsOrDsAdd: _ts_or_ds_add_sql,
    -383            exp.TsOrDsDiff: _ts_or_ds_diff_sql,
    -384            exp.TsOrDsToDate: _ts_or_ds_to_date_sql,
    -385            exp.Unhex: rename_func("FROM_HEX"),
    -386            exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})",
    -387            exp.UnixToTime: _unix_to_time_sql,
    -388            exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)",
    -389            exp.VariancePop: rename_func("VAR_POP"),
    -390            exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]),
    -391            exp.WithinGroup: transforms.preprocess(
    -392                [transforms.remove_within_group_for_percentiles]
    -393            ),
    -394            exp.Xor: bool_xor_sql,
    -395        }
    -396
    -397        def bracket_sql(self, expression: exp.Bracket) -> str:
    -398            if expression.args.get("safe"):
    -399                return self.func(
    -400                    "ELEMENT_AT",
    -401                    expression.this,
    -402                    seq_get(
    -403                        apply_index_offset(
    -404                            expression.this,
    -405                            expression.expressions,
    -406                            1 - expression.args.get("offset", 0),
    -407                        ),
    -408                        0,
    -409                    ),
    -410                )
    -411            return super().bracket_sql(expression)
    +214    class Tokenizer(tokens.Tokenizer):
    +215        KEYWORDS = {
    +216            **tokens.Tokenizer.KEYWORDS,
    +217            "START": TokenType.BEGIN,
    +218            "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE,
    +219            "ROW": TokenType.STRUCT,
    +220            "IPADDRESS": TokenType.IPADDRESS,
    +221            "IPPREFIX": TokenType.IPPREFIX,
    +222        }
    +223
    +224    class Parser(parser.Parser):
    +225        FUNCTIONS = {
    +226            **parser.Parser.FUNCTIONS,
    +227            "ARBITRARY": exp.AnyValue.from_arg_list,
    +228            "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list,
    +229            "APPROX_PERCENTILE": _approx_percentile,
    +230            "BITWISE_AND": binary_from_function(exp.BitwiseAnd),
    +231            "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)),
    +232            "BITWISE_OR": binary_from_function(exp.BitwiseOr),
    +233            "BITWISE_XOR": binary_from_function(exp.BitwiseXor),
    +234            "CARDINALITY": exp.ArraySize.from_arg_list,
    +235            "CONTAINS": exp.ArrayContains.from_arg_list,
    +236            "DATE_ADD": lambda args: exp.DateAdd(
    +237                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    +238            ),
    +239            "DATE_DIFF": lambda args: exp.DateDiff(
    +240                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    +241            ),
    +242            "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"),
    +243            "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"),
    +244            "DATE_TRUNC": date_trunc_to_time,
    +245            "ELEMENT_AT": _parse_element_at,
    +246            "FROM_HEX": exp.Unhex.from_arg_list,
    +247            "FROM_UNIXTIME": _from_unixtime,
    +248            "FROM_UTF8": lambda args: exp.Decode(
    +249                this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8")
    +250            ),
    +251            "NOW": exp.CurrentTimestamp.from_arg_list,
    +252            "REGEXP_EXTRACT": lambda args: exp.RegexpExtract(
    +253                this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2)
    +254            ),
    +255            "REGEXP_REPLACE": lambda args: exp.RegexpReplace(
    +256                this=seq_get(args, 0),
    +257                expression=seq_get(args, 1),
    +258                replacement=seq_get(args, 2) or exp.Literal.string(""),
    +259            ),
    +260            "ROW": exp.Struct.from_arg_list,
    +261            "SEQUENCE": exp.GenerateSeries.from_arg_list,
    +262            "SET_AGG": exp.ArrayUniqueAgg.from_arg_list,
    +263            "SPLIT_TO_MAP": exp.StrToMap.from_arg_list,
    +264            "STRPOS": lambda args: exp.StrPosition(
    +265                this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2)
    +266            ),
    +267            "TO_UNIXTIME": exp.TimeToUnix.from_arg_list,
    +268            "TO_HEX": exp.Hex.from_arg_list,
    +269            "TO_UTF8": lambda args: exp.Encode(
    +270                this=seq_get(args, 0), charset=exp.Literal.string("utf-8")
    +271            ),
    +272        }
    +273
    +274        FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy()
    +275        FUNCTION_PARSERS.pop("TRIM")
    +276
    +277    class Generator(generator.Generator):
    +278        INTERVAL_ALLOWS_PLURAL_FORM = False
    +279        JOIN_HINTS = False
    +280        TABLE_HINTS = False
    +281        QUERY_HINTS = False
    +282        IS_BOOL_ALLOWED = False
    +283        TZ_TO_WITH_TIME_ZONE = True
    +284        NVL2_SUPPORTED = False
    +285        STRUCT_DELIMITER = ("(", ")")
    +286        LIMIT_ONLY_LITERALS = True
    +287        SUPPORTS_SINGLE_ARG_CONCAT = False
    +288
    +289        PROPERTIES_LOCATION = {
    +290            **generator.Generator.PROPERTIES_LOCATION,
    +291            exp.LocationProperty: exp.Properties.Location.UNSUPPORTED,
    +292            exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED,
    +293        }
    +294
    +295        TYPE_MAPPING = {
    +296            **generator.Generator.TYPE_MAPPING,
    +297            exp.DataType.Type.INT: "INTEGER",
    +298            exp.DataType.Type.FLOAT: "REAL",
    +299            exp.DataType.Type.BINARY: "VARBINARY",
    +300            exp.DataType.Type.TEXT: "VARCHAR",
    +301            exp.DataType.Type.TIMETZ: "TIME",
    +302            exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP",
    +303            exp.DataType.Type.STRUCT: "ROW",
    +304            exp.DataType.Type.DATETIME: "TIMESTAMP",
    +305            exp.DataType.Type.DATETIME64: "TIMESTAMP",
    +306        }
    +307
    +308        TRANSFORMS = {
    +309            **generator.Generator.TRANSFORMS,
    +310            exp.AnyValue: rename_func("ARBITRARY"),
    +311            exp.ApproxDistinct: _approx_distinct_sql,
    +312            exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"),
    +313            exp.ArgMax: rename_func("MAX_BY"),
    +314            exp.ArgMin: rename_func("MIN_BY"),
    +315            exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]",
    +316            exp.ArrayConcat: rename_func("CONCAT"),
    +317            exp.ArrayContains: rename_func("CONTAINS"),
    +318            exp.ArraySize: rename_func("CARDINALITY"),
    +319            exp.ArrayUniqueAgg: rename_func("SET_AGG"),
    +320            exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +321            exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +322            exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})",
    +323            exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +324            exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +325            exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +326            exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    +327            exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP",
    +328            exp.DateAdd: lambda self, e: self.func(
    +329                "DATE_ADD",
    +330                exp.Literal.string(e.text("unit") or "day"),
    +331                _to_int(
    +332                    e.expression,
    +333                ),
    +334                e.this,
    +335            ),
    +336            exp.DateDiff: lambda self, e: self.func(
    +337                "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    +338            ),
    +339            exp.DateStrToDate: datestrtodate_sql,
    +340            exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)",
    +341            exp.DateSub: lambda self, e: self.func(
    +342                "DATE_ADD",
    +343                exp.Literal.string(e.text("unit") or "day"),
    +344                _to_int(e.expression * -1),
    +345                e.this,
    +346            ),
    +347            exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"),
    +348            exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)",
    +349            exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"),
    +350            exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'",
    +351            exp.First: _first_last_sql,
    +352            exp.Group: transforms.preprocess([transforms.unalias_group]),
    +353            exp.GroupConcat: lambda self, e: self.func(
    +354                "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator")
    +355            ),
    +356            exp.Hex: rename_func("TO_HEX"),
    +357            exp.If: if_sql(),
    +358            exp.ILike: no_ilike_sql,
    +359            exp.Initcap: _initcap_sql,
    +360            exp.ParseJSON: rename_func("JSON_PARSE"),
    +361            exp.Last: _first_last_sql,
    +362            exp.Lateral: _explode_to_unnest_sql,
    +363            exp.Left: left_to_substring_sql,
    +364            exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"),
    +365            exp.LogicalAnd: rename_func("BOOL_AND"),
    +366            exp.LogicalOr: rename_func("BOOL_OR"),
    +367            exp.Pivot: no_pivot_sql,
    +368            exp.Quantile: _quantile_sql,
    +369            exp.RegexpExtract: regexp_extract_sql,
    +370            exp.Right: right_to_substring_sql,
    +371            exp.SafeDivide: no_safe_divide_sql,
    +372            exp.Schema: _schema_sql,
    +373            exp.Select: transforms.preprocess(
    +374                [
    +375                    transforms.eliminate_qualify,
    +376                    transforms.eliminate_distinct_on,
    +377                    transforms.explode_to_unnest(1),
    +378                    transforms.eliminate_semi_and_anti_joins,
    +379                ]
    +380            ),
    +381            exp.SortArray: _no_sort_array,
    +382            exp.StrPosition: rename_func("STRPOS"),
    +383            exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)",
    +384            exp.StrToMap: rename_func("SPLIT_TO_MAP"),
    +385            exp.StrToTime: _str_to_time_sql,
    +386            exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))",
    +387            exp.StructExtract: struct_extract_sql,
    +388            exp.Table: transforms.preprocess([_unnest_sequence]),
    +389            exp.Timestamp: no_timestamp_sql,
    +390            exp.TimestampTrunc: timestamptrunc_sql,
    +391            exp.TimeStrToDate: timestrtotime_sql,
    +392            exp.TimeStrToTime: timestrtotime_sql,
    +393            exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))",
    +394            exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})",
    +395            exp.TimeToUnix: rename_func("TO_UNIXTIME"),
    +396            exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    +397            exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)",
    +398            exp.TsOrDsAdd: _ts_or_ds_add_sql,
    +399            exp.TsOrDsDiff: _ts_or_ds_diff_sql,
    +400            exp.TsOrDsToDate: _ts_or_ds_to_date_sql,
    +401            exp.Unhex: rename_func("FROM_HEX"),
    +402            exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})",
    +403            exp.UnixToTime: _unix_to_time_sql,
    +404            exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)",
    +405            exp.VariancePop: rename_func("VAR_POP"),
    +406            exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]),
    +407            exp.WithinGroup: transforms.preprocess(
    +408                [transforms.remove_within_group_for_percentiles]
    +409            ),
    +410            exp.Xor: bool_xor_sql,
    +411        }
     412
    -413        def struct_sql(self, expression: exp.Struct) -> str:
    -414            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    -415                self.unsupported("Struct with key-value definitions is unsupported.")
    -416                return self.function_fallback_sql(expression)
    -417
    -418            return rename_func("ROW")(self, expression)
    -419
    -420        def interval_sql(self, expression: exp.Interval) -> str:
    -421            unit = self.sql(expression, "unit")
    -422            if expression.this and unit.lower().startswith("week"):
    -423                return f"({expression.this.name} * INTERVAL '7' day)"
    -424            return super().interval_sql(expression)
    -425
    -426        def transaction_sql(self, expression: exp.Transaction) -> str:
    -427            modes = expression.args.get("modes")
    -428            modes = f" {', '.join(modes)}" if modes else ""
    -429            return f"START TRANSACTION{modes}"
    -430
    -431        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    -432            start = expression.args["start"]
    -433            end = expression.args["end"]
    -434            step = expression.args.get("step")
    +413        def bracket_sql(self, expression: exp.Bracket) -> str:
    +414            if expression.args.get("safe"):
    +415                return self.func(
    +416                    "ELEMENT_AT",
    +417                    expression.this,
    +418                    seq_get(
    +419                        apply_index_offset(
    +420                            expression.this,
    +421                            expression.expressions,
    +422                            1 - expression.args.get("offset", 0),
    +423                        ),
    +424                        0,
    +425                    ),
    +426                )
    +427            return super().bracket_sql(expression)
    +428
    +429        def struct_sql(self, expression: exp.Struct) -> str:
    +430            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    +431                self.unsupported("Struct with key-value definitions is unsupported.")
    +432                return self.function_fallback_sql(expression)
    +433
    +434            return rename_func("ROW")(self, expression)
     435
    -436            if isinstance(start, exp.Cast):
    -437                target_type = start.to
    -438            elif isinstance(end, exp.Cast):
    -439                target_type = end.to
    -440            else:
    -441                target_type = None
    -442
    -443            if target_type and target_type.is_type("timestamp"):
    -444                if target_type is start.to:
    -445                    end = exp.cast(end, target_type)
    -446                else:
    -447                    start = exp.cast(start, target_type)
    -448
    -449            return self.func("SEQUENCE", start, end, step)
    -450
    -451        def offset_limit_modifiers(
    -452            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    -453        ) -> t.List[str]:
    -454            return [
    -455                self.sql(expression, "offset"),
    -456                self.sql(limit),
    -457            ]
    +436        def interval_sql(self, expression: exp.Interval) -> str:
    +437            unit = self.sql(expression, "unit")
    +438            if expression.this and unit.lower().startswith("week"):
    +439                return f"({expression.this.name} * INTERVAL '7' day)"
    +440            return super().interval_sql(expression)
    +441
    +442        def transaction_sql(self, expression: exp.Transaction) -> str:
    +443            modes = expression.args.get("modes")
    +444            modes = f" {', '.join(modes)}" if modes else ""
    +445            return f"START TRANSACTION{modes}"
    +446
    +447        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    +448            start = expression.args["start"]
    +449            end = expression.args["end"]
    +450            step = expression.args.get("step")
    +451
    +452            if isinstance(start, exp.Cast):
    +453                target_type = start.to
    +454            elif isinstance(end, exp.Cast):
    +455                target_type = end.to
    +456            else:
    +457                target_type = None
     458
    -459        def create_sql(self, expression: exp.Create) -> str:
    -460            """
    -461            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    -462            so we need to remove them
    -463            """
    -464            kind = expression.args["kind"]
    -465            schema = expression.this
    -466            if kind == "VIEW" and schema.expressions:
    -467                expression.this.set("expressions", None)
    -468            return super().create_sql(expression)
    +459            if target_type and target_type.is_type("timestamp"):
    +460                if target_type is start.to:
    +461                    end = exp.cast(end, target_type)
    +462                else:
    +463                    start = exp.cast(start, target_type)
    +464
    +465            return self.func("SEQUENCE", start, end, step)
    +466
    +467        def offset_limit_modifiers(
    +468            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    +469        ) -> t.List[str]:
    +470            return [
    +471                self.sql(expression, "offset"),
    +472                self.sql(limit),
    +473            ]
    +474
    +475        def create_sql(self, expression: exp.Create) -> str:
    +476            """
    +477            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    +478            so we need to remove them
    +479            """
    +480            kind = expression.args["kind"]
    +481            schema = expression.this
    +482            if kind == "VIEW" and schema.expressions:
    +483                expression.this.set("expressions", None)
    +484            return super().create_sql(expression)
     
    @@ -1329,6 +1354,7 @@
    NORMALIZE_FUNCTIONS
    LOG_BASE_FIRST
    SAFE_DIVISION
    +
    CONCAT_COALESCE
    DATE_FORMAT
    DATEINT_FORMAT
    FORMAT_MAPPING
    @@ -1364,15 +1390,15 @@
    -
    204    class Tokenizer(tokens.Tokenizer):
    -205        KEYWORDS = {
    -206            **tokens.Tokenizer.KEYWORDS,
    -207            "START": TokenType.BEGIN,
    -208            "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE,
    -209            "ROW": TokenType.STRUCT,
    -210            "IPADDRESS": TokenType.IPADDRESS,
    -211            "IPPREFIX": TokenType.IPPREFIX,
    -212        }
    +            
    214    class Tokenizer(tokens.Tokenizer):
    +215        KEYWORDS = {
    +216            **tokens.Tokenizer.KEYWORDS,
    +217            "START": TokenType.BEGIN,
    +218            "MATCH_RECOGNIZE": TokenType.MATCH_RECOGNIZE,
    +219            "ROW": TokenType.STRUCT,
    +220            "IPADDRESS": TokenType.IPADDRESS,
    +221            "IPPREFIX": TokenType.IPPREFIX,
    +222        }
     
    @@ -1411,12 +1437,12 @@
    COMMANDS
    COMMAND_PREFIX_TOKENS
    NUMERIC_LITERALS
    -
    ENCODE
    COMMENTS
    dialect
    reset
    tokenize
    peek
    +
    tokenize_rs
    size
    sql
    tokens
    @@ -1436,58 +1462,58 @@
    -
    214    class Parser(parser.Parser):
    -215        FUNCTIONS = {
    -216            **parser.Parser.FUNCTIONS,
    -217            "ARBITRARY": exp.AnyValue.from_arg_list,
    -218            "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list,
    -219            "APPROX_PERCENTILE": _approx_percentile,
    -220            "BITWISE_AND": binary_from_function(exp.BitwiseAnd),
    -221            "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)),
    -222            "BITWISE_OR": binary_from_function(exp.BitwiseOr),
    -223            "BITWISE_XOR": binary_from_function(exp.BitwiseXor),
    -224            "CARDINALITY": exp.ArraySize.from_arg_list,
    -225            "CONTAINS": exp.ArrayContains.from_arg_list,
    -226            "DATE_ADD": lambda args: exp.DateAdd(
    -227                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    -228            ),
    -229            "DATE_DIFF": lambda args: exp.DateDiff(
    -230                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    -231            ),
    -232            "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"),
    -233            "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"),
    -234            "DATE_TRUNC": date_trunc_to_time,
    -235            "ELEMENT_AT": _parse_element_at,
    -236            "FROM_HEX": exp.Unhex.from_arg_list,
    -237            "FROM_UNIXTIME": _from_unixtime,
    -238            "FROM_UTF8": lambda args: exp.Decode(
    -239                this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8")
    -240            ),
    -241            "NOW": exp.CurrentTimestamp.from_arg_list,
    -242            "REGEXP_EXTRACT": lambda args: exp.RegexpExtract(
    -243                this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2)
    -244            ),
    -245            "REGEXP_REPLACE": lambda args: exp.RegexpReplace(
    -246                this=seq_get(args, 0),
    -247                expression=seq_get(args, 1),
    -248                replacement=seq_get(args, 2) or exp.Literal.string(""),
    -249            ),
    -250            "ROW": exp.Struct.from_arg_list,
    -251            "SEQUENCE": exp.GenerateSeries.from_arg_list,
    -252            "SET_AGG": exp.ArrayUniqueAgg.from_arg_list,
    -253            "SPLIT_TO_MAP": exp.StrToMap.from_arg_list,
    -254            "STRPOS": lambda args: exp.StrPosition(
    -255                this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2)
    -256            ),
    -257            "TO_UNIXTIME": exp.TimeToUnix.from_arg_list,
    -258            "TO_HEX": exp.Hex.from_arg_list,
    -259            "TO_UTF8": lambda args: exp.Encode(
    -260                this=seq_get(args, 0), charset=exp.Literal.string("utf-8")
    -261            ),
    -262        }
    -263
    -264        FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy()
    -265        FUNCTION_PARSERS.pop("TRIM")
    +            
    224    class Parser(parser.Parser):
    +225        FUNCTIONS = {
    +226            **parser.Parser.FUNCTIONS,
    +227            "ARBITRARY": exp.AnyValue.from_arg_list,
    +228            "APPROX_DISTINCT": exp.ApproxDistinct.from_arg_list,
    +229            "APPROX_PERCENTILE": _approx_percentile,
    +230            "BITWISE_AND": binary_from_function(exp.BitwiseAnd),
    +231            "BITWISE_NOT": lambda args: exp.BitwiseNot(this=seq_get(args, 0)),
    +232            "BITWISE_OR": binary_from_function(exp.BitwiseOr),
    +233            "BITWISE_XOR": binary_from_function(exp.BitwiseXor),
    +234            "CARDINALITY": exp.ArraySize.from_arg_list,
    +235            "CONTAINS": exp.ArrayContains.from_arg_list,
    +236            "DATE_ADD": lambda args: exp.DateAdd(
    +237                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    +238            ),
    +239            "DATE_DIFF": lambda args: exp.DateDiff(
    +240                this=seq_get(args, 2), expression=seq_get(args, 1), unit=seq_get(args, 0)
    +241            ),
    +242            "DATE_FORMAT": format_time_lambda(exp.TimeToStr, "presto"),
    +243            "DATE_PARSE": format_time_lambda(exp.StrToTime, "presto"),
    +244            "DATE_TRUNC": date_trunc_to_time,
    +245            "ELEMENT_AT": _parse_element_at,
    +246            "FROM_HEX": exp.Unhex.from_arg_list,
    +247            "FROM_UNIXTIME": _from_unixtime,
    +248            "FROM_UTF8": lambda args: exp.Decode(
    +249                this=seq_get(args, 0), replace=seq_get(args, 1), charset=exp.Literal.string("utf-8")
    +250            ),
    +251            "NOW": exp.CurrentTimestamp.from_arg_list,
    +252            "REGEXP_EXTRACT": lambda args: exp.RegexpExtract(
    +253                this=seq_get(args, 0), expression=seq_get(args, 1), group=seq_get(args, 2)
    +254            ),
    +255            "REGEXP_REPLACE": lambda args: exp.RegexpReplace(
    +256                this=seq_get(args, 0),
    +257                expression=seq_get(args, 1),
    +258                replacement=seq_get(args, 2) or exp.Literal.string(""),
    +259            ),
    +260            "ROW": exp.Struct.from_arg_list,
    +261            "SEQUENCE": exp.GenerateSeries.from_arg_list,
    +262            "SET_AGG": exp.ArrayUniqueAgg.from_arg_list,
    +263            "SPLIT_TO_MAP": exp.StrToMap.from_arg_list,
    +264            "STRPOS": lambda args: exp.StrPosition(
    +265                this=seq_get(args, 0), substr=seq_get(args, 1), instance=seq_get(args, 2)
    +266            ),
    +267            "TO_UNIXTIME": exp.TimeToUnix.from_arg_list,
    +268            "TO_HEX": exp.Hex.from_arg_list,
    +269            "TO_UTF8": lambda args: exp.Encode(
    +270                this=seq_get(args, 0), charset=exp.Literal.string("utf-8")
    +271            ),
    +272        }
    +273
    +274        FUNCTION_PARSERS = parser.Parser.FUNCTION_PARSERS.copy()
    +275        FUNCTION_PARSERS.pop("TRIM")
     
    @@ -1512,7 +1538,7 @@ Default: 3
    FUNCTIONS = - {'ABS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Abs'>>, 'ANY_VALUE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.AnyValue'>>, 'APPROX_DISTINCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxDistinct'>>, 'APPROX_COUNT_DISTINCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxDistinct'>>, 'APPROX_QUANTILE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxQuantile'>>, 'APPROX_TOP_K': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxTopK'>>, 'ARG_MAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'ARGMAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'MAX_BY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'ARG_MIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'ARGMIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'MIN_BY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Array'>>, 'ARRAY_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAgg'>>, 'ARRAY_ALL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAll'>>, 'ARRAY_ANY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAny'>>, 'ARRAY_CONCAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayConcat'>>, 'ARRAY_CAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayConcat'>>, 'ARRAY_CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayContains'>>, 'FILTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayFilter'>>, 'ARRAY_FILTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayFilter'>>, 'ARRAY_JOIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayJoin'>>, 'ARRAY_SIZE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySize'>>, 'ARRAY_SORT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySort'>>, 'ARRAY_SUM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySum'>>, 'ARRAY_UNION_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUnionAgg'>>, 'ARRAY_UNIQUE_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUniqueAgg'>>, 'AVG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Avg'>>, 'CASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Case'>>, 'CAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Cast'>>, 'CAST_TO_STR_TYPE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CastToStrType'>>, 'CEIL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ceil'>>, 'CEILING': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ceil'>>, 'CHR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Chr'>>, 'CHAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Chr'>>, 'COALESCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'IFNULL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'NVL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'COLLATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Collate'>>, 'CONCAT': <function parse_concat>, 'CONCAT_WS': <function parse_concat_ws>, 'COUNT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Count'>>, 'COUNT_IF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CountIf'>>, 'CURRENT_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentDate'>>, 'CURRENT_DATETIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentDatetime'>>, 'CURRENT_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTime'>>, 'CURRENT_TIMESTAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTimestamp'>>, 'CURRENT_USER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentUser'>>, 'DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Date'>>, 'DATE_ADD': <function Presto.Parser.<lambda>>, 'DATEDIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateDiff'>>, 'DATE_DIFF': <function Presto.Parser.<lambda>>, 'DATEFROMPARTS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateFromParts'>>, 'DATE_STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateStrToDate'>>, 'DATE_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateSub'>>, 'DATE_TO_DATE_STR': <function Parser.<lambda>>, 'DATE_TO_DI': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateToDi'>>, 'DATE_TRUNC': <function date_trunc_to_time>, 'DATETIME_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeAdd'>>, 'DATETIME_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeDiff'>>, 'DATETIME_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeSub'>>, 'DATETIME_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeTrunc'>>, 'DAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Day'>>, 'DAY_OF_MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfMonth'>>, 'DAYOFMONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfMonth'>>, 'DAY_OF_WEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfWeek'>>, 'DAYOFWEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfWeek'>>, 'DAY_OF_YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfYear'>>, 'DAYOFYEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfYear'>>, 'DECODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Decode'>>, 'DI_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DiToDate'>>, 'ENCODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Encode'>>, 'EXP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Exp'>>, 'EXPLODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Explode'>>, 'EXPLODE_OUTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ExplodeOuter'>>, 'EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Extract'>>, 'FIRST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.First'>>, 'FLATTEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Flatten'>>, 'FLOOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Floor'>>, 'FROM_BASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.FromBase'>>, 'FROM_BASE64': <bound method Func.from_arg_list of <class 'sqlglot.expressions.FromBase64'>>, 'GENERATE_SERIES': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GenerateSeries'>>, 'GREATEST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Greatest'>>, 'GROUP_CONCAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GroupConcat'>>, 'HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hex'>>, 'HLL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hll'>>, 'IF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.If'>>, 'INITCAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Initcap'>>, 'IS_INF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsInf'>>, 'ISINF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsInf'>>, 'IS_NAN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsNan'>>, 'ISNAN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsNan'>>, 'J_S_O_N_ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArray'>>, 'J_S_O_N_ARRAY_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArrayAgg'>>, 'JSON_ARRAY_CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArrayContains'>>, 'JSONB_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONBExtract'>>, 'JSONB_EXTRACT_SCALAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONBExtractScalar'>>, 'JSON_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONExtract'>>, 'JSON_EXTRACT_SCALAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONExtractScalar'>>, 'JSON_FORMAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONFormat'>>, 'J_S_O_N_OBJECT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONObject'>>, 'J_S_O_N_TABLE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONTable'>>, 'LAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Last'>>, 'LAST_DATE_OF_MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LastDateOfMonth'>>, 'LEAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Least'>>, 'LEFT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Left'>>, 'LENGTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Length'>>, 'LEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Length'>>, 'LEVENSHTEIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Levenshtein'>>, 'LN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ln'>>, 'LOG': <function parse_logarithm>, 'LOG10': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Log10'>>, 'LOG2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Log2'>>, 'LOGICAL_AND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'BOOL_AND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'BOOLAND_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'LOGICAL_OR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'BOOL_OR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'BOOLOR_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'LOWER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Lower'>>, 'LCASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Lower'>>, 'MD5': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MD5'>>, 'MD5_DIGEST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MD5Digest'>>, 'MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Map'>>, 'MAP_FROM_ENTRIES': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MapFromEntries'>>, 'MATCH_AGAINST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MatchAgainst'>>, 'MAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Max'>>, 'MIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Min'>>, 'MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Month'>>, 'MONTHS_BETWEEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MonthsBetween'>>, 'NEXT_VALUE_FOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.NextValueFor'>>, 'NULLIF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Nullif'>>, 'NUMBER_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.NumberToStr'>>, 'NVL2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Nvl2'>>, 'OPEN_J_S_O_N': <bound method Func.from_arg_list of <class 'sqlglot.expressions.OpenJSON'>>, 'PARAMETERIZED_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParameterizedAgg'>>, 'PARSE_JSON': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParseJSON'>>, 'JSON_PARSE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParseJSON'>>, 'PERCENTILE_CONT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PercentileCont'>>, 'PERCENTILE_DISC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PercentileDisc'>>, 'POSEXPLODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Posexplode'>>, 'POSEXPLODE_OUTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PosexplodeOuter'>>, 'POWER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Pow'>>, 'POW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Pow'>>, 'PREDICT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Predict'>>, 'QUANTILE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Quantile'>>, 'RANGE_N': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RangeN'>>, 'READ_CSV': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ReadCSV'>>, 'REDUCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Reduce'>>, 'REGEXP_EXTRACT': <function Presto.Parser.<lambda>>, 'REGEXP_I_LIKE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpILike'>>, 'REGEXP_LIKE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpLike'>>, 'REGEXP_REPLACE': <function Presto.Parser.<lambda>>, 'REGEXP_SPLIT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpSplit'>>, 'REPEAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Repeat'>>, 'RIGHT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Right'>>, 'ROUND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Round'>>, 'ROW_NUMBER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RowNumber'>>, 'SHA': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA'>>, 'SHA1': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA'>>, 'SHA2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA2'>>, 'SAFE_DIVIDE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SafeDivide'>>, 'SORT_ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SortArray'>>, 'SPLIT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Split'>>, 'SQRT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Sqrt'>>, 'STANDARD_HASH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StandardHash'>>, 'STAR_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StarMap'>>, 'STARTS_WITH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StartsWith'>>, 'STARTSWITH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StartsWith'>>, 'STDDEV': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stddev'>>, 'STDDEV_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StddevPop'>>, 'STDDEV_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StddevSamp'>>, 'STR_POSITION': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrPosition'>>, 'STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToDate'>>, 'STR_TO_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToMap'>>, 'STR_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToTime'>>, 'STR_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToUnix'>>, 'STRUCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Struct'>>, 'STRUCT_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StructExtract'>>, 'STUFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stuff'>>, 'INSERT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stuff'>>, 'SUBSTRING': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Substring'>>, 'SUM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Sum'>>, 'TIME_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeAdd'>>, 'TIME_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeDiff'>>, 'TIME_STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToDate'>>, 'TIME_STR_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToTime'>>, 'TIME_STR_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToUnix'>>, 'TIME_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeSub'>>, 'TIME_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToStr'>>, 'TIME_TO_TIME_STR': <function Parser.<lambda>>, 'TIME_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToUnix'>>, 'TIME_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeTrunc'>>, 'TIMESTAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Timestamp'>>, 'TIMESTAMP_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampAdd'>>, 'TIMESTAMP_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampDiff'>>, 'TIMESTAMP_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampSub'>>, 'TIMESTAMP_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampTrunc'>>, 'TO_BASE64': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToBase64'>>, 'TO_CHAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToChar'>>, 'TO_DAYS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToDays'>>, 'TRANSFORM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Transform'>>, 'TRIM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Trim'>>, 'TRY_CAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TryCast'>>, 'TS_OR_DI_TO_DI': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDiToDi'>>, 'TS_OR_DS_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsAdd'>>, 'TS_OR_DS_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsDiff'>>, 'TS_OR_DS_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsToDate'>>, 'TS_OR_DS_TO_DATE_STR': <function Parser.<lambda>>, 'UNHEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Unhex'>>, 'UNIX_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToStr'>>, 'UNIX_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToTime'>>, 'UNIX_TO_TIME_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToTimeStr'>>, 'UPPER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Upper'>>, 'UCASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Upper'>>, 'VAR_MAP': <function parse_var_map>, 'VARIANCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VARIANCE_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VAR_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VARIANCE_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.VariancePop'>>, 'VAR_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.VariancePop'>>, 'WEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Week'>>, 'WEEK_OF_YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.WeekOfYear'>>, 'WEEKOFYEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.WeekOfYear'>>, 'WHEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.When'>>, 'X_M_L_TABLE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.XMLTable'>>, 'XOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Xor'>>, 'YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Year'>>, 'GLOB': <function Parser.<lambda>>, 'LIKE': <function parse_like>, 'ARBITRARY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.AnyValue'>>, 'APPROX_PERCENTILE': <function _approx_percentile>, 'BITWISE_AND': <function binary_from_function.<locals>.<lambda>>, 'BITWISE_NOT': <function Presto.Parser.<lambda>>, 'BITWISE_OR': <function binary_from_function.<locals>.<lambda>>, 'BITWISE_XOR': <function binary_from_function.<locals>.<lambda>>, 'CARDINALITY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySize'>>, 'CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayContains'>>, 'DATE_FORMAT': <function format_time_lambda.<locals>._format_time>, 'DATE_PARSE': <function format_time_lambda.<locals>._format_time>, 'ELEMENT_AT': <function _parse_element_at>, 'FROM_HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Unhex'>>, 'FROM_UNIXTIME': <function _from_unixtime>, 'FROM_UTF8': <function Presto.Parser.<lambda>>, 'NOW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTimestamp'>>, 'ROW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Struct'>>, 'SEQUENCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GenerateSeries'>>, 'SET_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUniqueAgg'>>, 'SPLIT_TO_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToMap'>>, 'STRPOS': <function Presto.Parser.<lambda>>, 'TO_UNIXTIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToUnix'>>, 'TO_HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hex'>>, 'TO_UTF8': <function Presto.Parser.<lambda>>} + {'ABS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Abs'>>, 'ANY_VALUE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.AnyValue'>>, 'APPROX_DISTINCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxDistinct'>>, 'APPROX_COUNT_DISTINCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxDistinct'>>, 'APPROX_QUANTILE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxQuantile'>>, 'APPROX_TOP_K': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ApproxTopK'>>, 'ARG_MAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'ARGMAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'MAX_BY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMax'>>, 'ARG_MIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'ARGMIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'MIN_BY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArgMin'>>, 'ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Array'>>, 'ARRAY_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAgg'>>, 'ARRAY_ALL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAll'>>, 'ARRAY_ANY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayAny'>>, 'ARRAY_CONCAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayConcat'>>, 'ARRAY_CAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayConcat'>>, 'ARRAY_CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayContains'>>, 'FILTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayFilter'>>, 'ARRAY_FILTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayFilter'>>, 'ARRAY_JOIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayJoin'>>, 'ARRAY_SIZE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySize'>>, 'ARRAY_SORT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySort'>>, 'ARRAY_SUM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySum'>>, 'ARRAY_UNION_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUnionAgg'>>, 'ARRAY_UNIQUE_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUniqueAgg'>>, 'AVG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Avg'>>, 'CASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Case'>>, 'CAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Cast'>>, 'CAST_TO_STR_TYPE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CastToStrType'>>, 'CEIL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ceil'>>, 'CEILING': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ceil'>>, 'CHR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Chr'>>, 'CHAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Chr'>>, 'COALESCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'IFNULL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'NVL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Coalesce'>>, 'COLLATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Collate'>>, 'CONCAT': <function Parser.<lambda>>, 'CONCAT_WS': <function Parser.<lambda>>, 'COUNT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Count'>>, 'COUNT_IF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CountIf'>>, 'CURRENT_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentDate'>>, 'CURRENT_DATETIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentDatetime'>>, 'CURRENT_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTime'>>, 'CURRENT_TIMESTAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTimestamp'>>, 'CURRENT_USER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentUser'>>, 'DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Date'>>, 'DATE_ADD': <function Presto.Parser.<lambda>>, 'DATEDIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateDiff'>>, 'DATE_DIFF': <function Presto.Parser.<lambda>>, 'DATEFROMPARTS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateFromParts'>>, 'DATE_STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateStrToDate'>>, 'DATE_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateSub'>>, 'DATE_TO_DATE_STR': <function Parser.<lambda>>, 'DATE_TO_DI': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DateToDi'>>, 'DATE_TRUNC': <function date_trunc_to_time>, 'DATETIME_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeAdd'>>, 'DATETIME_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeDiff'>>, 'DATETIME_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeSub'>>, 'DATETIME_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DatetimeTrunc'>>, 'DAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Day'>>, 'DAY_OF_MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfMonth'>>, 'DAYOFMONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfMonth'>>, 'DAY_OF_WEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfWeek'>>, 'DAYOFWEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfWeek'>>, 'DAY_OF_YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfYear'>>, 'DAYOFYEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DayOfYear'>>, 'DECODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Decode'>>, 'DI_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.DiToDate'>>, 'ENCODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Encode'>>, 'EXP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Exp'>>, 'EXPLODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Explode'>>, 'EXPLODE_OUTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ExplodeOuter'>>, 'EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Extract'>>, 'FIRST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.First'>>, 'FLATTEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Flatten'>>, 'FLOOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Floor'>>, 'FROM_BASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.FromBase'>>, 'FROM_BASE64': <bound method Func.from_arg_list of <class 'sqlglot.expressions.FromBase64'>>, 'GENERATE_SERIES': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GenerateSeries'>>, 'GREATEST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Greatest'>>, 'GROUP_CONCAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GroupConcat'>>, 'HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hex'>>, 'HLL': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hll'>>, 'IF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.If'>>, 'INITCAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Initcap'>>, 'IS_INF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsInf'>>, 'ISINF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsInf'>>, 'IS_NAN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsNan'>>, 'ISNAN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.IsNan'>>, 'J_S_O_N_ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArray'>>, 'J_S_O_N_ARRAY_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArrayAgg'>>, 'JSON_ARRAY_CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONArrayContains'>>, 'JSONB_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONBExtract'>>, 'JSONB_EXTRACT_SCALAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONBExtractScalar'>>, 'JSON_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONExtract'>>, 'JSON_EXTRACT_SCALAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONExtractScalar'>>, 'JSON_FORMAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONFormat'>>, 'J_S_O_N_OBJECT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONObject'>>, 'J_S_O_N_TABLE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.JSONTable'>>, 'LAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Last'>>, 'LAST_DATE_OF_MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LastDateOfMonth'>>, 'LEAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Least'>>, 'LEFT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Left'>>, 'LENGTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Length'>>, 'LEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Length'>>, 'LEVENSHTEIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Levenshtein'>>, 'LN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Ln'>>, 'LOG': <function parse_logarithm>, 'LOG10': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Log10'>>, 'LOG2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Log2'>>, 'LOGICAL_AND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'BOOL_AND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'BOOLAND_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalAnd'>>, 'LOGICAL_OR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'BOOL_OR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'BOOLOR_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.LogicalOr'>>, 'LOWER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Lower'>>, 'LCASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Lower'>>, 'MD5': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MD5'>>, 'MD5_DIGEST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MD5Digest'>>, 'MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Map'>>, 'MAP_FROM_ENTRIES': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MapFromEntries'>>, 'MATCH_AGAINST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MatchAgainst'>>, 'MAX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Max'>>, 'MIN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Min'>>, 'MONTH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Month'>>, 'MONTHS_BETWEEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.MonthsBetween'>>, 'NEXT_VALUE_FOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.NextValueFor'>>, 'NULLIF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Nullif'>>, 'NUMBER_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.NumberToStr'>>, 'NVL2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Nvl2'>>, 'OPEN_J_S_O_N': <bound method Func.from_arg_list of <class 'sqlglot.expressions.OpenJSON'>>, 'PARAMETERIZED_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParameterizedAgg'>>, 'PARSE_JSON': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParseJSON'>>, 'JSON_PARSE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ParseJSON'>>, 'PERCENTILE_CONT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PercentileCont'>>, 'PERCENTILE_DISC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PercentileDisc'>>, 'POSEXPLODE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Posexplode'>>, 'POSEXPLODE_OUTER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.PosexplodeOuter'>>, 'POWER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Pow'>>, 'POW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Pow'>>, 'PREDICT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Predict'>>, 'QUANTILE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Quantile'>>, 'RANGE_N': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RangeN'>>, 'READ_CSV': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ReadCSV'>>, 'REDUCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Reduce'>>, 'REGEXP_EXTRACT': <function Presto.Parser.<lambda>>, 'REGEXP_I_LIKE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpILike'>>, 'REGEXP_LIKE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpLike'>>, 'REGEXP_REPLACE': <function Presto.Parser.<lambda>>, 'REGEXP_SPLIT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RegexpSplit'>>, 'REPEAT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Repeat'>>, 'RIGHT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Right'>>, 'ROUND': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Round'>>, 'ROW_NUMBER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.RowNumber'>>, 'SHA': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA'>>, 'SHA1': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA'>>, 'SHA2': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SHA2'>>, 'SAFE_DIVIDE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SafeDivide'>>, 'SORT_ARRAY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.SortArray'>>, 'SPLIT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Split'>>, 'SQRT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Sqrt'>>, 'STANDARD_HASH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StandardHash'>>, 'STAR_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StarMap'>>, 'STARTS_WITH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StartsWith'>>, 'STARTSWITH': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StartsWith'>>, 'STDDEV': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stddev'>>, 'STDDEV_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StddevPop'>>, 'STDDEV_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StddevSamp'>>, 'STR_POSITION': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrPosition'>>, 'STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToDate'>>, 'STR_TO_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToMap'>>, 'STR_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToTime'>>, 'STR_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToUnix'>>, 'STRUCT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Struct'>>, 'STRUCT_EXTRACT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StructExtract'>>, 'STUFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stuff'>>, 'INSERT': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Stuff'>>, 'SUBSTRING': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Substring'>>, 'SUM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Sum'>>, 'TIME_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeAdd'>>, 'TIME_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeDiff'>>, 'TIME_STR_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToDate'>>, 'TIME_STR_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToTime'>>, 'TIME_STR_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeStrToUnix'>>, 'TIME_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeSub'>>, 'TIME_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToStr'>>, 'TIME_TO_TIME_STR': <function Parser.<lambda>>, 'TIME_TO_UNIX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToUnix'>>, 'TIME_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeTrunc'>>, 'TIMESTAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Timestamp'>>, 'TIMESTAMP_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampAdd'>>, 'TIMESTAMP_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampDiff'>>, 'TIMESTAMP_FROM_PARTS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampFromParts'>>, 'TIMESTAMP_SUB': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampSub'>>, 'TIMESTAMP_TRUNC': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimestampTrunc'>>, 'TO_BASE64': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToBase64'>>, 'TO_CHAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToChar'>>, 'TO_DAYS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ToDays'>>, 'TRANSFORM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Transform'>>, 'TRIM': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Trim'>>, 'TRY_CAST': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TryCast'>>, 'TS_OR_DI_TO_DI': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDiToDi'>>, 'TS_OR_DS_ADD': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsAdd'>>, 'TS_OR_DS_DIFF': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsDiff'>>, 'TS_OR_DS_TO_DATE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TsOrDsToDate'>>, 'TS_OR_DS_TO_DATE_STR': <function Parser.<lambda>>, 'UNHEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Unhex'>>, 'UNIX_TO_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToStr'>>, 'UNIX_TO_TIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToTime'>>, 'UNIX_TO_TIME_STR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.UnixToTimeStr'>>, 'UPPER': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Upper'>>, 'UCASE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Upper'>>, 'VAR_MAP': <function parse_var_map>, 'VARIANCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VARIANCE_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VAR_SAMP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Variance'>>, 'VARIANCE_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.VariancePop'>>, 'VAR_POP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.VariancePop'>>, 'WEEK': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Week'>>, 'WEEK_OF_YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.WeekOfYear'>>, 'WEEKOFYEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.WeekOfYear'>>, 'WHEN': <bound method Func.from_arg_list of <class 'sqlglot.expressions.When'>>, 'X_M_L_TABLE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.XMLTable'>>, 'XOR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Xor'>>, 'YEAR': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Year'>>, 'GLOB': <function Parser.<lambda>>, 'LIKE': <function parse_like>, 'ARBITRARY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.AnyValue'>>, 'APPROX_PERCENTILE': <function _approx_percentile>, 'BITWISE_AND': <function binary_from_function.<locals>.<lambda>>, 'BITWISE_NOT': <function Presto.Parser.<lambda>>, 'BITWISE_OR': <function binary_from_function.<locals>.<lambda>>, 'BITWISE_XOR': <function binary_from_function.<locals>.<lambda>>, 'CARDINALITY': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArraySize'>>, 'CONTAINS': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayContains'>>, 'DATE_FORMAT': <function format_time_lambda.<locals>._format_time>, 'DATE_PARSE': <function format_time_lambda.<locals>._format_time>, 'ELEMENT_AT': <function _parse_element_at>, 'FROM_HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Unhex'>>, 'FROM_UNIXTIME': <function _from_unixtime>, 'FROM_UTF8': <function Presto.Parser.<lambda>>, 'NOW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.CurrentTimestamp'>>, 'ROW': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Struct'>>, 'SEQUENCE': <bound method Func.from_arg_list of <class 'sqlglot.expressions.GenerateSeries'>>, 'SET_AGG': <bound method Func.from_arg_list of <class 'sqlglot.expressions.ArrayUniqueAgg'>>, 'SPLIT_TO_MAP': <bound method Func.from_arg_list of <class 'sqlglot.expressions.StrToMap'>>, 'STRPOS': <function Presto.Parser.<lambda>>, 'TO_UNIXTIME': <bound method Func.from_arg_list of <class 'sqlglot.expressions.TimeToUnix'>>, 'TO_HEX': <bound method Func.from_arg_list of <class 'sqlglot.expressions.Hex'>>, 'TO_UTF8': <function Presto.Parser.<lambda>>}
    @@ -1538,7 +1564,7 @@ Default: 3
    TABLE_ALIAS_TOKENS = - {<TokenType.VARCHAR: 'VARCHAR'>, <TokenType.OVERLAPS: 'OVERLAPS'>, <TokenType.MERGE: 'MERGE'>, <TokenType.TEXT: 'TEXT'>, <TokenType.CURRENT_DATETIME: 'CURRENT_DATETIME'>, <TokenType.DESC: 'DESC'>, <TokenType.FILTER: 'FILTER'>, <TokenType.END: 'END'>, <TokenType.ASC: 'ASC'>, <TokenType.SOME: 'SOME'>, <TokenType.INT8MULTIRANGE: 'INT8MULTIRANGE'>, <TokenType.ENUM16: 'ENUM16'>, <TokenType.TABLE: 'TABLE'>, <TokenType.FLOAT: 'FLOAT'>, <TokenType.EXISTS: 'EXISTS'>, <TokenType.ENUM8: 'ENUM8'>, <TokenType.TIMESTAMPLTZ: 'TIMESTAMPLTZ'>, <TokenType.YEAR: 'YEAR'>, <TokenType.ENUM: 'ENUM'>, <TokenType.HSTORE: 'HSTORE'>, <TokenType.DIV: 'DIV'>, <TokenType.FALSE: 'FALSE'>, <TokenType.FORMAT: 'FORMAT'>, <TokenType.MEDIUMBLOB: 'MEDIUMBLOB'>, <TokenType.ANY: 'ANY'>, <TokenType.IPADDRESS: 'IPADDRESS'>, <TokenType.CURRENT_TIMESTAMP: 'CURRENT_TIMESTAMP'>, <TokenType.KEEP: 'KEEP'>, <TokenType.KILL: 'KILL'>, <TokenType.TINYBLOB: 'TINYBLOB'>, <TokenType.NUMRANGE: 'NUMRANGE'>, <TokenType.UNIQUE: 'UNIQUE'>, <TokenType.REPLACE: 'REPLACE'>, <TokenType.DATEMULTIRANGE: 'DATEMULTIRANGE'>, <TokenType.USE: 'USE'>, <TokenType.AUTO_INCREMENT: 'AUTO_INCREMENT'>, <TokenType.JSONB: 'JSONB'>, <TokenType.TOP: 'TOP'>, <TokenType.RECURSIVE: 'RECURSIVE'>, <TokenType.INT128: 'INT128'>, <TokenType.OPERATOR: 'OPERATOR'>, <TokenType.OVERWRITE: 'OVERWRITE'>, <TokenType.SMALLSERIAL: 'SMALLSERIAL'>, <TokenType.UUID: 'UUID'>, <TokenType.SET: 'SET'>, <TokenType.USERDEFINED: 'USERDEFINED'>, <TokenType.VARBINARY: 'VARBINARY'>, <TokenType.SMALLMONEY: 'SMALLMONEY'>, <TokenType.BIGSERIAL: 'BIGSERIAL'>, <TokenType.CONSTRAINT: 'CONSTRAINT'>, <TokenType.DICTIONARY: 'DICTIONARY'>, <TokenType.INT: 'INT'>, <TokenType.INDEX: 'INDEX'>, <TokenType.BIGINT: 'BIGINT'>, <TokenType.NCHAR: 'NCHAR'>, <TokenType.ROW: 'ROW'>, <TokenType.DEFAULT: 'DEFAULT'>, <TokenType.REFERENCES: 'REFERENCES'>, <TokenType.UNPIVOT: 'UNPIVOT'>, <TokenType.LOAD: 'LOAD'>, <TokenType.NESTED: 'NESTED'>, <TokenType.NULLABLE: 'NULLABLE'>, <TokenType.BEGIN: 'BEGIN'>, <TokenType.GEOGRAPHY: 'GEOGRAPHY'>, <TokenType.UNKNOWN: 'UNKNOWN'>, <TokenType.ESCAPE: 'ESCAPE'>, <TokenType.SEMI: 'SEMI'>, <TokenType.FUNCTION: 'FUNCTION'>, <TokenType.TSTZMULTIRANGE: 'TSTZMULTIRANGE'>, <TokenType.CURRENT_DATE: 'CURRENT_DATE'>, <TokenType.SETTINGS: 'SETTINGS'>, <TokenType.OBJECT_IDENTIFIER: 'OBJECT_IDENTIFIER'>, <TokenType.INT8RANGE: 'INT8RANGE'>, <TokenType.ARRAY: 'ARRAY'>, <TokenType.LOWCARDINALITY: 'LOWCARDINALITY'>, <TokenType.PSEUDO_TYPE: 'PSEUDO_TYPE'>, <TokenType.UMEDIUMINT: 'UMEDIUMINT'>, <TokenType.TIME: 'TIME'>, <TokenType.TINYINT: 'TINYINT'>, <TokenType.PERCENT: 'PERCENT'>, <TokenType.STRUCT: 'STRUCT'>, <TokenType.BOOLEAN: 'BOOLEAN'>, <TokenType.CHAR: 'CHAR'>, <TokenType.HLLSKETCH: 'HLLSKETCH'>, <TokenType.VARIANT: 'VARIANT'>, <TokenType.UINT128: 'UINT128'>, <TokenType.LONGTEXT: 'LONGTEXT'>, <TokenType.JSON: 'JSON'>, <TokenType.DECIMAL: 'DECIMAL'>, <TokenType.INTERVAL: 'INTERVAL'>, <TokenType.INT256: 'INT256'>, <TokenType.DATABASE: 'DATABASE'>, <TokenType.ALL: 'ALL'>, <TokenType.DATERANGE: 'DATERANGE'>, <TokenType.DESCRIBE: 'DESCRIBE'>, <TokenType.PIVOT: 'PIVOT'>, <TokenType.OBJECT: 'OBJECT'>, <TokenType.SCHEMA: 'SCHEMA'>, <TokenType.TIMESTAMPTZ: 'TIMESTAMPTZ'>, <TokenType.MONEY: 'MONEY'>, <TokenType.PARTITION: 'PARTITION'>, <TokenType.ROWS: 'ROWS'>, <TokenType.COLLATE: 'COLLATE'>, <TokenType.DATE: 'DATE'>, <TokenType.SERIAL: 'SERIAL'>, <TokenType.MAP: 'MAP'>, <TokenType.NEXT: 'NEXT'>, <TokenType.NUMMULTIRANGE: 'NUMMULTIRANGE'>, <TokenType.COMMIT: 'COMMIT'>, <TokenType.BINARY: 'BINARY'>, <TokenType.IPPREFIX: 'IPPREFIX'>, <TokenType.INET: 'INET'>, <TokenType.IS: 'IS'>, <TokenType.MODEL: 'MODEL'>, <TokenType.TIMESTAMP_NS: 'TIMESTAMP_NS'>, <TokenType.UTINYINT: 'UTINYINT'>, <TokenType.SMALLINT: 'SMALLINT'>, <TokenType.UDECIMAL: 'UDECIMAL'>, <TokenType.CURRENT_USER: 'CURRENT_USER'>, <TokenType.FOREIGN_KEY: 'FOREIGN_KEY'>, <TokenType.MEDIUMTEXT: 'MEDIUMTEXT'>, <TokenType.DOUBLE: 'DOUBLE'>, <TokenType.FIXEDSTRING: 'FIXEDSTRING'>, <TokenType.SHOW: 'SHOW'>, <TokenType.TEMPORARY: 'TEMPORARY'>, <TokenType.NVARCHAR: 'NVARCHAR'>, <TokenType.COMMENT: 'COMMENT'>, <TokenType.XML: 'XML'>, <TokenType.ISNULL: 'ISNULL'>, <TokenType.DATETIME: 'DATETIME'>, <TokenType.IMAGE: 'IMAGE'>, <TokenType.TIMETZ: 'TIMETZ'>, <TokenType.LONGBLOB: 'LONGBLOB'>, <TokenType.UNIQUEIDENTIFIER: 'UNIQUEIDENTIFIER'>, <TokenType.ORDINALITY: 'ORDINALITY'>, <TokenType.REFRESH: 'REFRESH'>, <TokenType.TSTZRANGE: 'TSTZRANGE'>, <TokenType.COLUMN: 'COLUMN'>, <TokenType.USMALLINT: 'USMALLINT'>, <TokenType.VAR: 'VAR'>, <TokenType.NULL: 'NULL'>, <TokenType.CASE: 'CASE'>, <TokenType.PROCEDURE: 'PROCEDURE'>, <TokenType.UINT: 'UINT'>, <TokenType.CURRENT_TIME: 'CURRENT_TIME'>, <TokenType.TSRANGE: 'TSRANGE'>, <TokenType.TINYTEXT: 'TINYTEXT'>, <TokenType.DELETE: 'DELETE'>, <TokenType.MEDIUMINT: 'MEDIUMINT'>, <TokenType.EXECUTE: 'EXECUTE'>, <TokenType.TIMESTAMP_S: 'TIMESTAMP_S'>, <TokenType.ANTI: 'ANTI'>, <TokenType.GEOMETRY: 'GEOMETRY'>, <TokenType.RANGE: 'RANGE'>, <TokenType.TIMESTAMP: 'TIMESTAMP'>, <TokenType.CACHE: 'CACHE'>, <TokenType.VIEW: 'VIEW'>, <TokenType.UPDATE: 'UPDATE'>, <TokenType.VOLATILE: 'VOLATILE'>, <TokenType.ROWVERSION: 'ROWVERSION'>, <TokenType.TIMESTAMP_MS: 'TIMESTAMP_MS'>, <TokenType.BIT: 'BIT'>, <TokenType.COMMAND: 'COMMAND'>, <TokenType.TSMULTIRANGE: 'TSMULTIRANGE'>, <TokenType.FIRST: 'FIRST'>, <TokenType.BIGDECIMAL: 'BIGDECIMAL'>, <TokenType.SUPER: 'SUPER'>, <TokenType.UBIGINT: 'UBIGINT'>, <TokenType.TRUE: 'TRUE'>, <TokenType.PRAGMA: 'PRAGMA'>, <TokenType.DATETIME64: 'DATETIME64'>, <TokenType.UINT256: 'UINT256'>, <TokenType.INT4MULTIRANGE: 'INT4MULTIRANGE'>, <TokenType.INT4RANGE: 'INT4RANGE'>} + {<TokenType.TIMESTAMP_MS: 'TIMESTAMP_MS'>, <TokenType.INT4MULTIRANGE: 'INT4MULTIRANGE'>, <TokenType.AUTO_INCREMENT: 'AUTO_INCREMENT'>, <TokenType.USERDEFINED: 'USERDEFINED'>, <TokenType.VAR: 'VAR'>, <TokenType.TINYINT: 'TINYINT'>, <TokenType.DATE: 'DATE'>, <TokenType.CASE: 'CASE'>, <TokenType.MONEY: 'MONEY'>, <TokenType.HSTORE: 'HSTORE'>, <TokenType.SMALLMONEY: 'SMALLMONEY'>, <TokenType.OVERLAPS: 'OVERLAPS'>, <TokenType.TEXT: 'TEXT'>, <TokenType.COLLATE: 'COLLATE'>, <TokenType.REFERENCES: 'REFERENCES'>, <TokenType.UPDATE: 'UPDATE'>, <TokenType.UUID: 'UUID'>, <TokenType.INT4RANGE: 'INT4RANGE'>, <TokenType.TINYBLOB: 'TINYBLOB'>, <TokenType.BIGDECIMAL: 'BIGDECIMAL'>, <TokenType.FIRST: 'FIRST'>, <TokenType.TIMESTAMP_S: 'TIMESTAMP_S'>, <TokenType.ISNULL: 'ISNULL'>, <TokenType.DOUBLE: 'DOUBLE'>, <TokenType.DEFAULT: 'DEFAULT'>, <TokenType.ROWS: 'ROWS'>, <TokenType.NUMRANGE: 'NUMRANGE'>, <TokenType.INDEX: 'INDEX'>, <TokenType.DATABASE: 'DATABASE'>, <TokenType.INT128: 'INT128'>, <TokenType.ALL: 'ALL'>, <TokenType.SET: 'SET'>, <TokenType.JSONB: 'JSONB'>, <TokenType.CACHE: 'CACHE'>, <TokenType.NULL: 'NULL'>, <TokenType.BOOLEAN: 'BOOLEAN'>, <TokenType.OPERATOR: 'OPERATOR'>, <TokenType.TSTZMULTIRANGE: 'TSTZMULTIRANGE'>, <TokenType.VARBINARY: 'VARBINARY'>, <TokenType.COMMENT: 'COMMENT'>, <TokenType.ROW: 'ROW'>, <TokenType.BIT: 'BIT'>, <TokenType.ENUM: 'ENUM'>, <TokenType.UDECIMAL: 'UDECIMAL'>, <TokenType.FALSE: 'FALSE'>, <TokenType.TIMESTAMP: 'TIMESTAMP'>, <TokenType.IMAGE: 'IMAGE'>, <TokenType.HLLSKETCH: 'HLLSKETCH'>, <TokenType.REFRESH: 'REFRESH'>, <TokenType.BIGINT: 'BIGINT'>, <TokenType.DATERANGE: 'DATERANGE'>, <TokenType.OBJECT_IDENTIFIER: 'OBJECT_IDENTIFIER'>, <TokenType.NEXT: 'NEXT'>, <TokenType.SOME: 'SOME'>, <TokenType.FUNCTION: 'FUNCTION'>, <TokenType.TEMPORARY: 'TEMPORARY'>, <TokenType.ASC: 'ASC'>, <TokenType.IPADDRESS: 'IPADDRESS'>, <TokenType.ARRAY: 'ARRAY'>, <TokenType.TINYTEXT: 'TINYTEXT'>, <TokenType.TIMESTAMPTZ: 'TIMESTAMPTZ'>, <TokenType.XML: 'XML'>, <TokenType.LOAD: 'LOAD'>, <TokenType.TIMESTAMP_NS: 'TIMESTAMP_NS'>, <TokenType.TIMETZ: 'TIMETZ'>, <TokenType.DATEMULTIRANGE: 'DATEMULTIRANGE'>, <TokenType.UNIQUEIDENTIFIER: 'UNIQUEIDENTIFIER'>, <TokenType.INTERVAL: 'INTERVAL'>, <TokenType.FIXEDSTRING: 'FIXEDSTRING'>, <TokenType.VARIANT: 'VARIANT'>, <TokenType.BINARY: 'BINARY'>, <TokenType.UMEDIUMINT: 'UMEDIUMINT'>, <TokenType.MERGE: 'MERGE'>, <TokenType.LONGBLOB: 'LONGBLOB'>, <TokenType.STRUCT: 'STRUCT'>, <TokenType.JSON: 'JSON'>, <TokenType.COLUMN: 'COLUMN'>, <TokenType.PSEUDO_TYPE: 'PSEUDO_TYPE'>, <TokenType.NESTED: 'NESTED'>, <TokenType.OBJECT: 'OBJECT'>, <TokenType.SETTINGS: 'SETTINGS'>, <TokenType.SMALLINT: 'SMALLINT'>, <TokenType.UNIQUE: 'UNIQUE'>, <TokenType.CONSTRAINT: 'CONSTRAINT'>, <TokenType.NULLABLE: 'NULLABLE'>, <TokenType.BEGIN: 'BEGIN'>, <TokenType.UINT: 'UINT'>, <TokenType.INT8MULTIRANGE: 'INT8MULTIRANGE'>, <TokenType.SHOW: 'SHOW'>, <TokenType.OVERWRITE: 'OVERWRITE'>, <TokenType.UNPIVOT: 'UNPIVOT'>, <TokenType.USE: 'USE'>, <TokenType.GEOMETRY: 'GEOMETRY'>, <TokenType.VOLATILE: 'VOLATILE'>, <TokenType.MODEL: 'MODEL'>, <TokenType.PROCEDURE: 'PROCEDURE'>, <TokenType.UINT256: 'UINT256'>, <TokenType.MEDIUMTEXT: 'MEDIUMTEXT'>, <TokenType.INT8RANGE: 'INT8RANGE'>, <TokenType.RANGE: 'RANGE'>, <TokenType.ESCAPE: 'ESCAPE'>, <TokenType.DESC: 'DESC'>, <TokenType.ANY: 'ANY'>, <TokenType.INET: 'INET'>, <TokenType.ENUM8: 'ENUM8'>, <TokenType.DECIMAL: 'DECIMAL'>, <TokenType.COMMIT: 'COMMIT'>, <TokenType.CURRENT_TIME: 'CURRENT_TIME'>, <TokenType.MAP: 'MAP'>, <TokenType.KILL: 'KILL'>, <TokenType.CURRENT_USER: 'CURRENT_USER'>, <TokenType.TIME: 'TIME'>, <TokenType.CURRENT_DATETIME: 'CURRENT_DATETIME'>, <TokenType.TIMESTAMPLTZ: 'TIMESTAMPLTZ'>, <TokenType.UBIGINT: 'UBIGINT'>, <TokenType.NVARCHAR: 'NVARCHAR'>, <TokenType.FOREIGN_KEY: 'FOREIGN_KEY'>, <TokenType.FLOAT: 'FLOAT'>, <TokenType.SERIAL: 'SERIAL'>, <TokenType.DESCRIBE: 'DESCRIBE'>, <TokenType.MEDIUMINT: 'MEDIUMINT'>, <TokenType.DIV: 'DIV'>, <TokenType.IS: 'IS'>, <TokenType.KEEP: 'KEEP'>, <TokenType.NCHAR: 'NCHAR'>, <TokenType.FILTER: 'FILTER'>, <TokenType.ENUM16: 'ENUM16'>, <TokenType.RECURSIVE: 'RECURSIVE'>, <TokenType.YEAR: 'YEAR'>, <TokenType.CHAR: 'CHAR'>, <TokenType.UTINYINT: 'UTINYINT'>, <TokenType.LOWCARDINALITY: 'LOWCARDINALITY'>, <TokenType.INT256: 'INT256'>, <TokenType.DATETIME: 'DATETIME'>, <TokenType.IPPREFIX: 'IPPREFIX'>, <TokenType.MEDIUMBLOB: 'MEDIUMBLOB'>, <TokenType.NUMMULTIRANGE: 'NUMMULTIRANGE'>, <TokenType.ANTI: 'ANTI'>, <TokenType.PIVOT: 'PIVOT'>, <TokenType.UNKNOWN: 'UNKNOWN'>, <TokenType.ORDINALITY: 'ORDINALITY'>, <TokenType.TRUE: 'TRUE'>, <TokenType.LONGTEXT: 'LONGTEXT'>, <TokenType.BIGSERIAL: 'BIGSERIAL'>, <TokenType.PERCENT: 'PERCENT'>, <TokenType.CURRENT_TIMESTAMP: 'CURRENT_TIMESTAMP'>, <TokenType.END: 'END'>, <TokenType.TABLE: 'TABLE'>, <TokenType.UINT128: 'UINT128'>, <TokenType.TOP: 'TOP'>, <TokenType.CURRENT_DATE: 'CURRENT_DATE'>, <TokenType.DELETE: 'DELETE'>, <TokenType.REPLACE: 'REPLACE'>, <TokenType.GEOGRAPHY: 'GEOGRAPHY'>, <TokenType.PARTITION: 'PARTITION'>, <TokenType.INT: 'INT'>, <TokenType.EXECUTE: 'EXECUTE'>, <TokenType.COMMAND: 'COMMAND'>, <TokenType.DICTIONARY: 'DICTIONARY'>, <TokenType.FORMAT: 'FORMAT'>, <TokenType.SUPER: 'SUPER'>, <TokenType.TSTZRANGE: 'TSTZRANGE'>, <TokenType.DATETIME64: 'DATETIME64'>, <TokenType.VIEW: 'VIEW'>, <TokenType.TSMULTIRANGE: 'TSMULTIRANGE'>, <TokenType.SMALLSERIAL: 'SMALLSERIAL'>, <TokenType.ROWVERSION: 'ROWVERSION'>, <TokenType.TSRANGE: 'TSRANGE'>, <TokenType.SEMI: 'SEMI'>, <TokenType.SCHEMA: 'SCHEMA'>, <TokenType.VARCHAR: 'VARCHAR'>, <TokenType.PRAGMA: 'PRAGMA'>, <TokenType.EXISTS: 'EXISTS'>, <TokenType.USMALLINT: 'USMALLINT'>}
    @@ -1632,7 +1658,7 @@ Default: 3
    TRANSACTION_CHARACTERISTICS
    INSERT_ALTERNATIVES
    CLONE_KEYWORDS
    -
    CLONE_KINDS
    +
    HISTORICAL_DATA_KIND
    OPCLASS_FOLLOW_KEYWORDS
    OPTYPE_FOLLOW_TOKENS
    TABLE_INDEX_HINT_TOKENS
    @@ -1645,7 +1671,6 @@ Default: 3
    NULL_TOKENS
    UNNEST_OFFSET_ALIAS_TOKENS
    STRICT_CAST
    -
    CONCAT_NULL_OUTPUTS_STRING
    PREFIXED_PIVOT_COLUMNS
    IDENTIFY_PIVOT_STRINGS
    LOG_DEFAULTS_TO_LN
    @@ -1653,6 +1678,8 @@ Default: 3
    TABLESAMPLE_CSV
    SET_REQUIRES_ASSIGNMENT_DELIMITER
    TRIM_PATTERN_FIRST
    +
    MODIFIERS_ATTACHED_TO_UNION
    +
    UNION_MODIFIERS
    error_level
    error_message_context
    max_errors
    @@ -1682,208 +1709,214 @@ Default: 3
    -
    267    class Generator(generator.Generator):
    -268        INTERVAL_ALLOWS_PLURAL_FORM = False
    -269        JOIN_HINTS = False
    -270        TABLE_HINTS = False
    -271        QUERY_HINTS = False
    -272        IS_BOOL_ALLOWED = False
    -273        TZ_TO_WITH_TIME_ZONE = True
    -274        NVL2_SUPPORTED = False
    -275        STRUCT_DELIMITER = ("(", ")")
    -276        LIMIT_ONLY_LITERALS = True
    -277
    -278        PROPERTIES_LOCATION = {
    -279            **generator.Generator.PROPERTIES_LOCATION,
    -280            exp.LocationProperty: exp.Properties.Location.UNSUPPORTED,
    -281            exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED,
    -282        }
    -283
    -284        TYPE_MAPPING = {
    -285            **generator.Generator.TYPE_MAPPING,
    -286            exp.DataType.Type.INT: "INTEGER",
    -287            exp.DataType.Type.FLOAT: "REAL",
    -288            exp.DataType.Type.BINARY: "VARBINARY",
    -289            exp.DataType.Type.TEXT: "VARCHAR",
    -290            exp.DataType.Type.TIMETZ: "TIME",
    -291            exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP",
    -292            exp.DataType.Type.STRUCT: "ROW",
    -293            exp.DataType.Type.DATETIME: "TIMESTAMP",
    -294            exp.DataType.Type.DATETIME64: "TIMESTAMP",
    -295        }
    -296
    -297        TRANSFORMS = {
    -298            **generator.Generator.TRANSFORMS,
    -299            exp.AnyValue: rename_func("ARBITRARY"),
    -300            exp.ApproxDistinct: _approx_distinct_sql,
    -301            exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"),
    -302            exp.ArgMax: rename_func("MAX_BY"),
    -303            exp.ArgMin: rename_func("MIN_BY"),
    -304            exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]",
    -305            exp.ArrayConcat: rename_func("CONCAT"),
    -306            exp.ArrayContains: rename_func("CONTAINS"),
    -307            exp.ArraySize: rename_func("CARDINALITY"),
    -308            exp.ArrayUniqueAgg: rename_func("SET_AGG"),
    -309            exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -310            exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -311            exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})",
    -312            exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -313            exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -314            exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    -315            exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    -316            exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP",
    -317            exp.DateAdd: lambda self, e: self.func(
    -318                "DATE_ADD", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    -319            ),
    -320            exp.DateDiff: lambda self, e: self.func(
    -321                "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    -322            ),
    -323            exp.DateStrToDate: datestrtodate_sql,
    -324            exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)",
    -325            exp.DateSub: lambda self, e: self.func(
    -326                "DATE_ADD",
    -327                exp.Literal.string(e.text("unit") or "day"),
    -328                e.expression * -1,
    -329                e.this,
    -330            ),
    -331            exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"),
    -332            exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)",
    -333            exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"),
    -334            exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'",
    -335            exp.First: _first_last_sql,
    -336            exp.Group: transforms.preprocess([transforms.unalias_group]),
    -337            exp.GroupConcat: lambda self, e: self.func(
    -338                "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator")
    -339            ),
    -340            exp.Hex: rename_func("TO_HEX"),
    -341            exp.If: if_sql(),
    -342            exp.ILike: no_ilike_sql,
    -343            exp.Initcap: _initcap_sql,
    -344            exp.ParseJSON: rename_func("JSON_PARSE"),
    -345            exp.Last: _first_last_sql,
    -346            exp.Lateral: _explode_to_unnest_sql,
    -347            exp.Left: left_to_substring_sql,
    -348            exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"),
    -349            exp.LogicalAnd: rename_func("BOOL_AND"),
    -350            exp.LogicalOr: rename_func("BOOL_OR"),
    -351            exp.Pivot: no_pivot_sql,
    -352            exp.Quantile: _quantile_sql,
    -353            exp.RegexpExtract: regexp_extract_sql,
    -354            exp.Right: right_to_substring_sql,
    -355            exp.SafeDivide: no_safe_divide_sql,
    -356            exp.Schema: _schema_sql,
    -357            exp.Select: transforms.preprocess(
    -358                [
    -359                    transforms.eliminate_qualify,
    -360                    transforms.eliminate_distinct_on,
    -361                    transforms.explode_to_unnest(1),
    -362                    transforms.eliminate_semi_and_anti_joins,
    -363                ]
    -364            ),
    -365            exp.SortArray: _no_sort_array,
    -366            exp.StrPosition: rename_func("STRPOS"),
    -367            exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)",
    -368            exp.StrToMap: rename_func("SPLIT_TO_MAP"),
    -369            exp.StrToTime: _str_to_time_sql,
    -370            exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))",
    -371            exp.StructExtract: struct_extract_sql,
    -372            exp.Table: transforms.preprocess([_unnest_sequence]),
    -373            exp.Timestamp: no_timestamp_sql,
    -374            exp.TimestampTrunc: timestamptrunc_sql,
    -375            exp.TimeStrToDate: timestrtotime_sql,
    -376            exp.TimeStrToTime: timestrtotime_sql,
    -377            exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))",
    -378            exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})",
    -379            exp.TimeToUnix: rename_func("TO_UNIXTIME"),
    -380            exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    -381            exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)",
    -382            exp.TsOrDsAdd: _ts_or_ds_add_sql,
    -383            exp.TsOrDsDiff: _ts_or_ds_diff_sql,
    -384            exp.TsOrDsToDate: _ts_or_ds_to_date_sql,
    -385            exp.Unhex: rename_func("FROM_HEX"),
    -386            exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})",
    -387            exp.UnixToTime: _unix_to_time_sql,
    -388            exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)",
    -389            exp.VariancePop: rename_func("VAR_POP"),
    -390            exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]),
    -391            exp.WithinGroup: transforms.preprocess(
    -392                [transforms.remove_within_group_for_percentiles]
    -393            ),
    -394            exp.Xor: bool_xor_sql,
    -395        }
    -396
    -397        def bracket_sql(self, expression: exp.Bracket) -> str:
    -398            if expression.args.get("safe"):
    -399                return self.func(
    -400                    "ELEMENT_AT",
    -401                    expression.this,
    -402                    seq_get(
    -403                        apply_index_offset(
    -404                            expression.this,
    -405                            expression.expressions,
    -406                            1 - expression.args.get("offset", 0),
    -407                        ),
    -408                        0,
    -409                    ),
    -410                )
    -411            return super().bracket_sql(expression)
    +            
    277    class Generator(generator.Generator):
    +278        INTERVAL_ALLOWS_PLURAL_FORM = False
    +279        JOIN_HINTS = False
    +280        TABLE_HINTS = False
    +281        QUERY_HINTS = False
    +282        IS_BOOL_ALLOWED = False
    +283        TZ_TO_WITH_TIME_ZONE = True
    +284        NVL2_SUPPORTED = False
    +285        STRUCT_DELIMITER = ("(", ")")
    +286        LIMIT_ONLY_LITERALS = True
    +287        SUPPORTS_SINGLE_ARG_CONCAT = False
    +288
    +289        PROPERTIES_LOCATION = {
    +290            **generator.Generator.PROPERTIES_LOCATION,
    +291            exp.LocationProperty: exp.Properties.Location.UNSUPPORTED,
    +292            exp.VolatileProperty: exp.Properties.Location.UNSUPPORTED,
    +293        }
    +294
    +295        TYPE_MAPPING = {
    +296            **generator.Generator.TYPE_MAPPING,
    +297            exp.DataType.Type.INT: "INTEGER",
    +298            exp.DataType.Type.FLOAT: "REAL",
    +299            exp.DataType.Type.BINARY: "VARBINARY",
    +300            exp.DataType.Type.TEXT: "VARCHAR",
    +301            exp.DataType.Type.TIMETZ: "TIME",
    +302            exp.DataType.Type.TIMESTAMPTZ: "TIMESTAMP",
    +303            exp.DataType.Type.STRUCT: "ROW",
    +304            exp.DataType.Type.DATETIME: "TIMESTAMP",
    +305            exp.DataType.Type.DATETIME64: "TIMESTAMP",
    +306        }
    +307
    +308        TRANSFORMS = {
    +309            **generator.Generator.TRANSFORMS,
    +310            exp.AnyValue: rename_func("ARBITRARY"),
    +311            exp.ApproxDistinct: _approx_distinct_sql,
    +312            exp.ApproxQuantile: rename_func("APPROX_PERCENTILE"),
    +313            exp.ArgMax: rename_func("MAX_BY"),
    +314            exp.ArgMin: rename_func("MIN_BY"),
    +315            exp.Array: lambda self, e: f"ARRAY[{self.expressions(e, flat=True)}]",
    +316            exp.ArrayConcat: rename_func("CONCAT"),
    +317            exp.ArrayContains: rename_func("CONTAINS"),
    +318            exp.ArraySize: rename_func("CARDINALITY"),
    +319            exp.ArrayUniqueAgg: rename_func("SET_AGG"),
    +320            exp.BitwiseAnd: lambda self, e: f"BITWISE_AND({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +321            exp.BitwiseLeftShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_LEFT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +322            exp.BitwiseNot: lambda self, e: f"BITWISE_NOT({self.sql(e, 'this')})",
    +323            exp.BitwiseOr: lambda self, e: f"BITWISE_OR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +324            exp.BitwiseRightShift: lambda self, e: f"BITWISE_ARITHMETIC_SHIFT_RIGHT({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +325            exp.BitwiseXor: lambda self, e: f"BITWISE_XOR({self.sql(e, 'this')}, {self.sql(e, 'expression')})",
    +326            exp.Cast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    +327            exp.CurrentTimestamp: lambda *_: "CURRENT_TIMESTAMP",
    +328            exp.DateAdd: lambda self, e: self.func(
    +329                "DATE_ADD",
    +330                exp.Literal.string(e.text("unit") or "day"),
    +331                _to_int(
    +332                    e.expression,
    +333                ),
    +334                e.this,
    +335            ),
    +336            exp.DateDiff: lambda self, e: self.func(
    +337                "DATE_DIFF", exp.Literal.string(e.text("unit") or "day"), e.expression, e.this
    +338            ),
    +339            exp.DateStrToDate: datestrtodate_sql,
    +340            exp.DateToDi: lambda self, e: f"CAST(DATE_FORMAT({self.sql(e, 'this')}, {Presto.DATEINT_FORMAT}) AS INT)",
    +341            exp.DateSub: lambda self, e: self.func(
    +342                "DATE_ADD",
    +343                exp.Literal.string(e.text("unit") or "day"),
    +344                _to_int(e.expression * -1),
    +345                e.this,
    +346            ),
    +347            exp.Decode: lambda self, e: encode_decode_sql(self, e, "FROM_UTF8"),
    +348            exp.DiToDate: lambda self, e: f"CAST(DATE_PARSE(CAST({self.sql(e, 'this')} AS VARCHAR), {Presto.DATEINT_FORMAT}) AS DATE)",
    +349            exp.Encode: lambda self, e: encode_decode_sql(self, e, "TO_UTF8"),
    +350            exp.FileFormatProperty: lambda self, e: f"FORMAT='{e.name.upper()}'",
    +351            exp.First: _first_last_sql,
    +352            exp.Group: transforms.preprocess([transforms.unalias_group]),
    +353            exp.GroupConcat: lambda self, e: self.func(
    +354                "ARRAY_JOIN", self.func("ARRAY_AGG", e.this), e.args.get("separator")
    +355            ),
    +356            exp.Hex: rename_func("TO_HEX"),
    +357            exp.If: if_sql(),
    +358            exp.ILike: no_ilike_sql,
    +359            exp.Initcap: _initcap_sql,
    +360            exp.ParseJSON: rename_func("JSON_PARSE"),
    +361            exp.Last: _first_last_sql,
    +362            exp.Lateral: _explode_to_unnest_sql,
    +363            exp.Left: left_to_substring_sql,
    +364            exp.Levenshtein: rename_func("LEVENSHTEIN_DISTANCE"),
    +365            exp.LogicalAnd: rename_func("BOOL_AND"),
    +366            exp.LogicalOr: rename_func("BOOL_OR"),
    +367            exp.Pivot: no_pivot_sql,
    +368            exp.Quantile: _quantile_sql,
    +369            exp.RegexpExtract: regexp_extract_sql,
    +370            exp.Right: right_to_substring_sql,
    +371            exp.SafeDivide: no_safe_divide_sql,
    +372            exp.Schema: _schema_sql,
    +373            exp.Select: transforms.preprocess(
    +374                [
    +375                    transforms.eliminate_qualify,
    +376                    transforms.eliminate_distinct_on,
    +377                    transforms.explode_to_unnest(1),
    +378                    transforms.eliminate_semi_and_anti_joins,
    +379                ]
    +380            ),
    +381            exp.SortArray: _no_sort_array,
    +382            exp.StrPosition: rename_func("STRPOS"),
    +383            exp.StrToDate: lambda self, e: f"CAST({_str_to_time_sql(self, e)} AS DATE)",
    +384            exp.StrToMap: rename_func("SPLIT_TO_MAP"),
    +385            exp.StrToTime: _str_to_time_sql,
    +386            exp.StrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {self.format_time(e)}))",
    +387            exp.StructExtract: struct_extract_sql,
    +388            exp.Table: transforms.preprocess([_unnest_sequence]),
    +389            exp.Timestamp: no_timestamp_sql,
    +390            exp.TimestampTrunc: timestamptrunc_sql,
    +391            exp.TimeStrToDate: timestrtotime_sql,
    +392            exp.TimeStrToTime: timestrtotime_sql,
    +393            exp.TimeStrToUnix: lambda self, e: f"TO_UNIXTIME(DATE_PARSE({self.sql(e, 'this')}, {Presto.TIME_FORMAT}))",
    +394            exp.TimeToStr: lambda self, e: f"DATE_FORMAT({self.sql(e, 'this')}, {self.format_time(e)})",
    +395            exp.TimeToUnix: rename_func("TO_UNIXTIME"),
    +396            exp.TryCast: transforms.preprocess([transforms.epoch_cast_to_ts]),
    +397            exp.TsOrDiToDi: lambda self, e: f"CAST(SUBSTR(REPLACE(CAST({self.sql(e, 'this')} AS VARCHAR), '-', ''), 1, 8) AS INT)",
    +398            exp.TsOrDsAdd: _ts_or_ds_add_sql,
    +399            exp.TsOrDsDiff: _ts_or_ds_diff_sql,
    +400            exp.TsOrDsToDate: _ts_or_ds_to_date_sql,
    +401            exp.Unhex: rename_func("FROM_HEX"),
    +402            exp.UnixToStr: lambda self, e: f"DATE_FORMAT(FROM_UNIXTIME({self.sql(e, 'this')}), {self.format_time(e)})",
    +403            exp.UnixToTime: _unix_to_time_sql,
    +404            exp.UnixToTimeStr: lambda self, e: f"CAST(FROM_UNIXTIME({self.sql(e, 'this')}) AS VARCHAR)",
    +405            exp.VariancePop: rename_func("VAR_POP"),
    +406            exp.With: transforms.preprocess([transforms.add_recursive_cte_column_names]),
    +407            exp.WithinGroup: transforms.preprocess(
    +408                [transforms.remove_within_group_for_percentiles]
    +409            ),
    +410            exp.Xor: bool_xor_sql,
    +411        }
     412
    -413        def struct_sql(self, expression: exp.Struct) -> str:
    -414            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    -415                self.unsupported("Struct with key-value definitions is unsupported.")
    -416                return self.function_fallback_sql(expression)
    -417
    -418            return rename_func("ROW")(self, expression)
    -419
    -420        def interval_sql(self, expression: exp.Interval) -> str:
    -421            unit = self.sql(expression, "unit")
    -422            if expression.this and unit.lower().startswith("week"):
    -423                return f"({expression.this.name} * INTERVAL '7' day)"
    -424            return super().interval_sql(expression)
    -425
    -426        def transaction_sql(self, expression: exp.Transaction) -> str:
    -427            modes = expression.args.get("modes")
    -428            modes = f" {', '.join(modes)}" if modes else ""
    -429            return f"START TRANSACTION{modes}"
    -430
    -431        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    -432            start = expression.args["start"]
    -433            end = expression.args["end"]
    -434            step = expression.args.get("step")
    +413        def bracket_sql(self, expression: exp.Bracket) -> str:
    +414            if expression.args.get("safe"):
    +415                return self.func(
    +416                    "ELEMENT_AT",
    +417                    expression.this,
    +418                    seq_get(
    +419                        apply_index_offset(
    +420                            expression.this,
    +421                            expression.expressions,
    +422                            1 - expression.args.get("offset", 0),
    +423                        ),
    +424                        0,
    +425                    ),
    +426                )
    +427            return super().bracket_sql(expression)
    +428
    +429        def struct_sql(self, expression: exp.Struct) -> str:
    +430            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    +431                self.unsupported("Struct with key-value definitions is unsupported.")
    +432                return self.function_fallback_sql(expression)
    +433
    +434            return rename_func("ROW")(self, expression)
     435
    -436            if isinstance(start, exp.Cast):
    -437                target_type = start.to
    -438            elif isinstance(end, exp.Cast):
    -439                target_type = end.to
    -440            else:
    -441                target_type = None
    -442
    -443            if target_type and target_type.is_type("timestamp"):
    -444                if target_type is start.to:
    -445                    end = exp.cast(end, target_type)
    -446                else:
    -447                    start = exp.cast(start, target_type)
    -448
    -449            return self.func("SEQUENCE", start, end, step)
    -450
    -451        def offset_limit_modifiers(
    -452            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    -453        ) -> t.List[str]:
    -454            return [
    -455                self.sql(expression, "offset"),
    -456                self.sql(limit),
    -457            ]
    +436        def interval_sql(self, expression: exp.Interval) -> str:
    +437            unit = self.sql(expression, "unit")
    +438            if expression.this and unit.lower().startswith("week"):
    +439                return f"({expression.this.name} * INTERVAL '7' day)"
    +440            return super().interval_sql(expression)
    +441
    +442        def transaction_sql(self, expression: exp.Transaction) -> str:
    +443            modes = expression.args.get("modes")
    +444            modes = f" {', '.join(modes)}" if modes else ""
    +445            return f"START TRANSACTION{modes}"
    +446
    +447        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    +448            start = expression.args["start"]
    +449            end = expression.args["end"]
    +450            step = expression.args.get("step")
    +451
    +452            if isinstance(start, exp.Cast):
    +453                target_type = start.to
    +454            elif isinstance(end, exp.Cast):
    +455                target_type = end.to
    +456            else:
    +457                target_type = None
     458
    -459        def create_sql(self, expression: exp.Create) -> str:
    -460            """
    -461            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    -462            so we need to remove them
    -463            """
    -464            kind = expression.args["kind"]
    -465            schema = expression.this
    -466            if kind == "VIEW" and schema.expressions:
    -467                expression.this.set("expressions", None)
    -468            return super().create_sql(expression)
    +459            if target_type and target_type.is_type("timestamp"):
    +460                if target_type is start.to:
    +461                    end = exp.cast(end, target_type)
    +462                else:
    +463                    start = exp.cast(start, target_type)
    +464
    +465            return self.func("SEQUENCE", start, end, step)
    +466
    +467        def offset_limit_modifiers(
    +468            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    +469        ) -> t.List[str]:
    +470            return [
    +471                self.sql(expression, "offset"),
    +472                self.sql(limit),
    +473            ]
    +474
    +475        def create_sql(self, expression: exp.Create) -> str:
    +476            """
    +477            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    +478            so we need to remove them
    +479            """
    +480            kind = expression.args["kind"]
    +481            schema = expression.this
    +482            if kind == "VIEW" and schema.expressions:
    +483                expression.this.set("expressions", None)
    +484            return super().create_sql(expression)
     
    @@ -2033,6 +2066,18 @@ Default: True +
    +
    +
    + SUPPORTS_SINGLE_ARG_CONCAT = +False + + +
    + + + +
    @@ -2084,21 +2129,21 @@ Default: True
    -
    397        def bracket_sql(self, expression: exp.Bracket) -> str:
    -398            if expression.args.get("safe"):
    -399                return self.func(
    -400                    "ELEMENT_AT",
    -401                    expression.this,
    -402                    seq_get(
    -403                        apply_index_offset(
    -404                            expression.this,
    -405                            expression.expressions,
    -406                            1 - expression.args.get("offset", 0),
    -407                        ),
    -408                        0,
    -409                    ),
    -410                )
    -411            return super().bracket_sql(expression)
    +            
    413        def bracket_sql(self, expression: exp.Bracket) -> str:
    +414            if expression.args.get("safe"):
    +415                return self.func(
    +416                    "ELEMENT_AT",
    +417                    expression.this,
    +418                    seq_get(
    +419                        apply_index_offset(
    +420                            expression.this,
    +421                            expression.expressions,
    +422                            1 - expression.args.get("offset", 0),
    +423                        ),
    +424                        0,
    +425                    ),
    +426                )
    +427            return super().bracket_sql(expression)
     
    @@ -2116,12 +2161,12 @@ Default: True
    -
    413        def struct_sql(self, expression: exp.Struct) -> str:
    -414            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    -415                self.unsupported("Struct with key-value definitions is unsupported.")
    -416                return self.function_fallback_sql(expression)
    -417
    -418            return rename_func("ROW")(self, expression)
    +            
    429        def struct_sql(self, expression: exp.Struct) -> str:
    +430            if any(isinstance(arg, self.KEY_VALUE_DEFINITONS) for arg in expression.expressions):
    +431                self.unsupported("Struct with key-value definitions is unsupported.")
    +432                return self.function_fallback_sql(expression)
    +433
    +434            return rename_func("ROW")(self, expression)
     
    @@ -2139,11 +2184,11 @@ Default: True
    -
    420        def interval_sql(self, expression: exp.Interval) -> str:
    -421            unit = self.sql(expression, "unit")
    -422            if expression.this and unit.lower().startswith("week"):
    -423                return f"({expression.this.name} * INTERVAL '7' day)"
    -424            return super().interval_sql(expression)
    +            
    436        def interval_sql(self, expression: exp.Interval) -> str:
    +437            unit = self.sql(expression, "unit")
    +438            if expression.this and unit.lower().startswith("week"):
    +439                return f"({expression.this.name} * INTERVAL '7' day)"
    +440            return super().interval_sql(expression)
     
    @@ -2161,10 +2206,10 @@ Default: True
    -
    426        def transaction_sql(self, expression: exp.Transaction) -> str:
    -427            modes = expression.args.get("modes")
    -428            modes = f" {', '.join(modes)}" if modes else ""
    -429            return f"START TRANSACTION{modes}"
    +            
    442        def transaction_sql(self, expression: exp.Transaction) -> str:
    +443            modes = expression.args.get("modes")
    +444            modes = f" {', '.join(modes)}" if modes else ""
    +445            return f"START TRANSACTION{modes}"
     
    @@ -2182,25 +2227,25 @@ Default: True
    -
    431        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    -432            start = expression.args["start"]
    -433            end = expression.args["end"]
    -434            step = expression.args.get("step")
    -435
    -436            if isinstance(start, exp.Cast):
    -437                target_type = start.to
    -438            elif isinstance(end, exp.Cast):
    -439                target_type = end.to
    -440            else:
    -441                target_type = None
    -442
    -443            if target_type and target_type.is_type("timestamp"):
    -444                if target_type is start.to:
    -445                    end = exp.cast(end, target_type)
    -446                else:
    -447                    start = exp.cast(start, target_type)
    -448
    -449            return self.func("SEQUENCE", start, end, step)
    +            
    447        def generateseries_sql(self, expression: exp.GenerateSeries) -> str:
    +448            start = expression.args["start"]
    +449            end = expression.args["end"]
    +450            step = expression.args.get("step")
    +451
    +452            if isinstance(start, exp.Cast):
    +453                target_type = start.to
    +454            elif isinstance(end, exp.Cast):
    +455                target_type = end.to
    +456            else:
    +457                target_type = None
    +458
    +459            if target_type and target_type.is_type("timestamp"):
    +460                if target_type is start.to:
    +461                    end = exp.cast(end, target_type)
    +462                else:
    +463                    start = exp.cast(start, target_type)
    +464
    +465            return self.func("SEQUENCE", start, end, step)
     
    @@ -2218,13 +2263,13 @@ Default: True
    -
    451        def offset_limit_modifiers(
    -452            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    -453        ) -> t.List[str]:
    -454            return [
    -455                self.sql(expression, "offset"),
    -456                self.sql(limit),
    -457            ]
    +            
    467        def offset_limit_modifiers(
    +468            self, expression: exp.Expression, fetch: bool, limit: t.Optional[exp.Fetch | exp.Limit]
    +469        ) -> t.List[str]:
    +470            return [
    +471                self.sql(expression, "offset"),
    +472                self.sql(limit),
    +473            ]
     
    @@ -2242,16 +2287,16 @@ Default: True
    -
    459        def create_sql(self, expression: exp.Create) -> str:
    -460            """
    -461            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    -462            so we need to remove them
    -463            """
    -464            kind = expression.args["kind"]
    -465            schema = expression.this
    -466            if kind == "VIEW" and schema.expressions:
    -467                expression.this.set("expressions", None)
    -468            return super().create_sql(expression)
    +            
    475        def create_sql(self, expression: exp.Create) -> str:
    +476            """
    +477            Presto doesn't support CREATE VIEW with expressions (ex: `CREATE VIEW x (cola)` then `(cola)` is the expression),
    +478            so we need to remove them
    +479            """
    +480            kind = expression.args["kind"]
    +481            schema = expression.this
    +482            if kind == "VIEW" and schema.expressions:
    +483                expression.this.set("expressions", None)
    +484            return super().create_sql(expression)
     
    @@ -2420,6 +2465,7 @@ so we need to remove them

    rowformatdelimitedproperty_sql
    withtablehint_sql
    indextablehint_sql
    +
    historicaldata_sql
    table_sql
    tablesample_sql
    pivot_sql
    @@ -2483,7 +2529,9 @@ so we need to remove them

    nextvaluefor_sql
    extract_sql
    trim_sql
    +
    convert_concat_args
    concat_sql
    +
    concatws_sql
    check_sql
    foreignkey_sql
    primarykey_sql
    -- cgit v1.2.3