Hello community,
here is the log from the commit of package python-django-filter for
openSUSE:Factory checked in at 2019-09-17 13:37:44
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/python-django-filter (Old)
and /work/SRC/openSUSE:Factory/.python-django-filter.new.7948 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-django-filter"
Tue Sep 17 13:37:44 2019 rev:4 rq:731220 version:2.2.0
Changes:
--------
---
/work/SRC/openSUSE:Factory/python-django-filter/python-django-filter.changes
2019-04-11 12:17:05.480929098 +0200
+++
/work/SRC/openSUSE:Factory/.python-django-filter.new.7948/python-django-filter.changes
2019-09-17 13:37:46.173839411 +0200
@@ -1,0 +2,10 @@
+Mon Sep 16 09:33:43 UTC 2019 - Tomáš Chvátal <[email protected]>
+
+- Update to 2.2.0:
+ * Added DjangoFilterBackend.get_schema_operation_parameters() for DRF 3.10+
+ * OpenAPI schema generation. (#1086)
+ * Added lookup_expr to MultipleChoiceFilter (#1054)
+ * Dropped support for EOL Python 3.4
+- Remove merged patch fix_tests.patch
+
+-------------------------------------------------------------------
Old:
----
django-filter-2.1.0.tar.gz
fix_tests.patch
New:
----
django-filter-2.2.0.tar.gz
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Other differences:
------------------
++++++ python-django-filter.spec ++++++
--- /var/tmp/diff_new_pack.Ni5HbK/_old 2019-09-17 13:37:46.601839343 +0200
+++ /var/tmp/diff_new_pack.Ni5HbK/_new 2019-09-17 13:37:46.605839342 +0200
@@ -19,14 +19,13 @@
%{?!python_module:%define python_module() python-%{**} python3-%{**}}
%define skip_python2 1
Name: python-django-filter
-Version: 2.1.0
+Version: 2.2.0
Release: 0
Summary: Reusable Django app to allow users to filter queryset
dynamically
License: BSD-3-Clause
Group: Development/Libraries/Python
URL: https://github.com/carltongibson/django-filter
Source:
https://files.pythonhosted.org/packages/source/d/django-filter/django-filter-%{version}.tar.gz
-Patch0: fix_tests.patch
BuildRequires: %{python_module Django}
BuildRequires: %{python_module django-crispy-forms}
BuildRequires: %{python_module djangorestframework}
@@ -45,7 +44,6 @@
%prep
%setup -q -n django-filter-%{version}
-%patch0 -p1
%build
%python_build
++++++ django-filter-2.1.0.tar.gz -> django-filter-2.2.0.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/CHANGES.rst
new/django-filter-2.2.0/CHANGES.rst
--- old/django-filter-2.1.0/CHANGES.rst 2019-01-20 20:39:10.000000000 +0100
+++ new/django-filter-2.2.0/CHANGES.rst 2019-07-16 20:19:30.000000000 +0200
@@ -1,3 +1,12 @@
+Version 2.2 (2019-7-16)
+-----------------------
+
+* Added ``DjangoFilterBackend.get_schema_operation_parameters()`` for DRF 3.10+
+ OpenAPI schema generation. (#1086)
+* Added ``lookup_expr`` to ``MultipleChoiceFilter`` (#1054)
+* Dropped support for EOL Python 3.4
+
+
Version 2.1 (2019-1-20)
-----------------------
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/PKG-INFO
new/django-filter-2.2.0/PKG-INFO
--- old/django-filter-2.1.0/PKG-INFO 2019-01-20 20:59:24.000000000 +0100
+++ new/django-filter-2.2.0/PKG-INFO 2019-07-16 20:28:47.000000000 +0200
@@ -1,6 +1,6 @@
Metadata-Version: 1.2
Name: django-filter
-Version: 2.1.0
+Version: 2.2.0
Summary: Django-filter is a reusable Django application for allowing users to
filter querysets dynamically.
Home-page: https://github.com/carltongibson/django-filter/tree/master
Author: Alex Gaynor
@@ -127,9 +127,9 @@
Classifier: Framework :: Django :: 1.11
Classifier: Framework :: Django :: 2.0
Classifier: Framework :: Django :: 2.1
+Classifier: Framework :: Django :: 2.2
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 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
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filter.egg-info/PKG-INFO
new/django-filter-2.2.0/django_filter.egg-info/PKG-INFO
--- old/django-filter-2.1.0/django_filter.egg-info/PKG-INFO 2019-01-20
20:59:24.000000000 +0100
+++ new/django-filter-2.2.0/django_filter.egg-info/PKG-INFO 2019-07-16
20:28:46.000000000 +0200
@@ -1,6 +1,6 @@
Metadata-Version: 1.2
Name: django-filter
-Version: 2.1.0
+Version: 2.2.0
Summary: Django-filter is a reusable Django application for allowing users to
filter querysets dynamically.
Home-page: https://github.com/carltongibson/django-filter/tree/master
Author: Alex Gaynor
@@ -127,9 +127,9 @@
Classifier: Framework :: Django :: 1.11
Classifier: Framework :: Django :: 2.0
Classifier: Framework :: Django :: 2.1
+Classifier: Framework :: Django :: 2.2
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 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
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/__init__.py
new/django-filter-2.2.0/django_filters/__init__.py
--- old/django-filter-2.1.0/django_filters/__init__.py 2019-01-20
20:39:10.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/__init__.py 2019-07-16
20:21:46.000000000 +0200
@@ -1,8 +1,8 @@
# flake8: noqa
import pkgutil
-from .filterset import FilterSet
from .filters import *
+from .filterset import FilterSet
# We make the `rest_framework` module available without an additional import.
# If DRF is not installed, no-op.
@@ -10,7 +10,7 @@
from . import rest_framework
del pkgutil
-__version__ = '2.1.0'
+__version__ = '2.2.0'
def parse_version(version):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/conf.py
new/django-filter-2.2.0/django_filters/conf.py
--- old/django-filter-2.1.0/django_filters/conf.py 2017-10-24
11:14:54.000000000 +0200
+++ new/django-filter-2.2.0/django_filters/conf.py 2019-07-16
20:13:20.000000000 +0200
@@ -1,6 +1,6 @@
from django.conf import settings as dj_settings
from django.core.signals import setting_changed
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
from .utils import deprecate
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/fields.py
new/django-filter-2.2.0/django_filters/fields.py
--- old/django-filter-2.1.0/django_filters/fields.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/fields.py 2019-07-16
20:13:20.000000000 +0200
@@ -4,7 +4,7 @@
from django import forms
from django.utils.dateparse import parse_datetime
from django.utils.encoding import force_str
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
from .conf import settings
from .constants import EMPTY_VALUES
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/filters.py
new/django-filter-2.2.0/django_filters/filters.py
--- old/django-filter-2.1.0/django_filters/filters.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/filters.py 2019-07-16
20:13:20.000000000 +0200
@@ -7,7 +7,7 @@
from django.forms.utils import pretty_name
from django.utils.itercompat import is_iterable
from django.utils.timezone import now
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
from .conf import settings
from .constants import EMPTY_VALUES
@@ -253,10 +253,13 @@
return qs.distinct() if self.distinct else qs
def get_filter_predicate(self, v):
+ name = self.field_name
+ if name and self.lookup_expr != 'exact':
+ name = LOOKUP_SEP.join([name, self.lookup_expr])
try:
- return {self.field_name: getattr(v, self.field.to_field_name)}
+ return {name: getattr(v, self.field.to_field_name)}
except (AttributeError, TypeError):
- return {self.field_name: v}
+ return {name: v}
class TypedMultipleChoiceFilter(MultipleChoiceFilter):
@@ -278,8 +281,8 @@
For context see:
* https://code.djangoproject.com/ticket/23448
- * https://github.com/tomchristie/django-rest-framework/issues/1338
- * https://github.com/alex/django-filter/pull/264
+ * https://github.com/encode/django-rest-framework/issues/1338
+ * https://github.com/carltongibson/django-filter/pull/264
"""
field_class = IsoDateTimeField
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/django-filter-2.1.0/django_filters/rest_framework/__init__.py
new/django-filter-2.2.0/django_filters/rest_framework/__init__.py
--- old/django-filter-2.1.0/django_filters/rest_framework/__init__.py
2017-10-24 11:14:54.000000000 +0200
+++ new/django-filter-2.2.0/django_filters/rest_framework/__init__.py
2019-03-08 16:38:58.000000000 +0100
@@ -1,4 +1,4 @@
# flake8: noqa
from .backends import DjangoFilterBackend
-from .filterset import FilterSet
from .filters import *
+from .filterset import FilterSet
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/django-filter-2.1.0/django_filters/rest_framework/backends.py
new/django-filter-2.2.0/django_filters/rest_framework/backends.py
--- old/django-filter-2.1.0/django_filters/rest_framework/backends.py
2019-01-20 09:57:38.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/rest_framework/backends.py
2019-07-16 20:13:20.000000000 +0200
@@ -3,8 +3,8 @@
from django.template import loader
from django.utils.deprecation import RenameMethodsBase
-from . import filters, filterset
from .. import compat, utils
+from . import filters, filterset
# TODO: remove metaclass in 2.1
@@ -138,3 +138,25 @@
schema=self.get_coreschema_field(field)
) for field_name, field in filterset_class.base_filters.items()
]
+
+ def get_schema_operation_parameters(self, view):
+ try:
+ queryset = view.get_queryset()
+ except Exception:
+ queryset = None
+ warnings.warn(
+ "{} is not compatible with schema
generation".format(view.__class__)
+ )
+
+ filterset_class = self.get_filterset_class(view, queryset)
+ return [] if not filterset_class else [
+ ({
+ 'name': field_name,
+ 'required': field.extra['required'],
+ 'in': 'query',
+ 'description': field.label if field.label is not None else
field_name,
+ 'schema': {
+ 'type': 'string',
+ },
+ }) for field_name, field in filterset_class.base_filters.items()
+ ]
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/django-filter-2.1.0/django_filters/rest_framework/filterset.py
new/django-filter-2.2.0/django_filters/rest_framework/filterset.py
--- old/django-filter-2.1.0/django_filters/rest_framework/filterset.py
2018-07-13 11:44:46.000000000 +0200
+++ new/django-filter-2.2.0/django_filters/rest_framework/filterset.py
2019-07-16 20:13:20.000000000 +0200
@@ -1,7 +1,7 @@
from copy import deepcopy
from django.db import models
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
from django_filters import filterset
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/utils.py
new/django-filter-2.2.0/django_filters/utils.py
--- old/django-filter-2.1.0/django_filters/utils.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/utils.py 2019-07-16
20:13:20.000000000 +0200
@@ -10,9 +10,9 @@
from django.db.models.fields import FieldDoesNotExist
from django.db.models.fields.related import ForeignObjectRel, RelatedField
from django.utils import timezone
-from django.utils.encoding import force_text
+from django.utils.encoding import force_str
from django.utils.text import capfirst
-from django.utils.translation import ugettext as _
+from django.utils.translation import gettext as _
from .exceptions import FieldLookupError
@@ -184,7 +184,7 @@
This method is based on django.db.models.sql.query.Query.build_lookup
For more info on the lookup API:
- https://docs.djangoproject.com/en/1.9/ref/models/lookups/
+ https://docs.djangoproject.com/en/stable/ref/models/lookups/
"""
query = model_field.model._default_manager.all().query
@@ -253,7 +253,7 @@
else:
return '[invalid name]'
else:
- names.append(force_text(part.verbose_name))
+ names.append(force_str(part.verbose_name))
return ' '.join(names)
@@ -278,7 +278,7 @@
VERBOSE_LOOKUPS = app_settings.VERBOSE_LOOKUPS or {}
lookups = [
- force_text(VERBOSE_LOOKUPS.get(lookup, _(lookup)))
+ force_str(VERBOSE_LOOKUPS.get(lookup, _(lookup)))
for lookup in lookup_expr.split(LOOKUP_SEP)
]
@@ -302,7 +302,7 @@
if isinstance(lookup_expr, str):
verbose_expression += [verbose_lookup_expr(lookup_expr)]
- verbose_expression = [force_text(part) for part in verbose_expression if
part]
+ verbose_expression = [force_str(part) for part in verbose_expression if
part]
verbose_expression = capfirst(' '.join(verbose_expression))
return verbose_expression
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/django_filters/widgets.py
new/django-filter-2.2.0/django_filters/widgets.py
--- old/django-filter-2.1.0/django_filters/widgets.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/django_filters/widgets.py 2019-07-16
20:13:20.000000000 +0200
@@ -6,10 +6,10 @@
from django.db.models.fields import BLANK_CHOICE_DASH
from django.forms.utils import flatatt
from django.utils.datastructures import MultiValueDict
-from django.utils.encoding import force_text
+from django.utils.encoding import force_str
from django.utils.http import urlencode
from django.utils.safestring import mark_safe
-from django.utils.translation import ugettext as _
+from django.utils.translation import gettext as _
class LinkWidget(forms.Widget):
@@ -37,7 +37,7 @@
return mark_safe('\n'.join(output))
def render_options(self, choices, selected_choices, name):
- selected_choices = set(force_text(v) for v in selected_choices)
+ selected_choices = set(force_str(v) for v in selected_choices)
output = []
for option_value, option_label in chain(self.choices, choices):
if isinstance(option_label, (list, tuple)):
@@ -52,7 +52,7 @@
def render_option(self, name, selected_choices,
option_value, option_label):
- option_value = force_text(option_value)
+ option_value = force_str(option_value)
if option_label == BLANK_CHOICE_DASH[0][1]:
option_label = _("All")
data = self.data.copy()
@@ -65,7 +65,7 @@
return self.option_string() % {
'attrs': selected and ' class="selected"' or '',
'query_string': url,
- 'label': force_text(option_label)
+ 'label': force_str(option_label)
}
def option_string(self):
@@ -213,7 +213,7 @@
# if we have multiple values, we need to force render as a text input
# (otherwise, the additional values are lost)
surrogate = forms.TextInput()
- value = [force_text(surrogate.format_value(v)) for v in value]
+ value = [force_str(surrogate.format_value(v)) for v in value]
value = ','.join(list(value))
return surrogate.render(name, value, attrs, renderer=renderer)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/conf.py
new/django-filter-2.2.0/docs/conf.py
--- old/django-filter-2.1.0/docs/conf.py 2019-01-20 20:39:10.000000000
+0100
+++ new/django-filter-2.2.0/docs/conf.py 2019-07-16 20:21:32.000000000
+0200
@@ -48,9 +48,9 @@
# built documents.
#
# The short X.Y version.
-version = '2.1'
+version = '2.2'
# The full version, including alpha/beta/rc tags.
-release = '2.1.0'
+release = '2.2.0'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/guide/migration.txt
new/django-filter-2.2.0/docs/guide/migration.txt
--- old/django-filter-2.1.0/docs/guide/migration.txt 2018-10-25
10:05:51.000000000 +0200
+++ new/django-filter-2.2.0/docs/guide/migration.txt 2019-02-23
16:37:14.000000000 +0100
@@ -117,6 +117,17 @@
``_0`` and ``_1``.
+Filters like ``RangeFilter, DateRangeFilter, DateTimeFromToRangeFilter...``
(`#770`__)
+--------------------------------------------------------------------------------------
+__ https://github.com/carltongibson/django-filter/pull/770
+
+As they depend on ``MultiWidget``, they need to be adjusted. In 1.0 release
+ parameters were provided using ``_0`` and ``_1`` as suffix``. For example,
+ a parameter ``creation_date`` using``DateRangeFilter`` will expect
+ ``creation_date_after`` and ``creation_date_before`` instead of
+ ``creation_date_0`` and ``creation_date_1``.
+
+
----------------
Migrating to 1.0
----------------
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/guide/rest_framework.txt
new/django-filter-2.2.0/docs/guide/rest_framework.txt
--- old/django-filter-2.1.0/docs/guide/rest_framework.txt 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/docs/guide/rest_framework.txt 2019-07-16
20:13:20.000000000 +0200
@@ -148,10 +148,10 @@
'author': self.get_author(),
}
-Schema Generation with Core API
--------------------------------
+Schema Generation with Core API and Open API
+--------------------------------------------
-The backend class integrates with DRF's schema generation by implementing
``get_schema_fields()``. This is automatically enabled when Core API is
installed. Schema generation usually functions seamlessly, however the
implementation does expect to invoke the view's ``get_queryset()`` method.
There is a caveat in that views are artificially constructed during schema
generation, so the ``args`` and ``kwargs`` attributes will be empty. If you
depend on arguments parsed from the URL, you will need to handle their absence
in ``get_queryset()``.
+The backend class integrates with DRF's schema generation by implementing
``get_schema_fields()`` and ``get_schema_operation_parameters()``.
``get_schema_fields()`` is automatically enabled when Core API is installed.
``get_schema_operation_parameters()`` is always enabled for Open API (new since
DRF 3.9). Schema generation usually functions seamlessly, however the
implementation does expect to invoke the view's ``get_queryset()`` method.
There is a caveat in that views are artificially constructed during schema
generation, so the ``args`` and ``kwargs`` attributes will be empty. If you
depend on arguments parsed from the URL, you will need to handle their absence
in ``get_queryset()``.
For example, your get queryset method may look like this:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/guide/usage.txt
new/django-filter-2.2.0/docs/guide/usage.txt
--- old/django-filter-2.1.0/docs/guide/usage.txt 2018-10-25
10:05:51.000000000 +0200
+++ new/django-filter-2.2.0/docs/guide/usage.txt 2019-02-23
16:37:14.000000000 +0100
@@ -75,14 +75,14 @@
syntax can again be used in order to support lookup transforms.
ex, ``year__gte``.
-.. _`field lookup`:
https://docs.djangoproject.com/en/dev/ref/models/querysets/#field-lookups
+.. _`field lookup`:
https://docs.djangoproject.com/en/stable/ref/models/querysets/#field-lookups
Together, the field ``field_name`` and ``lookup_expr`` represent a complete
Django
lookup expression. A detailed explanation of lookup expressions is provided in
Django's `lookup reference`_. django-filter supports expressions containing
both transforms and a final lookup.
-.. _`lookup reference`:
https://docs.djangoproject.com/en/dev/ref/models/lookups/#module-django.db.models.lookups
+.. _`lookup reference`:
https://docs.djangoproject.com/en/stable/ref/models/lookups/#module-django.db.models.lookups
Generating filters with Meta.fields
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/ref/fields.txt
new/django-filter-2.2.0/docs/ref/fields.txt
--- old/django-filter-2.1.0/docs/ref/fields.txt 2016-11-17 15:46:03.000000000
+0100
+++ new/django-filter-2.2.0/docs/ref/fields.txt 2019-02-23 16:37:14.000000000
+0100
@@ -19,5 +19,5 @@
f.input_formats = [IsoDateTimeField.ISO_8601] + DateTimeField.input_formats
-.. _`DateTimeField Docs`:
https://docs.djangoproject.com/en/1.8/ref/forms/fields/#django.forms.DateTimeField.input_formats
+.. _`DateTimeField Docs`:
https://docs.djangoproject.com/en/stable/ref/forms/fields/#django.forms.DateTimeField.input_formats
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/ref/filters.txt
new/django-filter-2.2.0/docs/ref/filters.txt
--- old/django-filter-2.1.0/docs/ref/filters.txt 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/docs/ref/filters.txt 2019-02-23
16:37:14.000000000 +0100
@@ -13,7 +13,7 @@
are joined to construct the complete `lookup expression`_ that is the left hand
side of the ORM ``.filter()`` call.
-.. _`lookup expression`:
https://docs.djangoproject.com/en/dev/ref/models/lookups/#module-django.db.models.lookups
+.. _`lookup expression`:
https://docs.djangoproject.com/en/stable/ref/models/lookups/#module-django.db.models.lookups
``field_name``
~~~~~~~~~~~~~~
@@ -31,7 +31,7 @@
are joined by the ORM lookup separator (``__``). e.g., filter a datetime by its
year part ``year__gt``.
-.. _`Field lookup`:
https://docs.djangoproject.com/en/dev/ref/models/querysets/#field-lookups
+.. _`Field lookup`:
https://docs.djangoproject.com/en/stable/ref/models/querysets/#field-lookups
.. _keyword-only-arguments:
@@ -433,7 +433,7 @@
Regular field lookups are available in addition to several containment
lookups, including
``overlap``, ``contains``, and ``contained_by``. More details in the Django
`docs`__.
-__
https://docs.djangoproject.com/en/1.8/ref/contrib/postgres/fields/#querying-range-fields
+__
https://docs.djangoproject.com/en/stable/ref/contrib/postgres/fields/#querying-range-fields
If the lower limit value is provided, the filter automatically defaults to
``startswith``
as the lookup and ``endswith`` if only the upper limit value is provided.
@@ -496,13 +496,13 @@
# Max-Only: Comments added before 2016-02-01
f = F({'date_before': '2016-02-01'})
- .. note::
- When filtering ranges that occurs on DST transition dates
``DateFromToRangeFilter`` will use the first valid hour of the day for start
datetime and the last valid hour of the day for end datetime.
- This is OK for most applications, but if you want to customize this
behavior you must extend ``DateFromToRangeFilter`` and make a custom field for
it.
-
- .. warning::
- If you're using Django prior to 1.9 you may hit ``AmbiguousTimeError``
or ``NonExistentTimeError`` when start/end date matches DST start/end
respectively.
- This occurs because versions before 1.9 don't allow to change the DST
behavior for making a datetime aware.
+.. note::
+ When filtering ranges that occurs on DST transition dates
``DateFromToRangeFilter`` will use the first valid hour of the day for start
datetime and the last valid hour of the day for end datetime.
+ This is OK for most applications, but if you want to customize this
behavior you must extend ``DateFromToRangeFilter`` and make a custom field for
it.
+
+.. warning::
+ If you're using Django prior to 1.9 you may hit ``AmbiguousTimeError`` or
``NonExistentTimeError`` when start/end date matches DST start/end respectively.
+ This occurs because versions before 1.9 don't allow to change the DST
behavior for making a datetime aware.
Example of using the ``DateTimeField`` field::
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/docs/ref/filterset.txt
new/django-filter-2.2.0/docs/ref/filterset.txt
--- old/django-filter-2.1.0/docs/ref/filterset.txt 2017-10-24
11:14:54.000000000 +0200
+++ new/django-filter-2.2.0/docs/ref/filterset.txt 2019-02-23
16:37:14.000000000 +0100
@@ -25,7 +25,7 @@
either the ``fields`` or ``exclude`` option, which is the same requirement for
Django's ``ModelForm`` class, detailed `here`__.
-__
https://docs.djangoproject.com/en/dev/topics/forms/modelforms/#selecting-the-fields-to-use
+__
https://docs.djangoproject.com/en/stable/topics/forms/modelforms/#selecting-the-fields-to-use
.. code-block:: python
@@ -69,7 +69,7 @@
expression declared for its corresponding model field. These expressions may
include both transforms and lookups, as detailed in the `lookup reference`__.
-__
https://docs.djangoproject.com/en/dev/ref/models/lookups/#module-django.db.models.lookups
+__
https://docs.djangoproject.com/en/stable/ref/models/lookups/#module-django.db.models.lookups
.. _exclude:
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/requirements/maintainer.txt
new/django-filter-2.2.0/requirements/maintainer.txt
--- old/django-filter-2.1.0/requirements/maintainer.txt 2018-12-17
21:18:30.000000000 +0100
+++ new/django-filter-2.2.0/requirements/maintainer.txt 2019-07-16
20:13:20.000000000 +0200
@@ -14,7 +14,7 @@
pkginfo==1.2.1
Pygments==2.1.3
pytz==2016.6.1
-PyYAML==3.11
+PyYAML==5.1
requests==2.20.0
six==1.9.0
snowballstemmer==1.2.1
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/setup.py
new/django-filter-2.2.0/setup.py
--- old/django-filter-2.1.0/setup.py 2019-01-20 20:57:39.000000000 +0100
+++ new/django-filter-2.2.0/setup.py 2019-07-16 20:21:09.000000000 +0200
@@ -6,7 +6,7 @@
readme = f.read()
f.close()
-version = '2.1.0'
+version = '2.2.0'
if sys.argv[-1] == 'publish':
if os.system("pip freeze | grep wheel"):
@@ -46,10 +46,9 @@
'Framework :: Django :: 1.11',
'Framework :: Django :: 2.0',
'Framework :: Django :: 2.1',
-# 'Framework :: Django :: 2.2',
+ 'Framework :: Django :: 2.2',
'Programming Language :: Python',
'Programming Language :: Python :: 3',
- 'Programming Language :: Python :: 3.4',
'Programming Language :: Python :: 3.5',
'Programming Language :: Python :: 3.6',
'Programming Language :: Python :: 3.7',
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/models.py
new/django-filter-2.2.0/tests/models.py
--- old/django-filter-2.1.0/tests/models.py 2018-07-13 11:44:46.000000000
+0200
+++ new/django-filter-2.2.0/tests/models.py 2019-07-16 20:13:20.000000000
+0200
@@ -1,6 +1,6 @@
from django import forms
from django.db import models
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
REGULAR = 0
MANAGER = 1
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/rest_framework/models.py
new/django-filter-2.2.0/tests/rest_framework/models.py
--- old/django-filter-2.1.0/tests/rest_framework/models.py 2016-09-20
22:19:17.000000000 +0200
+++ new/django-filter-2.2.0/tests/rest_framework/models.py 2019-07-16
20:13:20.000000000 +0200
@@ -1,6 +1,6 @@
from django.db import models
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import gettext_lazy as _
class BasicModel(models.Model):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore'
old/django-filter-2.1.0/tests/rest_framework/test_backends.py
new/django-filter-2.2.0/tests/rest_framework/test_backends.py
--- old/django-filter-2.1.0/tests/rest_framework/test_backends.py
2018-07-13 11:44:46.000000000 +0200
+++ new/django-filter-2.2.0/tests/rest_framework/test_backends.py
2019-07-16 20:13:20.000000000 +0200
@@ -229,6 +229,15 @@
self.assertEqual(fields, ['text', 'decimal', 'date', 'f'])
+class GetSchemaOperationParametersTests(TestCase):
+ def test_get_operation_parameters_with_filterset_fields_list(self):
+ backend = DjangoFilterBackend()
+ fields =
backend.get_schema_operation_parameters(FilterFieldsRootView())
+ fields = [f['name'] for f in fields]
+
+ self.assertEqual(fields, ['decimal', 'date'])
+
+
class TemplateTests(TestCase):
def test_backend_output(self):
"""
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/settings.py
new/django-filter-2.2.0/tests/settings.py
--- old/django-filter-2.1.0/tests/settings.py 2017-10-24 11:14:54.000000000
+0200
+++ new/django-filter-2.2.0/tests/settings.py 2019-07-16 20:13:20.000000000
+0200
@@ -25,6 +25,8 @@
USE_TZ = True
+TIME_ZONE = 'UTC'
+
SECRET_KEY = 'foobar'
TEMPLATES = [{
@@ -36,6 +38,10 @@
STATIC_URL = '/static/'
+# XMLTestRunner output
+TEST_OUTPUT_DIR = '.xmlcoverage'
+
+
# help verify that DEFAULTS is importable from conf.
def FILTERS_VERBOSE_LOOKUPS():
return DEFAULTS['VERBOSE_LOOKUPS']
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/test_filtering.py
new/django-filter-2.2.0/tests/test_filtering.py
--- old/django-filter-2.1.0/tests/test_filtering.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/tests/test_filtering.py 2019-07-16
20:13:20.000000000 +0200
@@ -978,6 +978,7 @@
self.assertEqual(len(results.qs), 2)
[email protected]
class IsoDateTimeFromToRangeFilterTests(TestCase):
def test_filtering(self):
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/test_filters.py
new/django-filter-2.2.0/tests/test_filters.py
--- old/django-filter-2.1.0/tests/test_filters.py 2019-01-20
09:57:58.000000000 +0100
+++ new/django-filter-2.2.0/tests/test_filters.py 2019-07-16
20:13:20.000000000 +0200
@@ -1,4 +1,3 @@
-# -*- coding: utf-8 -*-
import inspect
import mock
from collections import OrderedDict
@@ -7,7 +6,7 @@
from django import forms
from django.test import TestCase, override_settings
from django.utils import translation
-from django.utils.translation import ugettext as _
+from django.utils.translation import gettext as _
from django_filters import filters, widgets
from django_filters.fields import (
@@ -419,6 +418,21 @@
qs.exclude.assert_called_once_with(mockQ1.__ior__.return_value)
qs.exclude.return_value.distinct.assert_called_once_with()
+ def test_filtering_with_lookup_expr(self):
+ qs = mock.Mock(spec=['filter'])
+ f = MultipleChoiceFilter(field_name='somefield',
lookup_expr='icontains')
+ with mock.patch('django_filters.filters.Q') as mockQclass:
+ mockQ1, mockQ2 = mock.MagicMock(), mock.MagicMock()
+ mockQclass.side_effect = [mockQ1, mockQ2]
+
+ f.filter(qs, ['value'])
+
+ self.assertEqual(mockQclass.call_args_list,
+ [mock.call(),
mock.call(somefield__icontains='value')])
+ mockQ1.__ior__.assert_called_once_with(mockQ2)
+ qs.filter.assert_called_once_with(mockQ1.__ior__.return_value)
+ qs.filter.return_value.distinct.assert_called_once_with()
+
def
test_filtering_on_required_skipped_when_len_of_value_is_len_of_field_choices(self):
qs = mock.Mock(spec=[])
f = MultipleChoiceFilter(field_name='somefield', required=True)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/test_filterset.py
new/django-filter-2.2.0/tests/test_filterset.py
--- old/django-filter-2.1.0/tests/test_filterset.py 2019-01-20
11:22:12.000000000 +0100
+++ new/django-filter-2.2.0/tests/test_filterset.py 2019-02-23
16:37:14.000000000 +0100
@@ -851,7 +851,7 @@
def test_no__getitem__(self):
# The DTL processes variable lookups by the following rules:
- #
https://docs.djangoproject.com/en/1.9/ref/templates/language/#variables
+ #
https://docs.djangoproject.com/en/stable/ref/templates/language/#variables
# A __getitem__ implementation precedes normal attribute access, and in
# the case of #58, will force the queryset to evaluate when it should
# not (eg, when rendering a blank form).
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn'
'--exclude=.svnignore' old/django-filter-2.1.0/tests/test_views.py
new/django-filter-2.2.0/tests/test_views.py
--- old/django-filter-2.1.0/tests/test_views.py 2019-01-20 12:50:09.000000000
+0100
+++ new/django-filter-2.2.0/tests/test_views.py 2019-07-16 20:13:20.000000000
+0200
@@ -3,6 +3,7 @@
from django.core.exceptions import ImproperlyConfigured
from django.test import TestCase, override_settings
from django.test.client import RequestFactory
+from django.utils import html
from django_filters.filterset import FilterSet, filterset_factory
from django_filters.views import FilterView
@@ -27,13 +28,13 @@
def test_view(self):
response = self.client.get(self.base_url)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
def test_view_filtering_on_title(self):
response = self.client.get(self.base_url + '?title=Snowcrash')
- for b in ['Ender's Game', 'Rainbow Six']:
- self.assertNotContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six']:
+ self.assertNotContains(response, html.escape(b))
self.assertContains(response, 'Snowcrash')
def test_view_with_filterset_not_model(self):
@@ -43,8 +44,8 @@
view = FilterView.as_view(filterset_class=filterset)
response = view(request)
self.assertEqual(response.status_code, 200)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
def test_view_with_model_no_filterset(self):
factory = RequestFactory()
@@ -52,8 +53,8 @@
view = FilterView.as_view(model=Book)
response = view(request)
self.assertEqual(response.status_code, 200)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
def test_view_with_model_and_fields_no_filterset(self):
factory = RequestFactory()
@@ -63,15 +64,15 @@
# filtering only by price
response = view(request)
self.assertEqual(response.status_code, 200)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
# not filtering by title
request = factory.get(self.base_url + '?title=Snowcrash')
response = view(request)
self.assertEqual(response.status_code, 200)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
def test_view_with_strict_errors(self):
factory = RequestFactory()
@@ -142,14 +143,14 @@
def test_view(self):
response = self.client.get(self.base_url)
- for b in ['Ender's Game', 'Rainbow Six', 'Snowcrash']:
- self.assertContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six', 'Snowcrash']:
+ self.assertContains(response, html.escape(b))
# extra context
self.assertEqual(response.context_data['foo'], 'bar')
self.assertEqual(response.context_data['bar'], 'foo')
def test_view_filtering_on_price(self):
response = self.client.get(self.base_url + '?title=Snowcrash')
- for b in ['Ender's Game', 'Rainbow Six']:
- self.assertNotContains(response, b)
+ for b in ["Ender's Game", 'Rainbow Six']:
+ self.assertNotContains(response, html.escape(b))
self.assertContains(response, 'Snowcrash')