Skip to content

Commit

Permalink
Fixed invalid 'var IN ()' SQL generated using '__in=' and '__not_in' …
Browse files Browse the repository at this point in the history
…filters. (#321)
  • Loading branch information
grigi committed Mar 24, 2020
1 parent a3f0ff6 commit 90a9242
Show file tree
Hide file tree
Showing 3 changed files with 24 additions and 5 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.rst
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,10 @@ Changelog

0.16
====
0.16.3
------
* Fixed invalid ``var IN ()`` SQL generated using ``__in=`` and ``__not_in`` filters.

0.16.2
------
* Default ``values()`` & ``values_list()`` now includes annotations.
Expand Down
11 changes: 11 additions & 0 deletions tests/test_filters.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,11 @@ async def test_in(self):
{"moo", "baa"},
)

async def test_in_empty(self):
self.assertEqual(
await CharFields.filter(char__in=[]).values_list("char", flat=True), [],
)

async def test_not_in(self):
self.assertSetEqual(
set(
Expand All @@ -42,6 +47,12 @@ async def test_not_in(self):
{"oink"},
)

async def test_not_in_empty(self):
self.assertSetEqual(
set(await CharFields.filter(char__not_in=[]).values_list("char", flat=True)),
{"oink", "moo", "baa"},
)

async def test_isnull(self):
self.assertSetEqual(
set(await CharFields.filter(char_null__isnull=True).values_list("char", flat=True)),
Expand Down
14 changes: 9 additions & 5 deletions tortoise/filters.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
from pypika import Table
from pypika.enums import SqlTypes
from pypika.functions import Cast, Upper
from pypika.terms import Criterion, Term
from pypika.terms import Criterion, Term, ValueWrapper

from tortoise.fields import Field
from tortoise.fields.relational import BackwardFKRelation, ManyToManyFieldInstance
Expand Down Expand Up @@ -45,12 +45,16 @@ def string_encoder(value: Any, instance: "Model", field: Field) -> str:
##############################################################################


def is_in(field: Term, value: Any) -> Criterion:
return field.isin(value)
def is_in(field: Term, value: Any) -> Term:
if value:
return field.isin(value)
return ValueWrapper(False)


def not_in(field: Term, value: Any) -> Criterion:
return field.notin(value) | field.isnull()
def not_in(field: Term, value: Any) -> Term:
if value:
return field.notin(value) | field.isnull()
return ValueWrapper(True)


def between_and(field: Term, value: Tuple[Any, Any]) -> Criterion:
Expand Down

0 comments on commit 90a9242

Please sign in to comment.