Skip to content

Commit

Permalink
only qualify non-alias column references in the having clause (#635)
Browse files Browse the repository at this point in the history
* only qualify non-alias column references in the having clause

* rename other_columns

Co-authored-by: Chris Ginter <chris_ginter@airbnb.com>
  • Loading branch information
ginter and Chris Ginter committed Oct 24, 2022
1 parent 18eca15 commit ff5f6b1
Show file tree
Hide file tree
Showing 3 changed files with 31 additions and 9 deletions.
21 changes: 13 additions & 8 deletions sqlglot/optimizer/qualify_columns.py
Original file line number Diff line number Diff line change
Expand Up @@ -211,21 +211,26 @@ def _qualify_columns(scope, resolver):
if column_table:
column.set("table", exp.to_identifier(column_table))

columns_missing_from_scope = []
# Determine whether each reference in the order by clause is to a column or an alias.
for ordered in scope.find_all(exp.Ordered):
for column in ordered.find_all(exp.Column):
column_table = column.table
column_name = column.name
if not column.table and column.parent is not ordered and column.name in resolver.all_columns:
columns_missing_from_scope.append(column)

if column_table or column.parent is ordered or column_name not in resolver.all_columns:
continue
# Determine whether each reference in the having clause is to a column or an alias.
for having in scope.find_all(exp.Having):
for column in having.find_all(exp.Column):
if not column.table and column.find_ancestor(exp.AggFunc) and column.name in resolver.all_columns:
columns_missing_from_scope.append(column)

column_table = resolver.get_table(column_name)
for column in columns_missing_from_scope:
column_table = resolver.get_table(column.name)

if column_table is None:
raise OptimizeError(f"Ambiguous column: {column_name}")
if column_table is None:
raise OptimizeError(f"Ambiguous column: {column.name}")

column.set("table", exp.to_identifier(column_table))
column.set("table", exp.to_identifier(column_table))


def _expand_stars(scope, resolver):
Expand Down
2 changes: 1 addition & 1 deletion sqlglot/optimizer/scope.py
Original file line number Diff line number Diff line change
Expand Up @@ -232,7 +232,7 @@ def columns(self):

self._columns = []
for column in columns + external_columns:
ancestor = column.find_ancestor(exp.Qualify, exp.Order, exp.Hint)
ancestor = column.find_ancestor(exp.Qualify, exp.Order, exp.Having, exp.Hint)
if (
not ancestor
or column.table
Expand Down
17 changes: 17 additions & 0 deletions tests/fixtures/optimizer/qualify_columns.sql
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,23 @@ SELECT x.a + x.b AS "_col_0" FROM x AS x;
SELECT a, SUM(b) FROM x WHERE a > 1 AND b > 1 GROUP BY a;
SELECT x.a AS a, SUM(x.b) AS "_col_1" FROM x AS x WHERE x.a > 1 AND x.b > 1 GROUP BY x.a;

SELECT SUM(a) AS c FROM x HAVING SUM(a) > 3;
SELECT SUM(x.a) AS c FROM x AS x HAVING SUM(x.a) > 3;

SELECT SUM(a) AS a FROM x HAVING SUM(a) > 3;
SELECT SUM(x.a) AS a FROM x AS x HAVING SUM(x.a) > 3;

SELECT SUM(a) AS c FROM x HAVING c > 3;
SELECT SUM(x.a) AS c FROM x AS x HAVING c > 3;

# execute: false
SELECT SUM(a) AS a FROM x HAVING a > 3;
SELECT SUM(x.a) AS a FROM x AS x HAVING a > 3;

# execute: false
SELECT SUM(a) AS c FROM x HAVING SUM(c) > 3;
SELECT SUM(x.a) AS c FROM x AS x HAVING SUM(c) > 3;

SELECT a AS j, b FROM x ORDER BY j;
SELECT x.a AS j, x.b AS b FROM x AS x ORDER BY j;

Expand Down

0 comments on commit ff5f6b1

Please sign in to comment.