Hello community,
here is the log from the commit of package python-python-sql for
openSUSE:Factory checked in at 2020-10-07 14:18:15
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-python-sql (Old)
and /work/SRC/openSUSE:Factory/.python-python-sql.new.4249 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-python-sql"
Wed Oct 7 14:18:15 2020 rev:5 rq:839885 version:1.2.0
Changes:
--------
--- /work/SRC/openSUSE:Factory/python-python-sql/python-python-sql.changes
2020-01-27 20:16:59.320506081 +0100
+++
/work/SRC/openSUSE:Factory/.python-python-sql.new.4249/python-python-sql.changes
2020-10-07 14:18:23.049480805 +0200
@@ -1,0 +2,7 @@
+Tue Oct 6 08:20:02 UTC 2020 - Axel Braun <[email protected]>
+
+- Version 1.2.0
+ * Add explicit Windows to Select
+ * Fix missing Windows definitions in nested expressions
+
+-------------------------------------------------------------------
Old:
----
python-sql-1.1.0.tar.gz
New:
----
python-sql-1.2.0.tar.gz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ python-python-sql.spec ++++++
--- /var/tmp/diff_new_pack.EkEC8t/_old 2020-10-07 14:18:23.609481250 +0200
+++ /var/tmp/diff_new_pack.EkEC8t/_new 2020-10-07 14:18:23.613481253 +0200
@@ -1,7 +1,7 @@
#
# spec file for package python-python-sql
#
-# Copyright (c) 2018 SUSE LINUX GmbH, Nuernberg, Germany.
+# Copyright (c) 2020 SUSE LLC
#
# All modifications and additions to the file contributed by third parties
# remain the property of their copyright owners, unless otherwise agreed
@@ -19,7 +19,7 @@
%{?!python_module:%define python_module() python-%{**} python3-%{**}}
%define base_name python-sql
Name: python-%{base_name}
-Version: 1.1.0
+Version: 1.2.0
Release: 0
Summary: Library to write SQL queries
License: BSD-3-Clause
++++++ python-sql-1.1.0.tar.gz -> python-sql-1.2.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/.drone.yml
new/python-sql-1.2.0/.drone.yml
--- old/python-sql-1.1.0/.drone.yml 2019-12-26 10:47:34.000000000 +0100
+++ new/python-sql-1.2.0/.drone.yml 2020-10-02 21:26:48.000000000 +0200
@@ -19,8 +19,6 @@
include:
- IMAGE: python:2.7
TOXENV: py27
- - IMAGE: python:3.4
- TOXENV: py34
- IMAGE: python:3.5
TOXENV: py35
- IMAGE: python:3.6
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/.flake8 new/python-sql-1.2.0/.flake8
--- old/python-sql-1.1.0/.flake8 1970-01-01 01:00:00.000000000 +0100
+++ new/python-sql-1.2.0/.flake8 2020-03-01 00:00:32.000000000 +0100
@@ -0,0 +1,2 @@
+[flake8]
+ignore=E123,E124,E126,E128,W503
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/.hgtags new/python-sql-1.2.0/.hgtags
--- old/python-sql-1.1.0/.hgtags 2020-01-25 11:11:52.000000000 +0100
+++ new/python-sql-1.2.0/.hgtags 2020-10-05 18:37:13.000000000 +0200
@@ -9,3 +9,4 @@
e3bdeb99dd975024e30d8af18c324a0a7f860e63 0.9
7459778aa23150aa6ac39356621c29d368ae1f36 1.0.0
194182e5b0e2dc6486a32778860f29c80c0672f9 1.1.0
+de68c850bc6a809b0c88ddbe2fa99b02df07bee3 1.2.0
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/CHANGELOG
new/python-sql-1.2.0/CHANGELOG
--- old/python-sql-1.1.0/CHANGELOG 2020-01-25 11:04:49.000000000 +0100
+++ new/python-sql-1.2.0/CHANGELOG 2020-10-05 18:33:14.000000000 +0200
@@ -1,3 +1,7 @@
+Version 1.2.0 - 2020-10-05
+* Add explicit Windows to Select
+* Fix missing Windows definitions in nested expressions
+
Version 1.1.0 - 2020-01-25
* Add ORDER BY clause to aggregate functions
* Add support for Python 3.8
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/PKG-INFO
new/python-sql-1.2.0/PKG-INFO
--- old/python-sql-1.1.0/PKG-INFO 2020-01-25 11:12:36.000000000 +0100
+++ new/python-sql-1.2.0/PKG-INFO 2020-10-05 18:37:51.000000000 +0200
@@ -1,11 +1,15 @@
-Metadata-Version: 1.1
+Metadata-Version: 1.2
Name: python-sql
-Version: 1.1.0
+Version: 1.2.0
Summary: Library to write SQL queries
-Home-page: http://python-sql.tryton.org/
+Home-page: https://pypi.org/project/python-sql/
Author: Tryton
Author-email: [email protected]
License: BSD
+Download-URL: https://downloads.tryton.org/python-sql/
+Project-URL: Bug Tracker, https://python-sql.tryton.org/
+Project-URL: Forum, https://discuss.tryton.org/tags/python-sql
+Project-URL: Source Code, https://hg.tryton.org/python-sql/
Description: python-sql
==========
@@ -211,6 +215,7 @@
>>> format2numeric(*select)
('SELECT * FROM "user" AS "a" WHERE ("a"."name" = :0)', ('foo',))
+Keywords: SQL database query
Platform: UNKNOWN
Classifier: Development Status :: 5 - Production/Stable
Classifier: Intended Audience :: Developers
@@ -219,5 +224,11 @@
Classifier: Programming Language :: Python :: 2.6
Classifier: Programming Language :: Python :: 2.7
Classifier: Programming Language :: Python :: 3
+Classifier: Programming Language :: Python :: 3.3
+Classifier: Programming Language :: Python :: 3.4
+Classifier: Programming Language :: Python :: 3.5
+Classifier: Programming Language :: Python :: 3.6
+Classifier: Programming Language :: Python :: 3.7
+Classifier: Programming Language :: Python :: 3.8
Classifier: Topic :: Database
Classifier: Topic :: Software Development :: Libraries :: Python Modules
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/python_sql.egg-info/PKG-INFO
new/python-sql-1.2.0/python_sql.egg-info/PKG-INFO
--- old/python-sql-1.1.0/python_sql.egg-info/PKG-INFO 2020-01-25
11:12:35.000000000 +0100
+++ new/python-sql-1.2.0/python_sql.egg-info/PKG-INFO 2020-10-05
18:37:50.000000000 +0200
@@ -1,11 +1,15 @@
-Metadata-Version: 1.1
+Metadata-Version: 1.2
Name: python-sql
-Version: 1.1.0
+Version: 1.2.0
Summary: Library to write SQL queries
-Home-page: http://python-sql.tryton.org/
+Home-page: https://pypi.org/project/python-sql/
Author: Tryton
Author-email: [email protected]
License: BSD
+Download-URL: https://downloads.tryton.org/python-sql/
+Project-URL: Bug Tracker, https://python-sql.tryton.org/
+Project-URL: Forum, https://discuss.tryton.org/tags/python-sql
+Project-URL: Source Code, https://hg.tryton.org/python-sql/
Description: python-sql
==========
@@ -211,6 +215,7 @@
>>> format2numeric(*select)
('SELECT * FROM "user" AS "a" WHERE ("a"."name" = :0)', ('foo',))
+Keywords: SQL database query
Platform: UNKNOWN
Classifier: Development Status :: 5 - Production/Stable
Classifier: Intended Audience :: Developers
@@ -219,5 +224,11 @@
Classifier: Programming Language :: Python :: 2.6
Classifier: Programming Language :: Python :: 2.7
Classifier: Programming Language :: Python :: 3
+Classifier: Programming Language :: Python :: 3.3
+Classifier: Programming Language :: Python :: 3.4
+Classifier: Programming Language :: Python :: 3.5
+Classifier: Programming Language :: Python :: 3.6
+Classifier: Programming Language :: Python :: 3.7
+Classifier: Programming Language :: Python :: 3.8
Classifier: Topic :: Database
Classifier: Topic :: Software Development :: Libraries :: Python Modules
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/python_sql.egg-info/SOURCES.txt
new/python-sql-1.2.0/python_sql.egg-info/SOURCES.txt
--- old/python-sql-1.1.0/python_sql.egg-info/SOURCES.txt 2020-01-25
11:12:36.000000000 +0100
+++ new/python-sql-1.2.0/python_sql.egg-info/SOURCES.txt 2020-10-05
18:37:50.000000000 +0200
@@ -1,4 +1,5 @@
.drone.yml
+.flake8
.hgtags
CHANGELOG
MANIFEST.in
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/setup.py
new/python-sql-1.2.0/setup.py
--- old/python-sql-1.1.0/setup.py 2019-11-25 21:20:07.000000000 +0100
+++ new/python-sql-1.2.0/setup.py 2020-05-11 00:47:40.000000000 +0200
@@ -49,7 +49,14 @@
long_description=read('README'),
author='Tryton',
author_email='[email protected]',
- url='http://python-sql.tryton.org/',
+ url='https://pypi.org/project/python-sql/',
+ download_url='https://downloads.tryton.org/python-sql/',
+ project_urls={
+ "Bug Tracker": 'https://python-sql.tryton.org/',
+ "Forum": 'https://discuss.tryton.org/tags/python-sql',
+ "Source Code": 'https://hg.tryton.org/python-sql/',
+ },
+ keywords='SQL database query',
packages=find_packages(),
classifiers=[
'Development Status :: 5 - Production/Stable',
@@ -59,6 +66,12 @@
'Programming Language :: Python :: 2.6',
'Programming Language :: Python :: 2.7',
'Programming Language :: Python :: 3',
+ 'Programming Language :: Python :: 3.3',
+ 'Programming Language :: Python :: 3.4',
+ 'Programming Language :: Python :: 3.5',
+ 'Programming Language :: Python :: 3.6',
+ 'Programming Language :: Python :: 3.7',
+ 'Programming Language :: Python :: 3.8',
'Topic :: Database',
'Topic :: Software Development :: Libraries :: Python Modules',
],
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/__init__.py
new/python-sql-1.2.0/sql/__init__.py
--- old/python-sql-1.1.0/sql/__init__.py 2020-01-25 11:03:48.000000000
+0100
+++ new/python-sql-1.2.0/sql/__init__.py 2020-10-05 18:33:38.000000000
+0200
@@ -30,12 +30,13 @@
from __future__ import division
import string
+import numbers
import warnings
from threading import local, currentThread
from collections import defaultdict
from itertools import chain
-__version__ = '1.1.0'
+__version__ = '1.2.0'
__all__ = ['Flavor', 'Table', 'Values', 'Literal', 'Column', 'Join',
'Asc', 'Desc', 'NullsFirst', 'NullsLast', 'format2numeric']
@@ -160,6 +161,14 @@
return cls.local.alias[id(from_)]
@classmethod
+ def contains(cls, from_):
+ if getattr(cls.local, 'alias', None) is None:
+ return False
+ if from_ in cls.local.exclude:
+ return False
+ return id(from_) in cls.local.alias
+
+ @classmethod
def set(cls, from_, alias):
assert cls.local.alias.get(from_) is None
cls.local.alias[id(from_)] = alias
@@ -250,6 +259,10 @@
def alias(self):
return AliasManager.get(self)
+ @property
+ def has_alias(self):
+ return AliasManager.contains(self)
+
def __getattr__(self, name):
if name.startswith('__'):
raise AttributeError
@@ -348,7 +361,7 @@
@limit.setter
def limit(self, value):
if value is not None:
- assert isinstance(value, (int, long))
+ assert isinstance(value, numbers.Integral)
self._limit = value
@property
@@ -358,7 +371,7 @@
@offset.setter
def offset(self, value):
if value is not None:
- assert isinstance(value, (int, long))
+ assert isinstance(value, numbers.Integral)
self._offset = value
@property
@@ -390,11 +403,11 @@
class Select(FromItem, SelectQuery):
__slots__ = ('_columns', '_where', '_group_by', '_having', '_for_',
- 'from_', '_distinct', '_distinct_on')
+ 'from_', '_distinct', '_distinct_on', '_windows')
def __init__(self, columns, from_=None, where=None, group_by=None,
having=None, for_=None, distinct=False, distinct_on=None,
- **kwargs):
+ windows=None, **kwargs):
self._distinct = False
self._distinct_on = []
self._columns = None
@@ -402,6 +415,7 @@
self._group_by = None
self._having = None
self._for_ = None
+ self._windows = []
super(Select, self).__init__(**kwargs)
self.distinct = distinct
self.distinct_on = distinct_on
@@ -411,6 +425,7 @@
self.group_by = group_by
self.having = having
self.for_ = for_
+ self.windows = windows
@property
def distinct(self):
@@ -487,6 +502,34 @@
assert all(isinstance(f, For) for f in value)
self._for_ = value
+ @property
+ def windows(self):
+ from sql.functions import WindowFunction
+ from sql.aggregate import Aggregate
+ windows = set()
+ if self._windows is not None:
+ for window in self._windows:
+ windows.add(window)
+ yield window
+ for column in self.columns:
+ window_function = None
+ if isinstance(column, (WindowFunction, Aggregate)):
+ window_function = column
+ elif (isinstance(column, As)
+ and isinstance(column.expression,
+ (WindowFunction, Aggregate))):
+ window_function = column.expression
+ if (window_function and window_function.window
+ and window_function.window not in windows):
+ windows.add(window_function.window)
+ yield window_function.window
+
+ @windows.setter
+ def windows(self, value):
+ if value is not None:
+ assert all(isinstance(w, Window) for w in value)
+ self._windows = value
+
@staticmethod
def _format_column(column):
if isinstance(column, As):
@@ -504,23 +547,6 @@
else:
return str(column)
- def _window_functions(self):
- from sql.functions import WindowFunction
- from sql.aggregate import Aggregate
- windows = set()
- for column in self.columns:
- window_function = None
- if isinstance(column, (WindowFunction, Aggregate)):
- window_function = column
- elif (isinstance(column, As)
- and isinstance(column.expression,
- (WindowFunction, Aggregate))):
- window_function = column.expression
- if (window_function and window_function.window
- and window_function.window not in windows):
- windows.add(window_function.window)
- yield window_function
-
def _rownum(self, func):
aliases = [c.output_name if isinstance(c, As) else None
for c in self.columns]
@@ -568,6 +594,13 @@
from_ = ' FROM %s' % self.from_
else:
from_ = ''
+
+ # format window before expressions to set alias
+ window = ', '.join(
+ '"%s" AS (%s)' % (w.alias, w) for w in self.windows)
+ if window:
+ window = ' WINDOW ' + window
+
if self.distinct:
distinct = 'DISTINCT '
if self.distinct_on:
@@ -588,11 +621,6 @@
having = ''
if self.having:
having = ' HAVING ' + str(self.having)
- window = ''
- windows = [f.window for f in self._window_functions()]
- if windows:
- window = ' WINDOW ' + ', '.join(
- '"%s" AS (%s)' % (w.alias, w) for w in windows)
for_ = ''
if self.for_ is not None:
for_ = ' ' + ' '.join(map(str, self.for_))
@@ -607,25 +635,30 @@
and (self.limit is not None or self.offset is not None)):
return self._rownum(lambda q: q.params)
p = []
- p.extend(self._with_params())
- for column in chain(self.distinct_on or (), self.columns):
- if isinstance(column, As):
- p.extend(column.expression.params)
- p.extend(column.params)
- if self.from_ is not None:
- p.extend(self.from_.params)
- if self.where:
- p.extend(self.where.params)
- if self.group_by:
- for expression in self.group_by:
- p.extend(expression.params)
- if self.order_by:
- for expression in self.order_by:
- p.extend(expression.params)
- if self.having:
- p.extend(self.having.params)
- for window_function in self._window_functions():
- p.extend(window_function.window.params)
+ with AliasManager():
+ # Set alias to window function to skip their params
+ for window_function in self.windows:
+ window_function.alias
+
+ p.extend(self._with_params())
+ for column in chain(self.distinct_on or (), self.columns):
+ if isinstance(column, As):
+ p.extend(column.expression.params)
+ p.extend(column.params)
+ if self.from_ is not None:
+ p.extend(self.from_.params)
+ if self.where:
+ p.extend(self.where.params)
+ if self.group_by:
+ for expression in self.group_by:
+ p.extend(expression.params)
+ if self.order_by:
+ for expression in self.order_by:
+ p.extend(expression.params)
+ if self.having:
+ p.extend(self.having.params)
+ for window_function in self.windows:
+ p.extend(window_function.window.params)
return tuple(p)
@@ -1040,6 +1073,10 @@
def alias(self):
raise AttributeError
+ @property
+ def has_alias(self):
+ raise AttributeError
+
def __getattr__(self, name):
raise AttributeError
@@ -1452,7 +1489,7 @@
@start.setter
def start(self, value):
if value:
- assert isinstance(value, (int, long))
+ assert isinstance(value, numbers.Integral)
self._start = value
@property
@@ -1462,13 +1499,17 @@
@end.setter
def end(self, value):
if value:
- assert isinstance(value, (int, long))
+ assert isinstance(value, numbers.Integral)
self._end = value
@property
def alias(self):
return AliasManager.get(self)
+ @property
+ def has_alias(self):
+ return AliasManager.contains(self)
+
def __str__(self):
partition = ''
if self.partition:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/aggregate.py
new/python-sql-1.2.0/sql/aggregate.py
--- old/python-sql-1.1.0/sql/aggregate.py 2020-01-18 00:21:28.000000000
+0100
+++ new/python-sql-1.2.0/sql/aggregate.py 2020-09-29 12:39:19.000000000
+0200
@@ -127,7 +127,10 @@
filter_ = ' FILTER (WHERE %s)' % self.filter_
window = ''
if self.window:
- window = ' OVER "%s"' % self.window.alias
+ if self.window.has_alias:
+ window = ' OVER "%s"' % self.window.alias
+ else:
+ window = ' OVER (%s)' % self.window
return aggregate + within + filter_ + window
@property
@@ -147,6 +150,8 @@
p.extend(expression.params)
if self.filter_ and has_filter:
p.extend(self.filter_.params)
+ if self.window and not self.window.has_alias:
+ p.extend(self.window.params)
return tuple(p)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/functions.py
new/python-sql-1.2.0/sql/functions.py
--- old/python-sql-1.1.0/sql/functions.py 2019-11-07 13:48:36.000000000
+0100
+++ new/python-sql-1.2.0/sql/functions.py 2020-09-29 12:40:42.000000000
+0200
@@ -30,6 +30,11 @@
from sql import Expression, Flavor, FromItem, Window
+try:
+ basestring
+except NameError:
+ basestring = str
+
__all__ = ['Abs', 'Cbrt', 'Ceil', 'Degrees', 'Div', 'Exp', 'Floor', 'Ln',
'Log', 'Mod', 'Pi', 'Power', 'Radians', 'Random', 'Round', 'SetSeed',
'Sign', 'Sqrt', 'Trunc', 'WidthBucket',
@@ -523,7 +528,10 @@
filter_ = ''
if self.filter_:
filter_ = ' FILTER (WHERE %s)' % self.filter_
- over = ' OVER "%s"' % self.window.alias
+ if self.window.has_alias:
+ over = ' OVER "%s"' % self.window.alias
+ else:
+ over = ' OVER (%s)' % self.window
return function + filter_ + over
@property
@@ -531,6 +539,8 @@
p = list(super(WindowFunction, self).params)
if self.filter_:
p.extend(self.filter_.params)
+ if not self.window.has_alias:
+ p.extend(self.window.params)
return tuple(p)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/operators.py
new/python-sql-1.2.0/sql/operators.py
--- old/python-sql-1.1.0/sql/operators.py 2018-09-30 14:17:53.000000000
+0200
+++ new/python-sql-1.2.0/sql/operators.py 2020-03-01 00:00:56.000000000
+0100
@@ -86,7 +86,7 @@
return param
def __str__(self):
- raise NotImplemented
+ raise NotImplementedError
def __and__(self, other):
if isinstance(other, And):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/tests/test_aggregate.py
new/python-sql-1.2.0/sql/tests/test_aggregate.py
--- old/python-sql-1.1.0/sql/tests/test_aggregate.py 2020-01-18
00:21:28.000000000 +0100
+++ new/python-sql-1.2.0/sql/tests/test_aggregate.py 2020-09-29
12:28:01.000000000 +0200
@@ -84,7 +84,7 @@
def test_window(self):
avg = Avg(self.table.c, window=Window([]))
with AliasManager():
- self.assertEqual(str(avg), 'AVG("a"."c") OVER "b"')
+ self.assertEqual(str(avg), 'AVG("a"."c") OVER ()')
self.assertEqual(avg.params, ())
def test_distinct(self):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/tests/test_functions.py
new/python-sql-1.2.0/sql/tests/test_functions.py
--- old/python-sql-1.1.0/sql/tests/test_functions.py 2018-08-18
13:25:33.000000000 +0200
+++ new/python-sql-1.2.0/sql/tests/test_functions.py 2020-09-29
12:30:11.000000000 +0200
@@ -149,7 +149,7 @@
function = Rank(t.c, window=Window([]))
with AliasManager():
- self.assertEqual(str(function), 'RANK("a"."c") OVER "b"')
+ self.assertEqual(str(function), 'RANK("a"."c") OVER ()')
self.assertEqual(function.params, ())
def test_filter(self):
@@ -158,5 +158,5 @@
with AliasManager():
self.assertEqual(str(function),
- 'RANK("a"."c") FILTER (WHERE ("a"."c" > %s)) OVER "b"')
+ 'RANK("a"."c") FILTER (WHERE ("a"."c" > %s)) OVER ()')
self.assertEqual(function.params, (0,))
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/python-sql-1.1.0/sql/tests/test_select.py
new/python-sql-1.2.0/sql/tests/test_select.py
--- old/python-sql-1.1.0/sql/tests/test_select.py 2019-11-07
13:56:08.000000000 +0100
+++ new/python-sql-1.2.0/sql/tests/test_select.py 2020-09-29
12:59:59.000000000 +0200
@@ -33,7 +33,7 @@
from sql import Table, Join, Union, Literal, Flavor, For, With, Window, Select
from sql.functions import Now, Function, Rank, DatePart
-from sql.aggregate import Min
+from sql.aggregate import Min, Max
class TestSelect(unittest.TestCase):
@@ -420,6 +420,39 @@
'WINDOW "b" AS (PARTITION BY DATE_PART(%s, "a"."date_col"))')
self.assertEqual(query.params, ('year',))
+ window = Window([self.table.c2])
+ query = self.table.select(
+ Max(self.table.c1, window=window)
+ / Min(self.table.c1, window=window))
+ self.assertEqual(str(query),
+ 'SELECT (MAX("a"."c1") OVER (PARTITION BY "a"."c2") '
+ '/ MIN("a"."c1") OVER (PARTITION BY "a"."c2")) '
+ 'FROM "t" AS "a"')
+ self.assertEqual(query.params, ())
+
+ window = Window([Literal(1)])
+ query = self.table.select(
+ Max(self.table.c1, window=window)
+ / Min(self.table.c1, window=window))
+ self.assertEqual(str(query),
+ 'SELECT (MAX("a"."c1") OVER (PARTITION BY %s) '
+ '/ MIN("a"."c1") OVER (PARTITION BY %s)) '
+ 'FROM "t" AS "a"')
+ self.assertEqual(query.params, (1, 1))
+
+ window1 = Window([self.table.c2])
+ window2 = Window([Literal(1)])
+ query = self.table.select(
+ Max(self.table.c1, window=window1)
+ / Min(self.table.c1, window=window2),
+ windows=[window1])
+ self.assertEqual(str(query),
+ 'SELECT (MAX("a"."c1") OVER "b" '
+ '/ MIN("a"."c1") OVER (PARTITION BY %s)) '
+ 'FROM "t" AS "a" '
+ 'WINDOW "b" AS (PARTITION BY "a"."c2")')
+ self.assertEqual(query.params, (1,))
+
def test_order_params(self):
with_ = With(query=self.table.select(self.table.c,
where=(self.table.c > 1)))