Skip to content

Commit 8583c2d

Browse files
jvsteingeorgesittas
authored andcommitted
Fix: correctly handle follow-tokens for unit-less intervals (#7529)
1 parent 9f2f894 commit 8583c2d

3 files changed

Lines changed: 29 additions & 11 deletions

File tree

sqlglot/parser.py

Lines changed: 9 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5829,17 +5829,15 @@ def _parse_interval_span(self, this: exp.Expr) -> exp.Interval:
58295829

58305830
self._retreat(index)
58315831

5832-
unit = (
5833-
None
5834-
if interval_span_units_omitted
5835-
else (
5836-
self._parse_function()
5837-
or (
5838-
not self._match_set((TokenType.ALIAS, TokenType.DCOLON), advance=False)
5839-
and self._parse_var(any_token=True, upper=True)
5840-
)
5841-
)
5842-
)
5832+
if interval_span_units_omitted:
5833+
unit = None
5834+
else:
5835+
unit = self._parse_function()
5836+
if not unit and (
5837+
self._curr.token_type == TokenType.VAR
5838+
or self._curr.text.upper() in self.dialect.VALID_INTERVAL_UNITS
5839+
):
5840+
unit = self._parse_var(any_token=True, upper=True)
58435841

58445842
# Most dialects support, e.g., the form INTERVAL '5' day, thus we try to parse
58455843
# each INTERVAL expression into this canonical form so it's easy to transpile

tests/dialects/test_postgres.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,16 @@ def test_postgres(self):
9191
self.validate_identity("SELECT INTERVAL '2.5 MONTH'")
9292
self.validate_identity("SELECT INTERVAL '-10.75 MINUTE'")
9393
self.validate_identity("SELECT INTERVAL '0.123456789 SECOND'")
94+
self.validate_identity("SELECT date_col - INTERVAL '30' FROM t")
95+
self.validate_identity("SELECT date_col - INTERVAL '1' AS one_second_later")
96+
self.validate_identity(
97+
"SELECT date_col - INTERVAL '30' DAY FROM t",
98+
"SELECT date_col - INTERVAL '30 DAY' FROM t",
99+
)
100+
self.validate_identity(
101+
"SELECT date_col - INTERVAL '1' HOUR AS one_hour_later",
102+
"SELECT date_col - INTERVAL '1 HOUR' AS one_hour_later",
103+
)
94104
self.validate_identity(
95105
"SELECT SUM(x) OVER (PARTITION BY y ORDER BY interval ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) - SUM(x) OVER (PARTITION BY y ORDER BY interval ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS total"
96106
)

tests/dialects/test_redshift.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -344,6 +344,16 @@ def test_identity(self):
344344
self.validate_identity("SELECT DATEADD(DAY, 1, 'today')")
345345
self.validate_identity("SELECT * FROM #x")
346346
self.validate_identity("SELECT INTERVAL '5 DAY'")
347+
self.validate_identity("SELECT date_col - INTERVAL '30' FROM t")
348+
self.validate_identity("SELECT date_col - INTERVAL '1' AS one_second_later")
349+
self.validate_identity(
350+
"SELECT date_col - INTERVAL '30' DAY FROM t",
351+
"SELECT date_col - INTERVAL '30 DAY' FROM t",
352+
)
353+
self.validate_identity(
354+
"SELECT date_col - INTERVAL '1' HOUR AS one_hour_later",
355+
"SELECT date_col - INTERVAL '1 HOUR' AS one_hour_later",
356+
)
347357
self.validate_identity("foo$")
348358
self.validate_identity("CAST('bla' AS SUPER)")
349359
self.validate_identity("CREATE TABLE real1 (realcol REAL)")

0 commit comments

Comments
 (0)