Changelogs » Django

PyUp Safety actively tracks 263,166 Python packages for vulnerabilities and notifies you when to upgrade.

Django

3.1.1

==========================
  
  *September 1, 2020*
  
  Django 3.1.1 fixes two security issues and several bugs in 3.1.
  
  CVE-2020-24583: Incorrect permissions on intermediate-level directories on Python 3.7+
  ======================================================================================
  
  On Python 3.7+, :setting:`FILE_UPLOAD_DIRECTORY_PERMISSIONS` mode was not
  applied to intermediate-level directories created in the process of uploading
  files and to intermediate-level collected static directories when using the
  :djadmin:`collectstatic` management command.
  
  You should review and manually fix permissions on existing intermediate-level
  directories.
  
  CVE-2020-24584: Permission escalation in intermediate-level directories of the file system cache on Python 3.7+
  ===============================================================================================================
  
  On Python 3.7+, the intermediate-level directories of the file system cache had
  the system's standard umask rather than ``0o077`` (no group or others
  permissions).
  
  Bugfixes
  ========
  
  * Fixed wrapping of translated action labels in the admin's navigation sidebar
  for East Asian languages (:ticket:`31853`).
  
  * Fixed wrapping of long model names in the admin's navigation sidebar
  (:ticket:`31854`).
  
  * Fixed encoding session data while upgrading multiple instances of the same
  project to Django 3.1 (:ticket:`31864`).
  
  * Adjusted admin's navigation sidebar template to reduce debug logging when
  rendering (:ticket:`31865`).
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update()`. When using
  related fields pointing to a proxy model in the ``of`` argument, the
  corresponding model was not locked (:ticket:`31866`).
  
  * Fixed a data loss possibility, following a regression in Django 2.0, when
  copying model instances with a cached fields value (:ticket:`31863`).
  
  * Fixed a regression in Django 3.1 that caused a crash when decoding an invalid
  session data (:ticket:`31895`).
  
  * Reverted a deprecation in Django 3.1 that caused a crash when passing
  deprecated keyword arguments to a queryset in
  ``TemplateView.get_context_data()`` (:ticket:`31877`).
  
  * Enforced thread sensitivity of the :class:`MiddlewareMixin.process_request()
  <django.utils.deprecation.MiddlewareMixin>` and ``process_response()`` hooks
  when in an async context (:ticket:`31905`).
  
  * Fixed ``__in`` lookup on key transforms for
  :class:`~django.db.models.JSONField` with MariaDB, MySQL, Oracle, and SQLite
  (:ticket:`31936`).
  
  * Fixed a regression in Django 3.1 that caused permission errors in
  ``CommonPasswordValidator`` and ``settings.py`` generated by the
  :djadmin:`startproject` command, when user didn't have permissions to all
  intermediate directories in a Django installation path (:ticket:`31912`).
  
  * Fixed detecting an async ``get_response`` callable in various builtin
  middlewares (:ticket:`31928`).
  
  * Fixed a ``QuerySet.order_by()`` crash on PostgreSQL when ordering and
  grouping by :class:`~django.db.models.JSONField` with a custom
  :attr:`~django.db.models.JSONField.decoder` (:ticket:`31956`).
  
  * Fixed a ``QuerySet.delete()`` crash on MySQL, following a performance
  regression in Django 3.1 on MariaDB 10.3.2+, when filtering against an
  aggregate function (:ticket:`31965`).
  
  * Fixed a ``django.contrib.admin.EmptyFieldListFilter`` crash when using on
  reverse relations (:ticket:`31952`).
  
  * Prevented content overflowing in the admin changelist view when the
  navigation sidebar is enabled (:ticket:`31901`).
  
  
  ========================

3.1

========================
  
  *August 4, 2020*
  
  Welcome to Django 3.1!
  
  These release notes cover the :ref:`new features <whats-new-3.1>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-3.1>` you'll
  want to be aware of when upgrading from Django 3.0 or earlier. We've
  :ref:`dropped some features<removed-features-3.1>` that have reached the end of
  their deprecation cycle, and we've :ref:`begun the deprecation process for
  some features <deprecated-features-3.1>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Django 3.1 supports Python 3.6, 3.7, and 3.8. We **highly recommend** and only
  officially support the latest release of each series.
  
  .. _whats-new-3.1:
  
  What's new in Django 3.1
  ========================
  
  Asynchronous views and middleware support
  -----------------------------------------
  
  Django now supports a fully asynchronous request path, including:
  
  * :ref:`Asynchronous views <async-views>`
  * :ref:`Asynchronous middleware <async-middleware>`
  * :ref:`Asynchronous tests and test client <async-tests>`
  
  To get started with async views, you need to declare a view using
  ``async def``::
  
  async def my_view(request):
  await asyncio.sleep(0.5)
  return HttpResponse('Hello, async world!')
  
  All asynchronous features are supported whether you are running under WSGI or
  ASGI mode. However, there will be performance penalties using async code in
  WSGI mode. You can read more about the specifics in :doc:`/topics/async`
  documentation.
  
  You are free to mix async and sync views, middleware, and tests as much as you
  want. Django will ensure that you always end up with the right execution
  context. We expect most projects will keep the majority of their views
  synchronous, and only have a select few running in async mode - but it is
  entirely your choice.
  
  Django's ORM, cache layer, and other pieces of code that do long-running
  network calls do not yet support async access. We expect to add support for
  them in upcoming releases. Async views are ideal, however, if you are doing a
  lot of API or HTTP calls inside your view, you can now natively do all those
  HTTP calls in parallel to considerably speed up your view's execution.
  
  Asynchronous support should be entirely backwards-compatible and we have tried
  to ensure that it has no speed regressions for your existing, synchronous code.
  It should have no noticeable effect on any existing Django projects.
  
  JSONField for all supported database backends
  ---------------------------------------------
  
  Django now includes :class:`.models.JSONField` and
  :class:`forms.JSONField <django.forms.JSONField>` that can be used on all
  supported database backends. Both fields support the use of custom JSON
  encoders and decoders. The model field supports the introspection,
  :ref:`lookups, and transforms <querying-jsonfield>` that were previously
  PostgreSQL-only::
  
  from django.db import models
  
  class ContactInfo(models.Model):
  data = models.JSONField()
  
  ContactInfo.objects.create(data={
  'name': 'John',
  'cities': ['London', 'Cambridge'],
  'pets': {'dogs': ['Rufus', 'Meg']},
  })
  ContactInfo.objects.filter(
  data__name='John',
  data__pets__has_key='dogs',
  data__cities__contains='London',
  ).delete()
  
  If your project uses ``django.contrib.postgres.fields.JSONField``, plus the
  related form field and transforms, you should adjust to use the new fields,
  and generate and apply a database migration. For now, the old fields and
  transforms are left as a reference to the new ones and are :ref:`deprecated as
  of this release <deprecated-jsonfield>`.
  
  .. _default-hashing-algorithm-usage:
  
  ``DEFAULT_HASHING_ALGORITHM`` settings
  --------------------------------------
  
  The new :setting:`DEFAULT_HASHING_ALGORITHM` transitional setting allows
  specifying the default hashing algorithm to use for encoding cookies, password
  reset tokens in the admin site, user sessions, and signatures created by
  :class:`django.core.signing.Signer` and :meth:`django.core.signing.dumps`.
  
  Support for SHA-256 was added in Django 3.1. If you are upgrading multiple
  instances of the same project to Django 3.1, you should set
  :setting:`DEFAULT_HASHING_ALGORITHM` to ``'sha1'`` during the transition, in
  order to allow compatibility with the older versions of Django. Note that this
  requires Django 3.1.1+. Once the transition to 3.1 is complete you can stop
  overriding :setting:`DEFAULT_HASHING_ALGORITHM`.
  
  This setting is deprecated as of this release, because support for tokens,
  cookies, sessions, and signatures that use SHA-1 algorithm will be removed in
  Django 4.0.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new ``django.contrib.admin.EmptyFieldListFilter`` for
  :attr:`.ModelAdmin.list_filter` allows filtering on empty values (empty
  strings and nulls) in the admin changelist view.
  
  * Filters in the right sidebar of the admin changelist view now contain a link
  to clear all filters.
  
  * The admin now has a sidebar on larger screens for easier navigation. It is
  enabled by default but can be disabled by using a custom ``AdminSite`` and
  setting :attr:`.AdminSite.enable_nav_sidebar` to ``False``.
  
  Rendering the sidebar requires access to the current request in order to set
  CSS and ARIA role affordances. This requires using
  ``'django.template.context_processors.request'`` in the
  ``'context_processors'`` option of :setting:`OPTIONS <TEMPLATES-OPTIONS>`.
  
  * ``XRegExp`` is upgraded from version 2.0.0 to 3.2.0.
  
  * jQuery is upgraded from version 3.4.1 to 3.5.1.
  
  * Select2 library is upgraded from version 4.0.7 to 4.0.13.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The default iteration count for the PBKDF2 password hasher is increased from
  180,000 to 216,000.
  
  * The new :setting:`PASSWORD_RESET_TIMEOUT` setting allows defining the number
  of seconds a password reset link is valid for. This is encouraged instead of
  the deprecated ``PASSWORD_RESET_TIMEOUT_DAYS`` setting, which will be removed
  in Django 4.0.
  
  * The password reset mechanism now uses the SHA-256 hashing algorithm. Support
  for tokens that use the old hashing algorithm remains until Django 4.0.
  
  * :meth:`.AbstractBaseUser.get_session_auth_hash` now uses the SHA-256 hashing
  algorithm. Support for user sessions that use the old hashing algorithm
  remains until Django 4.0.
  
  :mod:`django.contrib.contenttypes`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`remove_stale_contenttypes --include-stale-apps` option
  allows removing stale content types from previously installed apps that have
  been removed from :setting:`INSTALLED_APPS`.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :lookup:`relate` lookup is now supported on MariaDB.
  
  * Added the :attr:`.LinearRing.is_counterclockwise` property.
  
  * :class:`~django.contrib.gis.db.models.functions.AsGeoJSON` is now supported
  on Oracle.
  
  * Added the :class:`~django.contrib.gis.db.models.functions.AsWKB` and
  :class:`~django.contrib.gis.db.models.functions.AsWKT` functions.
  
  * Added support for PostGIS 3 and GDAL 3.
  
  :mod:`django.contrib.humanize`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :tfilter:`intword` template filter now supports negative integers.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :class:`~django.contrib.postgres.indexes.BloomIndex` class allows
  creating ``bloom`` indexes in the database. The new
  :class:`~django.contrib.postgres.operations.BloomExtension` migration
  operation installs the ``bloom`` extension to add support for this index.
  
  * :meth:`~django.db.models.Model.get_FOO_display` now supports
  :class:`~django.contrib.postgres.fields.ArrayField` and
  :class:`~django.contrib.postgres.fields.RangeField`.
  
  * The new :lookup:`rangefield.lower_inc`, :lookup:`rangefield.lower_inf`,
  :lookup:`rangefield.upper_inc`, and :lookup:`rangefield.upper_inf` lookups
  allow querying :class:`~django.contrib.postgres.fields.RangeField` by a bound
  type.
  
  * :lookup:`rangefield.contained_by` now supports
  :class:`~django.db.models.SmallAutoField`,
  :class:`~django.db.models.AutoField`,
  :class:`~django.db.models.BigAutoField`,
  :class:`~django.db.models.SmallIntegerField`, and
  :class:`~django.db.models.DecimalField`.
  
  * :class:`~django.contrib.postgres.search.SearchQuery` now supports
  ``'websearch'`` search type on PostgreSQL 11+.
  
  * :class:`SearchQuery.value <django.contrib.postgres.search.SearchQuery>` now
  supports query expressions.
  
  * The new :class:`~django.contrib.postgres.search.SearchHeadline` class allows
  highlighting search results.
  
  * :lookup:`search` lookup now supports query expressions.
  
  * The new ``cover_density`` parameter of
  :class:`~django.contrib.postgres.search.SearchRank` allows ranking by cover
  density.
  
  * The new ``normalization`` parameter of
  :class:`~django.contrib.postgres.search.SearchRank` allows rank
  normalization.
  
  * The new :attr:`.ExclusionConstraint.deferrable` attribute allows creating
  deferrable exclusion constraints.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :setting:`SESSION_COOKIE_SAMESITE` setting now allows ``'None'`` (string)
  value to explicitly state that the cookie is sent with all same-site and
  cross-site requests.
  
  :mod:`django.contrib.staticfiles`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :setting:`STATICFILES_DIRS` setting now supports :class:`pathlib.Path`.
  
  Cache
  ~~~~~
  
  * The :func:`~django.views.decorators.cache.cache_control` decorator and
  :func:`~django.utils.cache.patch_cache_control` method now support multiple
  field names in the ``no-cache`` directive for the ``Cache-Control`` header,
  according to :rfc:`7234section-5.2.2.2`.
  
  * :meth:`~django.core.caches.cache.delete` now returns ``True`` if the key was
  successfully deleted, ``False`` otherwise.
  
  CSRF
  ~~~~
  
  * The :setting:`CSRF_COOKIE_SAMESITE` setting now allows ``'None'`` (string)
  value to explicitly state that the cookie is sent with all same-site and
  cross-site requests.
  
  Email
  ~~~~~
  
  * The :setting:`EMAIL_FILE_PATH` setting, used by the :ref:`file email backend
  <topic-email-file-backend>`, now supports :class:`pathlib.Path`.
  
  Error Reporting
  ~~~~~~~~~~~~~~~
  
  * :class:`django.views.debug.SafeExceptionReporterFilter` now filters sensitive
  values from ``request.META`` in exception reports.
  
  * The new :attr:`.SafeExceptionReporterFilter.cleansed_substitute` and
  :attr:`.SafeExceptionReporterFilter.hidden_settings` attributes allow
  customization of sensitive settings and ``request.META`` filtering in
  exception reports.
  
  * The technical 404 debug view now respects
  :setting:`DEFAULT_EXCEPTION_REPORTER_FILTER` when applying settings
  filtering.
  
  * The new :setting:`DEFAULT_EXCEPTION_REPORTER` allows providing a
  :class:`django.views.debug.ExceptionReporter` subclass to customize exception
  report generation. See :ref:`custom-error-reports` for details.
  
  File Storage
  ~~~~~~~~~~~~
  
  * ``FileSystemStorage.save()`` method now supports :class:`pathlib.Path`.
  
  * :class:`~django.db.models.FileField` and
  :class:`~django.db.models.ImageField` now accept a callable for ``storage``.
  This allows you to modify the used storage at runtime, selecting different
  storages for different environments, for example.
  
  Forms
  ~~~~~
  
  * :class:`~django.forms.ModelChoiceIterator`, used by
  :class:`~django.forms.ModelChoiceField` and
  :class:`~django.forms.ModelMultipleChoiceField`, now uses
  :class:`~django.forms.ModelChoiceIteratorValue` that can be used by widgets
  to access model instances. See :ref:`iterating-relationship-choices` for
  details.
  
  * :class:`django.forms.DateTimeField` now accepts dates in a subset of ISO 8601
  datetime formats, including optional timezone, e.g. ``2019-10-10T06:47``,
  ``2019-10-10T06:47:23+04:00``, or ``2019-10-10T06:47:23Z``. The timezone will
  always be retained if provided, with timezone-aware datetimes being returned
  even when :setting:`USE_TZ` is ``False``.
  
  Additionally, ``DateTimeField`` now uses ``DATE_INPUT_FORMATS`` in addition
  to ``DATETIME_INPUT_FORMATS`` when converting a field input to a ``datetime``
  value.
  
  * :attr:`.MultiWidget.widgets` now accepts a dictionary which allows
  customizing subwidget ``name`` attributes.
  
  * The new :attr:`.BoundField.widget_type` property can be used to dynamically
  adjust form rendering based upon the widget type.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * The :setting:`LANGUAGE_COOKIE_SAMESITE` setting now allows ``'None'``
  (string) value to explicitly state that the cookie is sent with all same-site
  and cross-site requests.
  
  * Added support and translations for the Algerian Arabic, Igbo, Kyrgyz, Tajik,
  and Turkmen languages.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`check --database` option allows specifying database aliases
  for running the ``database`` system checks. Previously these checks were
  enabled for all configured :setting:`DATABASES` by passing the ``database``
  tag to the command.
  
  * The new :option:`migrate --check` option makes the command exit with a
  non-zero status when unapplied migrations are detected.
  
  * The new ``returncode`` argument for
  :attr:`~django.core.management.CommandError` allows customizing the exit
  status for management commands.
  
  * The new :option:`dbshell -- ARGUMENTS <dbshell -->` option allows passing
  extra arguments to the command-line client for the database.
  
  * The :djadmin:`flush` and :djadmin:`sqlflush` commands now include SQL to
  reset sequences on SQLite.
  
  Models
  ~~~~~~
  
  * The new :class:`~django.db.models.functions.ExtractIsoWeekDay` function
  extracts ISO-8601 week days from :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField`, and the new :lookup:`iso_week_day`
  lookup allows querying by an ISO-8601 day of week.
  
  * :meth:`.QuerySet.explain` now supports:
  
  * ``TREE`` format on MySQL 8.0.16+,
  * ``analyze`` option on MySQL 8.0.18+ and MariaDB.
  
  * Added :class:`~django.db.models.PositiveBigIntegerField` which acts much like
  a :class:`~django.db.models.PositiveIntegerField` except that it only allows
  values under a certain (database-dependent) limit. Values from ``0`` to
  ``9223372036854775807`` are safe in all databases supported by Django.
  
  * The new :class:`~django.db.models.RESTRICT` option for
  :attr:`~django.db.models.ForeignKey.on_delete` argument of ``ForeignKey`` and
  ``OneToOneField`` emulates the behavior of the SQL constraint ``ON DELETE
  RESTRICT``.
  
  * :attr:`.CheckConstraint.check` now supports boolean expressions.
  
  * The :meth:`.RelatedManager.add`, :meth:`~.RelatedManager.create`, and
  :meth:`~.RelatedManager.set` methods now accept callables as values in the
  ``through_defaults`` argument.
  
  * The new ``is_dst``  parameter of the :meth:`.QuerySet.datetimes` determines
  the treatment of nonexistent and ambiguous datetimes.
  
  * The new :class:`~django.db.models.F` expression ``bitxor()`` method allows
  :ref:`bitwise XOR operation <using-f-expressions-in-filters>`.
  
  * :meth:`.QuerySet.bulk_create` now sets the primary key on objects when using
  MariaDB 10.5+.
  
  * The ``DatabaseOperations.sql_flush()`` method now generates more efficient
  SQL on MySQL by using ``DELETE`` instead of ``TRUNCATE`` statements for
  tables which don't require resetting sequences.
  
  * SQLite functions are now marked as :py:meth:`deterministic
  <sqlite3.Connection.create_function>` on Python 3.8+. This allows using them
  in check constraints and partial indexes.
  
  * The new :attr:`.UniqueConstraint.deferrable` attribute allows creating
  deferrable unique constraints.
  
  Pagination
  ~~~~~~~~~~
  
  * :class:`~django.core.paginator.Paginator` can now be iterated over to yield
  its pages.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * If :setting:`ALLOWED_HOSTS` is empty and ``DEBUG=True``, subdomains of
  localhost are now allowed in the ``Host`` header, e.g. ``static.localhost``.
  
  * :meth:`.HttpResponse.set_cookie` and :meth:`.HttpResponse.set_signed_cookie`
  now allow using ``samesite='None'`` (string) to explicitly state that the
  cookie is sent with all same-site and cross-site requests.
  
  * The new :meth:`.HttpRequest.accepts` method returns whether the request
  accepts the given MIME type according to the ``Accept`` HTTP header.
  
  .. _whats-new-security-3.1:
  
  Security
  ~~~~~~~~
  
  * The :setting:`SECURE_REFERRER_POLICY` setting now defaults to
  ``'same-origin'``. With this configured,
  :class:`~django.middleware.security.SecurityMiddleware` sets the
  :ref:`referrer-policy` header to ``same-origin`` on all responses that do not
  already have it. This prevents the ``Referer`` header being sent to other
  origins. If you need the previous behavior, explicitly set
  :setting:`SECURE_REFERRER_POLICY` to ``None``.
  
  * The default algorithm of :class:`django.core.signing.Signer`,
  :meth:`django.core.signing.loads`, and :meth:`django.core.signing.dumps` is
  changed to the SHA-256. Support for signatures made with the old SHA-1
  algorithm remains until Django 4.0.
  
  Also, the new ``algorithm`` parameter of the
  :class:`~django.core.signing.Signer` allows customizing the hashing
  algorithm.
  
  Templates
  ~~~~~~~~~
  
  * The renamed :ttag:`translate` and :ttag:`blocktranslate` template tags are
  introduced for internationalization in template code. The older :ttag:`trans`
  and :ttag:`blocktrans` template tags aliases continue to work, and will be
  retained for the foreseeable future.
  
  * The :ttag:`include` template tag now accepts iterables of template names.
  
  Tests
  ~~~~~
  
  * :class:`~django.test.SimpleTestCase` now implements the ``debug()`` method to
  allow running a test without collecting the result and catching exceptions.
  This can be used to support running tests under a debugger.
  
  * The new :setting:`MIGRATE <TEST_MIGRATE>` test database setting allows
  disabling of migrations during a test database creation.
  
  * Django test runner now supports a :option:`test --buffer` option to discard
  output for passing tests.
  
  * :class:`~django.test.runner.DiscoverRunner` now skips running the system
  checks on databases not :ref:`referenced by tests<testing-multi-db>`.
  
  * :class:`~django.test.TransactionTestCase` teardown is now faster on MySQL
  due to :djadmin:`flush` command improvements. As a side effect the latter
  doesn't automatically reset sequences on teardown anymore. Enable
  :attr:`.TransactionTestCase.reset_sequences` if your tests require this
  feature.
  
  URLs
  ~~~~
  
  * :ref:`Path converters <registering-custom-path-converters>` can now raise
  ``ValueError`` in ``to_url()`` to indicate no match when reversing URLs.
  
  Utilities
  ~~~~~~~~~
  
  * :func:`~django.utils.encoding.filepath_to_uri` now supports
  :class:`pathlib.Path`.
  
  * :func:`~django.utils.dateparse.parse_duration` now supports comma separators
  for decimal fractions in the ISO 8601 format.
  
  * :func:`~django.utils.dateparse.parse_datetime`,
  :func:`~django.utils.dateparse.parse_duration`, and
  :func:`~django.utils.dateparse.parse_time` now support comma separators for
  milliseconds.
  
  Miscellaneous
  ~~~~~~~~~~~~~
  
  * The SQLite backend now supports :class:`pathlib.Path` for the ``NAME``
  setting.
  
  * The ``settings.py`` generated by the :djadmin:`startproject` command now uses
  :class:`pathlib.Path` instead of :mod:`os.path` for building filesystem
  paths.
  
  * The :setting:`TIME_ZONE <DATABASE-TIME_ZONE>` setting is now allowed on
  databases that support time zones.
  
  .. _backwards-incompatible-3.1:
  
  Backwards incompatible changes in 3.1
  =====================================
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * ``DatabaseOperations.fetch_returned_insert_columns()`` now requires an
  additional ``returning_params`` argument.
  
  * ``connection.timezone`` property is now ``'UTC'`` by default, or the
  :setting:`TIME_ZONE <DATABASE-TIME_ZONE>` when :setting:`USE_TZ` is ``True``
  on databases that support time zones. Previously, it was ``None`` on
  databases that support time zones.
  
  * ``connection._nodb_connection`` property is changed to the
  ``connection._nodb_cursor()`` method and now returns a context manager that
  yields a cursor and automatically closes the cursor and connection upon
  exiting the ``with`` statement.
  
  * ``DatabaseClient.runshell()`` now requires an additional ``parameters``
  argument as a list of extra arguments to pass on to the command-line client.
  
  * The ``sequences`` positional argument of ``DatabaseOperations.sql_flush()``
  is replaced by the boolean keyword-only argument ``reset_sequences``. If
  ``True``, the sequences of the truncated tables will be reset.
  
  * The ``allow_cascade`` argument of ``DatabaseOperations.sql_flush()`` is now a
  keyword-only argument.
  
  * The ``using`` positional argument of
  ``DatabaseOperations.execute_sql_flush()`` is removed. The method now uses
  the database of the called instance.
  
  * Third-party database backends must implement support for ``JSONField`` or set
  ``DatabaseFeatures.supports_json_field`` to ``False``. If storing primitives
  is not supported, set ``DatabaseFeatures.supports_primitives_in_json_field``
  to ``False``. If there is a true datatype for JSON, set
  ``DatabaseFeatures.has_native_json_field`` to ``True``. If
  :lookup:`jsonfield.contains` and :lookup:`jsonfield.contained_by` are not
  supported, set ``DatabaseFeatures.supports_json_field_contains`` to
  ``False``.
  
  * Third party database backends must implement introspection for ``JSONField``
  or set ``can_introspect_json_field`` to ``False``.
  
  Dropped support for MariaDB 10.1
  --------------------------------
  
  Upstream support for MariaDB 10.1 ends in October 2020. Django 3.1 supports
  MariaDB 10.2 and higher.
  
  ``contrib.admin`` browser support
  ---------------------------------
  
  The admin no longer supports the legacy Internet Explorer browser. See
  :ref:`the admin FAQ <admin-browser-support>` for details on supported browsers.
  
  :attr:`AbstractUser.first_name <django.contrib.auth.models.User.first_name>` ``max_length`` increased to 150
  ------------------------------------------------------------------------------------------------------------
  
  A migration for :attr:`django.contrib.auth.models.User.first_name` is included.
  If you have a custom user model inheriting from ``AbstractUser``, you'll need
  to generate and apply a database migration for your user model.
  
  If you want to preserve the 30 character limit for first names, use a custom
  form::
  
  from django import forms
  from django.contrib.auth.forms import UserChangeForm
  
  class MyUserChangeForm(UserChangeForm):
  first_name = forms.CharField(max_length=30, required=False)
  
  If you wish to keep this restriction in the admin when editing users, set
  ``UserAdmin.form`` to use this form::
  
  from django.contrib.auth.admin import UserAdmin
  from django.contrib.auth.models import User
  
  class MyUserAdmin(UserAdmin):
  form = MyUserChangeForm
  
  admin.site.unregister(User)
  admin.site.register(User, MyUserAdmin)
  
  Miscellaneous
  -------------
  
  * The cache keys used by :ttag:`cache` and generated by
  :func:`~django.core.cache.utils.make_template_fragment_key` are different
  from the keys generated by older versions of Django. After upgrading to
  Django 3.1, the first request to any previously cached template fragment will
  be a cache miss.
  
  * The logic behind the decision to return a redirection fallback or a 204 HTTP
  response from the :func:`~django.views.i18n.set_language` view is now based
  on the ``Accept`` HTTP header instead of the ``X-Requested-With`` HTTP header
  presence.
  
  * The compatibility imports of ``django.core.exceptions.EmptyResultSet`` in
  ``django.db.models.query``, ``django.db.models.sql``, and
  ``django.db.models.sql.datastructures`` are removed.
  
  * The compatibility import of ``django.core.exceptions.FieldDoesNotExist`` in
  ``django.db.models.fields`` is removed.
  
  * The compatibility imports of ``django.forms.utils.pretty_name()`` and
  ``django.forms.boundfield.BoundField`` in ``django.forms.forms`` are removed.
  
  * The compatibility imports of ``Context``, ``ContextPopException``, and
  ``RequestContext`` in ``django.template.base`` are removed.
  
  * The compatibility import of
  ``django.contrib.admin.helpers.ACTION_CHECKBOX_NAME`` in
  ``django.contrib.admin`` is removed.
  
  * The :setting:`STATIC_URL` and :setting:`MEDIA_URL` settings set to relative
  paths are now prefixed by the server-provided value of ``SCRIPT_NAME`` (or
  ``/`` if not set). This change should not affect settings set to valid URLs
  or absolute paths.
  
  * :class:`~django.middleware.http.ConditionalGetMiddleware` no longer adds the
  ``ETag`` header to responses with an empty
  :attr:`~django.http.HttpResponse.content`.
  
  * ``django.utils.decorators.classproperty()`` decorator is made public and
  moved to :class:`django.utils.functional.classproperty()`.
  
  * :tfilter:`floatformat` template filter now outputs (positive) ``0`` for
  negative numbers which round to zero.
  
  * :attr:`Meta.ordering <django.db.models.Options.ordering>` and
  :attr:`Meta.unique_together <django.db.models.Options.unique_together>`
  options on models in ``django.contrib`` modules that were formerly tuples are
  now lists.
  
  * The admin calendar widget now handles two-digit years according to the Open
  Group Specification, i.e. values between 69 and 99 are mapped to the previous
  century, and values between 0 and 68 are mapped to the current century.
  
  * Date-only formats are removed from the default list for
  :setting:`DATETIME_INPUT_FORMATS`.
  
  * The :class:`~django.forms.FileInput` widget no longer renders with the
  ``required`` HTML attribute when initial data exists.
  
  * The undocumented ``django.views.debug.ExceptionReporterFilter`` class is
  removed. As per the :ref:`custom-error-reports` documentation, classes to be
  used with :setting:`DEFAULT_EXCEPTION_REPORTER_FILTER` need to inherit from
  :class:`django.views.debug.SafeExceptionReporterFilter`.
  
  * The cache timeout set by :func:`~django.views.decorators.cache.cache_page`
  decorator now takes precedence over the ``max-age`` directive from the
  ``Cache-Control`` header.
  
  * Providing a non-local remote field in the :attr:`.ForeignKey.to_field`
  argument now raises :class:`~django.core.exceptions.FieldError`.
  
  * :setting:`SECURE_REFERRER_POLICY` now defaults to ``'same-origin'``. See the
  *What's New* :ref:`Security section <whats-new-security-3.1>` above for more
  details.
  
  * :djadmin:`check` management command now runs the ``database`` system checks
  only for database aliases specified using :option:`check --database` option.
  
  * :djadmin:`migrate` management command now runs the ``database`` system checks
  only for a database to migrate.
  
  * The admin CSS classes ``row1`` and ``row2`` are removed in favor of
  ``:nth-child(odd)`` and ``:nth-child(even)`` pseudo-classes.
  
  * The :func:`~django.contrib.auth.hashers.make_password` function now requires
  its argument to be a string or bytes. Other types should be explicitly cast
  to one of these.
  
  * The undocumented ``version`` parameter to the
  :class:`~django.contrib.gis.db.models.functions.AsKML` function is removed.
  
  * :ref:`JSON and YAML serializers <serialization-formats>`, used by
  :djadmin:`dumpdata`, now dump all data with Unicode by default. If you need
  the previous behavior, pass ``ensure_ascii=True`` to JSON serializer, or
  ``allow_unicode=False`` to YAML serializer.
  
  * The auto-reloader no longer monitors changes in built-in Django translation
  files.
  
  * The minimum supported version of ``mysqlclient`` is increased from 1.3.13 to
  1.4.0.
  
  * The undocumented ``django.contrib.postgres.forms.InvalidJSONInput`` and
  ``django.contrib.postgres.forms.JSONString`` are moved to
  ``django.forms.fields``.
  
  * The undocumented ``django.contrib.postgres.fields.jsonb.JsonAdapter`` class
  is removed.
  
  * The :ttag:`{% localize off %} <localize>` tag and :tfilter:`unlocalize`
  filter no longer respect :setting:`DECIMAL_SEPARATOR` setting.
  
  * The minimum supported version of ``asgiref`` is increased from 3.2 to
  3.2.10.
  
  * The :doc:`Media </topics/forms/media>` class now renders ``<script>`` tags
  without the ``type`` attribute to follow `WHATWG recommendations
  <https://html.spec.whatwg.org/multipage/scripting.htmlthe-script-element>`_.
  
  .. _deprecated-features-3.1:
  
  Features deprecated in 3.1
  ==========================
  
  .. _deprecated-jsonfield:
  
  PostgreSQL ``JSONField``
  ------------------------
  
  ``django.contrib.postgres.fields.JSONField`` and
  ``django.contrib.postgres.forms.JSONField`` are deprecated in favor of
  :class:`.models.JSONField` and
  :class:`forms.JSONField <django.forms.JSONField>`.
  
  The undocumented ``django.contrib.postgres.fields.jsonb.KeyTransform`` and
  ``django.contrib.postgres.fields.jsonb.KeyTextTransform`` are also deprecated
  in favor of the transforms in ``django.db.models.fields.json``.
  
  The new ``JSONField``\s, ``KeyTransform``, and ``KeyTextTransform`` can be used
  on all supported database backends.
  
  Miscellaneous
  -------------
  
  * ``PASSWORD_RESET_TIMEOUT_DAYS`` setting is deprecated in favor of
  :setting:`PASSWORD_RESET_TIMEOUT`.
  
  * The undocumented usage of the :lookup:`isnull` lookup with non-boolean values
  as the right-hand side is deprecated, use ``True`` or ``False`` instead.
  
  * The barely documented ``django.db.models.query_utils.InvalidQuery`` exception
  class is deprecated in favor of
  :class:`~django.core.exceptions.FieldDoesNotExist` and
  :class:`~django.core.exceptions.FieldError`.
  
  * The ``django-admin.py`` entry point is deprecated in favor of
  ``django-admin``.
  
  * The ``HttpRequest.is_ajax()`` method is deprecated as it relied on a
  jQuery-specific way of signifying AJAX calls, while current usage tends to
  use the JavaScript `Fetch API
  <https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API>`_. Depending on
  your use case, you can either write your own AJAX detection method, or use
  the new :meth:`.HttpRequest.accepts` method if your code depends on the
  client ``Accept`` HTTP header.
  
  If you are writing your own AJAX detection method, ``request.is_ajax()`` can
  be reproduced exactly as
  ``request.headers.get('x-requested-with') == 'XMLHttpRequest'``.
  
  * Passing ``None`` as the first argument to
  ``django.utils.deprecation.MiddlewareMixin.__init__()`` is deprecated.
  
  * The encoding format of cookies values used by
  :class:`~django.contrib.messages.storage.cookie.CookieStorage` is different
  from the format generated by older versions of Django. Support for the old
  format remains until Django 4.0.
  
  * The encoding format of sessions is different from the format generated by
  older versions of Django. Support for the old format remains until Django
  4.0.
  
  * The purely documentational ``providing_args`` argument for
  :class:`~django.dispatch.Signal` is deprecated. If you rely on this
  argument as documentation, you can move the text to a code comment or
  docstring.
  
  * Calling ``django.utils.crypto.get_random_string()`` without a ``length``
  argument is deprecated.
  
  * The ``list`` message for :class:`~django.forms.ModelMultipleChoiceField` is
  deprecated in favor of ``invalid_list``.
  
  * Passing raw column aliases to :meth:`.QuerySet.order_by` is deprecated. The
  same result can be achieved by passing aliases in a
  :class:`~django.db.models.expressions.RawSQL` instead beforehand.
  
  * The ``NullBooleanField`` model field is deprecated in favor of
  ``BooleanField(null=True)``.
  
  * ``django.conf.urls.url()`` alias of :func:`django.urls.re_path` is
  deprecated.
  
  * The ``{% ifequal %}`` and ``{% ifnotequal %}`` template tags are deprecated
  in favor of :ttag:`{% if %}<if>`. ``{% if %}`` covers all use cases, but if
  you need to continue using these tags, they can be extracted from Django to a
  module and included as a built-in tag in the :class:`'builtins'
  <django.template.backends.django.DjangoTemplates>` option in
  :setting:`OPTIONS <TEMPLATES-OPTIONS>`.
  
  * ``DEFAULT_HASHING_ALGORITHM`` transitional setting is deprecated.
  
  .. _removed-features-3.1:
  
  Features removed in 3.1
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 3.1.
  
  See :ref:`deprecated-features-2.2` for details on these changes, including how
  to remove usage of these features.
  
  * ``django.utils.timezone.FixedOffset`` is removed.
  
  * ``django.core.paginator.QuerySetPaginator`` is removed.
  
  * A model's ``Meta.ordering`` doesn't affect ``GROUP BY`` queries.
  
  * ``django.contrib.postgres.fields.FloatRangeField`` and
  ``django.contrib.postgres.forms.FloatRangeField`` are removed.
  
  * The ``FILE_CHARSET`` setting is removed.
  
  * ``django.contrib.staticfiles.storage.CachedStaticFilesStorage`` is removed.
  
  * The ``RemoteUserBackend.configure_user()`` method requires ``request`` as the
  first positional argument.
  
  * Support for ``SimpleTestCase.allow_database_queries`` and
  ``TransactionTestCase.multi_db`` is removed.
  
  
  ===========================

3.0.10

===========================
  
  *September 1, 2020*
  
  Django 3.0.10 fixes two security issues and two data loss bugs in 3.0.9.
  
  CVE-2020-24583: Incorrect permissions on intermediate-level directories on Python 3.7+
  ======================================================================================
  
  On Python 3.7+, :setting:`FILE_UPLOAD_DIRECTORY_PERMISSIONS` mode was not
  applied to intermediate-level directories created in the process of uploading
  files and to intermediate-level collected static directories when using the
  :djadmin:`collectstatic` management command.
  
  You should review and manually fix permissions on existing intermediate-level
  directories.
  
  CVE-2020-24584: Permission escalation in intermediate-level directories of the file system cache on Python 3.7+
  ===============================================================================================================
  
  On Python 3.7+, the intermediate-level directories of the file system cache had
  the system's standard umask rather than ``0o077`` (no group or others
  permissions).
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update()`. When using
  related fields pointing to a proxy model in the ``of`` argument, the
  corresponding model was not locked (:ticket:`31866`).
  
  * Fixed a data loss possibility, following a regression in Django 2.0, when
  copying model instances with a cached fields value (:ticket:`31863`).
  
  
  ==========================

3.0.9

==========================
  
  *August 3, 2020*
  
  Django 3.0.9 fixes several bugs in 3.0.8.
  
  Bugfixes
  ========
  
  * Allowed setting the ``SameSite`` cookie flag in
  :meth:`.HttpResponse.delete_cookie` (:ticket:`31790`).
  
  * Fixed crash when sending emails to addresses with display names longer than
  75 chars on Python 3.6.11+, 3.7.8+, and 3.8.4+ (:ticket:`31784`).
  
  
  ==========================

3.0.8

==========================
  
  *July 1, 2020*
  
  Django 3.0.8 fixes several bugs in 3.0.7.
  
  Bugfixes
  ========
  
  * Fixed messages of ``InvalidCacheKey`` exceptions and ``CacheKeyWarning``
  warnings raised by cache key validation (:ticket:`31654`).
  
  * Fixed a regression in Django 3.0.7 that caused a queryset crash when grouping
  by a many-to-one relationship (:ticket:`31660`).
  
  * Reallowed, following a regression in Django 3.0, non-expressions having a
  ``filterable`` attribute to be used as the right-hand side in queryset
  filters (:ticket:`31664`).
  
  * Fixed a regression in Django 3.0.2 that caused a migration crash on
  PostgreSQL when adding a foreign key to a model with a namespaced
  ``db_table`` (:ticket:`31735`).
  
  * Added compatibility for ``cx_Oracle`` 8 (:ticket:`31751`).
  
  
  ==========================

3.0.7

==========================
  
  *June 3, 2020*
  
  Django 3.0.7 fixes two security issues and several bugs in 3.0.6.
  
  CVE-2020-13254: Potential data leakage via malformed memcached keys
  ===================================================================
  
  In cases where a memcached backend does not perform key validation, passing
  malformed cache keys could result in a key collision, and potential data
  leakage. In order to avoid this vulnerability, key validation is added to the
  memcached cache backends.
  
  CVE-2020-13596: Possible XSS via admin ``ForeignKeyRawIdWidget``
  ================================================================
  
  Query parameters for the admin ``ForeignKeyRawIdWidget`` were not properly URL
  encoded, posing an XSS attack vector. ``ForeignKeyRawIdWidget`` now
  ensures query parameters are correctly URL encoded.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 3.0 by restoring the ability to use field
  lookups in ``Meta.ordering`` (:ticket:`31538`).
  
  * Fixed a regression in Django 3.0 where ``QuerySet.values()`` and
  ``values_list()`` crashed if a queryset contained an aggregation and a
  subquery annotation (:ticket:`31566`).
  
  * Fixed a regression in Django 3.0 where aggregates used wrong annotations when
  a queryset has multiple subqueries annotations (:ticket:`31568`).
  
  * Fixed a regression in Django 3.0 where ``QuerySet.values()`` and
  ``values_list()`` crashed if a queryset contained an aggregation and an
  ``Exists()`` annotation on Oracle (:ticket:`31584`).
  
  * Fixed a regression in Django 3.0 where all resolved ``Subquery()``
  expressions were considered equal (:ticket:`31607`).
  
  * Fixed a regression in Django 3.0.5 that affected translation loading for apps
  providing translations for territorial language variants as well as a generic
  language, where the project has different plural equations for the language
  (:ticket:`31570`).
  
  * Tracking a jQuery security release, upgraded the version of jQuery used by
  the admin from 3.4.1 to 3.5.1.
  
  
  ==========================

3.0.6 not secure

==========================
  
  *May 4, 2020*
  
  Django 3.0.6 fixes a bug in 3.0.5.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 3.0 that caused a crash when filtering a
  ``Subquery()`` annotation of a queryset containing a single related field
  against a ``SimpleLazyObject`` (:ticket:`31420`).
  
  
  ==========================

3.0.5 not secure

==========================
  
  *April 1, 2020*
  
  Django 3.0.5 fixes several bugs in 3.0.4.
  
  Bugfixes
  ========
  
  * Added the ability to handle ``.po`` files containing different plural
  equations for the same language (:ticket:`30439`).
  
  * Fixed a regression in Django 3.0 where ``QuerySet.values()`` and
  ``values_list()`` crashed if a queryset contained an aggregation and
  ``Subquery()`` annotation that collides with a field name (:ticket:`31377`).
  
  
  ==========================

3.0.4 not secure

==========================
  
  *March 4, 2020*
  
  Django 3.0.4 fixes a security issue and several bugs in 3.0.3.
  
  CVE-2020-9402: Potential SQL injection via ``tolerance`` parameter in GIS functions and aggregates on Oracle
  ============================================================================================================
  
  GIS functions and aggregates on Oracle were subject to SQL injection,
  using a suitably crafted ``tolerance``.
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility when using caching from async code
  (:ticket:`31253`).
  
  * Fixed a regression in Django 3.0 that caused a file response using a
  temporary file to be closed incorrectly (:ticket:`31240`).
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update`. When using
  related fields or parent link fields with :ref:`multi-table-inheritance` in
  the ``of`` argument, the corresponding models were not locked
  (:ticket:`31246`).
  
  * Fixed a regression in Django 3.0 that caused misplacing parameters in logged
  SQL queries on Oracle (:ticket:`31271`).
  
  * Fixed a regression in Django 3.0.3 that caused misplacing parameters of SQL
  queries when subtracting ``DateField`` or ``DateTimeField`` expressions on
  MySQL (:ticket:`31312`).
  
  * Fixed a regression in Django 3.0 that didn't include subqueries spanning
  multivalued relations in the ``GROUP BY`` clause (:ticket:`31150`).
  
  
  ==========================

3.0.3 not secure

==========================
  
  *February 3, 2020*
  
  Django 3.0.3 fixes a security issue and several bugs in 3.0.2.
  
  CVE-2020-7471: Potential SQL injection via ``StringAgg(delimiter)``
  ===================================================================
  
  :class:`~django.contrib.postgres.aggregates.StringAgg` aggregation function was
  subject to SQL injection, using a suitably crafted ``delimiter``.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 3.0 that caused a crash when subtracting
  ``DateField``, ``DateTimeField``, or ``TimeField`` from a ``Subquery()``
  annotation (:ticket:`31133`).
  
  * Fixed a regression in Django 3.0 where ``QuerySet.values()`` and
  ``values_list()`` crashed if a queryset contained an aggregation and
  ``Exists()`` annotation (:ticket:`31136`).
  
  * Relaxed the system check added in Django 3.0 to reallow use of a sublanguage
  in the :setting:`LANGUAGE_CODE` setting, when a base language is available in
  Django but the sublanguage is not (:ticket:`31141`).
  
  * Added support for using enumeration types ``TextChoices``,
  ``IntegerChoices``, and ``Choices`` in templates (:ticket:`31154`).
  
  * Fixed a system check to ensure the ``max_length`` attribute fits the longest
  choice, when a named group contains only non-string values (:ticket:`31155`).
  
  * Fixed a regression in Django 2.2 that caused a crash of
  :class:`~django.contrib.postgres.aggregates.ArrayAgg` and
  :class:`~django.contrib.postgres.aggregates.StringAgg` with ``filter``
  argument when used in a ``Subquery`` (:ticket:`31097`).
  
  * Fixed a regression in Django 2.2.7 that caused
  :meth:`~django.db.models.Model.get_FOO_display` to work incorrectly when
  overriding inherited choices (:ticket:`31124`).
  
  * Fixed a regression in Django 3.0 that caused a crash of
  ``QuerySet.prefetch_related()`` for ``GenericForeignKey`` with a custom
  ``ContentType`` foreign key (:ticket:`31190`).
  
  
  ==========================

3.0.2 not secure

==========================
  
  *January 2, 2020*
  
  Django 3.0.2 fixes several bugs in 3.0.1.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 3.0 that didn't include columns referenced by a
  ``Subquery()`` in the ``GROUP BY`` clause (:ticket:`31094`).
  
  * Fixed a regression in Django 3.0 where ``QuerySet.exists()`` crashed if a
  queryset contained an aggregation over a ``Subquery()`` (:ticket:`31109`).
  
  * Fixed a regression in Django 3.0 that caused a migration crash on PostgreSQL
  10+ when adding a foreign key and changing data in the same migration
  (:ticket:`31106`).
  
  * Fixed a regression in Django 3.0 where loading fixtures crashed for models
  defining a :attr:`~django.db.models.Field.default` for the primary key
  (:ticket:`31071`).
  
  
  ==========================

3.0.1 not secure

==========================
  
  *December 18, 2019*
  
  Django 3.0.1 fixes a security issue and several bugs in 3.0.
  
  CVE-2019-19844: Potential account hijack via password reset form
  ================================================================
  
  By submitting a suitably crafted email address making use of Unicode
  characters, that compared equal to an existing user email when lower-cased for
  comparison, an attacker could be sent a password reset token for the matched
  account.
  
  In order to avoid this vulnerability, password reset requests now compare the
  submitted email using the stricter, recommended algorithm for case-insensitive
  comparison of two identifiers from `Unicode Technical Report 36, section
  2.11.2(B)(2)`__. Upon a match, the email containing the reset token will be
  sent to the email address on record rather than the submitted address.
  
  .. __: https://www.unicode.org/reports/tr36/Recommendations_General
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 3.0 by restoring the ability to use Django
  inside Jupyter and other environments that force an async context, by adding
  an option to disable :ref:`async-safety` mechanism with
  :envvar:`DJANGO_ALLOW_ASYNC_UNSAFE` environment variable (:ticket:`31056`).
  
  * Fixed a regression in Django 3.0 where ``RegexPattern``, used by
  :func:`~django.urls.re_path`, returned positional arguments to be passed to
  the view when all optional named groups were missing (:ticket:`31061`).
  
  * Reallowed, following a regression in Django 3.0,
  :class:`~django.db.models.expressions.Window` expressions to be used in
  conditions outside of queryset filters, e.g. in
  :class:`~django.db.models.expressions.When` conditions (:ticket:`31060`).
  
  * Fixed a data loss possibility in
  :class:`~django.contrib.postgres.forms.SplitArrayField`. When using with
  ``ArrayField(BooleanField())``, all values after the first ``True`` value
  were marked as checked instead of preserving passed values (:ticket:`31073`).
  
  
  ========================

3.0 not secure

========================
  
  *December 2, 2019*
  
  Welcome to Django 3.0!
  
  These release notes cover the :ref:`new features <whats-new-3.0>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-3.0>` you'll
  want to be aware of when upgrading from Django 2.2 or earlier. We've
  :ref:`dropped some features<removed-features-3.0>` that have reached the end of
  their deprecation cycle, and we've :ref:`begun the deprecation process for
  some features <deprecated-features-3.0>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Django 3.0 supports Python 3.6, 3.7, and 3.8. We **highly recommend** and only
  officially support the latest release of each series.
  
  The Django 2.2.x series is the last to support Python 3.5.
  
  Third-party library support for older version of Django
  =======================================================
  
  Following the release of Django 3.0, we suggest that third-party app authors
  drop support for all versions of Django prior to 2.2. At that time, you should
  be able to run your package's tests using ``python -Wd`` so that deprecation
  warnings appear. After making the deprecation warning fixes, your app should be
  compatible with Django 3.0.
  
  .. _whats-new-3.0:
  
  What's new in Django 3.0
  ========================
  
  MariaDB support
  ---------------
  
  Django now officially supports `MariaDB <https://mariadb.org/>`_ 10.1 and
  higher. See :ref:`MariaDB notes <mariadb-notes>` for more details.
  
  ASGI support
  ------------
  
  Django 3.0 begins our journey to making Django fully async-capable by providing
  support for running as an `ASGI <https://asgi.readthedocs.io/>`_ application.
  
  This is in addition to our existing WSGI support. Django intends to support
  both for the foreseeable future. Async features will only be available to
  applications that run under ASGI, however.
  
  At this stage async support only applies to the outer ASGI application.
  Internally everything remains synchronous. Asynchronous middleware, views, etc.
  are not yet supported. You can, however, use ASGI middleware around Django's
  application, allowing you to combine Django with other ASGI frameworks.
  
  There is no need to switch your applications over unless you want to start
  experimenting with asynchronous code, but we have
  :doc:`documentation on deploying with ASGI </howto/deployment/asgi/index>` if
  you want to learn more.
  
  Note that as a side-effect of this change, Django is now aware of asynchronous
  event loops and will block you calling code marked as "async unsafe" - such as
  ORM operations - from an asynchronous context. If you were using Django from
  async code before, this may trigger if you were doing it incorrectly. If you
  see a ``SynchronousOnlyOperation`` error, then closely examine your code and
  move any database operations to be in a synchronous child thread.
  
  Exclusion constraints on PostgreSQL
  -----------------------------------
  
  The new :class:`~django.contrib.postgres.constraints.ExclusionConstraint` class
  enable adding exclusion constraints on PostgreSQL. Constraints are added to
  models using the
  :attr:`Meta.constraints <django.db.models.Options.constraints>` option.
  
  Filter expressions
  ------------------
  
  Expressions that output :class:`~django.db.models.BooleanField` may now be
  used directly in ``QuerySet`` filters, without having to first annotate and
  then filter against the annotation.
  
  Enumerations for model field choices
  ------------------------------------
  
  Custom enumeration types ``TextChoices``, ``IntegerChoices``, and ``Choices``
  are now available as a way to define :attr:`.Field.choices`. ``TextChoices``
  and ``IntegerChoices`` types are provided for text and integer fields. The
  ``Choices`` class allows defining a compatible enumeration for other concrete
  data types. These custom enumeration types support human-readable labels that
  can be translated and accessed via a property on the enumeration or its
  members. See :ref:`Enumeration types <field-choices-enum-types>` for more
  details and examples.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added support for the ``admin_order_field`` attribute on properties in
  :attr:`.ModelAdmin.list_display`.
  
  * The new :meth:`ModelAdmin.get_inlines()
  <django.contrib.admin.ModelAdmin.get_inlines>` method allows specifying the
  inlines based on the request or model instance.
  
  * Select2 library is upgraded from version 4.0.3 to 4.0.7.
  
  * jQuery is upgraded from version 3.3.1 to 3.4.1.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new ``reset_url_token`` attribute in
  :class:`~django.contrib.auth.views.PasswordResetConfirmView` allows
  specifying a token parameter displayed as a component of password reset
  URLs.
  
  * Added :class:`~django.contrib.auth.backends.BaseBackend` class to ease
  customization of authentication backends.
  
  * Added :meth:`~django.contrib.auth.models.User.get_user_permissions()` method
  to mirror the existing
  :meth:`~django.contrib.auth.models.User.get_group_permissions()` method.
  
  * Added HTML ``autocomplete`` attribute to widgets of username, email, and
  password fields in :mod:`django.contrib.auth.forms` for better interaction
  with browser password managers.
  
  * :djadmin:`createsuperuser` now falls back to environment variables for
  password and required fields, when a corresponding command line argument
  isn't provided in non-interactive mode.
  
  * :attr:`~django.contrib.auth.models.CustomUser.REQUIRED_FIELDS` now supports
  :class:`~django.db.models.ManyToManyField`\s.
  
  * The new :meth:`.UserManager.with_perm` method returns users that have the
  specified permission.
  
  * The default iteration count for the PBKDF2 password hasher is increased from
  150,000 to 180,000.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Allowed MySQL spatial lookup functions to operate on real geometries.
  Previous support was limited to bounding boxes.
  
  * Added the :class:`~django.contrib.gis.db.models.functions.GeometryDistance`
  function, supported on PostGIS.
  
  * Added support for the ``furlong`` unit in
  :class:`~django.contrib.gis.measure.Distance`.
  
  * The :setting:`GEOIP_PATH` setting now supports :class:`pathlib.Path`.
  
  * The :class:`~django.contrib.gis.geoip2.GeoIP2` class now accepts
  :class:`pathlib.Path` ``path``.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :class:`~django.contrib.postgres.fields.RangeOperators` helps to
  avoid typos in SQL operators that can be used together with
  :class:`~django.contrib.postgres.fields.RangeField`.
  
  * The new :class:`~django.contrib.postgres.fields.RangeBoundary` expression
  represents the range boundaries.
  
  * The new :class:`~django.contrib.postgres.operations.AddIndexConcurrently`
  and :class:`~django.contrib.postgres.operations.RemoveIndexConcurrently`
  classes allow creating and dropping indexes ``CONCURRENTLY`` on PostgreSQL.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new
  :meth:`~django.contrib.sessions.backends.base.SessionBase.get_session_cookie_age()`
  method allows dynamically specifying the session cookie age.
  
  :mod:`django.contrib.syndication`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added the ``language`` class attribute to the
  :class:`django.contrib.syndication.views.Feed` to customize a feed language.
  The default value is :func:`~django.utils.translation.get_language()` instead
  of :setting:`LANGUAGE_CODE`.
  
  Cache
  ~~~~~
  
  * :func:`~django.utils.cache.add_never_cache_headers` and
  :func:`~django.views.decorators.cache.never_cache` now add the ``private``
  directive to ``Cache-Control`` headers.
  
  File Storage
  ~~~~~~~~~~~~
  
  * The new :meth:`.Storage.get_alternative_name` method allows customizing the
  algorithm for generating filenames if a file with the uploaded name already
  exists.
  
  Forms
  ~~~~~
  
  * Formsets may control the widget used when ordering forms via
  :attr:`~django.forms.formsets.BaseFormSet.can_order` by setting the
  :attr:`~django.forms.formsets.BaseFormSet.ordering_widget` attribute or
  overriding :attr:`~django.forms.formsets.BaseFormSet.get_ordering_widget()`.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * Added the :setting:`LANGUAGE_COOKIE_HTTPONLY`,
  :setting:`LANGUAGE_COOKIE_SAMESITE`, and :setting:`LANGUAGE_COOKIE_SECURE`
  settings to set the ``HttpOnly``, ``SameSite``, and ``Secure`` flags on
  language cookies. The default values of these settings preserve the previous
  behavior.
  
  * Added support and translations for the Uzbek language.
  
  Logging
  ~~~~~~~
  
  * The new ``reporter_class`` parameter of
  :class:`~django.utils.log.AdminEmailHandler` allows providing an
  ``django.views.debug.ExceptionReporter`` subclass to customize the traceback
  text sent to site :setting:`ADMINS` when :setting:`DEBUG` is ``False``.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`compilemessages --ignore` option allows ignoring specific
  directories when searching for ``.po`` files to compile.
  
  * :option:`showmigrations --list` now shows the applied datetimes when
  ``--verbosity`` is 2 and above.
  
  * On PostgreSQL, :djadmin:`dbshell` now supports client-side TLS certificates.
  
  * :djadmin:`inspectdb` now introspects :class:`~django.db.models.OneToOneField`
  when a foreign key has a unique or primary key constraint.
  
  * The new :option:`--skip-checks` option skips running system checks prior to
  running the command.
  
  * The :option:`startapp --template` and :option:`startproject --template`
  options now support templates stored in XZ archives (``.tar.xz``, ``.txz``)
  and LZMA archives (``.tar.lzma``, ``.tlz``).
  
  Models
  ~~~~~~
  
  * Added hash database functions :class:`~django.db.models.functions.MD5`,
  :class:`~django.db.models.functions.SHA1`,
  :class:`~django.db.models.functions.SHA224`,
  :class:`~django.db.models.functions.SHA256`,
  :class:`~django.db.models.functions.SHA384`, and
  :class:`~django.db.models.functions.SHA512`.
  
  * Added the :class:`~django.db.models.functions.Sign` database function.
  
  * The new ``is_dst``  parameter of the
  :class:`~django.db.models.functions.Trunc` database functions determines the
  treatment of nonexistent and ambiguous datetimes.
  
  * ``connection.queries`` now shows ``COPY … TO`` statements on PostgreSQL.
  
  * :class:`~django.db.models.FilePathField` now accepts a callable for ``path``.
  
  * Allowed symmetrical intermediate table for self-referential
  :class:`~django.db.models.ManyToManyField`.
  
  * The ``name`` attributes of :class:`~django.db.models.CheckConstraint`,
  :class:`~django.db.models.UniqueConstraint`, and
  :class:`~django.db.models.Index` now support app label and class
  interpolation using the ``'%(app_label)s'`` and ``'%(class)s'`` placeholders.
  
  * The new :attr:`.Field.descriptor_class` attribute allows model fields to
  customize the get and set behavior by overriding their
  :py:ref:`descriptors <descriptors>`.
  
  * :class:`~django.db.models.Avg` and :class:`~django.db.models.Sum` now support
  the ``distinct`` argument.
  
  * Added :class:`~django.db.models.SmallAutoField` which acts much like an
  :class:`~django.db.models.AutoField` except that it only allows values under
  a certain (database-dependent) limit. Values from ``1`` to ``32767`` are safe
  in all databases supported by Django.
  
  * :class:`~django.db.models.AutoField`,
  :class:`~django.db.models.BigAutoField`, and
  :class:`~django.db.models.SmallAutoField` now inherit from
  ``IntegerField``, ``BigIntegerField`` and ``SmallIntegerField`` respectively.
  System checks and validators are now also properly inherited.
  
  * :attr:`.FileField.upload_to` now supports :class:`pathlib.Path`.
  
  * :class:`~django.db.models.CheckConstraint` is now supported on MySQL 8.0.16+.
  
  * The new ``allows_group_by_selected_pks_on_model()`` method of
  ``django.db.backends.base.BaseDatabaseFeatures`` allows optimization of
  ``GROUP BY`` clauses to require only the selected models' primary keys. By
  default, it's supported only for managed models on PostgreSQL.
  
  To enable the ``GROUP BY`` primary key-only optimization for unmanaged
  models, you have to subclass the PostgreSQL database engine, overriding the
  features class ``allows_group_by_selected_pks_on_model()`` method as you
  require. See :ref:`Subclassing the built-in database backends
  <subclassing-database-backends>` for an example.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Allowed :class:`~django.http.HttpResponse` to be initialized with
  :class:`memoryview` content.
  
  * For use in, for example, Django templates, :attr:`.HttpRequest.headers` now
  allows lookups using underscores (e.g. ``user_agent``) in place of hyphens.
  
  .. _whats-new-security-3.0:
  
  Security
  ~~~~~~~~
  
  * :setting:`X_FRAME_OPTIONS` now defaults to ``'DENY'``. In older versions, the
  :setting:`X_FRAME_OPTIONS` setting defaults to ``'SAMEORIGIN'``. If your site
  uses frames of itself, you will need to explicitly set ``X_FRAME_OPTIONS =
  'SAMEORIGIN'`` for them to continue working.
  
  * :setting:`SECURE_CONTENT_TYPE_NOSNIFF` now defaults to ``True``. With this
  enabled, :class:`~django.middleware.security.SecurityMiddleware` sets the
  :ref:`x-content-type-options` header on all responses that do not already
  have it.
  
  * :class:`~django.middleware.security.SecurityMiddleware` can now send the
  :ref:`Referrer-Policy <referrer-policy>` header.
  
  Tests
  ~~~~~
  
  * The new test :class:`~django.test.Client` argument
  ``raise_request_exception`` allows controlling whether or not exceptions
  raised during the request should also be raised in the test. The value
  defaults to ``True`` for backwards compatibility. If it is ``False`` and an
  exception occurs, the test client will return a 500 response with the
  attribute :attr:`~django.test.Response.exc_info`, a tuple providing
  information of the exception that occurred.
  
  * Tests and test cases to run can be selected by test name pattern using the
  new :option:`test -k` option.
  
  * HTML comparison, as used by
  :meth:`~django.test.SimpleTestCase.assertHTMLEqual`, now treats text, character
  references, and entity references that refer to the same character as
  equivalent.
  
  * Django test runner now supports headless mode for selenium tests on supported
  browsers. Add the ``--headless`` option to enable this mode.
  
  * Django test runner now supports ``--start-at`` and ``--start-after`` options
  to run tests starting from a specific top-level module.
  
  * Django test runner now supports a ``--pdb`` option to spawn a debugger at
  each error or failure.
  
  .. _backwards-incompatible-3.0:
  
  Backwards incompatible changes in 3.0
  =====================================
  
  ``Model.save()`` when providing a default for the primary key
  -------------------------------------------------------------
  
  :meth:`.Model.save` no longer attempts to find a row when saving a new
  ``Model`` instance and a default value for the primary key is provided, and
  always performs a single ``INSERT`` query. In older Django versions,
  ``Model.save()`` performed either an ``INSERT`` or an ``UPDATE`` based on
  whether or not the row exists.
  
  This makes calling ``Model.save()`` while providing a default primary key value
  equivalent to passing :ref:`force_insert=True <ref-models-force-insert>` to
  model's ``save()``. Attempts to use a new ``Model`` instance to update an
  existing row will result in an ``IntegrityError``.
  
  In order to update an existing model for a specific primary key value, use the
  :meth:`~django.db.models.query.QuerySet.update_or_create` method or
  ``QuerySet.filter(pk=…).update(…)`` instead. For example::
  
  >>> MyModel.objects.update_or_create(pk=existing_pk, defaults={'name': 'new name'})
  >>> MyModel.objects.filter(pk=existing_pk).update(name='new name')
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * The second argument of ``DatabaseIntrospection.get_geometry_type()`` is now
  the row description instead of the column name.
  
  * ``DatabaseIntrospection.get_field_type()`` may no longer return tuples.
  
  * If the database can create foreign keys in the same SQL statement that adds a
  field, add ``SchemaEditor.sql_create_column_inline_fk`` with the appropriate
  SQL; otherwise, set ``DatabaseFeatures.can_create_inline_fk = False``.
  
  * ``DatabaseFeatures.can_return_id_from_insert`` and
  ``can_return_ids_from_bulk_insert`` are renamed to
  ``can_return_columns_from_insert`` and ``can_return_rows_from_bulk_insert``.
  
  * Database functions now handle :class:`datetime.timezone` formats when created
  using :class:`datetime.timedelta` instances (e.g.
  ``timezone(timedelta(hours=5))``, which would output ``'UTC+05:00'``).
  Third-party backends should handle this format when preparing
  :class:`~django.db.models.DateTimeField` in ``datetime_cast_date_sql()``,
  ``datetime_extract_sql()``, etc.
  
  * Entries for ``AutoField``, ``BigAutoField``, and ``SmallAutoField`` are added
  to  ``DatabaseOperations.integer_field_ranges`` to support the integer range
  validators on these field types. Third-party backends may need to customize
  the default entries.
  
  * ``DatabaseOperations.fetch_returned_insert_id()`` is replaced by
  ``fetch_returned_insert_columns()`` which returns a list of values returned
  by the ``INSERT … RETURNING`` statement, instead of a single value.
  
  * ``DatabaseOperations.return_insert_id()`` is replaced by
  ``return_insert_columns()`` that accepts a ``fields``
  argument, which is an iterable of fields to be returned after insert. Usually
  this is only the auto-generated primary key.
  
  :mod:`django.contrib.admin`
  ---------------------------
  
  * Admin's model history change messages now prefers more readable field labels
  instead of field names.
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * Support for PostGIS 2.1 is removed.
  
  * Support for SpatiaLite 4.1 and 4.2 is removed.
  
  * Support for GDAL 1.11 and GEOS 3.4 is removed.
  
  Dropped support for PostgreSQL 9.4
  ----------------------------------
  
  Upstream support for PostgreSQL 9.4 ends in December 2019. Django 3.0 supports
  PostgreSQL 9.5 and higher.
  
  Dropped support for Oracle 12.1
  -------------------------------
  
  Upstream support for Oracle 12.1 ends in July 2021. Django 2.2 will be
  supported until April 2022. Django 3.0 officially supports Oracle 12.2 and 18c.
  
  Removed private Python 2 compatibility APIs
  -------------------------------------------
  
  While Python 2 support was removed in Django 2.0, some private APIs weren't
  removed from Django so that third party apps could continue using them until
  the Python 2 end-of-life.
  
  Since we expect apps to drop Python 2 compatibility when adding support for
  Django 3.0, we're removing these APIs at this time.
  
  * ``django.test.utils.str_prefix()`` - Strings don't have 'u' prefixes in
  Python 3.
  
  * ``django.test.utils.patch_logger()`` - Use
  :meth:`unittest.TestCase.assertLogs` instead.
  
  * ``django.utils.lru_cache.lru_cache()`` - Alias of
  :func:`functools.lru_cache`.
  
  * ``django.utils.decorators.available_attrs()`` - This function returns
  ``functools.WRAPPER_ASSIGNMENTS``.
  
  * ``django.utils.decorators.ContextDecorator`` - Alias of
  :class:`contextlib.ContextDecorator`.
  
  * ``django.utils._os.abspathu()`` - Alias of :func:`os.path.abspath`.
  
  * ``django.utils._os.upath()`` and ``npath()`` - These functions do nothing on
  Python 3.
  
  * ``django.utils.six`` - Remove usage of this vendored library or switch to
  `six <https://pypi.org/project/six/>`_.
  
  * ``django.utils.encoding.python_2_unicode_compatible()`` - Alias of
  ``six.python_2_unicode_compatible()``.
  
  * ``django.utils.functional.curry()`` - Use :func:`functools.partial` or
  :class:`functools.partialmethod`. See :commit:`5b1c389603a353625ae1603`.
  
  * ``django.utils.safestring.SafeBytes`` - Unused since Django 2.0.
  
  New default value for the ``FILE_UPLOAD_PERMISSIONS`` setting
  -------------------------------------------------------------
  
  In older versions, the :setting:`FILE_UPLOAD_PERMISSIONS` setting defaults to
  ``None``. With the default :setting:`FILE_UPLOAD_HANDLERS`, this results in
  uploaded files having different permissions depending on their size and which
  upload handler is used.
  
  ``FILE_UPLOAD_PERMISSIONS`` now defaults to ``0o644`` to avoid this
  inconsistency.
  
  New default values for security settings
  ----------------------------------------
  
  To make Django projects more secure by default, some security settings now have
  more secure default values:
  
  * :setting:`X_FRAME_OPTIONS` now defaults to ``'DENY'``.
  
  * :setting:`SECURE_CONTENT_TYPE_NOSNIFF` now defaults to ``True``.
  
  See the *What's New* :ref:`Security section <whats-new-security-3.0>` above for
  more details on these changes.
  
  Miscellaneous
  -------------
  
  * ``ContentType.__str__()`` now includes the model's ``app_label`` to
  disambiguate models with the same name in different apps.
  
  * Because accessing the language in the session rather than in the cookie is
  deprecated, ``LocaleMiddleware`` no longer looks for the user's language in
  the session and :func:`django.contrib.auth.logout` no longer preserves the
  session's language after logout.
  
  * :func:`django.utils.html.escape` now uses :func:`html.escape` to escape HTML.
  This converts ``'`` to ``&x27;`` instead of the previous equivalent decimal
  code ``&39;``.
  
  * The ``django-admin test -k`` option now works as the :option:`unittest
  -k<unittest.-k>` option rather than as a shortcut for ``--keepdb``.
  
  * Support for ``pywatchman`` < 1.2.0 is removed.
  
  * :func:`~django.utils.http.urlencode` now encodes iterable values as they are
  when ``doseq=False``, rather than iterating them, bringing it into line with
  the standard library :func:`urllib.parse.urlencode` function.
  
  * ``intword`` template filter now translates ``1.0`` as a singular phrase and
  all other numeric values as plural. This may be incorrect for some languages.
  
  * Assigning a value to a model's :class:`~django.db.models.ForeignKey` or
  :class:`~django.db.models.OneToOneField` ``'_id'`` attribute now unsets the
  corresponding field. Accessing the field afterwards will result in a query.
  
  * :func:`~django.utils.cache.patch_vary_headers` now handles an asterisk
  ``'*'`` according to :rfc:`7231section-7.1.4`, i.e. if a list of header
  field names contains an asterisk, then the ``Vary`` header will consist of a
  single asterisk ``'*'``.
  
  * On MySQL 8.0.16+, ``PositiveIntegerField`` and ``PositiveSmallIntegerField``
  now include a check constraint to prevent negative values in the database.
  
  * ``alias=None`` is added to the signature of
  :meth:`.Expression.get_group_by_cols`.
  
  * ``RegexPattern``, used by :func:`~django.urls.re_path`, no longer returns
  keyword arguments with ``None`` values to be passed to the view for the
  optional named groups that are missing.
  
  .. _deprecated-features-3.0:
  
  Features deprecated in 3.0
  ==========================
  
  ``django.utils.encoding.force_text()`` and ``smart_text()``
  -----------------------------------------------------------
  
  The ``smart_text()`` and ``force_text()`` aliases (since Django 2.0) of
  ``smart_str()`` and ``force_str()`` are deprecated. Ignore this deprecation if
  your code supports Python 2 as the behavior of ``smart_str()`` and
  ``force_str()`` is different there.
  
  Miscellaneous
  -------------
  
  * ``django.utils.http.urlquote()``, ``urlquote_plus()``, ``urlunquote()``, and
  ``urlunquote_plus()`` are deprecated in favor of the functions that they're
  aliases for: :func:`urllib.parse.quote`, :func:`~urllib.parse.quote_plus`,
  :func:`~urllib.parse.unquote`, and :func:`~urllib.parse.unquote_plus`.
  
  * ``django.utils.translation.ugettext()``, ``ugettext_lazy()``,
  ``ugettext_noop()``, ``ungettext()``, and ``ungettext_lazy()`` are deprecated
  in favor of the functions that they're aliases for:
  :func:`django.utils.translation.gettext`,
  :func:`~django.utils.translation.gettext_lazy`,
  :func:`~django.utils.translation.gettext_noop`,
  :func:`~django.utils.translation.ngettext`, and
  :func:`~django.utils.translation.ngettext_lazy`.
  
  * To limit creation of sessions and hence favor some caching strategies,
  :func:`django.views.i18n.set_language` will stop setting the user's language
  in the session in Django 4.0. Since Django 2.1, the language is always stored
  in the :setting:`LANGUAGE_COOKIE_NAME` cookie.
  
  * ``django.utils.text.unescape_entities()`` is deprecated in favor of
  :func:`html.unescape`. Note that unlike ``unescape_entities()``,
  ``html.unescape()`` evaluates lazy strings immediately.
  
  * To avoid possible confusion as to effective scope, the private internal
  utility ``is_safe_url()`` is renamed to
  ``url_has_allowed_host_and_scheme()``. That a URL has an allowed host and
  scheme doesn't in general imply that it's "safe". It may still be quoted
  incorrectly, for example. Ensure to also use
  :func:`~django.utils.encoding.iri_to_uri` on the path component of untrusted
  URLs.
  
  .. _removed-features-3.0:
  
  Features removed in 3.0
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 3.0.
  
  See :ref:`deprecated-features-2.0` for details on these changes, including how
  to remove usage of these features.
  
  * The ``django.db.backends.postgresql_psycopg2`` module is removed.
  
  * ``django.shortcuts.render_to_response()`` is removed.
  
  * The ``DEFAULT_CONTENT_TYPE`` setting is removed.
  
  * ``HttpRequest.xreadlines()`` is removed.
  
  * Support for the ``context`` argument of ``Field.from_db_value()`` and
  ``Expression.convert_value()`` is removed.
  
  * The ``field_name`` keyword argument of ``QuerySet.earliest()`` and
  ``latest()`` is removed.
  
  See :ref:`deprecated-features-2.1` for details on these changes, including how
  to remove usage of these features.
  
  * The ``ForceRHR`` GIS function is removed.
  
  * ``django.utils.http.cookie_date()`` is removed.
  
  * The ``staticfiles`` and ``admin_static`` template tag libraries are removed.
  
  * ``django.contrib.staticfiles.templatetags.staticfiles.static()`` is removed.
  
  
  ===========================

2.2.16

===========================
  
  *September 1, 2020*
  
  Django 2.2.16 fixes two security issues and two data loss bugs in 2.2.15.
  
  CVE-2020-24583: Incorrect permissions on intermediate-level directories on Python 3.7+
  ======================================================================================
  
  On Python 3.7+, :setting:`FILE_UPLOAD_DIRECTORY_PERMISSIONS` mode was not
  applied to intermediate-level directories created in the process of uploading
  files and to intermediate-level collected static directories when using the
  :djadmin:`collectstatic` management command.
  
  You should review and manually fix permissions on existing intermediate-level
  directories.
  
  CVE-2020-24584: Permission escalation in intermediate-level directories of the file system cache on Python 3.7+
  ===============================================================================================================
  
  On Python 3.7+, the intermediate-level directories of the file system cache had
  the system's standard umask rather than ``0o077`` (no group or others
  permissions).
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update()`. When using
  related fields pointing to a proxy model in the ``of`` argument, the
  corresponding model was not locked (:ticket:`31866`).
  
  * Fixed a data loss possibility, following a regression in Django 2.0, when
  copying model instances with a cached fields value (:ticket:`31863`).
  
  
  ===========================

2.2.15

===========================
  
  *August 3, 2020*
  
  Django 2.2.15 fixes two bugs in 2.2.14.
  
  Bugfixes
  ========
  
  * Allowed setting the ``SameSite`` cookie flag in
  :meth:`.HttpResponse.delete_cookie` (:ticket:`31790`).
  
  * Fixed crash when sending emails to addresses with display names longer than
  75 chars on Python 3.6.11+, 3.7.8+, and 3.8.4+ (:ticket:`31784`).
  
  
  ===========================

2.2.14

===========================
  
  *July 1, 2020*
  
  Django 2.2.14 fixes a bug in 2.2.13.
  
  Bugfixes
  ========
  
  * Fixed messages of ``InvalidCacheKey`` exceptions and ``CacheKeyWarning``
  warnings raised by cache key validation (:ticket:`31654`).
  
  
  ===========================

2.2.13

===========================
  
  *June 3, 2020*
  
  Django 2.2.13 fixes two security issues and a regression in 2.2.12.
  
  CVE-2020-13254: Potential data leakage via malformed memcached keys
  ===================================================================
  
  In cases where a memcached backend does not perform key validation, passing
  malformed cache keys could result in a key collision, and potential data
  leakage. In order to avoid this vulnerability, key validation is added to the
  memcached cache backends.
  
  CVE-2020-13596: Possible XSS via admin ``ForeignKeyRawIdWidget``
  ================================================================
  
  Query parameters for the admin ``ForeignKeyRawIdWidget`` were not properly URL
  encoded, posing an XSS attack vector. ``ForeignKeyRawIdWidget`` now
  ensures query parameters are correctly URL encoded.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.2.12 that affected translation loading for
  apps providing translations for territorial language variants as well as a
  generic language, where the project has different plural equations for the
  language (:ticket:`31570`).
  
  * Tracking a jQuery security release, upgraded the version of jQuery used by
  the admin from 3.3.1 to 3.5.1.
  
  
  ===========================

2.2.12 not secure

===========================
  
  *April 1, 2020*
  
  Django 2.2.12 fixes a bug in 2.2.11.
  
  Bugfixes
  ========
  
  * Added the ability to handle ``.po`` files containing different plural
  equations for the same language (:ticket:`30439`).
  
  
  ===========================

2.2.11 not secure

===========================
  
  *March 4, 2020*
  
  Django 2.2.11 fixes a security issue and a data loss bug in 2.2.10.
  
  CVE-2020-9402: Potential SQL injection via ``tolerance`` parameter in GIS functions and aggregates on Oracle
  ============================================================================================================
  
  GIS functions and aggregates on Oracle were subject to SQL injection,
  using a suitably crafted ``tolerance``.
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update`. When using
  related fields or parent link fields with :ref:`multi-table-inheritance` in
  the ``of`` argument, the corresponding models were not locked
  (:ticket:`31246`).
  
  
  ===========================

2.2.10 not secure

===========================
  
  *February 3, 2020*
  
  Django 2.2.10 fixes a security issue in 2.2.9.
  
  CVE-2020-7471: Potential SQL injection via ``StringAgg(delimiter)``
  ===================================================================
  
  :class:`~django.contrib.postgres.aggregates.StringAgg` aggregation function was
  subject to SQL injection, using a suitably crafted ``delimiter``.
  
  
  ==========================

2.2.9 not secure

==========================
  
  *December 18, 2019*
  
  Django 2.2.9 fixes a security issue and a data loss bug in 2.2.8.
  
  CVE-2019-19844: Potential account hijack via password reset form
  ================================================================
  
  By submitting a suitably crafted email address making use of Unicode
  characters, that compared equal to an existing user email when lower-cased for
  comparison, an attacker could be sent a password reset token for the matched
  account.
  
  In order to avoid this vulnerability, password reset requests now compare the
  submitted email using the stricter, recommended algorithm for case-insensitive
  comparison of two identifiers from `Unicode Technical Report 36, section
  2.11.2(B)(2)`__. Upon a match, the email containing the reset token will be
  sent to the email address on record rather than the submitted address.
  
  .. __: https://www.unicode.org/reports/tr36/Recommendations_General
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in
  :class:`~django.contrib.postgres.forms.SplitArrayField`. When using with
  ``ArrayField(BooleanField())``, all values after the first ``True`` value
  were marked as checked instead of preserving passed values (:ticket:`31073`).
  
  
  ==========================

2.2.8 not secure

==========================
  
  *December 2, 2019*
  
  Django 2.2.8 fixes a security issue, several bugs in 2.2.7, and adds
  compatibility with Python 3.8.
  
  CVE-2019-19118: Privilege escalation in the Django admin.
  =========================================================
  
  Since Django 2.1, a Django model admin displaying a parent model with related
  model inlines, where the user has view-only permissions to a parent model but
  edit permissions to the inline model, would display a read-only view of the
  parent model but editable forms for the inline.
  
  Submitting these forms would not allow direct edits to the parent model, but
  would trigger the parent model's ``save()`` method, and cause pre and post-save
  signal handlers to be invoked. This is a privilege escalation as a user who
  lacks permission to edit a model should not be able to trigger its save-related
  signals.
  
  To resolve this issue, the permission handling code of the Django admin
  interface has been changed. Now, if a user has only the "view" permission for a
  parent model, the entire displayed form will not be editable, even if the user
  has permission to edit models included in inlines.
  
  This is a backwards-incompatible change, and the Django security team is aware
  that some users of Django were depending on the ability to allow editing of
  inlines in the admin form of an otherwise view-only parent model.
  
  Given the complexity of the Django admin, and in-particular the permissions
  related checks, it is the view of the Django security team that this change was
  necessary: that it is not currently feasible to maintain the existing behavior
  while escaping the potential privilege escalation in a way that would avoid a
  recurrence of similar issues in the future, and that would be compatible with
  Django's *safe by default* philosophy.
  
  For the time being, developers whose applications are affected by this change
  should replace the use of inlines in read-only parents with custom forms and
  views that explicitly implement the desired functionality. In the longer term,
  adding a documented, supported, and properly-tested mechanism for
  partially-editable multi-model forms to the admin interface may occur in Django
  itself.
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in the admin changelist view when a custom
  :ref:`formset's prefix <formset-prefix>` contains regular expression special
  characters, e.g. ``'$'`` (:ticket:`31031`).
  
  * Fixed a regression in Django 2.2.1 that caused a crash when migrating
  permissions for proxy models with a multiple database setup if the
  ``default`` entry was empty (:ticket:`31021`).
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update()`. When using
  ``'self'`` in the ``of`` argument with :ref:`multi-table inheritance
  <multi-table-inheritance>`, a parent model was locked instead of the
  queryset's model (:ticket:`30953`).
  
  
  ==========================

2.2.7 not secure

==========================
  
  *November 4, 2019*
  
  Django 2.2.7 fixes several bugs in 2.2.6.
  
  Bugfixes
  ========
  
  * Fixed a crash when using a ``contains``, ``contained_by``, ``has_key``,
  ``has_keys``, or ``has_any_keys`` lookup on
  :class:`~django.contrib.postgres.fields.JSONField`, if the right or left hand
  side of an expression is a key transform (:ticket:`30826`).
  
  * Prevented :option:`migrate --plan` from showing that ``RunPython`` operations
  are irreversible when ``reverse_code`` callables don't have docstrings or
  when showing a forward migration plan (:ticket:`30870`).
  
  * Fixed migrations crash on PostgreSQL when adding an
  :class:`~django.db.models.Index` with fields ordering and
  :attr:`~.Index.opclasses` (:ticket:`30903`).
  
  * Restored the ability to override
  :meth:`~django.db.models.Model.get_FOO_display` (:ticket:`30931`).
  
  
  ==========================

2.2.6 not secure

==========================
  
  *October 1, 2019*
  
  Django 2.2.6 fixes several bugs in 2.2.5.
  
  Bugfixes
  ========
  
  * Fixed migrations crash on SQLite when altering a model containing partial
  indexes (:ticket:`30754`).
  
  * Fixed a regression in Django 2.2.4 that caused a crash when filtering with a
  ``Subquery()`` annotation of a queryset containing
  :class:`~django.contrib.postgres.fields.JSONField` or
  :class:`~django.contrib.postgres.fields.HStoreField` (:ticket:`30769`).
  
  
  ==========================

2.2.5 not secure

==========================
  
  *September 2, 2019*
  
  Django 2.2.5 fixes several bugs in 2.2.4.
  
  Bugfixes
  ========
  
  * Relaxed the system check added in Django 2.2 for models to reallow use of the
  same ``db_table`` by multiple models when database routers are installed
  (:ticket:`30673`).
  
  * Fixed crash of ``KeyTransform()`` for
  :class:`~django.contrib.postgres.fields.JSONField` and
  :class:`~django.contrib.postgres.fields.HStoreField` when using on
  expressions with params (:ticket:`30672`).
  
  * Fixed a regression in Django 2.2 where
  :attr:`ModelAdmin.list_filter <django.contrib.admin.ModelAdmin.list_filter>`
  choices to foreign objects don't respect a model's ``Meta.ordering``
  (:ticket:`30449`).
  
  
  ==========================

2.2.4 not secure

==========================
  
  *August 1, 2019*
  
  Django 2.2.4 fixes security issues and several bugs in 2.2.3.
  
  CVE-2019-14232: Denial-of-service possibility in ``django.utils.text.Truncator``
  ================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods
  were passed the ``html=True`` argument, they were extremely slow to evaluate
  certain inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  :tfilter:`truncatechars_html` and :tfilter:`truncatewords_html` template
  filters, which were thus vulnerable.
  
  The regular expressions used by ``Truncator`` have been simplified in order to
  avoid potential backtracking issues. As a consequence, trailing punctuation may
  now at times be included in the truncated output.
  
  CVE-2019-14233: Denial-of-service possibility in ``strip_tags()``
  =================================================================
  
  Due to the behavior of the underlying ``HTMLParser``,
  :func:`django.utils.html.strip_tags` would be extremely slow to evaluate
  certain inputs containing large sequences of nested incomplete HTML entities.
  The ``strip_tags()`` method is used to implement the corresponding
  :tfilter:`striptags` template filter, which was thus also vulnerable.
  
  ``strip_tags()`` now avoids recursive calls to ``HTMLParser`` when progress
  removing tags, but necessarily incomplete HTML entities, stops being made.
  
  Remember that absolutely NO guarantee is provided about the results of
  ``strip_tags()`` being HTML safe. So NEVER mark safe the result of a
  ``strip_tags()`` call without escaping it first, for example with
  :func:`django.utils.html.escape`.
  
  CVE-2019-14234: SQL injection possibility in key and index lookups for ``JSONField``/``HStoreField``
  ====================================================================================================
  
  :lookup:`Key and index lookups <jsonfield.key>` for
  :class:`~django.contrib.postgres.fields.JSONField` and :lookup:`key lookups
  <hstorefield.key>` for :class:`~django.contrib.postgres.fields.HStoreField`
  were subject to SQL injection, using a suitably crafted dictionary, with
  dictionary expansion, as the ``**kwargs`` passed to ``QuerySet.filter()``.
  
  CVE-2019-14235: Potential memory exhaustion in ``django.utils.encoding.uri_to_iri()``
  =====================================================================================
  
  If passed certain inputs, :func:`django.utils.encoding.uri_to_iri` could lead
  to significant memory usage due to excessive recursion when re-percent-encoding
  invalid UTF-8 octet sequences.
  
  ``uri_to_iri()`` now avoids recursion when re-percent-encoding invalid UTF-8
  octet sequences.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.2 when ordering a ``QuerySet.union()``,
  ``intersection()``, or ``difference()`` by a field type present more than
  once results in the wrong ordering being used (:ticket:`30628`).
  
  * Fixed a migration crash on PostgreSQL when adding a check constraint
  with a ``contains`` lookup on
  :class:`~django.contrib.postgres.fields.DateRangeField` or
  :class:`~django.contrib.postgres.fields.DateTimeRangeField`, if the right
  hand side of an expression is the same type (:ticket:`30621`).
  
  * Fixed a regression in Django 2.2 where auto-reloader crashes if a file path
  contains nulls characters (``'\x00'``) (:ticket:`30506`).
  
  * Fixed a regression in Django 2.2 where auto-reloader crashes if a translation
  directory cannot be resolved (:ticket:`30647`).
  
  
  ==========================

2.2.3 not secure

==========================
  
  *July 1, 2019*
  
  Django 2.2.3 fixes a security issue and several bugs in 2.2.2. Also, the latest
  string translations from Transifex are incorporated.
  
  CVE-2019-12781: Incorrect HTTP detection with reverse-proxy connecting via HTTPS
  --------------------------------------------------------------------------------
  
  When deployed behind a reverse-proxy connecting to Django via HTTPS,
  :attr:`django.http.HttpRequest.scheme` would incorrectly detect client
  requests made via HTTP as using HTTPS. This entails incorrect results for
  :meth:`~django.http.HttpRequest.is_secure`, and
  :meth:`~django.http.HttpRequest.build_absolute_uri`, and that HTTP
  requests would not be redirected to HTTPS in accordance with
  :setting:`SECURE_SSL_REDIRECT`.
  
  ``HttpRequest.scheme`` now respects :setting:`SECURE_PROXY_SSL_HEADER`, if it is
  configured, and the appropriate header is set on the request, for both HTTP and
  HTTPS requests.
  
  If you deploy Django behind a reverse-proxy that forwards HTTP requests, and
  that connects to Django via HTTPS, be sure to verify that your application
  correctly handles code paths relying on ``scheme``, ``is_secure()``,
  ``build_absolute_uri()``, and ``SECURE_SSL_REDIRECT``.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.2 where :class:`~django.db.models.Avg`,
  :class:`~django.db.models.StdDev`, and :class:`~django.db.models.Variance`
  crash with ``filter`` argument (:ticket:`30542`).
  
  * Fixed a regression in Django 2.2.2 where auto-reloader crashes with
  ``AttributeError``, e.g. when using ``ipdb`` (:ticket:`30588`).
  
  
  ==========================

2.2.2 not secure

==========================
  
  *June 3, 2019*
  
  Django 2.2.2 fixes security issues and several bugs in 2.2.1.
  
  CVE-2019-12308: AdminURLFieldWidget XSS
  ---------------------------------------
  
  The clickable "Current URL" link generated by ``AdminURLFieldWidget`` displayed
  the provided value without validating it as a safe URL. Thus, an unvalidated
  value stored in the database, or a value provided as a URL query parameter
  payload, could result in an clickable JavaScript link.
  
  ``AdminURLFieldWidget`` now validates the provided value using
  :class:`~django.core.validators.URLValidator` before displaying the clickable
  link. You may customize the validator by passing a ``validator_class`` kwarg to
  ``AdminURLFieldWidget.__init__()``, e.g. when using
  :attr:`~django.contrib.admin.ModelAdmin.formfield_overrides`.
  
  Patched bundled jQuery for CVE-2019-11358: Prototype pollution
  --------------------------------------------------------------
  
  jQuery before 3.4.0, mishandles ``jQuery.extend(true, {}, ...)`` because of
  ``Object.prototype`` pollution. If an unsanitized source object contained an
  enumerable ``__proto__`` property, it could extend the native
  ``Object.prototype``.
  
  The bundled version of jQuery used by the Django admin has been patched to
  allow for the ``select2`` library's use of ``jQuery.extend()``.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.2 that stopped Show/Hide toggles working on
  dynamically added admin inlines (:ticket:`30459`).
  
  * Fixed a regression in Django 2.2 where deprecation message crashes if
  ``Meta.ordering`` contains an expression (:ticket:`30463`).
  
  * Fixed a regression in Django 2.2.1 where
  :class:`~django.contrib.postgres.search.SearchVector` generates SQL with a
  redundant ``Coalesce`` call (:ticket:`30488`).
  
  * Fixed a regression in Django 2.2 where auto-reloader doesn't detect changes
  in ``manage.py`` file when using ``StatReloader`` (:ticket:`30479`).
  
  * Fixed crash of :class:`~django.contrib.postgres.aggregates.ArrayAgg` and
  :class:`~django.contrib.postgres.aggregates.StringAgg` with ``ordering``
  argument when used in a ``Subquery`` (:ticket:`30315`).
  
  * Fixed a regression in Django 2.2 that caused a crash of auto-reloader when
  an exception with custom signature is raised (:ticket:`30516`).
  
  * Fixed a regression in Django 2.2.1 where auto-reloader unnecessarily reloads
  translation files multiple times when using ``StatReloader``
  (:ticket:`30523`).
  
  
  ==========================

2.2.1 not secure

==========================
  
  *May 1, 2019*
  
  Django 2.2.1 fixes several bugs in 2.2.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.1 that caused the incorrect quoting of
  database user password when using :djadmin:`dbshell` on Oracle
  (:ticket:`30307`).
  
  * Added compatibility for ``psycopg2`` 2.8 (:ticket:`30331`).
  
  * Fixed a regression in Django 2.2 that caused a crash when loading the
  template for the technical 500 debug page (:ticket:`30324`).
  
  * Fixed crash of ``ordering`` argument in
  :class:`~django.contrib.postgres.aggregates.ArrayAgg` and
  :class:`~django.contrib.postgres.aggregates.StringAgg` when it contains an
  expression with params (:ticket:`30332`).
  
  * Fixed a regression in Django 2.2 that caused a single instance fast-delete
  to not set the primary key to ``None`` (:ticket:`30330`).
  
  * Prevented :djadmin:`makemigrations` from generating infinite migrations for
  check constraints and partial indexes when ``condition`` contains
  a :class:`~python:range` object (:ticket:`30350`).
  
  * Reverted an optimization in Django 2.2 (:ticket:`29725`) that caused the
  inconsistent behavior of ``count()`` and ``exists()`` on a reverse
  many-to-many relationship with a custom manager (:ticket:`30325`).
  
  * Fixed a regression in Django 2.2 where
  :class:`~django.core.paginator.Paginator` crashes if ``object_list`` is
  a queryset ordered or aggregated over a nested ``JSONField`` key transform
  (:ticket:`30335`).
  
  * Fixed a regression in Django 2.2 where ``IntegerField`` validation of
  database limits crashes if ``limit_value`` attribute in a custom validator is
  callable (:ticket:`30328`).
  
  * Fixed a regression in Django 2.2 where
  :class:`~django.contrib.postgres.search.SearchVector` generates SQL that is
  not indexable (:ticket:`30385`).
  
  * Fixed a regression in Django 2.2 that caused an exception to be raised when
  a custom error handler could not be imported (:ticket:`30318`).
  
  * Relaxed the system check added in Django 2.2 for the admin app's dependencies
  to reallow use of
  :class:`~django.contrib.sessions.middleware.SessionMiddleware` subclasses,
  rather than requiring :mod:`django.contrib.sessions` to be in
  :setting:`INSTALLED_APPS` (:ticket:`30312`).
  
  * Increased the default timeout when using ``Watchman`` to 5 seconds to prevent
  falling back to ``StatReloader`` on larger projects and made it customizable
  via the :envvar:`DJANGO_WATCHMAN_TIMEOUT` environment variable
  (:ticket:`30361`).
  
  * Fixed a regression in Django 2.2 that caused a crash when migrating
  permissions for proxy models if the target permissions already existed. For
  example, when a permission had been created manually or a model had been
  migrated from concrete to proxy (:ticket:`30351`).
  
  * Fixed a regression in Django 2.2 that caused a crash of :djadmin:`runserver`
  when URLConf modules raised exceptions (:ticket:`30323`).
  
  * Fixed a regression in Django 2.2 where changes were not reliably detected by
  auto-reloader when using ``StatReloader`` (:ticket:`30323`).
  
  * Fixed a migration crash on Oracle and PostgreSQL when adding a check
  constraint with a ``contains``, ``startswith``, or ``endswith`` lookup (or
  their case-insensitive variant) (:ticket:`30408`).
  
  * Fixed a migration crash on Oracle and SQLite when adding a check constraint
  with ``condition`` contains ``|`` (``OR``) operator (:ticket:`30412`).
  
  
  ========================

2.2 not secure

========================
  
  *April 1, 2019*
  
  Welcome to Django 2.2!
  
  These release notes cover the :ref:`new features <whats-new-2.2>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-2.2>` you'll
  want to be aware of when upgrading from Django 2.1 or earlier. We've
  :ref:`begun the deprecation process for some features
  <deprecated-features-2.2>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Django 2.2 is designated as a :term:`long-term support release
  <Long-term support release>`. It will receive security updates for at least
  three years after its release. Support for the previous LTS, Django 1.11, will
  end in April 2020.
  
  Python compatibility
  ====================
  
  Django 2.2 supports Python 3.5, 3.6, 3.7, and 3.8 (as of 2.2.8). We
  **highly recommend** and only officially support the latest release of each
  series.
  
  .. _whats-new-2.2:
  
  What's new in Django 2.2
  ========================
  
  Constraints
  -----------
  
  The new :class:`~django.db.models.CheckConstraint` and
  :class:`~django.db.models.UniqueConstraint` classes enable adding custom
  database constraints. Constraints are added to models using the
  :attr:`Meta.constraints <django.db.models.Options.constraints>` option.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added a CSS class to the column headers of
  :class:`~django.contrib.admin.TabularInline`.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The ``HttpRequest`` is now passed as the first positional argument to
  :meth:`.RemoteUserBackend.configure_user`, if it accepts it.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added Oracle support for the
  :class:`~django.contrib.gis.db.models.functions.Envelope` function.
  
  * Added SpatiaLite support for the :lookup:`coveredby` and :lookup:`covers`
  lookups.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new ``ordering`` argument for
  :class:`~django.contrib.postgres.aggregates.ArrayAgg` and
  :class:`~django.contrib.postgres.aggregates.StringAgg` determines the
  ordering of the aggregated elements.
  
  * The new :class:`~django.contrib.postgres.indexes.BTreeIndex`,
  :class:`~django.contrib.postgres.indexes.HashIndex` and
  :class:`~django.contrib.postgres.indexes.SpGistIndex` classes allow
  creating ``B-Tree``, ``hash``, and ``SP-GiST`` indexes in the database.
  
  * :class:`~django.contrib.postgres.indexes.BrinIndex` now has the
  ``autosummarize`` parameter.
  
  * The new ``search_type`` parameter of
  :class:`~django.contrib.postgres.search.SearchQuery` allows searching for
  a phrase or raw expression.
  
  :mod:`django.contrib.staticfiles`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added path matching to the :option:`collectstatic --ignore` option so that
  patterns like ``/vendor/*.js`` can be used.
  
  Database backends
  ~~~~~~~~~~~~~~~~~
  
  * Added result streaming for :meth:`.QuerySet.iterator` on SQLite.
  
  Generic Views
  ~~~~~~~~~~~~~
  
  * The new :meth:`View.setup <django.views.generic.base.View.setup>` hook
  initializes view attributes before calling
  :meth:`~django.views.generic.base.View.dispatch`. It allows mixins to setup
  instance attributes for reuse in child classes.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * Added support and translations for the Armenian language.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`--force-color` option forces colorization of the command
  output.
  
  * :djadmin:`inspectdb` now creates models for foreign tables on PostgreSQL.
  
  * :option:`inspectdb --include-views` now creates models for materialized views
  on Oracle and PostgreSQL.
  
  * The new :option:`inspectdb --include-partitions` option allows creating
  models for partition tables on PostgreSQL. In older versions, models are
  created child tables instead the parent.
  
  * :djadmin:`inspectdb` now introspects :class:`~django.db.models.DurationField`
  for Oracle and PostgreSQL, and :class:`~django.db.models.AutoField` for
  SQLite.
  
  * On Oracle, :djadmin:`dbshell` is wrapped with ``rlwrap``, if available.
  ``rlwrap`` provides a command history and editing of keyboard input.
  
  * The new :option:`makemigrations --no-header` option avoids writing header
  comments in generated migration file(s). This option is also available for
  :djadmin:`squashmigrations`.
  
  * :djadmin:`runserver` can now use `Watchman
  <https://facebook.github.io/watchman/>`_ to improve the performance of
  watching a large number of files for changes.
  
  Migrations
  ~~~~~~~~~~
  
  * The new :option:`migrate --plan` option prints the list of migration
  operations that will be performed.
  
  * ``NoneType`` can now be serialized in migrations.
  
  * You can now :ref:`register custom serializers <custom-migration-serializers>`
  for migrations.
  
  Models
  ~~~~~~
  
  * Added support for PostgreSQL operator classes (:attr:`.Index.opclasses`).
  
  * Added support for partial indexes (:attr:`.Index.condition`).
  
  * Added the :class:`~django.db.models.functions.NullIf` and
  :class:`~django.db.models.functions.Reverse` database functions, as well as
  many :ref:`math database functions <math-functions>`.
  
  * Setting the new ``ignore_conflicts`` parameter of
  :meth:`.QuerySet.bulk_create` to ``True`` tells the database to ignore
  failure to insert rows that fail uniqueness constraints or other checks.
  
  * The new :class:`~django.db.models.functions.ExtractIsoYear` function extracts
  ISO-8601 week-numbering years from :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField`, and the new :lookup:`iso_year`
  lookup allows querying by an ISO-8601 week-numbering year.
  
  * The new :meth:`.QuerySet.bulk_update` method allows efficiently updating
  specific fields on multiple model instances.
  
  * Django no longer always starts a transaction when a single query is being
  performed, such as ``Model.save()``, ``QuerySet.update()``, and
  ``Model.delete()``. This improves the performance of autocommit by reducing
  the number of database round trips.
  
  * Added SQLite support for the :class:`~django.db.models.StdDev` and
  :class:`~django.db.models.Variance` functions.
  
  * The handling of ``DISTINCT`` aggregation is added to the
  :class:`~django.db.models.Aggregate` class. Adding :attr:`allow_distinct =
  True <django.db.models.Aggregate.allow_distinct>` as a class attribute on
  ``Aggregate`` subclasses allows a ``distinct`` keyword argument to be
  specified on initialization to ensure that the aggregate function is only
  called for each distinct value of ``expressions``.
  
  * The :meth:`.RelatedManager.add`, :meth:`~.RelatedManager.create`,
  :meth:`~.RelatedManager.remove`,  :meth:`~.RelatedManager.set`,
  ``get_or_create()``, and ``update_or_create()`` methods are now allowed on
  many-to-many relationships with intermediate models. The new
  ``through_defaults`` argument is used to specify values for new intermediate
  model instance(s).
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Added :attr:`.HttpRequest.headers` to allow simple access to a request's
  headers.
  
  Serialization
  ~~~~~~~~~~~~~
  
  * You can now deserialize data using natural keys containing :ref:`forward
  references <natural-keys-and-forward-references>` by passing
  ``handle_forward_references=True`` to ``serializers.deserialize()``.
  Additionally, :djadmin:`loaddata` handles forward references automatically.
  
  Tests
  ~~~~~
  
  * The new :meth:`.SimpleTestCase.assertURLEqual` assertion checks for a given
  URL, ignoring the ordering of the query string.
  :meth:`~.SimpleTestCase.assertRedirects` uses the new assertion.
  
  * The test :class:`~.django.test.Client` now supports automatic JSON
  serialization of list and tuple ``data`` when
  ``content_type='application/json'``.
  
  * The new :setting:`ORACLE_MANAGED_FILES <TEST_ORACLE_MANAGED_FILES>` test
  database setting allows using Oracle Managed Files (OMF) tablespaces.
  
  * Deferrable database constraints are now checked at the end of each
  :class:`~django.test.TestCase` test on SQLite 3.20+, just like on other
  backends that support deferrable constraints. These checks aren't implemented
  for older versions of SQLite because they would require expensive table
  introspection there.
  
  * :class:`~django.test.runner.DiscoverRunner` now skips the setup of databases
  not :ref:`referenced by tests<testing-multi-db>`.
  
  URLs
  ~~~~
  
  * The new :attr:`.ResolverMatch.route` attribute stores the route of the
  matching URL pattern.
  
  Validators
  ~~~~~~~~~~
  
  * :class:`.MaxValueValidator`, :class:`.MinValueValidator`,
  :class:`.MinLengthValidator`, and :class:`.MaxLengthValidator` now accept
  a callable ``limit_value``.
  
  .. _backwards-incompatible-2.2:
  
  Backwards incompatible changes in 2.2
  =====================================
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * Third-party database backends must implement support for table check
  constraints or set ``DatabaseFeatures.supports_table_check_constraints`` to
  ``False``.
  
  * Third party database backends must implement support for ignoring
  constraints or uniqueness errors while inserting or set
  ``DatabaseFeatures.supports_ignore_conflicts`` to ``False``.
  
  * Third party database backends must implement introspection for
  ``DurationField`` or set ``DatabaseFeatures.can_introspect_duration_field``
  to ``False``.
  
  * ``DatabaseFeatures.uses_savepoints`` now defaults to ``True``.
  
  * Third party database backends must implement support for partial indexes or
  set ``DatabaseFeatures.supports_partial_indexes`` to ``False``.
  
  * ``DatabaseIntrospection.table_name_converter()`` and
  ``column_name_converter()`` are removed. Third party database backends may
  need to instead implement ``DatabaseIntrospection.identifier_converter()``.
  In that case, the constraint names that
  ``DatabaseIntrospection.get_constraints()`` returns must be normalized by
  ``identifier_converter()``.
  
  * SQL generation for indexes is moved from :class:`~django.db.models.Index` to
  ``SchemaEditor`` and these ``SchemaEditor`` methods are added:
  
  * ``_create_primary_key_sql()`` and ``_delete_primary_key_sql()``
  * ``_delete_index_sql()`` (to pair with ``_create_index_sql()``)
  * ``_delete_unique_sql`` (to pair with ``_create_unique_sql()``)
  * ``_delete_fk_sql()`` (to pair with ``_create_fk_sql()``)
  * ``_create_check_sql()`` and ``_delete_check_sql()``
  
  * The third argument of ``DatabaseWrapper.__init__()``,
  ``allow_thread_sharing``, is removed.
  
  Admin actions are no longer collected from base ``ModelAdmin`` classes
  ----------------------------------------------------------------------
  
  For example, in older versions of Django::
  
  from django.contrib import admin
  
  class BaseAdmin(admin.ModelAdmin):
  actions = ['a']
  
  class SubAdmin(BaseAdmin):
  actions = ['b']
  
  ``SubAdmin`` would have actions ``'a'`` and ``'b'``.
  
  Now ``actions`` follows standard Python inheritance. To get the same result as
  before::
  
  class SubAdmin(BaseAdmin):
  actions = BaseAdmin.actions + ['b']
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * Support for GDAL 1.9 and 1.10 is dropped.
  
  ``TransactionTestCase`` serialized data loading
  -----------------------------------------------
  
  Initial data migrations are now loaded in
  :class:`~django.test.TransactionTestCase` at the end of the test, after the
  database flush. In older versions, this data was loaded at the beginning of the
  test, but this prevents the :option:`test --keepdb` option from working
  properly (the database was empty at the end of the whole test suite). This
  change shouldn't have an impact on your tests unless you've customized
  :class:`~django.test.TransactionTestCase`'s internals.
  
  ``sqlparse`` is required dependency
  -----------------------------------
  
  To simplify a few parts of Django's database handling, `sqlparse 0.2.2+
  <https://pypi.org/project/sqlparse/>`_ is now a required dependency. It's
  automatically installed along with Django.
  
  ``cached_property`` aliases
  ---------------------------
  
  In usage like::
  
  from django.utils.functional import cached_property
  
  class A:
  
  cached_property
  def base(self):
  return ...
  
  alias = base
  
  ``alias`` is not cached. Where the problem can be detected (Python 3.6 and
  later), such usage now raises ``TypeError: Cannot assign the same
  cached_property to two different names ('base' and 'alias').``
  
  Use this instead::
  
  import operator
  
  class A:
  
  ...
  
  alias = property(operator.attrgetter('base'))
  
  Permissions for proxy models
  ----------------------------
  
  :ref:`Permissions for proxy models <proxy-models-permissions-topic>` are now
  created using the content type of the proxy model rather than the content type
  of the concrete model. A migration will update existing permissions when you
  run :djadmin:`migrate`.
  
  In the admin, the change is transparent for proxy models having the same
  ``app_label`` as their concrete model. However, in older versions, users with
  permissions for a proxy model with a *different* ``app_label`` than its
  concrete model couldn't access the model in the admin. That's now fixed, but
  you might want to audit the permissions assignments for such proxy models
  (``[add|view|change|delete]_myproxy``) prior to upgrading to ensure the new
  access is appropriate.
  
  Finally, proxy model permission strings must be updated to use their own
  ``app_label``. For example, for ``app.MyProxyModel`` inheriting from
  ``other_app.ConcreteModel``, update
  ``user.has_perm('other_app.add_myproxymodel')`` to
  ``user.has_perm('app.add_myproxymodel')``.
  
  Merging of form ``Media`` assets
  --------------------------------
  
  Form ``Media`` assets are now merged using a topological sort algorithm, as the
  old pairwise merging algorithm is insufficient for some cases. CSS and
  JavaScript files which don't include their dependencies may now be sorted
  incorrectly (where the old algorithm produced results correctly by
  coincidence).
  
  Audit all ``Media`` classes for any missing dependencies. For example,
  widgets depending on ``django.jQuery`` must specify
  ``js=['admin/js/jquery.init.js', ...]`` when :ref:`declaring form media assets
  <assets-as-a-static-definition>`.
  
  Miscellaneous
  -------------
  
  * To improve readability, the ``UUIDField`` form field now displays values with
  dashes, e.g. ``550e8400-e29b-41d4-a716-446655440000`` instead of
  ``550e8400e29b41d4a716446655440000``.
  
  * On SQLite, ``PositiveIntegerField`` and ``PositiveSmallIntegerField`` now
  include a check constraint to prevent negative values in the database. If you
  have existing invalid data and run a migration that recreates a table, you'll
  see ``CHECK constraint failed``.
  
  * For consistency with WSGI servers, the test client now sets the
  ``Content-Length`` header to a string rather than an integer.
  
  * The return value of :func:`django.utils.text.slugify` is no longer marked as
  HTML safe.
  
  * The default truncation character used by the :tfilter:`urlizetrunc`,
  :tfilter:`truncatechars`, :tfilter:`truncatechars_html`,
  :tfilter:`truncatewords`, and :tfilter:`truncatewords_html` template filters
  is now the real ellipsis character (``…``) instead of 3 dots. You may have to
  adapt some test output comparisons.
  
  * Support for bytestring paths in the template filesystem loader is removed.
  
  * :func:`django.utils.http.urlsafe_base64_encode` now returns a string instead
  of a bytestring, and :func:`django.utils.http.urlsafe_base64_decode` may no
  longer be passed a bytestring.
  
  * Support for ``cx_Oracle`` < 6.0 is removed.
  
  * The minimum supported version of ``mysqlclient`` is increased from 1.3.7 to
  1.3.13.
  
  * The minimum supported version of SQLite is increased from 3.7.15 to 3.8.3.
  
  * In an attempt to provide more semantic query data, ``NullBooleanSelect`` now
  renders ``<option>`` values of ``unknown``, ``true``, and ``false`` instead
  of ``1``, ``2``, and ``3``. For backwards compatibility, the old values are
  still accepted as data.
  
  * :attr:`Group.name <django.contrib.auth.models.Group.name>` ``max_length``
  is increased from 80 to 150 characters.
  
  * Tests that violate deferrable database constraints now error when run on
  SQLite 3.20+, just like on other backends that support such constraints.
  
  * To catch usage mistakes, the test :class:`~django.test.Client` and
  :func:`django.utils.http.urlencode` now raise ``TypeError`` if ``None`` is
  passed as a value to encode because ``None`` can't be encoded in GET and POST
  data. Either pass an empty string or omit the value.
  
  * The :djadmin:`ping_google` management command now defaults to ``https``
  instead of ``http`` for the sitemap's URL. If your site uses http, use the
  new :option:`ping_google --sitemap-uses-http` option. If you use the
  :func:`~django.contrib.sitemaps.ping_google` function, set the new
  ``sitemap_uses_https`` argument to ``False``.
  
  * :djadmin:`runserver` no longer supports ``pyinotify`` (replaced by Watchman).
  
  * The :class:`~django.db.models.Avg`, :class:`~django.db.models.StdDev`, and
  :class:`~django.db.models.Variance` aggregate functions now return a
  ``Decimal`` instead of a ``float`` when the input is ``Decimal``.
  
  * Tests will fail on SQLite if apps without migrations have relations to apps
  with migrations. This has been a documented restriction since migrations were
  added in Django 1.7, but it fails more reliably now. You'll see tests failing
  with errors like ``no such table: <app_label>_<model>``. This was observed
  with several third-party apps that had models in tests without migrations.
  You must add migrations for such models.
  
  * Providing an integer in the ``key`` argument of the :meth:`.cache.delete` or
  :meth:`.cache.get` now raises :exc:`ValueError`.
  
  * Plural equations for some languages are changed, because the latest versions
  from Transifex are incorporated.
  
  .. note::
  
  The ability to handle ``.po`` files containing different plural equations
  for the same language was added in Django 2.2.12.
  
  .. _deprecated-features-2.2:
  
  Features deprecated in 2.2
  ==========================
  
  Model ``Meta.ordering`` will no longer affect ``GROUP BY`` queries
  ------------------------------------------------------------------
  
  A model's ``Meta.ordering`` affecting ``GROUP BY`` queries (such as
  ``.annotate().values()``) is a common source of confusion. Such queries now
  issue a deprecation warning with the advice to add an ``order_by()`` to retain
  the current query. ``Meta.ordering`` will be ignored in such queries starting
  in Django 3.1.
  
  Miscellaneous
  -------------
  
  * ``django.utils.timezone.FixedOffset`` is deprecated in favor of
  :class:`datetime.timezone`.
  
  * The undocumented ``QuerySetPaginator`` alias of
  ``django.core.paginator.Paginator`` is deprecated.
  
  * The ``FloatRangeField`` model and form fields in ``django.contrib.postgres``
  are deprecated in favor of a new name, ``DecimalRangeField``, to match the
  underlying ``numrange`` data type used in the database.
  
  * The ``FILE_CHARSET`` setting is deprecated. Starting with Django 3.1, files
  read from disk must be UTF-8 encoded.
  
  * ``django.contrib.staticfiles.storage.CachedStaticFilesStorage`` is
  deprecated due to the intractable problems that it has. Use
  :class:`.ManifestStaticFilesStorage` or a third-party cloud storage instead.
  
  * :meth:`.RemoteUserBackend.configure_user` is now passed ``request`` as the
  first positional argument, if it accepts it. Support for overrides that don't
  accept it will be removed in Django 3.1.
  
  * The ``SimpleTestCase.allow_database_queries``,
  ``TransactionTestCase.multi_db``, and ``TestCase.multi_db``
  attributes are deprecated in favor of :attr:`.SimpleTestCase.databases`,
  :attr:`.TransactionTestCase.databases`, and :attr:`.TestCase.databases`.
  These new attributes allow databases dependencies to be declared in order to
  prevent unexpected queries against non-default databases to leak state
  between tests. The previous behavior of ``allow_database_queries=True`` and
  ``multi_db=True`` can be achieved by setting ``databases='__all__'``.
  
  
  ===========================

2.1.15 not secure

===========================
  
  *December 2, 2019*
  
  Django 2.1.15 fixes a security issue and a data loss bug in 2.1.14.
  
  CVE-2019-19118: Privilege escalation in the Django admin.
  =========================================================
  
  Since Django 2.1, a Django model admin displaying a parent model with related
  model inlines, where the user has view-only permissions to a parent model but
  edit permissions to the inline model, would display a read-only view of the
  parent model but editable forms for the inline.
  
  Submitting these forms would not allow direct edits to the parent model, but
  would trigger the parent model's ``save()`` method, and cause pre and post-save
  signal handlers to be invoked. This is a privilege escalation as a user who
  lacks permission to edit a model should not be able to trigger its save-related
  signals.
  
  To resolve this issue, the permission handling code of the Django admin
  interface has been changed. Now, if a user has only the "view" permission for a
  parent model, the entire displayed form will not be editable, even if the user
  has permission to edit models included in inlines.
  
  This is a backwards-incompatible change, and the Django security team is aware
  that some users of Django were depending on the ability to allow editing of
  inlines in the admin form of an otherwise view-only parent model.
  
  Given the complexity of the Django admin, and in-particular the permissions
  related checks, it is the view of the Django security team that this change was
  necessary: that it is not currently feasible to maintain the existing behavior
  while escaping the potential privilege escalation in a way that would avoid a
  recurrence of similar issues in the future, and that would be compatible with
  Django's *safe by default* philosophy.
  
  For the time being, developers whose applications are affected by this change
  should replace the use of inlines in read-only parents with custom forms and
  views that explicitly implement the desired functionality. In the longer term,
  adding a documented, supported, and properly-tested mechanism for
  partially-editable multi-model forms to the admin interface may occur in Django
  itself.
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in the
  :meth:`~django.db.models.query.QuerySet.select_for_update()`. When using
  ``'self'`` in the ``of`` argument with :ref:`multi-table inheritance
  <multi-table-inheritance>`, a parent model was locked instead of the
  queryset's model (:ticket:`30953`).
  
  
  ===========================

2.1.14 not secure

===========================
  
  *November 4, 2019*
  
  Django 2.1.14 fixes a regression in 2.1.13.
  
  Bugfixes
  ========
  
  * Fixed a crash when using a ``contains``, ``contained_by``, ``has_key``,
  ``has_keys``, or ``has_any_keys`` lookup on
  :class:`~django.contrib.postgres.fields.JSONField`, if the right or left hand
  side of an expression is a key transform (:ticket:`30826`).
  
  
  ===========================

2.1.13 not secure

===========================
  
  *October 1, 2019*
  
  Django 2.1.13 fixes a regression in 2.1.11.
  
  Bugfixes
  ========
  
  * Fixed a crash when filtering with a ``Subquery()`` annotation of a queryset
  containing :class:`~django.contrib.postgres.fields.JSONField` or
  :class:`~django.contrib.postgres.fields.HStoreField` (:ticket:`30769`).
  
  
  ===========================

2.1.12 not secure

===========================
  
  *September 2, 2019*
  
  Django 2.1.12 fixes a regression in 2.1.11.
  
  Bugfixes
  ========
  
  * Fixed crash of ``KeyTransform()`` for
  :class:`~django.contrib.postgres.fields.JSONField` and
  :class:`~django.contrib.postgres.fields.HStoreField` when using on
  expressions with params (:ticket:`30672`).
  
  
  ===========================

2.1.11 not secure

===========================
  
  *August 1, 2019*
  
  Django 2.1.11 fixes security issues in 2.1.10.
  
  CVE-2019-14232: Denial-of-service possibility in ``django.utils.text.Truncator``
  ================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods
  were passed the ``html=True`` argument, they were extremely slow to evaluate
  certain inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  :tfilter:`truncatechars_html` and :tfilter:`truncatewords_html` template
  filters, which were thus vulnerable.
  
  The regular expressions used by ``Truncator`` have been simplified in order to
  avoid potential backtracking issues. As a consequence, trailing punctuation may
  now at times be included in the truncated output.
  
  CVE-2019-14233: Denial-of-service possibility in ``strip_tags()``
  =================================================================
  
  Due to the behavior of the underlying ``HTMLParser``,
  :func:`django.utils.html.strip_tags` would be extremely slow to evaluate
  certain inputs containing large sequences of nested incomplete HTML entities.
  The ``strip_tags()`` method is used to implement the corresponding
  :tfilter:`striptags` template filter, which was thus also vulnerable.
  
  ``strip_tags()`` now avoids recursive calls to ``HTMLParser`` when progress
  removing tags, but necessarily incomplete HTML entities, stops being made.
  
  Remember that absolutely NO guarantee is provided about the results of
  ``strip_tags()`` being HTML safe. So NEVER mark safe the result of a
  ``strip_tags()`` call without escaping it first, for example with
  :func:`django.utils.html.escape`.
  
  CVE-2019-14234: SQL injection possibility in key and index lookups for ``JSONField``/``HStoreField``
  ====================================================================================================
  
  :lookup:`Key and index lookups <jsonfield.key>` for
  :class:`~django.contrib.postgres.fields.JSONField` and :lookup:`key lookups
  <hstorefield.key>` for :class:`~django.contrib.postgres.fields.HStoreField`
  were subject to SQL injection, using a suitably crafted dictionary, with
  dictionary expansion, as the ``**kwargs`` passed to ``QuerySet.filter()``.
  
  CVE-2019-14235: Potential memory exhaustion in ``django.utils.encoding.uri_to_iri()``
  =====================================================================================
  
  If passed certain inputs, :func:`django.utils.encoding.uri_to_iri` could lead
  to significant memory usage due to excessive recursion when re-percent-encoding
  invalid UTF-8 octet sequences.
  
  ``uri_to_iri()`` now avoids recursion when re-percent-encoding invalid UTF-8
  octet sequences.
  
  
  ===========================

2.1.10 not secure

===========================
  
  *July 1, 2019*
  
  Django 2.1.10 fixes a security issue in 2.1.9.
  
  CVE-2019-12781: Incorrect HTTP detection with reverse-proxy connecting via HTTPS
  --------------------------------------------------------------------------------
  
  When deployed behind a reverse-proxy connecting to Django via HTTPS,
  :attr:`django.http.HttpRequest.scheme` would incorrectly detect client
  requests made via HTTP as using HTTPS. This entails incorrect results for
  :meth:`~django.http.HttpRequest.is_secure`, and
  :meth:`~django.http.HttpRequest.build_absolute_uri`, and that HTTP
  requests would not be redirected to HTTPS in accordance with
  :setting:`SECURE_SSL_REDIRECT`.
  
  ``HttpRequest.scheme`` now respects :setting:`SECURE_PROXY_SSL_HEADER`, if it
  is configured, and the appropriate header is set on the request, for both HTTP
  and HTTPS requests.
  
  If you deploy Django behind a reverse-proxy that forwards HTTP requests, and
  that connects to Django via HTTPS, be sure to verify that your application
  correctly handles code paths relying on ``scheme``, ``is_secure()``,
  ``build_absolute_uri()``, and ``SECURE_SSL_REDIRECT``.
  
  
  ============================

2.1.9 not secure

============================
  
  *June 3, 2019*
  
  Django 2.1.9 fixes security issues in 2.1.8.
  
  CVE-2019-12308: AdminURLFieldWidget XSS
  ---------------------------------------
  
  The clickable "Current URL" link generated by ``AdminURLFieldWidget`` displayed
  the provided value without validating it as a safe URL. Thus, an unvalidated
  value stored in the database, or a value provided as a URL query parameter
  payload, could result in an clickable JavaScript link.
  
  ``AdminURLFieldWidget`` now validates the provided value using
  :class:`~django.core.validators.URLValidator` before displaying the clickable
  link. You may customize the validator by passing a ``validator_class`` kwarg to
  ``AdminURLFieldWidget.__init__()``, e.g. when using
  :attr:`~django.contrib.admin.ModelAdmin.formfield_overrides`.
  
  Patched bundled jQuery for CVE-2019-11358: Prototype pollution
  --------------------------------------------------------------
  
  jQuery before 3.4.0, mishandles ``jQuery.extend(true, {}, ...)`` because of
  ``Object.prototype`` pollution. If an unsanitized source object contained an
  enumerable ``__proto__`` property, it could extend the native
  ``Object.prototype``.
  
  The bundled version of jQuery used by the Django admin has been patched to
  allow for the ``select2`` library's use of ``jQuery.extend()``.
  
  
  ==========================

2.1.8 not secure

==========================
  
  *April 1, 2019*
  
  Django 2.1.8 fixes a bug in 2.1.7.
  
  Bugfixes
  ========
  
  * Prevented admin inlines for a ``ManyToManyField``\'s implicit through model
  from being editable if the user only has the view permission
  (:ticket:`30289`).
  
  
  ==========================

2.1.7 not secure

==========================
  
  *February 11, 2019*
  
  Django 2.1.7 fixes a packaging error in 2.1.6.
  
  Bugfixes
  ========
  
  * Corrected packaging error from 2.1.6 (:ticket:`30175`).
  
  
  ==========================

2.1.5 not secure

==========================
  
  *January 4, 2019*
  
  Django 2.1.5 fixes a security issue and several bugs in 2.1.4.
  
  CVE-2019-3498: Content spoofing possibility in the default 404 page
  -------------------------------------------------------------------
  
  An attacker could craft a malicious URL that could make spoofed content appear
  on the default page generated by the ``django.views.defaults.page_not_found()``
  view.
  
  The URL path is no longer displayed in the default 404 template and the
  ``request_path`` context variable is now quoted to fix the issue for custom
  templates that use the path.
  
  Bugfixes
  ========
  
  * Fixed compatibility with mysqlclient 1.3.14 (:ticket:`30013`).
  
  * Fixed a schema corruption issue on SQLite 3.26+. You might have to drop and
  rebuild your SQLite database if you applied a migration while using an older
  version of Django with SQLite 3.26 or later (:ticket:`29182`).
  
  * Prevented SQLite schema alterations while foreign key checks are enabled to
  avoid the possibility of schema corruption (:ticket:`30023`).
  
  * Fixed a regression in Django 2.1.4 (which enabled keep-alive connections)
  where request body data isn't properly consumed for such connections
  (:ticket:`30015`).
  
  * Fixed a regression in Django 2.1.4 where
  ``InlineModelAdmin.has_change_permission()`` is incorrectly called with a
  non-``None`` ``obj`` argument during an object add (:ticket:`30050`).
  
  
  ==========================

2.1.4 not secure

==========================
  
  *December 3, 2018*
  
  Django 2.1.4 fixes several bugs in 2.1.3.
  
  Bugfixes
  ========
  
  * Corrected the default password list that ``CommonPasswordValidator`` uses by
  lowercasing all passwords to match the format expected by the validator
  (:ticket:`29952`).
  
  * Prevented repetitive calls to ``geos_version_tuple()`` in the ``WKBWriter``
  class in an attempt to fix a random crash involving ``LooseVersion``
  (:ticket:`29959`).
  
  * Fixed keep-alive support in ``runserver`` after it was disabled to fix
  another issue in Django 2.0 (:ticket:`29849`).
  
  * Fixed admin view-only change form crash when using
  ``ModelAdmin.prepopulated_fields`` (:ticket:`29929`).
  
  * Fixed "Please correct the errors below" error message when editing an object
  in the admin if the user only has the "view" permission on inlines
  (:ticket:`29930`).
  
  
  ==========================

2.1.3 not secure

==========================
  
  *November 1, 2018*
  
  Django 2.1.3 fixes several bugs in 2.1.2.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.0 where combining ``Q`` objects with ``__in``
  lookups and lists crashed (:ticket:`29838`).
  
  * Fixed a regression in Django 1.11 where ``django-admin shell`` may hang
  on startup (:ticket:`29774`).
  
  * Fixed a regression in Django 2.0 where test databases aren't reused with
  ``manage.py test --keepdb`` on MySQL (:ticket:`29827`).
  
  * Fixed a regression where cached foreign keys that use ``to_field`` were
  incorrectly cleared in ``Model.save()`` (:ticket:`29896`).
  
  * Fixed a regression in Django 2.0 where ``FileSystemStorage`` crashes with
  ``FileExistsError`` if concurrent saves try to create the same directory
  (:ticket:`29890`).
  
  
  ==========================

2.1.2 not secure

==========================
  
  *October 1, 2018*
  
  Django 2.1.2 fixes a security issue and several bugs in 2.1.1. Also, the latest
  string translations from Transifex are incorporated.
  
  CVE-2018-16984: Password hash disclosure to "view only" admin users
  ===================================================================
  
  If an admin user has the change permission to the user model, only part of the
  password hash is displayed in the change form. Admin users with the view (but
  not change) permission to the user model were displayed the entire hash. While
  it's typically infeasible to reverse a strong password hash, if your site uses
  weaker password hashing algorithms such as MD5 or SHA1, it could be a problem.
  
  Bugfixes
  ========
  
  * Fixed a regression where nonexistent joins in ``F()`` no longer raised
  ``FieldError`` (:ticket:`29727`).
  
  * Fixed a regression where files starting with a tilde or underscore weren't
  ignored by the migrations loader (:ticket:`29749`).
  
  * Made migrations detect changes to ``Meta.default_related_name``
  (:ticket:`29755`).
  
  * Added compatibility for ``cx_Oracle`` 7 (:ticket:`29759`).
  
  * Fixed a regression in Django 2.0 where unique index names weren't quoted
  (:ticket:`29778`).
  
  * Fixed a regression where sliced queries with multiple columns with the same
  name crashed on Oracle 12.1 (:ticket:`29630`).
  
  * Fixed a crash when a user with the view (but not change) permission made a
  POST request to an admin user change form (:ticket:`29809`).
  
  
  ==========================

2.1.1 not secure

==========================
  
  *August 31, 2018*
  
  Django 2.1.1 fixes several bugs in 2.1.
  
  Bugfixes
  ========
  
  * Fixed a race condition in ``QuerySet.update_or_create()`` that could result
  in data loss (:ticket:`29499`).
  
  * Fixed a regression where ``QueryDict.urlencode()`` crashed if the dictionary
  contains a non-string value (:ticket:`29627`).
  
  * Fixed a regression in Django 2.0 where using ``manage.py test --keepdb``
  fails on PostgreSQL if the database exists and the user doesn't have
  permission to create databases (:ticket:`29613`).
  
  * Fixed a regression in Django 2.0 where combining ``Q`` objects with ``__in``
  lookups and lists crashed (:ticket:`29643`).
  
  * Fixed translation failure of ``DurationField``'s "overflow" error message
  (:ticket:`29623`).
  
  * Fixed a regression where the admin change form crashed if the user doesn't
  have the 'add' permission to a model that uses ``TabularInline``
  (:ticket:`29637`).
  
  * Fixed a regression where a ``related_query_name`` reverse accessor wasn't set
  up when a ``GenericRelation`` is declared on an abstract base model
  (:ticket:`29653`).
  
  * Fixed the test client's JSON serialization of a request data dictionary for
  structured content type suffixes (:ticket:`29662`).
  
  * Made the admin change view redirect to the changelist view after a POST if
  the user has the 'view' permission (:ticket:`29663`).
  
  * Fixed admin change view crash for view-only users if the form has an extra
  form field (:ticket:`29682`).
  
  * Fixed a regression in Django 2.0.5 where ``QuerySet.values()`` or
  ``values_list()`` after combining querysets with ``extra()`` with
  ``union()``, ``difference()``, or ``intersection()`` crashed due to
  mismatching columns (:ticket:`29694`).
  
  * Fixed crash if ``InlineModelAdmin.has_add_permission()`` doesn't accept the
  ``obj`` argument (:ticket:`29723`).
  
  
  ========================

2.1 not secure

========================
  
  *August 1, 2018*
  
  Welcome to Django 2.1!
  
  These release notes cover the :ref:`new features <whats-new-2.1>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-2.1>` you'll
  want to be aware of when upgrading from Django 2.0 or earlier. We've
  :ref:`dropped some features<removed-features-2.1>` that have reached the end of
  their deprecation cycle, and we've :ref:`begun the deprecation process for some
  features <deprecated-features-2.1>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Django 2.1 supports Python 3.5, 3.6, and 3.7. Django 2.0 is the last version to
  support Python 3.4.  We **highly recommend** and only officially support the
  latest release of each series.
  
  .. _whats-new-2.1:
  
  What's new in Django 2.1
  ========================
  
  Model "view" permission
  -----------------------
  
  A "view" permission is added to the model :attr:`Meta.default_permissions
  <django.db.models.Options.default_permissions>`. The new permissions will be
  created automatically when running :djadmin:`migrate`.
  
  This allows giving users read-only access to models in the admin.
  :meth:`.ModelAdmin.has_view_permission` is new. The implementation is backwards
  compatible in that there isn't a need to assign the "view" permission to allow
  users who have the "change" permission to edit objects.
  
  There are a couple of :ref:`backwards incompatible considerations
  <view_permission_backwards_incompatible>`.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :attr:`.ModelAdmin.search_fields` now accepts any lookup such as
  ``field__exact``.
  
  * jQuery is upgraded from version 2.2.3 to 3.3.1.
  
  * The new :meth:`.ModelAdmin.delete_queryset` method allows customizing the
  deletion process of the "delete selected objects" action.
  
  * You can now :ref:`override the default admin site
  <overriding-default-admin-site>`.
  
  * The new :attr:`.ModelAdmin.sortable_by` attribute and
  :meth:`.ModelAdmin.get_sortable_by` method allow limiting the columns that
  can be sorted in the change list page.
  
  * The ``admin_order_field`` attribute for elements in
  :attr:`.ModelAdmin.list_display` may now be a query expression.
  
  * The new :meth:`.ModelAdmin.get_deleted_objects()` method allows customizing
  the deletion process of the delete view and the "delete selected" action.
  
  * The ``actions.html``, ``change_list_results.html``, ``date_hierarchy.html``,
  ``pagination.html``, ``prepopulated_fields_js.html``, ``search_form.html``,
  and ``submit_line.html`` templates can now be :ref:`overridden per app or
  per model <admin-templates-overridden-per-app-or-model>` (besides overridden
  globally).
  
  * The admin change list and change form object tools can now be :ref:`overridden
  per app, per model, or globally <admin-templates-overridden-per-app-or-model>`
  with ``change_list_object_tools.html`` and
  ``change_form_object_tools.html`` templates.
  
  * :meth:`.InlineModelAdmin.has_add_permission` is now passed the parent object
  as the second positional argument, ``obj``.
  
  * Admin actions may now :ref:`specify permissions <admin-action-permissions>`
  to limit their availability to certain users.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :djadmin:`createsuperuser` now gives a prompt to allow bypassing the
  :setting:`AUTH_PASSWORD_VALIDATORS` checks.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :meth:`.GEOSGeometry.buffer_with_style` method is a version of
  :meth:`~.GEOSGeometry.buffer` that allows customizing the style of the
  buffer.
  
  * :class:`~django.contrib.gis.forms.widgets.OpenLayersWidget` is now based on
  OpenLayers 4.6.5 (previously 3.20.1).
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added the :setting:`SESSION_COOKIE_SAMESITE` setting to set the ``SameSite``
  cookie flag on session cookies.
  
  Cache
  ~~~~~
  
  * The :ref:`local-memory cache backend <local-memory-caching>` now uses a
  least-recently-used (LRU) culling strategy rather than a pseudo-random one.
  
  * The new :meth:`~django.core.caches.cache.touch` method of the :ref:`low-level
  cache API <low-level-cache-api>` updates the timeout of cache keys.
  
  CSRF
  ~~~~
  
  * Added the :setting:`CSRF_COOKIE_SAMESITE` setting to set the ``SameSite``
  cookie flag on CSRF cookies.
  
  Forms
  ~~~~~
  
  * The widget for ``ImageField`` now renders with the HTML attribute
  ``accept="image/*"``.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * Added the :meth:`~django.utils.translation.get_supported_language_variant`
  function.
  
  * Untranslated strings for territorial language variants now use the
  translations of the generic language. For example, untranslated ``pt_BR``
  strings use ``pt`` translations.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`inspectdb --include-views` option allows creating models
  for database views.
  
  * The :class:`~django.core.management.BaseCommand` class now uses a custom help
  formatter so that the standard options like ``--verbosity`` or ``--settings``
  appear last in the help output, giving a more prominent position to subclassed
  command's options.
  
  Migrations
  ~~~~~~~~~~
  
  * Added support for serialization of ``functools.partialmethod`` objects.
  
  * To support frozen environments, migrations may be loaded from ``.pyc`` files.
  
  Models
  ~~~~~~
  
  * Models can now use ``__init_subclass__()`` from :pep:`487`.
  
  * A ``BinaryField`` may now be set to ``editable=True`` if you wish to include
  it in model forms.
  
  * A number of new text database functions are added:
  :class:`~django.db.models.functions.Chr`,
  :class:`~django.db.models.functions.Left`,
  :class:`~django.db.models.functions.LPad`,
  :class:`~django.db.models.functions.LTrim`,
  :class:`~django.db.models.functions.Ord`,
  :class:`~django.db.models.functions.Repeat`,
  :class:`~django.db.models.functions.Replace`,
  :class:`~django.db.models.functions.Right`,
  :class:`~django.db.models.functions.RPad`,
  :class:`~django.db.models.functions.RTrim`, and
  :class:`~django.db.models.functions.Trim`.
  
  * The new :class:`~django.db.models.functions.TruncWeek` function truncates
  :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField` to the Monday of a week.
  
  * Query expressions can now be negated using a minus sign.
  
  * :meth:`.QuerySet.order_by` and :meth:`distinct(*fields) <.QuerySet.distinct>`
  now support using field transforms.
  
  * :class:`~django.db.models.BooleanField` can now be ``null=True``. This is
  encouraged instead of :class:`~django.db.models.NullBooleanField`, which will
  likely be deprecated in the future.
  
  * The new :meth:`.QuerySet.explain` method displays the database's execution
  plan of a queryset's query.
  
  *  :meth:`.QuerySet.raw` now supports :meth:`~.QuerySet.prefetch_related`.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Added :meth:`.HttpRequest.get_full_path_info`.
  
  * Added the ``samesite`` argument to :meth:`.HttpResponse.set_cookie` to allow
  setting the ``SameSite`` cookie flag.
  
  * The new ``as_attachment`` argument for :class:`~django.http.FileResponse`
  sets the ``Content-Disposition`` header to make the browser ask if the user
  wants to download the file. ``FileResponse`` also tries to set the
  ``Content-Type`` and ``Content-Length`` headers where appropriate.
  
  Templates
  ~~~~~~~~~
  
  * The new :tfilter:`json_script` filter safely outputs a Python object as JSON,
  wrapped in a ``<script>`` tag, ready for use with JavaScript.
  
  Tests
  ~~~~~
  
  * Added test :class:`~django.test.Client` support for 307 and 308 redirects.
  
  * The test :class:`~django.test.Client` now serializes a request data
  dictionary as JSON if ``content_type='application/json'``. You can customize
  the JSON encoder with test client's ``json_encoder`` parameter.
  
  * The new :meth:`.SimpleTestCase.assertWarnsMessage` method is a simpler
  version of :meth:`~unittest.TestCase.assertWarnsRegex`.
  
  .. _backwards-incompatible-2.1:
  
  Backwards incompatible changes in 2.1
  =====================================
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * To adhere to :pep:`249`, exceptions where a database doesn't support a
  feature are changed from :exc:`NotImplementedError` to
  :exc:`django.db.NotSupportedError`.
  
  * Renamed the ``allow_sliced_subqueries`` database feature flag to
  ``allow_sliced_subqueries_with_in``.
  
  * ``DatabaseOperations.distinct_sql()`` now requires an additional ``params``
  argument and returns a tuple of SQL and parameters instead of an SQL string.
  
  * ``DatabaseFeatures.introspected_boolean_field_type`` is changed from a method
  to a property.
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * Support for SpatiaLite 4.0 is removed.
  
  Dropped support for MySQL 5.5
  -----------------------------
  
  The end of upstream support for MySQL 5.5 is December 2018. Django 2.1 supports
  MySQL 5.6 and higher.
  
  Dropped support for PostgreSQL 9.3
  ----------------------------------
  
  The end of upstream support for PostgreSQL 9.3 is September 2018. Django 2.1
  supports PostgreSQL 9.4 and higher.
  
  Removed ``BCryptPasswordHasher`` from the default ``PASSWORD_HASHERS`` setting
  ------------------------------------------------------------------------------
  
  If you used bcrypt with Django 1.4 or 1.5 (before ``BCryptSHA256PasswordHasher``
  was added in Django 1.6), you might have some passwords that use the
  ``BCryptPasswordHasher`` hasher.
  
  You can check if that's the case like this::
  
  from django.contrib.auth import get_user_model
  User = get_user_model()
  User.objects.filter(password__startswith='bcrypt$$')
  
  If you want to continue to allow those passwords to be used, you'll
  have to define the :setting:`PASSWORD_HASHERS` setting (if you don't already)
  and include ``'django.contrib.auth.hashers.BCryptPasswordHasher'``.
  
  Moved ``wrap_label`` widget template context variable
  -----------------------------------------------------
  
  To fix the lack of ``<label>`` when using ``RadioSelect`` and
  ``CheckboxSelectMultiple`` with ``MultiWidget``, the ``wrap_label`` context
  variable now appears as an attribute of each option. For example, in a custom
  ``input_option.html`` template, change ``{% if wrap_label %}`` to
  ``{% if widget.wrap_label %}``.
  
  ``SameSite`` cookies
  --------------------
  
  The cookies used for ``django.contrib.sessions``, ``django.contrib.messages``,
  and Django's CSRF protection now set the ``SameSite`` flag to ``Lax`` by
  default. Browsers that respect this flag won't send these cookies on
  cross-origin requests. If you rely on the old behavior, set the
  :setting:`SESSION_COOKIE_SAMESITE` and/or :setting:`CSRF_COOKIE_SAMESITE`
  setting to ``None``.
  
  .. _view_permission_backwards_incompatible:
  
  Considerations for the new model "view" permission
  --------------------------------------------------
  
  Custom admin forms need to take the view-only case into account
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  With the new "view" permission, existing custom admin forms may raise errors
  when a user doesn't have the change permission because the form might access
  nonexistent fields. Fix this by overriding :meth:`.ModelAdmin.get_form` and
  checking if the user has the "change" permissions and returning the default
  form if not::
  
  class MyAdmin(admin.ModelAdmin):
  def get_form(self, request, obj=None, **kwargs):
  if not self.has_change_permission(request, obj):
  return super().get_form(request, obj, **kwargs)
  return CustomForm
  
  New default view permission could allow unwanted access to admin views
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  If you have a custom permission with a codename of the form
  ``view_<modelname>``, the new view permission handling in the admin will allow
  view access to the changelist and detail pages for those models. If this is
  unwanted, you must change your custom permission codename.
  
  Miscellaneous
  -------------
  
  * The minimum supported version of ``mysqlclient`` is increased from 1.3.3 to
  1.3.7.
  
  * Support for SQLite < 3.7.15 is removed.
  
  * The date format of ``Set-Cookie``'s ``Expires`` directive is changed to
  follow :rfc:`7231section-7.1.1.1` instead of Netscape's cookie standard.
  Hyphens present in dates like ``Tue, 25-Dec-2018 22:26:13 GMT`` are removed.
  This change should be merely cosmetic except perhaps for antiquated browsers
  that don't parse the new format.
  
  * ``allowed_hosts`` is now a required argument of private API
  ``django.utils.http.is_safe_url()``.
  
  * The ``multiple`` attribute rendered by the
  :class:`~django.forms.SelectMultiple` widget now uses HTML5 boolean syntax
  rather than XHTML's ``multiple="multiple"``.
  
  * HTML rendered by form widgets no longer includes a closing slash on void
  elements, e.g. ``<br>``. This is incompatible within XHTML, although some
  widgets already used aspects of HTML5 such as boolean attributes.
  
  * The value of :class:`~django.forms.SelectDateWidget`'s empty options is
  changed from 0 to an empty string, which mainly may require some adjustments
  in tests that compare HTML.
  
  * :meth:`.User.has_usable_password` and the
  :func:`~django.contrib.auth.hashers.is_password_usable` function no longer
  return ``False`` if the password is ``None`` or an empty string, or if the
  password uses a hasher that's not in the :setting:`PASSWORD_HASHERS` setting.
  This undocumented behavior was a regression in Django 1.6 and prevented users
  with such passwords from requesting a password reset. Audit your code to
  confirm that your usage of these APIs don't rely on the old behavior.
  
  * Since migrations are now loaded from ``.pyc`` files, you might need to delete
  them if you're working in a mixed Python 2 and Python 3 environment.
  
  * Using ``None`` as a :class:`~django.contrib.postgres.fields.JSONField` lookup
  value now matches objects that have the specified key and a null value rather
  than objects that don't have the key.
  
  * The admin CSS class ``field-box`` is renamed to ``fieldBox`` to prevent
  conflicts with the class given to model fields named "box".
  
  * Since the admin's ``actions.html``, ``change_list_results.html``,
  ``date_hierarchy.html``, ``pagination.html``, ``prepopulated_fields_js.html``,
  ``search_form.html``, and ``submit_line.html`` templates can now be
  overridden per app or per model, you may need to rename existing templates
  with those names that were written for a different purpose.
  
  * ``QuerySet.raw()`` now caches its results like regular querysets. Use
  ``iterator()`` if you don't want caching.
  
  * The database router :meth:`allow_relation` method is called in more cases.
  Improperly written routers may need to be updated accordingly.
  
  * Translations are no longer deactivated before running management commands.
  If your custom command requires translations to be deactivated (for example,
  to insert untranslated content into the database), use the new
  :ref:`no_translations decorator <management-commands-and-locales>`.
  
  * Management commands no longer allow the abbreviated forms of the
  ``--settings`` and ``--pythonpath`` arguments.
  
  * The private ``django.db.models.sql.constants.QUERY_TERMS`` constant is
  removed. The :meth:`~.RegisterLookupMixin.get_lookup`
  and :meth:`~.RegisterLookupMixin.get_lookups` methods
  of the :ref:`Lookup Registration API <lookup-registration-api>` may be
  suitable alternatives. Compared to the ``QUERY_TERMS`` constant, they allow
  your code to also account for any custom lookups that have been registered.
  
  * Compatibility with ``py-bcrypt`` is removed as it's unmaintained. Use `bcrypt
  <https://pypi.org/project/bcrypt/>`_ instead.
  
  .. _deprecated-features-2.1:
  
  Features deprecated in 2.1
  ==========================
  
  Miscellaneous
  -------------
  
  * The ``ForceRHR`` GIS function is deprecated in favor of the new
  :class:`~django.contrib.gis.db.models.functions.ForcePolygonCW` function.
  
  * ``django.utils.http.cookie_date()`` is deprecated in favor of
  :func:`~django.utils.http.http_date`, which follows the format of the latest
  RFC.
  
  * ``{% load staticfiles %}`` and ``{% load admin_static %}`` are deprecated
  in favor of ``{% load static %}``, which works the same.
  
  * ``django.contrib.staticfiles.templatetags.static()`` is deprecated in favor
  of ``django.templatetags.static.static()``.
  
  * Support for :meth:`.InlineModelAdmin.has_add_permission` methods that don't
  accept ``obj`` as the second positional argument will be removed in Django
  3.0.
  
  .. _removed-features-2.1:
  
  Features removed in 2.1
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 2.1. See :ref:`deprecated-features-1.11` for details, including how
  to remove usage of these features.
  
  * ``contrib.auth.views.login()``, ``logout()``, ``password_change()``,
  ``password_change_done()``, ``password_reset()``, ``password_reset_done()``,
  ``password_reset_confirm()``, and ``password_reset_complete()`` are removed.
  
  * The ``extra_context`` parameter of ``contrib.auth.views.logout_then_login()``
  is removed.
  
  * ``django.test.runner.setup_databases()`` is removed.
  
  * ``django.utils.translation.string_concat()`` is removed.
  
  * ``django.core.cache.backends.memcached.PyLibMCCache`` no longer supports
  passing ``pylibmc`` behavior settings as top-level attributes of ``OPTIONS``.
  
  * The ``host`` parameter of ``django.utils.http.is_safe_url()`` is removed.
  
  * Silencing of exceptions raised while rendering the ``{% include %}`` template
  tag is removed.
  
  * ``DatabaseIntrospection.get_indexes()`` is removed.
  
  * The ``authenticate()`` method of authentication backends requires ``request``
  as the first positional argument.
  
  * The ``django.db.models.permalink()`` decorator is removed.
  
  * The ``USE_ETAGS`` setting is removed. ``CommonMiddleware`` and
  ``django.utils.cache.patch_response_headers()`` no longer set ETags.
  
  * The ``Model._meta.has_auto_field`` attribute is removed.
  
  * ``url()``'s support for inline flags in regular expression groups (``(?i)``,
  ``(?L)``, ``(?m)``, ``(?s)``, and ``(?u)``) is removed.
  
  * Support for ``Widget.render()`` methods without the ``renderer`` argument
  is removed.
  
  
  ===========================

2.0.13 not secure

===========================
  
  *February 12, 2019*
  
  Django 2.0.13 fixes a regression in 2.0.12/2.0.11.
  
  Bugfixes
  ========
  
  * Fixed crash in ``django.utils.numberformat.format_number()`` when the number
  has over 200 digits (:ticket:`30177`).
  
  
  ===========================

2.0.12 not secure

===========================
  
  *February 11, 2019*
  
  Django 2.0.12 fixes a packaging error in 2.0.11.
  
  Bugfixes
  ========
  
  * Corrected packaging error from 2.0.11 (:ticket:`30175`).
  
  
  ===========================

2.0.10 not secure

===========================
  
  *January 4, 2019*
  
  Django 2.0.10 fixes a security issue and several bugs in 2.0.9.
  
  CVE-2019-3498: Content spoofing possibility in the default 404 page
  -------------------------------------------------------------------
  
  An attacker could craft a malicious URL that could make spoofed content appear
  on the default page generated by the ``django.views.defaults.page_not_found()``
  view.
  
  The URL path is no longer displayed in the default 404 template and the
  ``request_path`` context variable is now quoted to fix the issue for custom
  templates that use the path.
  
  Bugfixes
  ========
  
  * Prevented repetitive calls to ``geos_version_tuple()`` in the ``WKBWriter``
  class in an attempt to fix a random crash involving ``LooseVersion`` since
  Django 2.0.6 (:ticket:`29959`).
  
  * Fixed a schema corruption issue on SQLite 3.26+. You might have to drop and
  rebuild your SQLite database if you applied a migration while using an older
  version of Django with SQLite 3.26 or later (:ticket:`29182`).
  
  * Prevented SQLite schema alterations while foreign key checks are enabled to
  avoid the possibility of schema corruption (:ticket:`30023`).
  
  
  ==========================

2.0.9 not secure

==========================
  
  *October 1, 2018*
  
  Django 2.0.9 fixes a data loss bug in 2.0.8.
  
  Bugfixes
  ========
  
  * Fixed a race condition in ``QuerySet.update_or_create()`` that could result
  in data loss (:ticket:`29499`).
  
  
  ==========================

2.0.8 not secure

==========================
  
  *August 1, 2018*
  
  Django 2.0.8 fixes a security issue and several bugs in 2.0.7.
  
  CVE-2018-14574: Open redirect possibility in ``CommonMiddleware``
  =================================================================
  
  If the :class:`~django.middleware.common.CommonMiddleware` and the
  :setting:`APPEND_SLASH` setting are both enabled, and if the project has a
  URL pattern that accepts any path ending in a slash (many content management
  systems have such a pattern), then a request to a maliciously crafted URL of
  that site could lead to a redirect to another site, enabling phishing and other
  attacks.
  
  ``CommonMiddleware`` now escapes leading slashes to prevent redirects to other
  domains.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 2.0.7 that broke the ``regex`` lookup on MariaDB
  (even though MariaDB isn't officially supported) (:ticket:`29544`).
  
  * Fixed a regression where ``django.template.Template`` crashed if the
  ``template_string`` argument is lazy (:ticket:`29617`).
  
  
  ==========================

2.0.7 not secure

==========================
  
  *July 2, 2018*
  
  Django 2.0.7 fixes several bugs in 2.0.6.
  
  Bugfixes
  ========
  
  * Fixed admin changelist crash when using a query expression without ``asc()``
  or ``desc()`` in the page's ordering (:ticket:`29428`).
  
  * Fixed admin check crash when using a query expression in
  ``ModelAdmin.ordering`` (:ticket:`29428`).
  
  * Fixed ``__regex`` and ``__iregex`` lookups with MySQL 8 (:ticket:`29451`).
  
  * Fixed migrations crash with namespace packages on Python 3.7
  (:ticket:`28814`).
  
  
  ==========================

2.0.6 not secure

==========================
  
  *June 1, 2018*
  
  Django 2.0.6 fixes several bugs in 2.0.5.
  
  Bugfixes
  ========
  
  * Fixed a regression that broke custom template filters that use decorators
  (:ticket:`29400`).
  
  * Fixed detection of custom URL converters in included patterns
  (:ticket:`29415`).
  
  * Fixed a regression that added an unnecessary subquery to the ``GROUP BY``
  clause on MySQL when using a ``RawSQL`` annotation (:ticket:`29416`).
  
  * Fixed ``WKBWriter.write()`` and ``write_hex()`` for empty polygons on
  GEOS 3.6.1+ (:ticket:`29460`).
  
  * Fixed a regression in Django 1.10 that could result in large memory usage
  when making edits using ``ModelAdmin.list_editable`` (:ticket:`28462`).
  
  
  ==========================

2.0.5 not secure

==========================
  
  *May 1, 2018*
  
  Django 2.0.5 fixes several bugs in 2.0.4.
  
  Bugfixes
  ========
  
  * Corrected the import paths that ``inspectdb`` generates for
  ``django.contrib.postgres`` fields (:ticket:`29307`).
  
  * Fixed a regression in Django 1.11.8 where altering a field with a unique
  constraint may drop and rebuild more foreign keys than necessary
  (:ticket:`29193`).
  
  * Fixed crashes in ``django.contrib.admindocs`` when a view is a callable
  object, such as ``django.contrib.syndication.views.Feed`` (:ticket:`29296`).
  
  * Fixed a regression in Django 2.0.4 where ``QuerySet.values()`` or
  ``values_list()`` after combining an annotated and unannotated queryset with
  ``union()``, ``difference()``, or ``intersection()`` crashed due to mismatching
  columns (:ticket:`29286`).
  
  
  ==========================

2.0.4 not secure

==========================
  
  *April 2, 2018*
  
  Django 2.0.4 fixes several bugs in 2.0.3.
  
  Bugfixes
  ========
  
  * Fixed a crash when filtering with an ``Exists()`` annotation of a queryset
  containing a single field (:ticket:`29195`).
  
  * Fixed admin autocomplete widget's translations for ``zh-hans`` and
  ``zh-hant`` languages (:ticket:`29213`).
  
  * Corrected admin's autocomplete widget to add a space after custom classes
  (:ticket:`29221`).
  
  * Fixed ``PasswordResetConfirmView`` crash when using a user model with a
  ``UUIDField`` primary key and the reset URL contains an encoded primary key
  value that decodes to an invalid UUID (:ticket:`29206`).
  
  * Fixed a regression in Django 1.11.8 where combining two annotated
  ``values_list()`` querysets with ``union()``, ``difference()``, or
  ``intersection()`` crashed due to mismatching columns (:ticket:`29229`).
  
  * Fixed a regression in Django 1.11 where an empty choice could be initially
  selected for the ``SelectMultiple`` and ``CheckboxSelectMultiple`` widgets
  (:ticket:`29273`).
  
  * Fixed a regression in Django 2.0 where ``OpenLayersWidget`` deserialization
  ignored the widget map's SRID and assumed 4326 (WGS84) (:ticket:`29116`).
  
  
  ==========================

2.0.3 not secure

==========================
  
  *March 6, 2018*
  
  Django 2.0.3 fixes two security issues and several bugs in 2.0.2. Also, the
  latest string translations from Transifex are incorporated.
  
  CVE-2018-7536: Denial-of-service possibility in ``urlize`` and ``urlizetrunc`` template filters
  ===============================================================================================
  
  The ``django.utils.html.urlize()`` function was extremely slow to evaluate
  certain inputs due to catastrophic backtracking vulnerabilities in two regular
  expressions. The ``urlize()`` function is used to implement the ``urlize`` and
  ``urlizetrunc`` template filters, which were thus vulnerable.
  
  The problematic regular expressions are replaced with parsing logic that
  behaves similarly.
  
  CVE-2018-7537: Denial-of-service possibility in ``truncatechars_html`` and ``truncatewords_html`` template filters
  ==================================================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods were
  passed the ``html=True`` argument, they were extremely slow to evaluate certain
  inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  ``truncatechars_html`` and ``truncatewords_html`` template filters, which were
  thus vulnerable.
  
  The backtracking problem in the regular expression is fixed.
  
  Bugfixes
  ========
  
  * Fixed a regression that caused sliced ``QuerySet.distinct().order_by()``
  followed by ``count()`` to crash (:ticket:`29108`).
  
  * Prioritized the datetime and time input formats without ``%f`` for the Thai
  locale to fix the admin time picker widget displaying "undefined"
  (:ticket:`29109`).
  
  * Fixed crash with ``QuerySet.order_by(Exists(...))`` (:ticket:`29118`).
  
  * Made ``Q.deconstruct()`` deterministic with multiple keyword arguments
  (:ticket:`29125`). You may need to modify ``Q``'s in existing migrations, or
  accept an autogenerated migration.
  
  * Fixed a regression where a ``When()`` expression with a list argument crashes
  (:ticket:`29166`).
  
  * Fixed crash when using a ``Window()`` expression in a subquery
  (:ticket:`29172`).
  
  * Fixed ``AbstractBaseUser.normalize_username()`` crash if the ``username``
  argument isn't a string (:ticket:`29176`).
  
  
  ==========================

2.0.2 not secure

==========================
  
  *February 1, 2018*
  
  Django 2.0.2 fixes a security issue and several bugs in 2.0.1.
  
  CVE-2018-6188: Information leakage in ``AuthenticationForm``
  ============================================================
  
  A regression in Django 1.11.8 made
  :class:`~django.contrib.auth.forms.AuthenticationForm` run its
  ``confirm_login_allowed()`` method even if an incorrect password is entered.
  This can leak information about a user, depending on what messages
  ``confirm_login_allowed()`` raises. If ``confirm_login_allowed()`` isn't
  overridden, an attacker enter an arbitrary username and see if that user has
  been set to ``is_active=False``. If ``confirm_login_allowed()`` is overridden,
  more sensitive details could be leaked.
  
  This issue is fixed with the caveat that ``AuthenticationForm`` can no longer
  raise the "This account is inactive." error if the authentication backend
  rejects inactive users (the default authentication backend, ``ModelBackend``,
  has done that since Django 1.10). This issue will be revisited for Django 2.1
  as a fix to address the caveat will likely be too invasive for inclusion in
  older versions.
  
  Bugfixes
  ========
  
  * Fixed hidden content at the bottom of the "The install worked successfully!"
  page for some languages (:ticket:`28885`).
  
  * Fixed incorrect foreign key nullification if a model has two foreign keys to
  the same model and a target model is deleted (:ticket:`29016`).
  
  * Fixed regression in the use of ``QuerySet.values_list(..., flat=True)``
  followed by ``annotate()`` (:ticket:`29067`).
  
  * Fixed a regression where a queryset that annotates with geometry objects
  crashes (:ticket:`29054`).
  
  * Fixed a regression where ``contrib.auth.authenticate()`` crashes if an
  authentication backend doesn't accept ``request`` and a later one does
  (:ticket:`29071`).
  
  * Fixed a regression where ``makemigrations`` crashes if a migrations directory
  doesn't have an ``__init__.py`` file (:ticket:`29091`).
  
  * Fixed crash when entering an invalid uuid in ``ModelAdmin.raw_id_fields``
  (:ticket:`29094`).
  
  
  ==========================

2.0.1 not secure

==========================
  
  *January 1, 2018*
  
  Django 2.0.1 fixes several bugs in 2.0.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 1.11 that added newlines between ``MultiWidget``'s
  subwidgets (:ticket:`28890`).
  
  * Fixed incorrect class-based model index name generation for models with
  quoted ``db_table`` (:ticket:`28876`).
  
  * Fixed incorrect foreign key constraint name for models with quoted
  ``db_table`` (:ticket:`28876`).
  
  * Fixed a regression in caching of a ``GenericForeignKey`` when the referenced
  model instance uses more than one level of multi-table inheritance
  (:ticket:`28856`).
  
  * Reallowed filtering a queryset with ``GeometryField=None`` (:ticket:`28896`).
  
  * Corrected admin check to allow a ``OneToOneField`` in
  ``ModelAdmin.autocomplete_fields`` (:ticket:`28898`).
  
  * Fixed a regression on SQLite where ``DecimalField`` returned a result with
  trailing zeros in the fractional part truncated (:ticket:`28915`).
  
  * Fixed crash in the ``testserver`` command startup (:ticket:`28941`).
  
  * Fixed crash when coercing a translatable URL pattern to ``str``
  (:ticket:`28947`).
  
  * Fixed crash on SQLite when renaming a field in a model referenced by a
  ``ManyToManyField`` (:ticket:`28884`).
  
  * Fixed a crash when chaining ``values()`` or ``values_list()`` after
  ``QuerySet.select_for_update(of=(...))`` (:ticket:`28944`).
  
  * Fixed admin changelist crash when using a query expression in the page's
  ordering (:ticket:`28958`).
  
  
  ========================

2.0 not secure

========================
  
  *December 2, 2017*
  
  Welcome to Django 2.0!
  
  These release notes cover the :ref:`new features <whats-new-2.0>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-2.0>` you'll
  want to be aware of when upgrading from Django 1.11 or earlier. We've
  :ref:`dropped some features<removed-features-2.0>` that have reached the end of
  their deprecation cycle, and we've :ref:`begun the deprecation process for some
  features <deprecated-features-2.0>`.
  
  This release starts Django's use of a :ref:`loose form of semantic versioning
  <internal-release-cadence>`, but there aren't any major backwards incompatible
  changes that might be expected of a 2.0 release. Upgrading should be a similar
  amount of effort as past feature releases.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Django 2.0 supports Python 3.4, 3.5, 3.6, and 3.7. We **highly recommend** and
  only officially support the latest release of each series.
  
  The Django 1.11.x series is the last to support Python 2.7.
  
  Django 2.0 will be the last release series to support Python 3.4. If you plan
  a deployment of Python 3.4 beyond the end-of-life for Django 2.0 (April 2019),
  stick with Django 1.11 LTS (supported until April 2020) instead. Note, however,
  that the end-of-life for Python 3.4 is March 2019.
  
  Third-party library support for older version of Django
  =======================================================
  
  Following the release of Django 2.0, we suggest that third-party app authors
  drop support for all versions of Django prior to 1.11. At that time, you should
  be able to run your package's tests using ``python -Wd`` so that deprecation
  warnings do appear. After making the deprecation warning fixes, your app should
  be compatible with Django 2.0.
  
  .. _whats-new-2.0:
  
  What's new in Django 2.0
  ========================
  
  Simplified URL routing syntax
  -----------------------------
  
  The new :func:`django.urls.path()` function allows a simpler, more readable URL
  routing syntax. For example, this example from previous Django releases::
  
  url(r'^articles/(?P<year>[0-9]{4})/$', views.year_archive),
  
  could be written as::
  
  path('articles/<int:year>/', views.year_archive),
  
  The new syntax supports type coercion of URL parameters. In the example, the
  view will receive the ``year`` keyword argument as an integer rather than as
  a string. Also, the URLs that will match are slightly less constrained in the
  rewritten example. For example, the year 10000 will now match since the year
  integers aren't constrained to be exactly four digits long as they are in the
  regular expression.
  
  The ``django.conf.urls.url()`` function from previous versions is now available
  as :func:`django.urls.re_path`. The old location remains for backwards
  compatibility, without an imminent deprecation. The old
  ``django.conf.urls.include()`` function is now importable from ``django.urls``
  so you can use ``from django.urls import include, path, re_path`` in your
  URLconfs.
  
  The :doc:`/topics/http/urls` document is rewritten to feature the new syntax
  and provide more details.
  
  Mobile-friendly ``contrib.admin``
  ---------------------------------
  
  The admin is now responsive and supports all major mobile devices. Older
  browsers may experience varying levels of graceful degradation.
  
  Window expressions
  ------------------
  
  The new :class:`~django.db.models.expressions.Window` expression allows
  adding an ``OVER`` clause to querysets. You can use :ref:`window functions
  <window-functions>` and :ref:`aggregate functions <aggregation-functions>` in
  the expression.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :attr:`.ModelAdmin.autocomplete_fields` attribute and
  :meth:`.ModelAdmin.get_autocomplete_fields` method allow using a
  `Select2 <https://select2.org>`_ search widget for ``ForeignKey`` and
  ``ManyToManyField``.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The default iteration count for the PBKDF2 password hasher is increased from
  36,000 to 100,000.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added MySQL support for the
  :class:`~django.contrib.gis.db.models.functions.AsGeoJSON` function,
  :class:`~django.contrib.gis.db.models.functions.GeoHash` function,
  :class:`~django.contrib.gis.db.models.functions.IsValid` function,
  :lookup:`isvalid` lookup, and :ref:`distance lookups <distance-lookups>`.
  
  * Added the :class:`~django.contrib.gis.db.models.functions.Azimuth` and
  :class:`~django.contrib.gis.db.models.functions.LineLocatePoint` functions,
  supported on PostGIS and SpatiaLite.
  
  * Any :class:`~django.contrib.gis.geos.GEOSGeometry` imported from GeoJSON now
  has its SRID set.
  
  * Added the :attr:`.OSMWidget.default_zoom` attribute to customize the map's
  default zoom level.
  
  * Made metadata readable and editable on rasters through the
  :attr:`~django.contrib.gis.gdal.GDALRaster.metadata`,
  :attr:`~django.contrib.gis.gdal.GDALRaster.info`, and
  :attr:`~django.contrib.gis.gdal.GDALBand.metadata` attributes.
  
  * Allowed passing driver-specific creation options to
  :class:`~django.contrib.gis.gdal.GDALRaster` objects using ``papsz_options``.
  
  * Allowed creating :class:`~django.contrib.gis.gdal.GDALRaster` objects in
  GDAL's internal virtual filesystem. Rasters can now be :ref:`created from and
  converted to binary data <gdal-raster-vsimem>` in-memory.
  
  * The new :meth:`GDALBand.color_interp()
  <django.contrib.gis.gdal.GDALBand.color_interp>` method returns the color
  interpretation for the band.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new ``distinct`` argument for
  :class:`~django.contrib.postgres.aggregates.ArrayAgg` determines if
  concatenated values will be distinct.
  
  * The new :class:`~django.contrib.postgres.functions.RandomUUID` database
  function returns a version 4 UUID. It requires use of PostgreSQL's
  ``pgcrypto`` extension which can be activated using the new
  :class:`~django.contrib.postgres.operations.CryptoExtension` migration
  operation.
  
  * :class:`django.contrib.postgres.indexes.GinIndex` now supports the
  ``fastupdate`` and ``gin_pending_list_limit`` parameters.
  
  * The new :class:`~django.contrib.postgres.indexes.GistIndex` class allows
  creating ``GiST`` indexes in the database. The new
  :class:`~django.contrib.postgres.operations.BtreeGistExtension` migration
  operation installs the ``btree_gist`` extension to add support for operator
  classes that aren't built-in.
  
  * :djadmin:`inspectdb` can now introspect ``JSONField`` and various
  ``RangeField``\s (``django.contrib.postgres`` must be in ``INSTALLED_APPS``).
  
  :mod:`django.contrib.sitemaps`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added the ``protocol`` keyword argument to the
  :class:`~django.contrib.sitemaps.GenericSitemap` constructor.
  
  Cache
  ~~~~~
  
  * ``cache.set_many()`` now returns a list of keys that failed to be inserted.
  For the built-in backends, failed inserts can only happen on memcached.
  
  File Storage
  ~~~~~~~~~~~~
  
  * :meth:`File.open() <django.core.files.File.open>` can be used as a context
  manager, e.g. ``with file.open() as f:``.
  
  Forms
  ~~~~~
  
  * The new ``date_attrs`` and ``time_attrs`` arguments for
  :class:`~django.forms.SplitDateTimeWidget` and
  :class:`~django.forms.SplitHiddenDateTimeWidget` allow specifying different
  HTML attributes for the ``DateInput`` and ``TimeInput`` (or hidden)
  subwidgets.
  
  * The new :meth:`Form.errors.get_json_data()
  <django.forms.Form.errors.get_json_data>` method returns form errors as
  a dictionary suitable for including in a JSON response.
  
  Generic Views
  ~~~~~~~~~~~~~
  
  * The new :attr:`.ContextMixin.extra_context` attribute allows adding context
  in ``View.as_view()``.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * :djadmin:`inspectdb` now translates MySQL's unsigned integer columns to
  ``PositiveIntegerField`` or ``PositiveSmallIntegerField``.
  
  * The new :option:`makemessages --add-location` option controls the comment
  format in PO files.
  
  * :djadmin:`loaddata` can now :ref:`read from stdin <loading-fixtures-stdin>`.
  
  * The new :option:`diffsettings --output` option allows formatting the output
  in a unified diff format.
  
  * On Oracle, :djadmin:`inspectdb` can now introspect ``AutoField`` if the
  column is created as an identity column.
  
  * On MySQL, :djadmin:`dbshell` now supports client-side TLS certificates.
  
  Migrations
  ~~~~~~~~~~
  
  * The new :option:`squashmigrations --squashed-name` option allows naming the
  squashed migration.
  
  Models
  ~~~~~~
  
  * The new :class:`~django.db.models.functions.StrIndex` database function
  finds the starting index of a string inside another string.
  
  * On Oracle, ``AutoField`` and ``BigAutoField`` are now created as `identity
  columns <https://docs.oracle.com/en/database/oracle/oracle-database/18/drdaa/
  intro-to-tools-and-products-supporting-migraiton.htmlGUID-14E4817B-F3BC-4D99
  -B471-A0ACDC303CC9>`__.
  
  * The new ``chunk_size`` parameter of :meth:`.QuerySet.iterator` controls the
  number of rows fetched by the Python database client when streaming results
  from the database. For databases that don't support server-side cursors, it
  controls the number of results Django fetches from the database adapter.
  
  * :meth:`.QuerySet.earliest`, :meth:`.QuerySet.latest`, and
  :attr:`Meta.get_latest_by <django.db.models.Options.get_latest_by>` now
  allow ordering by several fields.
  
  * Added the :class:`~django.db.models.functions.ExtractQuarter` function to
  extract the quarter from :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField`, and exposed it through the
  :lookup:`quarter` lookup.
  
  * Added the :class:`~django.db.models.functions.TruncQuarter` function to
  truncate :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField` to the first day of a quarter.
  
  * Added the :attr:`~django.db.models.Index.db_tablespace` parameter to
  class-based indexes.
  
  * If the database supports a native duration field (Oracle and PostgreSQL),
  :class:`~django.db.models.functions.Extract` now works with
  :class:`~django.db.models.DurationField`.
  
  * Added the ``of`` argument to :meth:`.QuerySet.select_for_update()`, supported
  on PostgreSQL and Oracle, to lock only rows from specific tables rather than
  all selected tables. It may be helpful particularly when
  :meth:`~.QuerySet.select_for_update()` is used in conjunction with
  :meth:`~.QuerySet.select_related()`.
  
  * The new ``field_name`` parameter of :meth:`.QuerySet.in_bulk` allows fetching
  results based on any unique model field.
  
  * :meth:`.CursorWrapper.callproc()` now takes an optional dictionary of keyword
  parameters, if the backend supports this feature. Of Django's built-in
  backends, only Oracle supports it.
  
  * The new :meth:`connection.execute_wrapper()
  <django.db.backends.base.DatabaseWrapper.execute_wrapper>` method allows
  :doc:`installing wrappers around execution of database queries
  </topics/db/instrumentation>`.
  
  * The new ``filter`` argument for built-in aggregates allows :ref:`adding
  different conditionals <conditional-aggregation>` to multiple aggregations
  over the same fields or relations.
  
  * Added support for expressions in :attr:`Meta.ordering
  <django.db.models.Options.ordering>`.
  
  * The new ``named`` parameter of :meth:`.QuerySet.values_list` allows fetching
  results as named tuples.
  
  * The new :class:`.FilteredRelation` class allows adding an ``ON`` clause to
  querysets.
  
  Pagination
  ~~~~~~~~~~
  
  * Added :meth:`Paginator.get_page() <django.core.paginator.Paginator.get_page>`
  to provide the documented pattern of handling invalid page numbers.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * The :djadmin:`runserver` Web server supports HTTP 1.1.
  
  Templates
  ~~~~~~~~~
  
  * To increase the usefulness of :meth:`.Engine.get_default` in third-party
  apps, it now returns the first engine if multiple ``DjangoTemplates`` engines
  are configured in ``TEMPLATES`` rather than raising ``ImproperlyConfigured``.
  
  * Custom template tags may now accept keyword-only arguments.
  
  Tests
  ~~~~~
  
  * Added threading support to :class:`~django.test.LiveServerTestCase`.
  
  * Added settings that allow customizing the test tablespace parameters for
  Oracle: :setting:`DATAFILE_SIZE`, :setting:`DATAFILE_TMP_SIZE`,
  :setting:`DATAFILE_EXTSIZE`, and :setting:`DATAFILE_TMP_EXTSIZE`.
  
  Validators
  ~~~~~~~~~~
  
  * The new :class:`.ProhibitNullCharactersValidator` disallows the null
  character in the input of the :class:`~django.forms.CharField` form field
  and its subclasses. Null character input was observed from vulnerability
  scanning tools. Most databases silently discard null characters, but
  psycopg2 2.7+ raises an exception when trying to save a null character to
  a char/text field with PostgreSQL.
  
  .. _backwards-incompatible-2.0:
  
  Backwards incompatible changes in 2.0
  =====================================
  
  Removed support for bytestrings in some places
  ----------------------------------------------
  
  To support native Python 2 strings, older Django versions had to accept both
  bytestrings and Unicode strings. Now that Python 2 support is dropped,
  bytestrings should only be encountered around input/output boundaries (handling
  of binary fields or HTTP streams, for example). You might have to update your
  code to limit bytestring usage to a minimum, as Django no longer accepts
  bytestrings in certain code paths. Python's :option:`-b` option may help detect
  that mistake in your code.
  
  For example, ``reverse()`` now uses ``str()`` instead of ``force_text()`` to
  coerce the ``args`` and ``kwargs`` it receives, prior to their placement in
  the URL. For bytestrings, this creates a string with an undesired ``b`` prefix
  as well as additional quotes (``str(b'foo')`` is ``"b'foo'"``). To adapt, call
  ``decode()`` on the bytestring before passing it to ``reverse()``.
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * The ``DatabaseOperations.datetime_cast_date_sql()``,
  ``datetime_cast_time_sql()``, ``datetime_trunc_sql()``,
  ``datetime_extract_sql()``, and ``date_interval_sql()`` methods now return
  only the SQL to perform the operation instead of SQL and a list of
  parameters.
  
  * Third-party database backends should add a ``DatabaseWrapper.display_name``
  attribute with the name of the database that your backend works with. Django
  may use it in various messages, such as in system checks.
  
  * The first argument of ``SchemaEditor._alter_column_type_sql()`` is now
  ``model`` rather than ``table``.
  
  * The first argument of ``SchemaEditor._create_index_name()`` is now
  ``table_name`` rather than ``model``.
  
  * To enable ``FOR UPDATE OF`` support, set
  ``DatabaseFeatures.has_select_for_update_of = True``. If the database
  requires that the arguments to ``OF`` be columns rather than tables, set
  ``DatabaseFeatures.select_for_update_of_column = True``.
  
  * To enable support for :class:`~django.db.models.expressions.Window`
  expressions, set ``DatabaseFeatures.supports_over_clause`` to ``True``. You
  may need to customize the ``DatabaseOperations.window_start_rows_start_end()``
  and/or ``window_start_range_start_end()`` methods.
  
  * Third-party database backends should add a
  ``DatabaseOperations.cast_char_field_without_max_length`` attribute with the
  database data type that will be used in the
  :class:`~django.db.models.functions.Cast` function for a ``CharField`` if the
  ``max_length`` argument isn't provided.
  
  * The first argument of ``DatabaseCreation._clone_test_db()`` and
  ``get_test_db_clone_settings()`` is now ``suffix`` rather
  than ``number`` (in case you want to rename the signatures in your backend
  for consistency). ``django.test`` also now passes those values as strings
  rather than as integers.
  
  * Third-party database backends should add a
  ``DatabaseIntrospection.get_sequences()`` method based on the stub in
  ``BaseDatabaseIntrospection``.
  
  Dropped support for Oracle 11.2
  -------------------------------
  
  The end of upstream support for Oracle 11.2 is Dec. 2020. Django 1.11 will be
  supported until April 2020 which almost reaches this date. Django 2.0
  officially supports Oracle 12.1+.
  
  Default MySQL isolation level is read committed
  -----------------------------------------------
  
  MySQL's default isolation level, repeatable read, may cause data loss in
  typical Django usage. To prevent that and for consistency with other databases,
  the default isolation level is now read committed. You can use the
  :setting:`DATABASES` setting to :ref:`use a different isolation level
  <mysql-isolation-level>`, if needed.
  
  :attr:`AbstractUser.last_name <django.contrib.auth.models.User.last_name>` ``max_length`` increased to 150
  ----------------------------------------------------------------------------------------------------------
  
  A migration for :attr:`django.contrib.auth.models.User.last_name` is included.
  If you have a custom user model inheriting from ``AbstractUser``, you'll need
  to generate and apply a database migration for your user model.
  
  If you want to preserve the 30 character limit for last names, use a custom
  form::
  
  from django.contrib.auth.forms import UserChangeForm
  
  class MyUserChangeForm(UserChangeForm):
  last_name = forms.CharField(max_length=30, required=False)
  
  If you wish to keep this restriction in the admin when editing users, set
  ``UserAdmin.form`` to use this form::
  
  from django.contrib.auth.admin import UserAdmin
  from django.contrib.auth.models import User
  
  class MyUserAdmin(UserAdmin):
  form = MyUserChangeForm
  
  admin.site.unregister(User)
  admin.site.register(User, MyUserAdmin)
  
  ``QuerySet.reverse()`` and ``last()`` are prohibited after slicing
  ------------------------------------------------------------------
  
  Calling ``QuerySet.reverse()`` or ``last()`` on a sliced queryset leads to
  unexpected results due to the slice being applied after reordering. This is
  now prohibited, e.g.::
  
  >>> Model.objects.all()[:2].reverse()
  Traceback (most recent call last):
  ...
  TypeError: Cannot reverse a query once a slice has been taken.
  
  Form fields no longer accept optional arguments as positional arguments
  -----------------------------------------------------------------------
  
  To help prevent runtime errors due to incorrect ordering of form field
  arguments, optional arguments of built-in form fields are no longer accepted
  as positional arguments. For example::
  
  forms.IntegerField(25, 10)
  
  raises an exception and should be replaced with::
  
  forms.IntegerField(max_value=25, min_value=10)
  
  ``call_command()`` validates the options it receives
  ----------------------------------------------------
  
  ``call_command()`` now validates that the argument parser of the command being
  called defines all of the options passed to ``call_command()``.
  
  For custom management commands that use options not created using
  ``parser.add_argument()``, add a ``stealth_options`` attribute on the command::
  
  class MyCommand(BaseCommand):
  stealth_options = ('option_name', ...)
  
  Indexes no longer accept positional arguments
  ---------------------------------------------
  
  For example::
  
  models.Index(['headline', '-pub_date'], 'index_name')
  
  raises an exception and should be replaced with::
  
  models.Index(fields=['headline', '-pub_date'], name='index_name')
  
  Foreign key constraints are now enabled on SQLite
  -------------------------------------------------
  
  This will appear as a backwards-incompatible change (``IntegrityError:
  FOREIGN KEY constraint failed``) if attempting to save an existing model
  instance that's violating a foreign key constraint.
  
  Foreign keys are now created with ``DEFERRABLE INITIALLY DEFERRED`` instead of
  ``DEFERRABLE IMMEDIATE``. Thus, tables may need to be rebuilt to recreate
  foreign keys with the new definition, particularly if you're using a pattern
  like this::
  
  from django.db import transaction
  
  with transaction.atomic():
  Book.objects.create(author_id=1)
  Author.objects.create(id=1)
  
  If you don't recreate the foreign key as ``DEFERRED``, the first ``create()``
  would fail now that foreign key constraints are enforced.
  
  Backup your database first! After upgrading to Django 2.0, you can then
  rebuild tables using a script similar to this::
  
  from django.apps import apps
  from django.db import connection
  
  for app in apps.get_app_configs():
  for model in app.get_models(include_auto_created=True):
  if model._meta.managed and not (model._meta.proxy or model._meta.swapped):
  for base in model.__bases__:
  if hasattr(base, '_meta'):
  base._meta.local_many_to_many = []
  model._meta.local_many_to_many = []
  with connection.schema_editor() as editor:
  editor._remake_table(model)
  
  This script hasn't received extensive testing and needs adaption for various
  cases such as multiple databases. Feel free to contribute improvements.
  
  In addition, because of a table alteration limitation of SQLite, it's prohibited
  to perform :class:`~django.db.migrations.operations.RenameModel` and
  :class:`~django.db.migrations.operations.RenameField` operations on models or
  fields referenced by other models in a transaction. In order to allow migrations
  containing these operations to be applied, you must set the
  ``Migration.atomic`` attribute to ``False``.
  
  Miscellaneous
  -------------
  
  * The ``SessionAuthenticationMiddleware`` class is removed. It provided no
  functionality since session authentication is unconditionally enabled in
  Django 1.10.
  
  * The default HTTP error handlers (``handler404``, etc.) are now callables
  instead of dotted Python path strings. Django favors callable references
  since they provide better performance and debugging experience.
  
  * :class:`~django.views.generic.base.RedirectView` no longer silences
  ``NoReverseMatch`` if the ``pattern_name`` doesn't exist.
  
  * When :setting:`USE_L10N` is off, :class:`~django.forms.FloatField` and
  :class:`~django.forms.DecimalField` now respect :setting:`DECIMAL_SEPARATOR`
  and :setting:`THOUSAND_SEPARATOR` during validation. For example, with the
  settings::
  
  USE_L10N = False
  USE_THOUSAND_SEPARATOR = True
  DECIMAL_SEPARATOR = ','
  THOUSAND_SEPARATOR = '.'
  
  an input of ``"1.345"`` is now converted to ``1345`` instead of ``1.345``.
  
  * Subclasses of :class:`~django.contrib.auth.models.AbstractBaseUser` are no
  longer required to implement ``get_short_name()`` and ``get_full_name()``.
  (The base implementations that raise ``NotImplementedError`` are removed.)
  ``django.contrib.admin`` uses these methods if implemented but doesn't
  require them. Third-party apps that use these methods may want to adopt a
  similar approach.
  
  * The ``FIRST_DAY_OF_WEEK`` and ``NUMBER_GROUPING`` format settings are now
  kept as integers in JavaScript and JSON i18n view outputs.
  
  * :meth:`~django.test.TransactionTestCase.assertNumQueries` now ignores
  connection configuration queries. Previously, if a test opened a new database
  connection, those queries could be included as part of the
  ``assertNumQueries()`` count.
  
  * The default size of the Oracle test tablespace is increased from 20M to 50M
  and the default autoextend size is increased from 10M to 25M.
  
  * To improve performance when streaming large result sets from the database,
  :meth:`.QuerySet.iterator` now fetches 2000 rows at a time instead of 100.
  The old behavior can be restored using the ``chunk_size`` parameter. For
  example::
  
  Book.objects.iterator(chunk_size=100)
  
  * Providing unknown package names in the ``packages`` argument of the
  :class:`~django.views.i18n.JavaScriptCatalog` view now raises ``ValueError``
  instead of passing silently.
  
  * A model instance's primary key now appears in the default ``Model.__str__()``
  method, e.g. ``Question object (1)``.
  
  * ``makemigrations`` now detects changes to the model field ``limit_choices_to``
  option. Add this to your existing migrations or accept an auto-generated
  migration for fields that use it.
  
  * Performing queries that require :ref:`automatic spatial transformations
  <automatic-spatial-transformations>` now raises ``NotImplementedError``
  on MySQL instead of silently using non-transformed geometries.
  
  * ``django.core.exceptions.DjangoRuntimeWarning`` is removed. It was only used
  in the cache backend as an intermediate class in ``CacheKeyWarning``'s
  inheritance of ``RuntimeWarning``.
  
  * Renamed ``BaseExpression._output_field`` to ``output_field``. You may need
  to update custom expressions.
  
  * In older versions, forms and formsets combine their ``Media`` with widget
  ``Media`` by concatenating the two. The combining now tries to :ref:`preserve
  the relative order of elements in each list <form-media-asset-order>`.
  ``MediaOrderConflictWarning`` is issued if the order can't be preserved.
  
  * ``django.contrib.gis.gdal.OGRException`` is removed. It's been an alias for
  ``GDALException`` since Django 1.8.
  
  * Support for GEOS 3.3.x is dropped.
  
  * The way data is selected for ``GeometryField`` is changed to improve
  performance, and in raw SQL queries, those fields must now be wrapped in
  ``connection.ops.select``. See the :ref:`Raw queries note<gis-raw-sql>` in
  the GIS tutorial for an example.
  
  .. _deprecated-features-2.0:
  
  Features deprecated in 2.0
  ==========================
  
  ``context`` argument of ``Field.from_db_value()`` and ``Expression.convert_value()``
  ------------------------------------------------------------------------------------
  
  The ``context`` argument of ``Field.from_db_value()`` and
  ``Expression.convert_value()`` is unused as it's always an empty dictionary.
  The signature of both methods is now::
  
  (self, value, expression, connection)
  
  instead of::
  
  (self, value, expression, connection, context)
  
  Support for the old signature in custom fields and expressions remains until
  Django 3.0.
  
  Miscellaneous
  -------------
  
  * The ``django.db.backends.postgresql_psycopg2`` module is deprecated in favor
  of ``django.db.backends.postgresql``. It's been an alias since Django 1.9.
  This only affects code that imports from the module directly. The
  ``DATABASES`` setting can still use
  ``'django.db.backends.postgresql_psycopg2'``, though you can simplify that by
  using the ``'django.db.backends.postgresql'`` name added in Django 1.9.
  
  * ``django.shortcuts.render_to_response()`` is deprecated in favor of
  :func:`django.shortcuts.render`. ``render()`` takes the same arguments
  except that it also requires a ``request``.
  
  * The ``DEFAULT_CONTENT_TYPE`` setting is deprecated. It doesn't interact well
  with third-party apps and is obsolete since HTML5 has mostly superseded
  XHTML.
  
  * ``HttpRequest.xreadlines()`` is deprecated in favor of iterating over the
  request.
  
  * The ``field_name`` keyword argument to :meth:`.QuerySet.earliest` and
  :meth:`.QuerySet.latest` is deprecated in favor of passing the field
  names as arguments. Write ``.earliest('pub_date')`` instead of
  ``.earliest(field_name='pub_date')``.
  
  .. _removed-features-2.0:
  
  Features removed in 2.0
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 2.0.
  
  See :ref:`deprecated-features-1.9` for details on these changes, including how
  to remove usage of these features.
  
  * The ``weak`` argument to ``django.dispatch.signals.Signal.disconnect()`` is
  removed.
  
  * ``django.db.backends.base.BaseDatabaseOperations.check_aggregate_support()``
  is removed.
  
  * The ``django.forms.extras`` package is removed.
  
  * The ``assignment_tag`` helper is removed.
  
  * The ``host`` argument to ``SimpleTestCase.assertsRedirects()`` is removed.
  The compatibility layer which allows absolute URLs to be considered equal to
  relative ones when the path is identical is also removed.
  
  * ``Field.rel`` and ``Field.remote_field.to`` are removed.
  
  * The ``on_delete`` argument for ``ForeignKey`` and ``OneToOneField`` is now
  required in models and migrations. Consider squashing migrations so that you
  have fewer of them to update.
  
  * ``django.db.models.fields.add_lazy_relation()`` is removed.
  
  * When time zone support is enabled, database backends that don't support time
  zones no longer convert aware datetimes to naive values in UTC anymore when
  such values are passed as parameters to SQL queries executed outside of the
  ORM, e.g. with ``cursor.execute()``.
  
  * ``django.contrib.auth.tests.utils.skipIfCustomUser()`` is removed.
  
  * The ``GeoManager`` and ``GeoQuerySet`` classes are removed.
  
  * The ``django.contrib.gis.geoip`` module is removed.
  
  * The ``supports_recursion`` check for template loaders is removed from:
  
  * ``django.template.engine.Engine.find_template()``
  * ``django.template.loader_tags.ExtendsNode.find_template()``
  * ``django.template.loaders.base.Loader.supports_recursion()``
  * ``django.template.loaders.cached.Loader.supports_recursion()``
  
  * The ``load_template`` and ``load_template_sources`` template loader methods
  are removed.
  
  * The ``template_dirs`` argument for template loaders is removed:
  
  * ``django.template.loaders.base.Loader.get_template()``
  * ``django.template.loaders.cached.Loader.cache_key()``
  * ``django.template.loaders.cached.Loader.get_template()``
  * ``django.template.loaders.cached.Loader.get_template_sources()``
  * ``django.template.loaders.filesystem.Loader.get_template_sources()``
  
  * ``django.template.loaders.base.Loader.__call__()`` is removed.
  
  * Support for custom error views that don't accept an ``exception`` parameter
  is removed.
  
  * The ``mime_type`` attribute of ``django.utils.feedgenerator.Atom1Feed`` and
  ``django.utils.feedgenerator.RssFeed`` is removed.
  
  * The ``app_name`` argument to ``include()`` is removed.
  
  * Support for passing a 3-tuple (including ``admin.site.urls``) as the first
  argument to ``include()`` is removed.
  
  * Support for setting a URL instance namespace without an application namespace
  is removed.
  
  * ``Field._get_val_from_obj()`` is removed.
  
  * ``django.template.loaders.eggs.Loader`` is removed.
  
  * The ``current_app`` parameter to the ``contrib.auth`` function-based views is
  removed.
  
  * The ``callable_obj`` keyword argument to
  ``SimpleTestCase.assertRaisesMessage()`` is removed.
  
  * Support for the ``allow_tags`` attribute on ``ModelAdmin`` methods is
  removed.
  
  * The ``enclosure`` keyword argument to ``SyndicationFeed.add_item()`` is
  removed.
  
  * The ``django.template.loader.LoaderOrigin`` and
  ``django.template.base.StringOrigin`` aliases for
  ``django.template.base.Origin`` are removed.
  
  See :ref:`deprecated-features-1.10` for details on these changes.
  
  * The ``makemigrations --exit`` option is removed.
  
  * Support for direct assignment to a reverse foreign key or many-to-many
  relation is removed.
  
  * The ``get_srid()`` and ``set_srid()`` methods of
  ``django.contrib.gis.geos.GEOSGeometry`` are removed.
  
  * The ``get_x()``, ``set_x()``, ``get_y()``, ``set_y()``, ``get_z()``, and
  ``set_z()`` methods of ``django.contrib.gis.geos.Point`` are removed.
  
  * The ``get_coords()`` and ``set_coords()`` methods of
  ``django.contrib.gis.geos.Point`` are removed.
  
  * The ``cascaded_union`` property of ``django.contrib.gis.geos.MultiPolygon``
  is removed.
  
  * ``django.utils.functional.allow_lazy()`` is removed.
  
  * The ``shell --plain`` option is removed.
  
  * The ``django.core.urlresolvers`` module is removed in favor of its new
  location, ``django.urls``.
  
  * ``CommaSeparatedIntegerField`` is removed, except for support in historical
  migrations.
  
  * The template ``Context.has_key()`` method is removed.
  
  * Support for the ``django.core.files.storage.Storage.accessed_time()``,
  ``created_time()``, and ``modified_time()`` methods is removed.
  
  * Support for query lookups using the model name when
  ``Meta.default_related_name`` is set is removed.
  
  * The MySQL ``__search`` lookup is removed.
  
  * The shim for supporting custom related manager classes without a
  ``_apply_rel_filters()`` method is removed.
  
  * Using ``User.is_authenticated()`` and ``User.is_anonymous()`` as methods
  rather than properties is no longer supported.
  
  * The ``Model._meta.virtual_fields`` attribute is removed.
  
  * The keyword arguments ``virtual_only`` in ``Field.contribute_to_class()`` and
  ``virtual`` in ``Model._meta.add_field()`` are removed.
  
  * The ``javascript_catalog()`` and ``json_catalog()`` views are removed.
  
  * ``django.contrib.gis.utils.precision_wkt()`` is removed.
  
  * In multi-table inheritance, implicit promotion of a ``OneToOneField`` to a
  ``parent_link`` is removed.
  
  * Support for ``Widget._format_value()`` is removed.
  
  * ``FileField`` methods ``get_directory_name()`` and ``get_filename()`` are
  removed.
  
  * The ``mark_for_escaping()`` function and the classes it uses: ``EscapeData``,
  ``EscapeBytes``, ``EscapeText``, ``EscapeString``, and ``EscapeUnicode`` are
  removed.
  
  * The ``escape`` filter now uses ``django.utils.html.conditional_escape()``.
  
  * ``Manager.use_for_related_fields`` is removed.
  
  * Model ``Manager`` inheritance follows MRO inheritance rules. The requirement
  to use ``Meta.manager_inheritance_from_future`` to opt-in to the behavior is
  removed.
  
  * Support for old-style middleware using ``settings.MIDDLEWARE_CLASSES`` is
  removed.
  
  
  ============================

1.11.29

============================
  
  *March 4, 2020*
  
  Django 1.11.29 fixes a security issue in 1.11.28.
  
  CVE-2020-9402: Potential SQL injection via ``tolerance`` parameter in GIS functions and aggregates on Oracle
  ============================================================================================================
  
  GIS functions and aggregates on Oracle were subject to SQL injection,
  using a suitably crafted ``tolerance``.
  
  
  ============================

1.11.28 not secure

============================
  
  *February 3, 2020*
  
  Django 1.11.28 fixes a security issue in 1.11.27.
  
  CVE-2020-7471: Potential SQL injection via ``StringAgg(delimiter)``
  ===================================================================
  
  :class:`~django.contrib.postgres.aggregates.StringAgg` aggregation function was
  subject to SQL injection, using a suitably crafted ``delimiter``.
  
  
  ============================

1.11.27 not secure

============================
  
  *December 18, 2019*
  
  Django 1.11.27 fixes a security issue and a data loss bug in 1.11.26.
  
  CVE-2019-19844: Potential account hijack via password reset form
  ================================================================
  
  By submitting a suitably crafted email address making use of Unicode
  characters, that compared equal to an existing user email when lower-cased for
  comparison, an attacker could be sent a password reset token for the matched
  account.
  
  In order to avoid this vulnerability, password reset requests now compare the
  submitted email using the stricter, recommended algorithm for case-insensitive
  comparison of two identifiers from `Unicode Technical Report 36, section
  2.11.2(B)(2)`__. Upon a match, the email containing the reset token will be
  sent to the email address on record rather than the submitted address.
  
  .. __: https://www.unicode.org/reports/tr36/Recommendations_General
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility in
  :class:`~django.contrib.postgres.forms.SplitArrayField`. When using with
  ``ArrayField(BooleanField())``, all values after the first ``True`` value
  were marked as checked instead of preserving passed values (:ticket:`31073`).
  
  
  ============================

1.11.26 not secure

============================
  
  *November 4, 2019*
  
  Django 1.11.26 fixes a regression in 1.11.25.
  
  Bugfixes
  ========
  
  * Fixed a crash when using a ``contains``, ``contained_by``, ``has_key``,
  ``has_keys``, or ``has_any_keys`` lookup on
  :class:`~django.contrib.postgres.fields.JSONField`, if the right or left hand
  side of an expression is a key transform (:ticket:`30826`).
  
  
  ============================

1.11.25 not secure

============================
  
  *October 1, 2019*
  
  Django 1.11.25 fixes a regression in 1.11.23.
  
  Bugfixes
  ========
  
  * Fixed a crash when filtering with a ``Subquery()`` annotation of a queryset
  containing :class:`~django.contrib.postgres.fields.JSONField` or
  :class:`~django.contrib.postgres.fields.HStoreField` (:ticket:`30769`).
  
  
  ============================

1.11.24 not secure

============================
  
  *September 2, 2019*
  
  Django 1.11.24 fixes a regression in 1.11.23.
  
  Bugfixes
  ========
  
  * Fixed crash of ``KeyTransform()`` for
  :class:`~django.contrib.postgres.fields.JSONField` and
  :class:`~django.contrib.postgres.fields.HStoreField` when using on
  expressions with params (:ticket:`30672`).
  
  
  ============================

1.11.23 not secure

============================
  
  *August 1, 2019*
  
  Django 1.11.23 fixes security issues in 1.11.22.
  
  CVE-2019-14232: Denial-of-service possibility in ``django.utils.text.Truncator``
  ================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods
  were passed the ``html=True`` argument, they were extremely slow to evaluate
  certain inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  :tfilter:`truncatechars_html` and :tfilter:`truncatewords_html` template
  filters, which were thus vulnerable.
  
  The regular expressions used by ``Truncator`` have been simplified in order to
  avoid potential backtracking issues. As a consequence, trailing punctuation may
  now at times be included in the truncated output.
  
  CVE-2019-14233: Denial-of-service possibility in ``strip_tags()``
  =================================================================
  
  Due to the behavior of the underlying ``HTMLParser``,
  :func:`django.utils.html.strip_tags` would be extremely slow to evaluate
  certain inputs containing large sequences of nested incomplete HTML entities.
  The ``strip_tags()`` method is used to implement the corresponding
  :tfilter:`striptags` template filter, which was thus also vulnerable.
  
  ``strip_tags()`` now avoids recursive calls to ``HTMLParser`` when progress
  removing tags, but necessarily incomplete HTML entities, stops being made.
  
  Remember that absolutely NO guarantee is provided about the results of
  ``strip_tags()`` being HTML safe. So NEVER mark safe the result of a
  ``strip_tags()`` call without escaping it first, for example with
  :func:`django.utils.html.escape`.
  
  CVE-2019-14234: SQL injection possibility in key and index lookups for ``JSONField``/``HStoreField``
  ====================================================================================================
  
  :lookup:`Key and index lookups <jsonfield.key>` for
  :class:`~django.contrib.postgres.fields.JSONField` and :lookup:`key lookups
  <hstorefield.key>` for :class:`~django.contrib.postgres.fields.HStoreField`
  were subject to SQL injection, using a suitably crafted dictionary, with
  dictionary expansion, as the ``**kwargs`` passed to ``QuerySet.filter()``.
  
  CVE-2019-14235: Potential memory exhaustion in ``django.utils.encoding.uri_to_iri()``
  =====================================================================================
  
  If passed certain inputs, :func:`django.utils.encoding.uri_to_iri` could lead
  to significant memory usage due to excessive recursion when re-percent-encoding
  invalid UTF-8 octet sequences.
  
  ``uri_to_iri()`` now avoids recursion when re-percent-encoding invalid UTF-8
  octet sequences.
  
  
  ============================

1.11.22 not secure

============================
  
  *July 1, 2019*
  
  Django 1.11.22 fixes a security issue in 1.11.21.
  
  CVE-2019-12781: Incorrect HTTP detection with reverse-proxy connecting via HTTPS
  --------------------------------------------------------------------------------
  
  When deployed behind a reverse-proxy connecting to Django via HTTPS,
  :attr:`django.http.HttpRequest.scheme` would incorrectly detect client
  requests made via HTTP as using HTTPS. This entails incorrect results for
  :meth:`~django.http.HttpRequest.is_secure`, and
  :meth:`~django.http.HttpRequest.build_absolute_uri`, and that HTTP
  requests would not be redirected to HTTPS in accordance with
  :setting:`SECURE_SSL_REDIRECT`.
  
  ``HttpRequest.scheme`` now respects :setting:`SECURE_PROXY_SSL_HEADER`, if it
  is configured, and the appropriate header is set on the request, for both HTTP
  and HTTPS requests.
  
  If you deploy Django behind a reverse-proxy that forwards HTTP requests, and
  that connects to Django via HTTPS, be sure to verify that your application
  correctly handles code paths relying on ``scheme``, ``is_secure()``,
  ``build_absolute_uri()``, and ``SECURE_SSL_REDIRECT``.
  
  
  ============================

1.11.21 not secure

============================
  
  *June 3, 2019*
  
  Django 1.11.21 fixes a security issue in 1.11.20.
  
  CVE-2019-12308: AdminURLFieldWidget XSS
  ---------------------------------------
  
  The clickable "Current URL" link generated by ``AdminURLFieldWidget`` displayed
  the provided value without validating it as a safe URL. Thus, an unvalidated
  value stored in the database, or a value provided as a URL query parameter
  payload, could result in an clickable JavaScript link.
  
  ``AdminURLFieldWidget`` now validates the provided value using
  :class:`~django.core.validators.URLValidator` before displaying the clickable
  link. You may customize the validator by passing a ``validator_class`` kwarg to
  ``AdminURLFieldWidget.__init__()``, e.g. when using
  :attr:`~django.contrib.admin.ModelAdmin.formfield_overrides`.
  
  
  ============================

1.11.20 not secure

============================
  
  *February 11, 2019*
  
  Django 1.11.20 fixes a packaging error in 1.11.19.
  
  Bugfixes
  ========
  
  * Corrected packaging error from 1.11.19 (:ticket:`30175`).
  
  
  ============================

1.11.18 not secure

============================
  
  *January 4, 2019*
  
  Django 1.11.18 fixes a security issue in 1.11.17.
  
  CVE-2019-3498: Content spoofing possibility in the default 404 page
  -------------------------------------------------------------------
  
  An attacker could craft a malicious URL that could make spoofed content appear
  on the default page generated by the ``django.views.defaults.page_not_found()``
  view.
  
  The URL path is no longer displayed in the default 404 template and the
  ``request_path`` context variable is now quoted to fix the issue for custom
  templates that use the path.
  
  
  ============================

1.11.17 not secure

============================
  
  *December 3, 2018*
  
  Django 1.11.17 fixes several bugs in 1.11.16 and adds compatibility with
  Python 3.7.
  
  Bugfixes
  ========
  
  * Prevented repetitive calls to ``geos_version_tuple()`` in the ``WKBWriter``
  class in an attempt to fix a random crash involving ``LooseVersion`` since
  Django 1.11.14 (:ticket:`29959`).
  
  
  ============================

1.11.16 not secure

============================
  
  *October 1, 2018*
  
  Django 1.11.16 fixes a data loss bug in 1.11.15.
  
  Bugfixes
  ========
  
  * Fixed a race condition in ``QuerySet.update_or_create()`` that could result
  in data loss (:ticket:`29499`).
  
  
  ============================

1.11.15 not secure

============================
  
  *August 1, 2018*
  
  Django 1.11.15 fixes a security issue in 1.11.14.
  
  CVE-2018-14574: Open redirect possibility in ``CommonMiddleware``
  =================================================================
  
  If the :class:`~django.middleware.common.CommonMiddleware` and the
  :setting:`APPEND_SLASH` setting are both enabled, and if the project has a
  URL pattern that accepts any path ending in a slash (many content management
  systems have such a pattern), then a request to a maliciously crafted URL of
  that site could lead to a redirect to another site, enabling phishing and other
  attacks.
  
  ``CommonMiddleware`` now escapes leading slashes to prevent redirects to other
  domains.
  
  
  ============================

1.11.14 not secure

============================
  
  *July 2, 2018*
  
  Django 1.11.14 fixes several bugs in 1.11.13.
  
  Bugfixes
  ========
  
  * Fixed ``WKBWriter.write()`` and ``write_hex()`` for empty polygons on
  GEOS 3.6.1+ (:ticket:`29460`).
  
  * Fixed a regression in Django 1.10 that could result in large memory usage
  when making edits using ``ModelAdmin.list_editable`` (:ticket:`28462`).
  
  
  ============================

1.11.13 not secure

============================
  
  *May 1, 2018*
  
  Django 1.11.13 fixes several bugs in 1.11.12.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 1.11.8 where altering a field with a unique
  constraint may drop and rebuild more foreign keys than necessary
  (:ticket:`29193`).
  
  * Fixed crashes in ``django.contrib.admindocs`` when a view is a callable
  object, such as ``django.contrib.syndication.views.Feed`` (:ticket:`29296`).
  
  * Fixed a regression in Django 1.11.12 where ``QuerySet.values()`` or
  ``values_list()`` after combining an annotated and unannotated queryset with
  ``union()``, ``difference()``, or ``intersection()`` crashed due to mismatching
  columns (:ticket:`29286`).
  
  
  ============================

1.11.12 not secure

============================
  
  *April 2, 2018*
  
  Django 1.11.12 fixes two bugs in 1.11.11.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 1.11.8 where combining two annotated
  ``values_list()`` querysets with ``union()``, ``difference()``, or
  ``intersection()`` crashed due to mismatching columns (:ticket:`29229`).
  
  * Fixed a regression in Django 1.11 where an empty choice could be initially
  selected for the ``SelectMultiple`` and ``CheckboxSelectMultiple`` widgets
  (:ticket:`29273`).
  
  
  ============================

1.11.11 not secure

============================
  
  *March 6, 2018*
  
  Django 1.11.11 fixes two security issues in 1.11.10.
  
  CVE-2018-7536: Denial-of-service possibility in ``urlize`` and ``urlizetrunc`` template filters
  ===============================================================================================
  
  The ``django.utils.html.urlize()`` function was extremely slow to evaluate
  certain inputs due to catastrophic backtracking vulnerabilities in two regular
  expressions. The ``urlize()`` function is used to implement the ``urlize`` and
  ``urlizetrunc`` template filters, which were thus vulnerable.
  
  The problematic regular expressions are replaced with parsing logic that
  behaves similarly.
  
  CVE-2018-7537: Denial-of-service possibility in ``truncatechars_html`` and ``truncatewords_html`` template filters
  ==================================================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods were
  passed the ``html=True`` argument, they were extremely slow to evaluate certain
  inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  ``truncatechars_html`` and ``truncatewords_html`` template filters, which were
  thus vulnerable.
  
  The backtracking problem in the regular expression is fixed.
  
  
  ============================

1.11.10 not secure

============================
  
  *February 1, 2018*
  
  Django 1.11.10 fixes a security issue and several bugs in 1.11.9.
  
  CVE-2018-6188: Information leakage in ``AuthenticationForm``
  ============================================================
  
  A regression in Django 1.11.8 made
  :class:`~django.contrib.auth.forms.AuthenticationForm` run its
  ``confirm_login_allowed()`` method even if an incorrect password is entered.
  This can leak information about a user, depending on what messages
  ``confirm_login_allowed()`` raises. If ``confirm_login_allowed()`` isn't
  overridden, an attacker enter an arbitrary username and see if that user has
  been set to ``is_active=False``. If ``confirm_login_allowed()`` is overridden,
  more sensitive details could be leaked.
  
  This issue is fixed with the caveat that ``AuthenticationForm`` can no longer
  raise the "This account is inactive." error if the authentication backend
  rejects inactive users (the default authentication backend, ``ModelBackend``,
  has done that since Django 1.10). This issue will be revisited for Django 2.1
  as a fix to address the caveat will likely be too invasive for inclusion in
  older versions.
  
  Bugfixes
  ========
  
  * Fixed incorrect foreign key nullification if a model has two foreign keys to
  the same model and a target model is deleted (:ticket:`29016`).
  
  * Fixed a regression where ``contrib.auth.authenticate()`` crashes if an
  authentication backend doesn't accept ``request`` and a later one does
  (:ticket:`29071`).
  
  * Fixed crash when entering an invalid uuid in ``ModelAdmin.raw_id_fields``
  (:ticket:`29094`).
  
  
  ===========================

1.11.9 not secure

===========================
  
  *January 1, 2018*
  
  Django 1.11.9 fixes several bugs in 1.11.8.
  
  Bugfixes
  ========
  
  * Fixed a regression in Django 1.11 that added newlines between ``MultiWidget``'s
  subwidgets (:ticket:`28890`).
  
  * Fixed incorrect class-based model index name generation for models with
  quoted ``db_table`` (:ticket:`28876`).
  
  * Fixed incorrect foreign key constraint name for models with quoted
  ``db_table`` (:ticket:`28876`).
  
  * Fixed a regression in caching of a ``GenericForeignKey`` when the referenced
  model instance uses more than one level of multi-table inheritance
  (:ticket:`28856`).
  
  
  ===========================

1.11.8 not secure

===========================
  
  *December 2, 2017*
  
  Django 1.11.8 fixes several bugs in 1.11.7.
  
  Bugfixes
  ========
  
  * Reallowed, following a regression in Django 1.10, ``AuthenticationForm`` to
  raise the inactive user error when using ``ModelBackend`` (:ticket:`28645`).
  
  * Added support for ``QuerySet.values()`` and ``values_list()`` for
  ``union()``, ``difference()``, and ``intersection()`` queries
  (:ticket:`28781`).
  
  * Fixed incorrect index name truncation when using a namespaced ``db_table``
  (:ticket:`28792`).
  
  * Made ``QuerySet.iterator()`` use server-side cursors on PostgreSQL after
  ``values()`` and ``values_list()`` (:ticket:`28817`).
  
  * Fixed crash on SQLite and MySQL when ordering by a filtered subquery that
  uses ``nulls_first`` or ``nulls_last`` (:ticket:`28848`).
  
  * Made query lookups for ``CICharField``, ``CIEmailField``, and ``CITextField``
  use a ``citext`` cast (:ticket:`28702`).
  
  * Fixed a regression in caching of a ``GenericForeignKey`` when the referenced
  model instance uses multi-table inheritance (:ticket:`28856`).
  
  * Fixed "Cannot change column 'x': used in a foreign key constraint" crash on
  MySQL with a sequence of ``AlterField`` and/or ``RenameField`` operations in
  a migration (:ticket:`28305`).
  
  
  ===========================

1.11.7 not secure

===========================
  
  *November 1, 2017*
  
  Django 1.11.7 fixes several bugs in 1.11.6.
  
  Bugfixes
  ========
  
  * Prevented ``cache.get_or_set()`` from caching ``None`` if the ``default``
  argument is a callable that returns ``None`` (:ticket:`28601`).
  
  * Fixed the Basque ``DATE_FORMAT`` string (:ticket:`28710`).
  
  * Made ``QuerySet.reverse()`` affect ``nulls_first`` and ``nulls_last``
  (:ticket:`28722`).
  
  * Fixed unquoted table names in ``Subquery`` SQL when using ``OuterRef``
  (:ticket:`28689`).
  
  
  ===========================

1.11.6 not secure

===========================
  
  *October 5, 2017*
  
  Django 1.11.6 fixes several bugs in 1.11.5.
  
  Bugfixes
  ========
  
  * Made the ``CharField`` form field convert whitespace-only values to the
  ``empty_value`` when ``strip`` is enabled (:ticket:`28555`).
  
  * Fixed crash when using the name of a model's autogenerated primary key
  (``id``) in an ``Index``'s ``fields`` (:ticket:`28597`).
  
  * Fixed a regression in Django 1.9 where a custom view error handler such as
  ``handler404`` that accesses ``csrf_token`` could cause CSRF verification
  failures on other pages (:ticket:`28488`).
  
  
  ===========================

1.11.5 not secure

===========================
  
  *September 5, 2017*
  
  Django 1.11.5 fixes a security issue and several bugs in 1.11.4.
  
  CVE-2017-12794: Possible XSS in traceback section of technical 500 debug page
  =============================================================================
  
  In older versions, HTML autoescaping was disabled in a portion of the template
  for the technical 500 debug page. Given the right circumstances, this allowed
  a cross-site scripting attack. This vulnerability shouldn't affect most
  production sites since you shouldn't run with ``DEBUG = True`` (which makes
  this page accessible) in your production settings.
  
  Bugfixes
  ========
  
  * Fixed GEOS version parsing if the version has a commit hash at the end (new
  in GEOS 3.6.2) (:ticket:`28441`).
  
  * Added compatibility for ``cx_Oracle`` 6 (:ticket:`28498`).
  
  * Fixed select widget rendering when option values are tuples (:ticket:`28502`).
  
  * Django 1.11 inadvertently changed the sequence and trigger naming scheme on
  Oracle. This causes errors on INSERTs for some tables if
  ``'use_returning_into': False`` is in the ``OPTIONS`` part of ``DATABASES``.
  The pre-1.11 naming scheme is now restored. Unfortunately, it necessarily
  requires an update to Oracle tables created with Django 1.11.[1-4]. Use the
  upgrade script in :ticket:`28451` comment 8 to update sequence and trigger
  names to use the pre-1.11 naming scheme.
  
  * Added POST request support to ``LogoutView``, for equivalence with the
  function-based ``logout()`` view (:ticket:`28513`).
  
  * Omitted ``pages_per_range`` from ``BrinIndex.deconstruct()`` if it's ``None``
  (:ticket:`25809`).
  
  * Fixed a regression where ``SelectDateWidget`` localized the years in the
  select box (:ticket:`28530`).
  
  * Fixed a regression in 1.11.4 where ``runserver`` crashed with non-Unicode
  system encodings on Python 2 + Windows (:ticket:`28487`).
  
  * Fixed a regression in Django 1.10 where changes to a ``ManyToManyField``
  weren't logged in the admin change history (:ticket:`27998`) and prevented
  ``ManyToManyField`` initial data in model forms from being affected by
  subsequent model changes (:ticket:`28543`).
  
  * Fixed non-deterministic results or an ``AssertionError`` crash in some
  queries with multiple joins (:ticket:`26522`).
  
  * Fixed a regression in ``contrib.auth``'s ``login()`` and ``logout()`` views
  where they ignored positional arguments (:ticket:`28550`).
  
  
  ===========================

1.11.4 not secure

===========================
  
  *August 1, 2017*
  
  Django 1.11.4 fixes several bugs in 1.11.3.
  
  Bugfixes
  ========
  
  * Fixed a regression in 1.11.3 on Python 2 where non-ASCII ``format`` values
  for date/time widgets results in an empty ``value`` in the widget's HTML
  (:ticket:`28355`).
  
  * Fixed ``QuerySet.union()`` and ``difference()`` when combining with
  a queryset raising ``EmptyResultSet`` (:ticket:`28378`).
  
  * Fixed a regression in pickling of ``LazyObject`` on Python 2 when the wrapped
  object doesn't have ``__reduce__()`` (:ticket:`28389`).
  
  * Fixed crash in ``runserver``'s ``autoreload`` with Python 2 on Windows with
  non-``str`` environment variables (:ticket:`28174`).
  
  * Corrected ``Field.has_changed()`` to return ``False`` for disabled form
  fields: ``BooleanField``, ``MultipleChoiceField``, ``MultiValueField``,
  ``FileField``, ``ModelChoiceField``, and ``ModelMultipleChoiceField``.
  
  * Fixed ``QuerySet.count()`` for ``union()``, ``difference()``, and
  ``intersection()`` queries. (:ticket:`28399`).
  
  * Fixed ``ClearableFileInput`` rendering as a subwidget of ``MultiWidget``
  (:ticket:`28414`). Custom ``clearable_file_input.html`` widget templates
  will need to adapt for the fact that context values
  ``checkbox_name``, ``checkbox_id``, ``is_initial``, ``input_text``,
  ``initial_text``, and ``clear_checkbox_label`` are now attributes of
  ``widget`` rather than appearing in the top-level context.
  
  * Fixed queryset crash when using a ``GenericRelation`` to a proxy model
  (:ticket:`28418`).
  
  
  ===========================

1.11.3 not secure

===========================
  
  *July 1, 2017*
  
  Django 1.11.3 fixes several bugs in 1.11.2.
  
  Bugfixes
  ========
  
  * Removed an incorrect deprecation warning about a missing ``renderer``
  argument if a ``Widget.render()`` method accepts ``**kwargs``
  (:ticket:`28265`).
  
  * Fixed a regression causing ``Model.__init__()`` to crash if a field has an
  instance only descriptor (:ticket:`28269`).
  
  * Fixed an incorrect ``DisallowedModelAdminLookup`` exception when using
  a nested reverse relation in ``list_filter`` (:ticket:`28262`).
  
  * Fixed admin's ``FieldListFilter.get_queryset()`` crash on invalid input
  (:ticket:`28202`).
  
  * Fixed invalid HTML for a required ``AdminFileWidget`` (:ticket:`28278`).
  
  * Fixed model initialization to set the name of class-based model indexes
  for models that only inherit ``models.Model`` (:ticket:`28282`).
  
  * Fixed crash in admin's inlines when a model has an inherited non-editable
  primary key (:ticket:`27967`).
  
  * Fixed ``QuerySet.union()``, ``intersection()``, and ``difference()`` when
  combining with an ``EmptyQuerySet`` (:ticket:`28293`).
  
  * Prevented ``Paginator``’s unordered object list warning from evaluating a
  ``QuerySet`` (:ticket:`28284`).
  
  * Fixed the value of ``redirect_field_name`` in ``LoginView``’s template
  context. It's now an empty string (as it is for the original function-based
  ``login()`` view) if the corresponding parameter isn't sent in a request (in
  particular, when the login page is accessed directly) (:ticket:`28229`).
  
  * Prevented attribute values in the ``django/forms/widgets/attrs.html``
  template from being localized so that numeric attributes (e.g. ``max`` and
  ``min``) of ``NumberInput`` work correctly (:ticket:`28303`).
  
  * Removed casting of the option value to a string in the template context of
  the ``CheckboxSelectMultiple``, ``NullBooleanSelect``, ``RadioSelect``,
  ``SelectMultiple``, and ``Select`` widgets (:ticket:`28176`). In Django
  1.11.1, casting was added in Python to avoid localization of numeric values
  in Django templates, but this made some use cases more difficult. Casting is
  now done in the template using the ``|stringformat:'s'`` filter.
  
  * Prevented a primary key alteration from adding a foreign key constraint if
  ``db_constraint=False`` (:ticket:`28298`).
  
  * Fixed ``UnboundLocalError`` crash in ``RenameField`` with nonexistent field
  (:ticket:`28350`).
  
  * Fixed a regression preventing a model field's ``limit_choices_to`` from being
  evaluated when a ``ModelForm`` is instantiated (:ticket:`28345`).
  
  
  ===========================

1.11.2 not secure

===========================
  
  *June 1, 2017*
  
  Django 1.11.2 adds a minor feature and fixes several bugs in 1.11.1. Also, the
  latest string translations from Transifex are incorporated.
  
  Minor feature
  =============
  
  The new ``LiveServerTestCase.port`` attribute reallows the use case of binding
  to a specific port following the :ref:`bind to port zero
  <liveservertestcase-port-zero-change>` change in Django 1.11.
  
  Bugfixes
  ========
  
  * Added detection for GDAL 2.1 and 2.0, and removed detection for unsupported
  versions 1.7 and 1.8 (:ticket:`28181`).
  
  * Changed ``contrib.gis`` to raise ``ImproperlyConfigured`` rather than
  ``GDALException`` if ``gdal`` isn't installed, to allow third-party apps to
  catch that exception (:ticket:`28178`).
  
  * Fixed ``django.utils.http.is_safe_url()`` crash on invalid IPv6 URLs
  (:ticket:`28142`).
  
  * Fixed regression causing pickling of model fields to crash (:ticket:`28188`).
  
  * Fixed ``django.contrib.auth.authenticate()`` when multiple authentication
  backends don't accept a positional ``request`` argument (:ticket:`28207`).
  
  * Fixed introspection of index field ordering on PostgreSQL (:ticket:`28197`).
  
  * Fixed a regression where ``Model._state.adding`` wasn't set correctly on
  multi-table inheritance parent models after saving a child model
  (:ticket:`28210`).
  
  * Allowed ``DjangoJSONEncoder`` to serialize
  ``django.utils.deprecation.CallableBool`` (:ticket:`28230`).
  
  * Relaxed the validation added in Django 1.11 of the fields in the ``defaults``
  argument of ``QuerySet.get_or_create()`` and ``update_or_create()`` to
  reallow settable model properties (:ticket:`28222`).
  
  * Fixed ``MultipleObjectMixin.paginate_queryset()`` crash on Python 2 if the
  ``InvalidPage`` message contains non-ASCII (:ticket:`28204`).
  
  * Prevented ``Subquery`` from adding an unnecessary ``CAST`` which resulted in
  invalid SQL (:ticket:`28199`).
  
  * Corrected detection of GDAL 2.1 on Windows (:ticket:`28181`).
  
  * Made date-based generic views return a 404 rather than crash when given an
  out of range date (:ticket:`28209`).
  
  * Fixed a regression where ``file_move_safe()`` crashed when moving files to a
  CIFS mount (:ticket:`28170`).
  
  * Moved the ``ImageField`` file extension validation added in Django 1.11 from
  the model field to the form field to reallow the use case of storing images
  without an extension (:ticket:`28242`).
  
  
  ===========================

1.11.1 not secure

===========================
  
  *May 6, 2017*
  
  Django 1.11.1 adds a minor feature and fixes several bugs in 1.11.
  
  Allowed disabling server-side cursors on PostgreSQL
  ===================================================
  
  The change in Django 1.11 to make :meth:`.QuerySet.iterator()` use server-side
  cursors on PostgreSQL prevents running Django with PgBouncer in transaction
  pooling mode. To reallow that, use the :setting:`DISABLE_SERVER_SIDE_CURSORS
  <DATABASE-DISABLE_SERVER_SIDE_CURSORS>` setting in :setting:`DATABASES`.
  
  See :ref:`transaction-pooling-server-side-cursors` for more discussion.
  
  Bugfixes
  ========
  
  * Made migrations respect ``Index``’s ``name`` argument. If you created a
  named index with Django 1.11, ``makemigrations`` will create a migration to
  recreate the index with the correct name (:ticket:`28051`).
  
  * Fixed a crash when using a ``__icontains`` lookup on a ``ArrayField``
  (:ticket:`28038`).
  
  * Fixed a crash when using a two-tuple in ``EmailMessage``’s ``attachments``
  argument (:ticket:`28042`).
  
  * Fixed ``QuerySet.filter()`` crash when it references the name of a
  ``OneToOneField`` primary key (:ticket:`28047`).
  
  * Fixed empty POST data table appearing instead of "No POST data" in HTML debug
  page (:ticket:`28079`).
  
  * Restored ``BoundField``\s without any ``choices`` evaluating to ``True``
  (:ticket:`28058`).
  
  * Prevented ``SessionBase.cycle_key()`` from losing session data if
  ``_session_cache`` isn't populated (:ticket:`28066`).
  
  * Fixed layout of ``ReadOnlyPasswordHashWidget`` (used in the admin's user
  change page) (:ticket:`28097`).
  
  * Allowed prefetch calls on managers with custom ``ModelIterable`` subclasses
  (:ticket:`28096`).
  
  * Fixed change password link in the ``contrib.auth`` admin for ``el``,
  ``es_MX``, and ``pt`` translations (:ticket:`28100`).
  
  * Restored the output of the ``class`` attribute in the ``<ul>`` of widgets
  that use the ``multiple_input.html`` template. This fixes
  ``ModelAdmin.radio_fields`` with ``admin.HORIZONTAL`` (:ticket:`28059`).
  
  * Fixed crash in ``BaseGeometryWidget.subwidgets()`` (:ticket:`28039`).
  
  * Fixed exception reraising in ORM query execution when ``cursor.execute()``
  fails and the subsequent ``cursor.close()`` also fails (:ticket:`28091`).
  
  * Fixed a regression where ``CheckboxSelectMultiple``, ``NullBooleanSelect``,
  ``RadioSelect``, ``SelectMultiple``, and ``Select`` localized option values
  (:ticket:`28075`).
  
  * Corrected the stack level of unordered queryset pagination warnings
  (:ticket:`28109`).
  
  * Fixed a regression causing incorrect queries for ``__in`` subquery lookups
  when models use ``ForeignKey.to_field`` (:ticket:`28101`).
  
  * Fixed crash when overriding the template of
  ``django.views.static.directory_index()`` (:ticket:`28122`).
  
  * Fixed a regression in formset ``min_num`` validation with unchanged forms
  that have initial data (:ticket:`28130`).
  
  * Prepared for ``cx_Oracle`` 6.0 support (:ticket:`28138`).
  
  * Updated the ``contrib.postgres`` ``SplitArrayWidget`` to use template-based
  widget rendering (:ticket:`28040`).
  
  * Fixed crash in ``BaseGeometryWidget.get_context()`` when overriding existing
  ``attrs`` (:ticket:`28105`).
  
  * Prevented ``AddIndex`` and ``RemoveIndex`` from mutating model state
  (:ticket:`28043`).
  
  * Prevented migrations from dropping database indexes from ``Meta.indexes``
  when changing ``Field.db_index`` to ``False`` (:ticket:`28052`).
  
  * Fixed a regression in choice ordering in form fields with grouped and
  non-grouped options (:ticket:`28157`).
  
  * Fixed crash in  ``BaseInlineFormSet._construct_form()`` when using
  ``save_as_new`` (:ticket:`28159`).
  
  * Fixed a regression where ``Model._state.db`` wasn't set correctly on
  multi-table inheritance parent models after saving a child model
  (:ticket:`28166`).
  
  * Corrected the return type of ``ArrayField(CITextField())`` values retrieved
  from the database (:ticket:`28161`).
  
  * Fixed ``QuerySet.prefetch_related()`` crash when fetching relations in nested
  ``Prefetch`` objects (:ticket:`27554`).
  
  * Prevented hiding GDAL errors if it's not installed when using ``contrib.gis``
  (:ticket:`28160`). (It's a required dependency as of Django 1.11.)
  
  * Fixed a regression causing ``__in`` lookups on a foreign key to fail when
  using the foreign key's parent model as the lookup value (:ticket:`28175`).
  
  
  =========================

1.11 not secure

=========================
  
  *April 4, 2017*
  
  Welcome to Django 1.11!
  
  These release notes cover the :ref:`new features <whats-new-1.11>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.11>` you'll
  want to be aware of when upgrading from Django 1.10 or older versions. We've
  :ref:`begun the deprecation process for some features
  <deprecated-features-1.11>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Django 1.11 is designated as a :term:`long-term support release
  <Long-term support release>`. It will receive security updates for at least
  three years after its release. Support for the previous LTS, Django 1.8, will
  end in April 2018.
  
  Python compatibility
  ====================
  
  Django 1.11 requires Python 2.7, 3.4, 3.5, 3.6, or 3.7 (as of 1.11.17). We
  **highly recommend** and only officially support the latest release of each
  series.
  
  The Django 1.11.x series is the last to support Python 2. The next major
  release, Django 2.0, will only support Python 3.4+.
  
  Deprecating warnings are no longer loud by default
  ==================================================
  
  Unlike older versions of Django, Django's own deprecation warnings are no
  longer displayed by default. This is consistent with Python's default behavior.
  
  This change allows third-party apps to support both Django 1.11 LTS and Django
  1.8 LTS without having to add code to avoid deprecation warnings.
  
  Following the release of Django 2.0, we suggest that third-party app authors
  drop support for all versions of Django prior to 1.11. At that time, you should
  be able run your package's tests using ``python -Wd`` so that deprecation
  warnings do appear. After making the deprecation warning fixes, your app should
  be compatible with Django 2.0.
  
  .. _whats-new-1.11:
  
  What's new in Django 1.11
  =========================
  
  Class-based model indexes
  -------------------------
  
  The new :mod:`django.db.models.indexes` module contains classes which ease
  creating database indexes. Indexes are added to models using the
  :attr:`Meta.indexes <django.db.models.Options.indexes>` option.
  
  The :class:`~django.db.models.Index` class creates a b-tree index, as if you
  used :attr:`~django.db.models.Field.db_index` on the model field or
  :attr:`~django.db.models.Options.index_together` on the model ``Meta`` class.
  It can be subclassed to support different index types, such as
  :class:`~django.contrib.postgres.indexes.GinIndex`. It also allows defining the
  order (ASC/DESC) for the columns of the index.
  
  Template-based widget rendering
  -------------------------------
  
  To ease customizing widgets, form widget rendering is now done using the
  template system rather than in Python. See :doc:`/ref/forms/renderers`.
  
  You may need to adjust any custom widgets that you've written for a few
  :ref:`backwards incompatible changes <template-widget-incompatibilities-1-11>`.
  
  ``Subquery`` expressions
  ------------------------
  
  The new :class:`~django.db.models.Subquery` and
  :class:`~django.db.models.Exists` database expressions allow creating
  explicit subqueries. Subqueries may refer to fields from the outer queryset
  using the :class:`~django.db.models.OuterRef` class.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :attr:`.ModelAdmin.date_hierarchy` can now reference fields across relations.
  
  * The new :meth:`ModelAdmin.get_exclude()
  <django.contrib.admin.ModelAdmin.get_exclude>` hook allows specifying the
  exclude fields based on the request or model instance.
  
  * The ``popup_response.html`` template can now be overridden per app, per
  model, or by setting the :attr:`.ModelAdmin.popup_response_template`
  attribute.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The default iteration count for the PBKDF2 password hasher is increased by
  20%.
  
  * The :class:`~django.contrib.auth.views.LoginView` and
  :class:`~django.contrib.auth.views.LogoutView` class-based views supersede the
  deprecated ``login()`` and ``logout()`` function-based views.
  
  * The :class:`~django.contrib.auth.views.PasswordChangeView`,
  :class:`~django.contrib.auth.views.PasswordChangeDoneView`,
  :class:`~django.contrib.auth.views.PasswordResetView`,
  :class:`~django.contrib.auth.views.PasswordResetDoneView`,
  :class:`~django.contrib.auth.views.PasswordResetConfirmView`, and
  :class:`~django.contrib.auth.views.PasswordResetCompleteView` class-based
  views supersede the deprecated ``password_change()``,
  ``password_change_done()``, ``password_reset()``, ``password_reset_done()``,
  ``password_reset_confirm()``, and ``password_reset_complete()`` function-based
  views.
  
  * The new ``post_reset_login`` attribute for
  :class:`~django.contrib.auth.views.PasswordResetConfirmView` allows
  automatically logging in a user after a successful password reset.
  If you have multiple ``AUTHENTICATION_BACKENDS`` configured, use the
  ``post_reset_login_backend`` attribute to choose which one to use.
  
  * To avoid the possibility of leaking a password reset token via the HTTP
  Referer header (for example, if the reset page includes a reference to CSS or
  JavaScript hosted on another domain), the
  :class:`~django.contrib.auth.views.PasswordResetConfirmView` (but not the
  deprecated ``password_reset_confirm()`` function-based view) stores the token
  in a session and redirects to itself to present the password change form to
  the user without the token in the URL.
  
  * :func:`~django.contrib.auth.update_session_auth_hash` now rotates the session
  key to allow a password change to invalidate stolen session cookies.
  
  * The new ``success_url_allowed_hosts`` attribute for
  :class:`~django.contrib.auth.views.LoginView` and
  :class:`~django.contrib.auth.views.LogoutView` allows specifying a set of
  hosts that are safe for redirecting after login and logout.
  
  * Added password validators ``help_text`` to
  :class:`~django.contrib.auth.forms.UserCreationForm`.
  
  * The ``HttpRequest`` is now passed to :func:`~django.contrib.auth.authenticate`
  which in turn passes it to the authentication backend if it accepts a
  ``request`` argument.
  
  * The :func:`~django.contrib.auth.signals.user_login_failed` signal now
  receives a ``request`` argument.
  
  * :class:`~django.contrib.auth.forms.PasswordResetForm` supports custom user
  models that use an email field named something other than ``'email'``.
  Set :attr:`CustomUser.EMAIL_FIELD
  <django.contrib.auth.models.CustomUser.EMAIL_FIELD>` to the name of the field.
  
  * :func:`~django.contrib.auth.get_user_model` can now be called at import time,
  even in modules that define models.
  
  :mod:`django.contrib.contenttypes`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * When stale content types are detected in the
  :djadmin:`remove_stale_contenttypes` command, there's now a list of related
  objects such as ``auth.Permission``\s that will also be deleted. Previously,
  only the content types were listed (and this prompt was after ``migrate``
  rather than in a separate command).
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :meth:`.GEOSGeometry.from_gml` and :meth:`.OGRGeometry.from_gml`
  methods allow creating geometries from GML.
  
  * Added support for the :lookup:`dwithin` lookup on SpatiaLite.
  
  * The :class:`~django.contrib.gis.db.models.functions.Area` function,
  :class:`~django.contrib.gis.db.models.functions.Distance` function, and
  distance lookups now work with geodetic coordinates on SpatiaLite.
  
  * The OpenLayers-based form widgets now use ``OpenLayers.js`` from
  ``https://cdnjs.cloudflare.com`` which is more suitable for production use
  than the old ``https://openlayers.org/`` source. They are also updated to use
  OpenLayers 3.
  
  * PostGIS migrations can now change field dimensions.
  
  * Added the ability to pass the ``size``, ``shape``, and ``offset`` parameters
  when creating :class:`~django.contrib.gis.gdal.GDALRaster` objects.
  
  * Added SpatiaLite support for the
  :class:`~django.contrib.gis.db.models.functions.IsValid` function,
  :class:`~django.contrib.gis.db.models.functions.MakeValid` function, and
  :lookup:`isvalid` lookup.
  
  * Added Oracle support for the
  :class:`~django.contrib.gis.db.models.functions.AsGML` function,
  :class:`~django.contrib.gis.db.models.functions.BoundingCircle` function,
  :class:`~django.contrib.gis.db.models.functions.IsValid` function, and
  :lookup:`isvalid` lookup.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new ``distinct`` argument for
  :class:`~django.contrib.postgres.aggregates.StringAgg` determines if
  concatenated values will be distinct.
  
  * The new :class:`~django.contrib.postgres.indexes.GinIndex` and
  :class:`~django.contrib.postgres.indexes.BrinIndex` classes allow
  creating ``GIN`` and ``BRIN`` indexes in the database.
  
  * :class:`~django.contrib.postgres.fields.JSONField` accepts a new ``encoder``
  parameter to specify a custom class to encode data types not supported by the
  standard encoder.
  
  * The new :class:`~django.contrib.postgres.fields.CIText` mixin and
  :class:`~django.contrib.postgres.operations.CITextExtension` migration
  operation allow using PostgreSQL's ``citext`` extension for case-insensitive
  lookups. Three fields are provided: :class:`.CICharField`,
  :class:`.CIEmailField`, and :class:`.CITextField`.
  
  * The new :class:`~django.contrib.postgres.aggregates.JSONBAgg` allows
  aggregating values as a JSON array.
  
  * The :class:`~django.contrib.postgres.fields.HStoreField` (model field) and
  :class:`~django.contrib.postgres.forms.HStoreField` (form field) allow
  storing null values.
  
  Cache
  ~~~~~
  
  * Memcached backends now pass the contents of :setting:`OPTIONS <CACHES-OPTIONS>`
  as keyword arguments to the client constructors, allowing for more advanced
  control of client behavior. See the :ref:`cache arguments <cache_arguments>`
  documentation for examples.
  
  * Memcached backends now allow defining multiple servers as a comma-delimited
  string in :setting:`LOCATION <CACHES-LOCATION>`, for convenience with
  third-party services that use such strings in environment variables.
  
  CSRF
  ~~~~
  
  * Added the :setting:`CSRF_USE_SESSIONS` setting to allow storing the CSRF
  token in the user's session rather than in a cookie.
  
  Database backends
  ~~~~~~~~~~~~~~~~~
  
  * Added the ``skip_locked`` argument to :meth:`.QuerySet.select_for_update()`
  on PostgreSQL 9.5+ and Oracle to execute queries with
  ``FOR UPDATE SKIP LOCKED``.
  
  * Added the :setting:`TEST['TEMPLATE'] <TEST_TEMPLATE>` setting to let
  PostgreSQL users specify a template for creating the test database.
  
  * :meth:`.QuerySet.iterator()` now uses :ref:`server-side cursors
  <psycopg2:server-side-cursors>` on PostgreSQL. This feature transfers some of
  the worker memory load (used to hold query results) to the database and might
  increase database memory usage.
  
  * Added MySQL support for the ``'isolation_level'`` option in
  :setting:`OPTIONS` to allow specifying the :ref:`transaction isolation level
  <mysql-isolation-level>`. To avoid possible data loss, it's recommended to
  switch from MySQL's default level, repeatable read, to read committed.
  
  * Added support for ``cx_Oracle`` 5.3.
  
  Email
  ~~~~~
  
  * Added the :setting:`EMAIL_USE_LOCALTIME` setting to allow sending SMTP date
  headers in the local time zone rather than in UTC.
  
  * ``EmailMessage.attach()`` and ``attach_file()`` now fall back to MIME type
  :mimetype:`application/octet-stream` when binary content that can't be
  decoded as UTF-8 is specified for a :mimetype:`text/*` attachment.
  
  File Storage
  ~~~~~~~~~~~~
  
  * To make it wrappable by :class:`io.TextIOWrapper`,
  :class:`~django.core.files.File` now has the ``readable()``, ``writable()``,
  and ``seekable()`` methods.
  
  Forms
  ~~~~~
  
  * The new :attr:`CharField.empty_value <django.forms.CharField.empty_value>`
  attribute allows specifying the Python value to use to represent "empty".
  
  * The new :meth:`Form.get_initial_for_field()
  <django.forms.Form.get_initial_for_field>` method returns initial data for a
  form field.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * Number formatting and the :setting:`NUMBER_GROUPING` setting support
  non-uniform digit grouping.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`loaddata --exclude` option allows excluding models and apps
  while loading data from fixtures.
  
  * The new :option:`diffsettings --default` option allows specifying a settings
  module other than Django's default settings to compare against.
  
  * ``app_label``\s arguments now limit the :option:`showmigrations --plan`
  output.
  
  Migrations
  ~~~~~~~~~~
  
  * Added support for serialization of ``uuid.UUID`` objects.
  
  Models
  ~~~~~~
  
  * Added support for callable values in the ``defaults`` argument of
  :meth:`QuerySet.update_or_create()
  <django.db.models.query.QuerySet.update_or_create>` and
  :meth:`~django.db.models.query.QuerySet.get_or_create`.
  
  * :class:`~django.db.models.ImageField` now has a default
  :data:`~django.core.validators.validate_image_file_extension` validator.
  (This validator moved to the form field in :doc:`Django 1.11.2 <1.11.2>`.)
  
  * Added support for time truncation to
  :class:`~django.db.models.functions.Trunc` functions.
  
  * Added the :class:`~django.db.models.functions.ExtractWeek` function to
  extract the week from :class:`~django.db.models.DateField` and
  :class:`~django.db.models.DateTimeField` and exposed it through the
  :lookup:`week` lookup.
  
  * Added the :class:`~django.db.models.functions.TruncTime` function to truncate
  :class:`~django.db.models.DateTimeField` to its time component and exposed it
  through the :lookup:`time` lookup.
  
  * Added support for expressions in :meth:`.QuerySet.values` and
  :meth:`~.QuerySet.values_list`.
  
  * Added support for query expressions on lookups that take multiple arguments,
  such as ``range``.
  
  * You can now use the ``unique=True`` option with
  :class:`~django.db.models.FileField`.
  
  * Added the ``nulls_first`` and ``nulls_last`` parameters to
  :class:`Expression.asc() <django.db.models.Expression.asc>` and
  :meth:`~django.db.models.Expression.desc` to control
  the ordering of null values.
  
  * The new ``F`` expression ``bitleftshift()`` and ``bitrightshift()`` methods
  allow :ref:`bitwise shift operations <using-f-expressions-in-filters>`.
  
  * Added :meth:`.QuerySet.union`, :meth:`~.QuerySet.intersection`, and
  :meth:`~.QuerySet.difference`.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Added :meth:`QueryDict.fromkeys() <django.http.QueryDict.fromkeys>`.
  
  * :class:`~django.middleware.common.CommonMiddleware` now sets the
  ``Content-Length`` response header for non-streaming responses.
  
  * Added the :setting:`SECURE_HSTS_PRELOAD` setting to allow appending the
  ``preload`` directive to the ``Strict-Transport-Security`` header.
  
  * :class:`~django.middleware.http.ConditionalGetMiddleware` now adds the
  ``ETag`` header to responses.
  
  Serialization
  ~~~~~~~~~~~~~
  
  * The new ``django.core.serializers.base.Serializer.stream_class`` attribute
  allows subclasses to customize the default stream.
  
  * The encoder used by the :ref:`JSON serializer <serialization-formats-json>`
  can now be customized by passing a ``cls`` keyword argument to the
  ``serializers.serialize()`` function.
  
  * :class:`~django.core.serializers.json.DjangoJSONEncoder` now serializes
  :class:`~datetime.timedelta` objects (used by
  :class:`~django.db.models.DurationField`).
  
  Templates
  ~~~~~~~~~
  
  * :meth:`~django.utils.safestring.mark_safe` can now be used as a decorator.
  
  * The :class:`~django.template.backends.jinja2.Jinja2` template backend now
  supports context processors by setting the ``'context_processors'`` option in
  :setting:`OPTIONS <TEMPLATES-OPTIONS>`.
  
  * The :ttag:`regroup` tag now returns ``namedtuple``\s instead of dictionaries
  so you can unpack the group object directly in a loop, e.g.
  ``{% for grouper, list in regrouped %}``.
  
  * Added a :ttag:`resetcycle` template tag to allow resetting the sequence of
  the :ttag:`cycle` template tag.
  
  * You can now specify specific directories for a particular
  :class:`filesystem.Loader <django.template.loaders.filesystem.Loader>`.
  
  Tests
  ~~~~~
  
  * Added :meth:`.DiscoverRunner.get_test_runner_kwargs` to allow customizing the
  keyword arguments passed to the test runner.
  
  * Added the :option:`test --debug-mode` option to help troubleshoot test
  failures by setting the :setting:`DEBUG` setting to ``True``.
  
  * The new :func:`django.test.utils.setup_databases` (moved from
  ``django.test.runner``) and :func:`~django.test.utils.teardown_databases`
  functions make it easier to build custom test runners.
  
  * Added support for :meth:`python:unittest.TestCase.subTest`’s when using the
  :option:`test --parallel` option.
  
  * ``DiscoverRunner`` now runs the system checks at the start of a test run.
  Override the :meth:`.DiscoverRunner.run_checks` method if you want to disable
  that.
  
  Validators
  ~~~~~~~~~~
  
  * Added :class:`~django.core.validators.FileExtensionValidator` to validate
  file extensions and
  :data:`~django.core.validators.validate_image_file_extension` to validate
  image files.
  
  .. _backwards-incompatible-1.11:
  
  Backwards incompatible changes in 1.11
  ======================================
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * To simplify the codebase and because it's easier to install than when
  ``contrib.gis`` was first released, :ref:`gdalbuild` is now a required
  dependency for GeoDjango. In older versions, it's only required for SQLite.
  
  * ``contrib.gis.maps`` is removed as it interfaces with a retired version of
  the Google Maps API and seems to be unmaintained. If you're using it,
  :ticket:`let us know <14284>`.
  
  * The ``GEOSGeometry`` equality operator now also compares SRID.
  
  * The OpenLayers-based form widgets now use OpenLayers 3, and the
  ``gis/openlayers.html`` and ``gis/openlayers-osm.html`` templates have been
  updated. Check your project if you subclass these widgets or extend the
  templates. Also, the new widgets work a bit differently than the old ones.
  Instead of using a toolbar in the widget, you click to draw, click and drag
  to move the map, and click and drag a point/vertex/corner to move it.
  
  * Support for SpatiaLite < 4.0 is dropped.
  
  * Support for GDAL 1.7 and 1.8 is dropped.
  
  * The widgets in ``contrib.gis.forms.widgets`` and the admin's
  ``OpenLayersWidget`` use the :doc:`form rendering API </ref/forms/renderers>`
  rather than ``loader.render_to_string()``. If you're using a custom widget
  template, you'll need to be sure your form renderer can locate it. For
  example, you could use the :class:`~django.forms.renderers.TemplatesSetting`
  renderer.
  
  :mod:`django.contrib.staticfiles`
  ---------------------------------
  
  * ``collectstatic`` may now fail during post-processing when using a hashed
  static files storage if a reference loop exists (e.g. ``'foo.css'``
  references ``'bar.css'`` which itself references ``'foo.css'``) or if the
  chain of files referencing other files is too deep to resolve in several
  passes. In the latter case, increase the number of passes using
  :attr:`.ManifestStaticFilesStorage.max_post_process_passes`.
  
  * When using ``ManifestStaticFilesStorage``, static files not found in the
  manifest at runtime now raise a ``ValueError`` instead of returning an
  unchanged path. You can revert to the old behavior by setting
  :attr:`.ManifestStaticFilesStorage.manifest_strict` to ``False``.
  
  Database backend API
  --------------------
  
  This section describes changes that may be needed in third-party database
  backends.
  
  * The ``DatabaseOperations.time_trunc_sql()`` method is added to support
  ``TimeField`` truncation. It accepts a ``lookup_type`` and ``field_name``
  arguments and returns the appropriate SQL to truncate the given time field
  ``field_name`` to a time object with only the given specificity. The
  ``lookup_type`` argument can be either ``'hour'``, ``'minute'``, or
  ``'second'``.
  
  * The ``DatabaseOperations.datetime_cast_time_sql()`` method is added to
  support the :lookup:`time` lookup. It accepts a ``field_name`` and ``tzname``
  arguments and returns the SQL necessary to cast a datetime value to time value.
  
  * To enable ``FOR UPDATE SKIP LOCKED`` support, set
  ``DatabaseFeatures.has_select_for_update_skip_locked = True``.
  
  * The new ``DatabaseFeatures.supports_index_column_ordering`` attribute
  specifies if a database allows defining ordering for columns in indexes. The
  default value is ``True`` and the ``DatabaseIntrospection.get_constraints()``
  method should include an ``'orders'`` key in each of the returned
  dictionaries with a list of ``'ASC'`` and/or ``'DESC'`` values corresponding
  to the ordering of each column in the index.
  
  * :djadmin:`inspectdb` no longer calls ``DatabaseIntrospection.get_indexes()``
  which is deprecated. Custom database backends should ensure all types of
  indexes are returned by ``DatabaseIntrospection.get_constraints()``.
  
  * Renamed the ``ignores_quoted_identifier_case`` feature to
  ``ignores_table_name_case`` to more accurately reflect how it is used.
  
  * The ``name`` keyword argument is added to the
  ``DatabaseWrapper.create_cursor(self, name=None)`` method to allow usage of
  server-side cursors on backends that support it.
  
  Dropped support for PostgreSQL 9.2 and PostGIS 2.0
  --------------------------------------------------
  
  Upstream support for PostgreSQL 9.2 ends in September 2017. As a consequence,
  Django 1.11 sets PostgreSQL 9.3 as the minimum version it officially supports.
  
  Support for PostGIS 2.0 is also removed as PostgreSQL 9.2 is the last version
  to support it.
  
  Also, the minimum supported version of psycopg2 is increased from 2.4.5 to
  2.5.4.
  
  .. _liveservertestcase-port-zero-change:
  
  ``LiveServerTestCase`` binds to port zero
  -----------------------------------------
  
  Rather than taking a port range and iterating to find a free port,
  ``LiveServerTestCase`` binds to port zero and relies on the operating system
  to assign a free port. The ``DJANGO_LIVE_TEST_SERVER_ADDRESS`` environment
  variable is no longer used, and as it's also no longer used, the
  ``manage.py test --liveserver`` option is removed.
  
  If you need to bind ``LiveServerTestCase`` to a specific port, use the ``port``
  attribute added in Django 1.11.2.
  
  Protection against insecure redirects in :mod:`django.contrib.auth` and ``i18n`` views
  --------------------------------------------------------------------------------------
  
  ``LoginView``, ``LogoutView`` (and the deprecated function-based equivalents),
  and :func:`~django.views.i18n.set_language` protect users from being redirected
  to non-HTTPS ``next`` URLs when the app is running over HTTPS.
  
  ``QuerySet.get_or_create()`` and ``update_or_create()`` validate arguments
  --------------------------------------------------------------------------
  
  To prevent typos from passing silently,
  :meth:`~django.db.models.query.QuerySet.get_or_create` and
  :meth:`~django.db.models.query.QuerySet.update_or_create` check that their
  arguments are model fields. This should be backwards-incompatible only in the
  fact that it might expose a bug in your project.
  
  ``pytz`` is a required dependency and support for ``settings.TIME_ZONE = None`` is removed
  ------------------------------------------------------------------------------------------
  
  To simplify Django's timezone handling, ``pytz`` is now a required dependency.
  It's automatically installed along with Django.
  
  Support for ``settings.TIME_ZONE = None`` is removed as the behavior isn't
  commonly used and is questionably useful. If you want to automatically detect
  the timezone based on the system timezone, you can use `tzlocal
  <https://pypi.org/project/tzlocal/>`_::
  
  from tzlocal import get_localzone
  
  TIME_ZONE = get_localzone().zone
  
  This works similar to ``settings.TIME_ZONE = None`` except that it also sets
  ``os.environ['TZ']``. `Let us know
  <https://groups.google.com/d/topic/django-developers/OAV3FChfuPM/discussion>`__
  if there's a use case where you find you can't adapt your code to set a
  ``TIME_ZONE``.
  
  HTML changes in admin templates
  -------------------------------
  
  ``<p class="help">`` is replaced with a ``<div>`` tag to allow including lists
  inside help text.
  
  Read-only fields are wrapped in ``<div class="readonly">...</div>`` instead of
  ``<p>...</p>`` to allow any kind of HTML as the field's content.
  
  .. _template-widget-incompatibilities-1-11:
  
  Changes due to the introduction of template-based widget rendering
  ------------------------------------------------------------------
  
  Some undocumented classes in ``django.forms.widgets`` are removed:
  
  * ``SubWidget``
  * ``RendererMixin``, ``ChoiceFieldRenderer``, ``RadioFieldRenderer``,
  ``CheckboxFieldRenderer``
  * ``ChoiceInput``, ``RadioChoiceInput``, ``CheckboxChoiceInput``
  
  The undocumented ``Select.render_option()`` method is removed.
  
  The ``Widget.format_output()`` method is removed. Use a custom widget template
  instead.
  
  Some widget values, such as ``<select>`` options, are now localized if
  ``settings.USE_L10N=True``. You could revert to the old behavior with custom
  widget templates that uses the :ttag:`localize` template tag to turn off
  localization.
  
  ``django.template.backends.django.Template.render()`` prohibits non-dict context
  --------------------------------------------------------------------------------
  
  For compatibility with multiple template engines,
  ``django.template.backends.django.Template.render()`` (returned from high-level
  template loader APIs such as ``loader.get_template()``) must receive a
  dictionary of context rather than ``Context`` or ``RequestContext``. If you
  were passing either of the two classes, pass a dictionary instead -- doing so
  is backwards-compatible with older versions of Django.
  
  Model state changes in migration operations
  -------------------------------------------
  
  To improve the speed of applying migrations, rendering of related models is
  delayed until an operation that needs them (e.g. ``RunPython``). If you have a
  custom operation that works with model classes or model instances from the
  ``from_state`` argument in ``database_forwards()`` or ``database_backwards()``,
  you must render model states using the ``clear_delayed_apps_cache()`` method as
  described in :ref:`writing your own migration operation
  <writing-your-own-migration-operation>`.
  
  Server-side cursors on PostgreSQL
  ---------------------------------
  
  The change to make :meth:`.QuerySet.iterator()` use server-side cursors on
  PostgreSQL prevents running Django with PgBouncer in transaction pooling mode.
  To reallow that, use the :setting:`DISABLE_SERVER_SIDE_CURSORS
  <DATABASE-DISABLE_SERVER_SIDE_CURSORS>` setting (added in Django 1.11.1) in
  :setting:`DATABASES`.
  
  See :ref:`transaction-pooling-server-side-cursors` for more discussion.
  
  Miscellaneous
  -------------
  
  * If no items in the feed have a ``pubdate`` or ``updateddate`` attribute,
  :meth:`SyndicationFeed.latest_post_date()
  <django.utils.feedgenerator.SyndicationFeed.latest_post_date>` now returns
  the current UTC date/time, instead of a datetime without any timezone
  information.
  
  * CSRF failures are logged to the ``django.security.csrf`` logger instead of
  ``django.request``.
  
  * :setting:`ALLOWED_HOSTS` validation is no longer disabled when running tests.
  If your application includes tests with custom host names, you must include
  those host names in :setting:`ALLOWED_HOSTS`. See
  :ref:`topics-testing-advanced-multiple-hosts`.
  
  * Using a foreign key's id (e.g. ``'field_id'``) in ``ModelAdmin.list_display``
  displays the related object's ID. Remove the ``_id`` suffix if you want the
  old behavior of the string representation of the object.
  
  * In model forms, :class:`~django.db.models.CharField` with ``null=True`` now
  saves ``NULL`` for blank values instead of empty strings.
  
  * On Oracle, :meth:`Model.validate_unique()
  <django.db.models.Model.validate_unique>` no longer checks empty strings for
  uniqueness as the database interprets the value as ``NULL``.
  
  * If you subclass :class:`.AbstractUser` and override ``clean()``, be sure it
  calls ``super()``. :meth:`.BaseUserManager.normalize_email` is called in a
  new :meth:`.AbstractUser.clean` method so that normalization is applied in
  cases like model form validation.
  
  * ``EmailField`` and ``URLField`` no longer accept the ``strip`` keyword
  argument. Remove it because it doesn't have an effect in older versions of
  Django as these fields always strip whitespace.
  
  * The ``checked`` and ``selected`` attribute rendered by form widgets now uses
  HTML5 boolean syntax rather than XHTML's ``checked='checked'`` and
  ``selected='selected'``.
  
  * :meth:`RelatedManager.add()
  <django.db.models.fields.related.RelatedManager.add>`,
  :meth:`~django.db.models.fields.related.RelatedManager.remove`,
  :meth:`~django.db.models.fields.related.RelatedManager.clear`, and
  :meth:`~django.db.models.fields.related.RelatedManager.set` now
  clear the ``prefetch_related()`` cache.
  
  * To prevent possible loss of saved settings,
  :func:`~django.test.utils.setup_test_environment` now raises an exception if
  called a second time before calling
  :func:`~django.test.utils.teardown_test_environment`.
  
  * The undocumented ``DateTimeAwareJSONEncoder`` alias for
  :class:`~django.core.serializers.json.DjangoJSONEncoder` (renamed in Django
  1.0) is removed.
  
  * The :class:`cached template loader <django.template.loaders.cached.Loader>`
  is now enabled if :setting:`OPTIONS['loaders'] <TEMPLATES-OPTIONS>` isn't
  specified and :setting:`OPTIONS['debug'] <TEMPLATES-OPTIONS>` is ``False``
  (the latter option defaults to the value of :setting:`DEBUG`). This could
  be backwards-incompatible if you have some :ref:`template tags that aren't
  thread safe <template_tag_thread_safety>`.
  
  * The prompt for stale content type deletion no longer occurs after running the
  ``migrate`` command. Use the new :djadmin:`remove_stale_contenttypes` command
  instead.
  
  * The admin's widget for ``IntegerField`` uses ``type="number"`` rather than
  ``type="text"``.
  
  * Conditional HTTP headers are now parsed and compared according to the
  :rfc:`7232` Conditional Requests specification rather than the older
  :rfc:`2616`.
  
  * :func:`~django.utils.cache.patch_response_headers` no longer adds a
  ``Last-Modified`` header. According to the :rfc:`7234section-4.2.2`, this
  header is useless alongside other caching headers that provide an explicit
  expiration time, e.g. ``Expires`` or ``Cache-Control``.
  :class:`~django.middleware.cache.UpdateCacheMiddleware` and
  :func:`~django.utils.cache.add_never_cache_headers` call
  ``patch_response_headers()`` and therefore are also affected by this change.
  
  * In the admin templates, ``<p class="help">`` is replaced with a ``<div>`` tag
  to allow including lists inside help text.
  
  * :class:`~django.middleware.http.ConditionalGetMiddleware` no longer sets the
  ``Date`` header as Web servers set that header. It also no longer sets the
  ``Content-Length`` header as this is now done by
  :class:`~django.middleware.common.CommonMiddleware`.
  
  If you have a middleware that modifies a response's content and appears
  before ``CommonMiddleware`` in the ``MIDDLEWARE`` or ``MIDDLEWARE_CLASSES``
  settings, you must reorder your middleware so that responses aren't modified
  after ``Content-Length`` is set, or have the response modifying middleware
  reset the ``Content-Length`` header.
  
  * :meth:`~django.apps.AppConfig.get_model` and
  :meth:`~django.apps.AppConfig.get_models` now raise
  :exc:`~django.core.exceptions.AppRegistryNotReady` if they're called before
  models of all applications have been loaded. Previously they only required
  the target application's models to be loaded and thus could return models
  without all their relations set up. If you need the old behavior of
  ``get_model()``, set the ``require_ready`` argument to ``False``.
  
  * The unused ``BaseCommand.can_import_settings`` attribute is removed.
  
  * The undocumented ``django.utils.functional.lazy_property`` is removed.
  
  * For consistency with non-multipart requests, ``MultiPartParser.parse()`` now
  leaves ``request.POST`` immutable. If you're modifying that ``QueryDict``,
  you must now first copy it, e.g. ``request.POST.copy()``.
  
  * Support for ``cx_Oracle`` < 5.2 is removed.
  
  * Support for IPython < 1.0 is removed from the ``shell`` command.
  
  * The signature of private API ``Widget.build_attrs()`` changed from
  ``extra_attrs=None, **kwargs`` to ``base_attrs, extra_attrs=None``.
  
  * File-like objects (e.g., :class:`~io.StringIO` and :class:`~io.BytesIO`)
  uploaded to an :class:`~django.db.models.ImageField` using the test client
  now require a ``name`` attribute with a value that passes the
  :data:`~django.core.validators.validate_image_file_extension` validator.
  See the note in :meth:`.Client.post`.
  
  * :class:`~django.db.models.FileField` now moves rather than copies the file
  it receives. With the default file upload settings, files larger than
  :setting:`FILE_UPLOAD_MAX_MEMORY_SIZE` now have the same permissions as
  temporary files (often ``0o600``) rather than the system's standard umask
  (often ``0o6644``). Set the :setting:`FILE_UPLOAD_PERMISSIONS` if you need
  the same permission regardless of file size.
  
  .. _deprecated-features-1.11:
  
  Features deprecated in 1.11
  ===========================
  
  ``models.permalink()`` decorator
  --------------------------------
  
  Use :func:`django.urls.reverse` instead. For example::
  
  from django.db import models
  
  class MyModel(models.Model):
  ...
  
  models.permalink
  def url(self):
  return ('guitarist_detail', [self.slug])
  
  becomes::
  
  from django.db import models
  from django.urls import reverse
  
  class MyModel(models.Model):
  ...
  
  def url(self):
  return reverse('guitarist_detail', args=[self.slug])
  
  Miscellaneous
  -------------
  
  * ``contrib.auth``’s ``login()`` and ``logout()`` function-based views are
  deprecated in favor of new class-based views
  :class:`~django.contrib.auth.views.LoginView` and
  :class:`~django.contrib.auth.views.LogoutView`.
  
  * The unused ``extra_context`` parameter of
  ``contrib.auth.views.logout_then_login()``  is deprecated.
  
  * ``contrib.auth``’s ``password_change()``, ``password_change_done()``,
  ``password_reset()``, ``password_reset_done()``, ``password_reset_confirm()``,
  and ``password_reset_complete()`` function-based views are deprecated in favor
  of new class-based views
  :class:`~django.contrib.auth.views.PasswordChangeView`,
  :class:`~django.contrib.auth.views.PasswordChangeDoneView`,
  :class:`~django.contrib.auth.views.PasswordResetView`,
  :class:`~django.contrib.auth.views.PasswordResetDoneView`,
  :class:`~django.contrib.auth.views.PasswordResetConfirmView`, and
  :class:`~django.contrib.auth.views.PasswordResetCompleteView`.
  
  * ``django.test.runner.setup_databases()`` is moved to
  :func:`django.test.utils.setup_databases`. The old location is deprecated.
  
  * ``django.utils.translation.string_concat()`` is deprecated in
  favor of :func:`django.utils.text.format_lazy`. ``string_concat(*strings)``
  can be replaced by ``format_lazy('{}' * len(strings), *strings)``.
  
  * For the ``PyLibMCCache`` cache backend, passing ``pylibmc`` behavior settings
  as top-level attributes of ``OPTIONS`` is deprecated. Set them under a
  ``behaviors`` key within ``OPTIONS`` instead.
  
  * The ``host`` parameter of ``django.utils.http.is_safe_url()`` is deprecated
  in favor of the new ``allowed_hosts`` parameter.
  
  * Silencing exceptions raised while rendering the
  :ttag:`{% include %} <include>` template tag is deprecated as the behavior is
  often more confusing than helpful. In Django 2.1, the exception will be
  raised.
  
  * ``DatabaseIntrospection.get_indexes()`` is deprecated in favor of
  ``DatabaseIntrospection.get_constraints()``.
  
  * :func:`~django.contrib.auth.authenticate` now passes a ``request`` argument
  to the ``authenticate()`` method of authentication backends. Support for
  methods that don't accept ``request`` as the first positional argument will
  be removed in Django 2.1.
  
  * The ``USE_ETAGS`` setting is deprecated in favor of
  :class:`~django.middleware.http.ConditionalGetMiddleware` which now adds the
  ``ETag`` header to responses regardless of the setting. ``CommonMiddleware``
  and ``django.utils.cache.patch_response_headers()`` will no longer set ETags
  when the deprecation ends.
  
  * ``Model._meta.has_auto_field`` is deprecated in favor of checking if
  ``Model._meta.auto_field is not None``.
  
  * Using regular expression groups with ``iLmsu`` in ``url()`` is deprecated.
  The only group that's useful is ``(?i)`` for case-insensitive URLs, however,
  case-insensitive URLs aren't a good practice because they create multiple
  entries for search engines, for example. An alternative solution could be to
  create a :data:`~django.conf.urls.handler404` that looks for uppercase
  characters in the URL and redirects to a lowercase equivalent.
  
  * The ``renderer`` argument is added to the :meth:`Widget.render()
  <django.forms.Widget.render>` method. Methods that don't accept that argument
  will work through a deprecation period.
  
  
  ===========================

1.10.8 not secure

===========================
  
  *September 5, 2017*
  
  Django 1.10.8 fixes a security issue in 1.10.7.
  
  CVE-2017-12794: Possible XSS in traceback section of technical 500 debug page
  =============================================================================
  
  In older versions, HTML autoescaping was disabled in a portion of the template
  for the technical 500 debug page. Given the right circumstances, this allowed
  a cross-site scripting attack. This vulnerability shouldn't affect most
  production sites since you shouldn't run with ``DEBUG = True`` (which makes
  this page accessible) in your production settings.
  
  
  ===========================

1.10.7 not secure

===========================
  
  *April 4, 2017*
  
  Django 1.10.7 fixes two security issues and a bug in 1.10.6.
  
  CVE-2017-7233: Open redirect and possible XSS attack via user-supplied numeric redirect URLs
  ============================================================================================
  
  Django relies on user input in some cases  (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security check for these
  redirects (namely ``django.utils.http.is_safe_url()``) considered some numeric
  URLs (e.g. ``http:999999999``) "safe" when they shouldn't be.
  
  Also, if a developer relies on ``is_safe_url()`` to provide safe redirect
  targets and puts such a URL into a link, they could suffer from an XSS attack.
  
  CVE-2017-7234: Open redirect vulnerability in ``django.views.static.serve()``
  =============================================================================
  
  A maliciously crafted URL to a Django site using the
  :func:`~django.views.static.serve` view could redirect to any other domain. The
  view no longer does any redirects as they don't provide any known, useful
  functionality.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid.
  
  Bugfixes
  ========
  
  * Made admin's ``RelatedFieldWidgetWrapper`` use the wrapped widget's
  ``value_omitted_from_data()`` method (:ticket:`27905`).
  
  * Fixed model form ``default`` fallback for ``SelectMultiple``
  (:ticket:`27993`).
  
  
  ===========================

1.10.6 not secure

===========================
  
  *March 1, 2017*
  
  Django 1.10.6 fixes several bugs in 1.10.5.
  
  Bugfixes
  ========
  
  * Fixed ``ClearableFileInput``’s "Clear" checkbox on model form fields where
  the model field has a ``default`` (:ticket:`27805`).
  
  * Fixed ``RequestDataTooBig`` and ``TooManyFieldsSent`` exceptions crashing
  rather than generating a bad request response (:ticket:`27820`).
  
  * Fixed a crash on Oracle and PostgreSQL when subtracting ``DurationField``
  or ``IntegerField`` from ``DateField`` (:ticket:`27828`).
  
  * Fixed query expression date subtraction accuracy on PostgreSQL for
  differences larger than a month (:ticket:`27856`).
  
  * Fixed a ``GDALException`` raised by ``GDALClose`` on GDAL ≥ 2.0
  (:ticket:`27479`).
  
  
  ===========================

1.10.5 not secure

===========================
  
  *January 4, 2017*
  
  Django 1.10.5 fixes several bugs in 1.10.4.
  
  Bugfixes
  ========
  
  * Fixed a crash in the debug view if ``request.user`` can't be retrieved, such
  as if the database is unavailable (:ticket:`27567`).
  
  * Fixed occasional missing plural forms in ``JavaScriptCatalog``
  (:ticket:`27418`).
  
  * Fixed a regression in the ``timesince`` and ``timeuntil`` filters that caused
  incorrect results for dates in a leap year (:ticket:`27637`).
  
  * Fixed a regression where ``collectstatic`` overwrote newer files in remote
  storages (:ticket:`27658`).
  
  
  ===========================

1.10.4 not secure

===========================
  
  *December 1, 2016*
  
  Django 1.10.4 fixes several bugs in 1.10.3.
  
  Bugfixes
  ========
  
  * Quoted the Oracle test user's password in queries to fix the "ORA-00922:
  missing or invalid option" error when the password starts with a number or
  special character (:ticket:`27420`).
  
  * Fixed incorrect ``app_label`` / ``model_name`` arguments for
  ``allow_migrate()`` in ``makemigrations`` migration consistency checks
  (:ticket:`27461`).
  
  * Made ``Model.delete(keep_parents=True)`` preserve parent reverse
  relationships in multi-table inheritance (:ticket:`27407`).
  
  * Fixed a ``QuerySet.update()`` crash on SQLite when updating a
  ``DateTimeField`` with an ``F()`` expression and a ``timedelta``
  (:ticket:`27544`).
  
  * Prevented ``LocaleMiddleware`` from redirecting on URLs that should return
  404 when using ``prefix_default_language=False`` (:ticket:`27402`).
  
  * Prevented an unnecessary index from being created on an InnoDB ``ForeignKey``
  when the field was added after the model was created (:ticket:`27558`).
  
  
  ===========================

1.10.3 not secure

===========================
  
  *November 1, 2016*
  
  Django 1.10.3 fixes two security issues and several bugs in 1.10.2.
  
  User with hardcoded password created when running tests on Oracle
  =================================================================
  
  When running tests with an Oracle database, Django creates a temporary database
  user. In older versions, if a password isn't manually specified in the database
  settings ``TEST`` dictionary, a hardcoded password is used. This could allow
  an attacker with network access to the database server to connect.
  
  This user is usually dropped after the test suite completes, but not when using
  the ``manage.py test --keepdb`` option or if the user has an active session
  (such as an attacker's connection).
  
  A randomly generated password is now used for each test run.
  
  DNS rebinding vulnerability when ``DEBUG=True``
  ===============================================
  
  Older versions of Django don't validate the ``Host`` header against
  ``settings.ALLOWED_HOSTS`` when ``settings.DEBUG=True``. This makes them
  vulnerable to a `DNS rebinding attack
  <https://benmmurphy.github.io/blog/2016/07/11/rails-webconsole-dns-rebinding/>`_.
  
  While Django doesn't ship a module that allows remote code execution, this is
  at least a cross-site scripting vector, which could be quite serious if
  developers load a copy of the production database in development or connect to
  some production services for which there's no development instance, for
  example. If a project uses a package like the ``django-debug-toolbar``, then
  the attacker could execute arbitrary SQL, which could be especially bad if the
  developers connect to the database with a superuser account.
  
  ``settings.ALLOWED_HOSTS`` is now validated regardless of ``DEBUG``. For
  convenience, if ``ALLOWED_HOSTS`` is empty and ``DEBUG=True``, the following
  variations of localhost are allowed ``['localhost', '127.0.0.1', '::1']``. If
  your local settings file has your production ``ALLOWED_HOSTS`` value, you must
  now omit it to get those fallback values.
  
  Bugfixes
  ========
  
  * Allowed ``User.is_authenticated`` and ``User.is_anonymous`` properties to be
  tested for ``set`` membership (:ticket:`27309`).
  
  * Fixed a performance regression when running ``migrate`` in projects
  with ``RenameModel`` operations (:ticket:`27279`).
  
  * Added ``model_name`` to the ``allow_migrate()`` calls in ``makemigrations``
  (:ticket:`27200`).
  
  * Made the ``JavaScriptCatalog`` view respect the ``packages`` argument;
  previously it was ignored (:ticket:`27374`).
  
  * Fixed ``QuerySet.bulk_create()`` on PostgreSQL when the number of objects is
  a multiple plus one of ``batch_size`` (:ticket:`27385`).
  
  * Prevented ``i18n_patterns()`` from using too much of the URL as the language
  to fix a use case for ``prefix_default_language=False`` (:ticket:`27063`).
  
  * Replaced a possibly incorrect redirect from ``SessionMiddleware`` when a
  session is destroyed in a concurrent request with a ``SuspiciousOperation``
  to indicate that the request can't be completed (:ticket:`27363`).
  
  
  ===========================

1.10.2 not secure

===========================
  
  *October 1, 2016*
  
  Django 1.10.2 fixes several bugs in 1.10.1.
  
  Bugfixes
  ========
  
  * Fixed a crash in MySQL database validation where ``SELECT sql_mode``
  doesn't return a result (:ticket:`27180`).
  
  * Allowed combining ``contrib.postgres.search.SearchQuery`` with more than one
  ``&`` or ``|`` operators (:ticket:`27143`).
  
  * Disabled system check for URL patterns beginning with a '/' when
  ``APPEND_SLASH=False`` (:ticket:`27238`).
  
  * Fixed model form ``default`` fallback for ``CheckboxSelectMultiple``,
  ``MultiWidget``, ``FileInput``, ``SplitDateTimeWidget``, ``SelectDateWidget``,
  and ``SplitArrayWidget`` (:ticket:`27186`). Custom widgets affected by this
  issue should implement :meth:`~django.forms.Widget.value_omitted_from_data`.
  
  * Fixed a crash in ``runserver`` logging during a "Broken pipe" error
  (:ticket:`27271`).
  
  * Fixed a regression where unchanged localized date/time fields were listed as
  changed in the admin's model history messages (:ticket:`27302`).
  
  
  ===========================

1.10.1 not secure

===========================
  
  *September 1, 2016*
  
  Django 1.10.1 fixes several bugs in 1.10.
  
  Bugfixes
  ========
  
  * Fixed a crash in MySQL connections where ``SELECT SQL_AUTO_IS_NULL``
  doesn't return a result (:ticket:`26991`).
  
  * Allowed ``User.is_authenticated`` and ``User.is_anonymous`` properties to be
  compared using ``==``, ``!=``, and ``|`` (:ticket:`26988`, :ticket:`27154`).
  
  * Removed the broken ``BaseCommand.usage()`` method which was for
  ``optparse`` support (:ticket:`27000`).
  
  * Fixed a checks framework crash with an empty ``Meta.default_permissions``
  (:ticket:`26997`).
  
  * Fixed a regression in the number of queries when using ``RadioSelect`` with a
  ``ModelChoiceField`` form field (:ticket:`27001`).
  
  * Fixed a crash if ``request.META['CONTENT_LENGTH']`` is an empty string
  (:ticket:`27005`).
  
  * Fixed the ``isnull`` lookup on a ``ForeignKey`` with its ``to_field``
  pointing to a ``CharField`` or pointing to a ``CharField`` defined with
  ``primary_key=True`` (:ticket:`26983`).
  
  * Prevented the ``migrate`` command from raising
  ``InconsistentMigrationHistory`` in the presence of unapplied squashed
  migrations (:ticket:`27004`).
  
  * Fixed a regression in ``Client.force_login()`` which required specifying a
  ``backend`` rather than automatically using the first one if multiple
  backends are configured (:ticket:`27027`).
  
  * Made ``QuerySet.bulk_create()`` properly initialize model instances on
  backends, such as PostgreSQL, that support returning the IDs of the created
  records so that many-to-many relationships can be used on the new objects
  (:ticket:`27026`).
  
  * Fixed crash of ``django.views.static.serve()`` with ``show_indexes`` enabled
  (:ticket:`26973`).
  
  * Fixed ``ClearableFileInput`` to avoid the ``required`` HTML attribute when
  initial data exists (:ticket:`27037`).
  
  * Fixed annotations with database functions when combined with lookups on
  PostGIS (:ticket:`27014`).
  
  * Reallowed the ``{% for %}`` tag to unpack any iterable (:ticket:`27058`).
  
  * Made ``makemigrations`` skip inconsistent history checks on non-default
  databases if database routers aren't in use or if no apps can be migrated
  to the database (:ticket:`27054`, :ticket:`27110`, :ticket:`27142`).
  
  * Removed duplicated managers in ``Model._meta.managers`` (:ticket:`27073`).
  
  * Fixed ``contrib.admindocs`` crash when a view is in a class, such as some of
  the admin views (:ticket:`27018`).
  
  * Reverted a few admin checks that checked ``field.many_to_many`` back to
  ``isinstance(field, models.ManyToManyField)`` since it turned out the checks
  weren't suitable to be generalized like that (:ticket:`26998`).
  
  * Added the database alias to the ``InconsistentMigrationHistory`` message
  raised by ``makemigrations`` and ``migrate`` (:ticket:`27089`).
  
  * Fixed the creation of ``ContentType`` and ``Permission`` objects for models
  of applications without migrations when calling the ``migrate`` command with
  no migrations to apply (:ticket:`27044`).
  
  * Included the already applied migration state changes in the ``Apps`` instance
  provided to the ``pre_migrate`` signal receivers to allow ``ContentType``
  renaming to be performed on model rename (:ticket:`27100`).
  
  * Reallowed subclassing ``UserCreationForm`` without ``USERNAME_FIELD`` in
  ``Meta.fields`` (:ticket:`27111`).
  
  * Fixed a regression in model forms where model fields with a ``default`` that
  didn't appear in POST data no longer used the ``default`` (:ticket:`27039`).
  
  
  =========================

1.10 not secure

=========================
  
  *August 1, 2016*
  
  Welcome to Django 1.10!
  
  These release notes cover the :ref:`new features <whats-new-1.10>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.10>` you'll
  want to be aware of when upgrading from Django 1.9 or older versions. We've
  :ref:`dropped some features <removed-features-1.10>` that have reached the end
  of their deprecation cycle, and we've :ref:`begun the deprecation process for
  some features <deprecated-features-1.10>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Like Django 1.9, Django 1.10 requires Python 2.7, 3.4, or 3.5. We **highly
  recommend** and only officially support the latest release of each series.
  
  .. _whats-new-1.10:
  
  What's new in Django 1.10
  =========================
  
  Full text search for PostgreSQL
  -------------------------------
  
  ``django.contrib.postgres`` now includes a :doc:`collection of database
  functions </ref/contrib/postgres/search>` to allow the use of the full text
  search engine. You can search across multiple fields in your relational
  database, combine the searches with other lookups, use different language
  configurations and weightings, and rank the results by relevance.
  
  It also now includes trigram support, using the :lookup:`trigram_similar`
  lookup, and the :class:`~django.contrib.postgres.search.TrigramSimilarity` and
  :class:`~django.contrib.postgres.search.TrigramDistance` expressions.
  
  New-style middleware
  --------------------
  
  :doc:`A new style of middleware is introduced </topics/http/middleware>` to
  solve the lack of strict request/response layering of the old-style of
  middleware described in `DEP 0005
  <https://github.com/django/deps/blob/master/final/0005-improved-middleware.rst>`_.
  You'll need to :ref:`adapt old, custom middleware <upgrading-middleware>` and
  switch from the ``MIDDLEWARE_CLASSES`` setting to the new :setting:`MIDDLEWARE`
  setting to take advantage of the improvements.
  
  Official support for Unicode usernames
  --------------------------------------
  
  The :class:`~django.contrib.auth.models.User` model in ``django.contrib.auth``
  originally only accepted ASCII letters and numbers in usernames. Although it
  wasn't a deliberate choice, Unicode characters have always been accepted when
  using Python 3.
  
  The username validator now explicitly accepts Unicode characters by
  default on Python 3 only.
  
  Custom user models may use the new
  :class:`~django.contrib.auth.validators.ASCIIUsernameValidator` or
  :class:`~django.contrib.auth.validators.UnicodeUsernameValidator`.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * For sites running on a subpath, the default :attr:`URL for the "View site"
  link <django.contrib.admin.AdminSite.site_url>` at the top of each admin page
  will now point to ``request.META['SCRIPT_NAME']`` if set, instead of ``/``.
  
  * The success message that appears after adding or editing an object now
  contains a link to the object's change form.
  
  * All inline JavaScript is removed so you can enable the
  ``Content-Security-Policy`` HTTP header if you wish.
  
  * The new :attr:`InlineModelAdmin.classes
  <django.contrib.admin.InlineModelAdmin.classes>` attribute allows specifying
  classes on inline fieldsets. Inlines with a ``collapse`` class will be
  initially collapsed and their header will have a small "show" link.
  
  * If a user doesn't have the add permission, the ``object-tools`` block on a
  model's changelist will now be rendered (without the add button). This makes
  it easier to add custom tools in this case.
  
  * The :class:`~django.contrib.admin.models.LogEntry` model now stores change
  messages in a JSON structure so that the message can be dynamically translated
  using the current active language. A new ``LogEntry.get_change_message()``
  method is now the preferred way of retrieving the change message.
  
  * Selected objects for fields in ``ModelAdmin.raw_id_fields`` now have a link
  to object's change form.
  
  * Added "No date" and "Has date" choices for ``DateFieldListFilter`` if the
  field is nullable.
  
  * The jQuery library embedded in the admin is upgraded from version 2.1.4 to
  2.2.3.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added support for the :ref:`Argon2 password hash <argon2_usage>`. It's
  recommended over PBKDF2, however, it's not the default as it requires a
  third-party library.
  
  * The default iteration count for the PBKDF2 password hasher has been increased
  by 25%. This backwards compatible change will not affect users who have
  subclassed ``django.contrib.auth.hashers.PBKDF2PasswordHasher`` to change the
  default value.
  
  * The ``django.contrib.auth.views.logout()`` view sends "no-cache" headers
  to prevent an issue where Safari caches redirects and prevents a user from
  being able to log out.
  
  * Added the optional ``backend`` argument to :func:`django.contrib.auth.login`
  to allow using it without credentials.
  
  * The new :setting:`LOGOUT_REDIRECT_URL` setting controls the redirect of the
  ``django.contrib.auth.views.logout()`` view, if the view doesn't get a
  ``next_page`` argument.
  
  * The new ``redirect_authenticated_user`` parameter for the
  ``django.contrib.auth.views.login()`` view allows redirecting
  authenticated users visiting the login page.
  
  * The new :class:`~django.contrib.auth.backends.AllowAllUsersModelBackend` and
  :class:`~django.contrib.auth.backends.AllowAllUsersRemoteUserBackend` ignore
  the value of ``User.is_active``, while
  :class:`~django.contrib.auth.backends.ModelBackend` and
  :class:`~django.contrib.auth.backends.RemoteUserBackend` now reject inactive
  users.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :ref:`Distance lookups <distance-lookups>` now accept expressions as the
  distance value parameter.
  
  * The new :attr:`GEOSGeometry.unary_union
  <django.contrib.gis.geos.GEOSGeometry.unary_union>` property computes the
  union of all the elements of this geometry.
  
  * Added the :meth:`GEOSGeometry.covers()
  <django.contrib.gis.geos.GEOSGeometry.covers>` binary predicate.
  
  * Added the :meth:`GDALBand.statistics()
  <django.contrib.gis.gdal.GDALBand.statistics>` method and
  :attr:`~django.contrib.gis.gdal.GDALBand.mean`
  and :attr:`~django.contrib.gis.gdal.GDALBand.std` attributes.
  
  * Added support for the :class:`~django.contrib.gis.db.models.MakeLine`
  aggregate and :class:`~django.contrib.gis.db.models.functions.GeoHash`
  function on SpatiaLite.
  
  * Added support for the
  :class:`~django.contrib.gis.db.models.functions.Difference`,
  :class:`~django.contrib.gis.db.models.functions.Intersection`, and
  :class:`~django.contrib.gis.db.models.functions.SymDifference`
  functions on MySQL.
  
  * Added support for instantiating empty GEOS geometries.
  
  * The new :attr:`~django.contrib.gis.geos.WKTWriter.trim` and
  :attr:`~django.contrib.gis.geos.WKTWriter.precision` properties
  of :class:`~django.contrib.gis.geos.WKTWriter` allow controlling
  output of the fractional part of the coordinates in WKT.
  
  * Added the :attr:`LineString.closed
  <django.contrib.gis.geos.LineString.closed>` and
  :attr:`MultiLineString.closed
  <django.contrib.gis.geos.MultiLineString.closed>` properties.
  
  * The :doc:`GeoJSON serializer </ref/contrib/gis/serializers>` now outputs the
  primary key of objects in the ``properties`` dictionary if specific fields
  aren't specified.
  
  * The ability to replicate input data on the :meth:`GDALBand.data()
  <django.contrib.gis.gdal.GDALBand.data>` method was added. Band data can
  now be updated with repeated values efficiently.
  
  * Added database functions
  :class:`~django.contrib.gis.db.models.functions.IsValid` and
  :class:`~django.contrib.gis.db.models.functions.MakeValid`, as well as the
  :lookup:`isvalid` lookup, all for PostGIS. This allows filtering and
  repairing invalid geometries on the database side.
  
  * Added raster support for all :doc:`spatial lookups
  </ref/contrib/gis/geoquerysets>`.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * For convenience, :class:`~django.contrib.postgres.fields.HStoreField` now
  casts its keys and values to strings.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :djadmin:`clearsessions` management command now removes file-based
  sessions.
  
  :mod:`django.contrib.sites`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :class:`~django.contrib.sites.models.Site` model now supports
  :ref:`natural keys <topics-serialization-natural-keys>`.
  
  :mod:`django.contrib.staticfiles`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :ttag:`static` template tag now uses ``django.contrib.staticfiles``
  if it's in ``INSTALLED_APPS``. This is especially useful for third-party apps
  which can now always use ``{% load static %}`` (instead of
  ``{% load staticfiles %}`` or ``{% load static from staticfiles %}``) and
  not worry about whether or not the ``staticfiles`` app is installed.
  
  * You can :ref:`more easily customize <customize-staticfiles-ignore-patterns>`
  the ``collectstatic --ignore`` option with a custom ``AppConfig``.
  
  Cache
  ~~~~~
  
  * The file-based cache backend now uses the highest pickling protocol.
  
  CSRF
  ~~~~
  
  * The default :setting:`CSRF_FAILURE_VIEW`, ``views.csrf.csrf_failure()`` now
  accepts an optional ``template_name`` parameter, defaulting to
  ``'403_csrf.html'``, to control the template used to render the page.
  
  * To protect against `BREACH`_ attacks, the CSRF protection mechanism now
  changes the form token value on every request (while keeping an invariant
  secret which can be used to validate the different tokens).
  
  .. _BREACH: http://breachattack.com/
  
  Database backends
  ~~~~~~~~~~~~~~~~~
  
  * Temporal data subtraction was unified on all backends.
  
  * If the database supports it, backends can set
  ``DatabaseFeatures.can_return_ids_from_bulk_insert=True`` and implement
  ``DatabaseOperations.fetch_returned_insert_ids()`` to set primary keys
  on objects created using ``QuerySet.bulk_create()``.
  
  * Added keyword arguments to the ``as_sql()`` methods of various expressions
  (``Func``, ``When``, ``Case``, and ``OrderBy``) to allow database backends to
  customize them without mutating ``self``, which isn't safe when using
  different database backends. See the ``arg_joiner`` and ``**extra_context``
  parameters of :meth:`Func.as_sql() <django.db.models.Func.as_sql>` for an
  example.
  
  File Storage
  ~~~~~~~~~~~~
  
  * Storage backends now present a timezone-aware API with new methods
  :meth:`~django.core.files.storage.Storage.get_accessed_time`,
  :meth:`~django.core.files.storage.Storage.get_created_time`, and
  :meth:`~django.core.files.storage.Storage.get_modified_time`. They return a
  timezone-aware ``datetime`` if :setting:`USE_TZ` is ``True`` and a naive
  ``datetime`` in the local timezone otherwise.
  
  * The new :meth:`Storage.generate_filename()
  <django.core.files.storage.Storage.generate_filename>` method makes it easier
  to implement custom storages that don't use the ``os.path`` calls previously
  in :class:`~django.db.models.FileField`.
  
  Forms
  ~~~~~
  
  * Form and widget ``Media`` is now served using
  :mod:`django.contrib.staticfiles` if installed.
  
  * The ``<input>`` tag rendered by :class:`~django.forms.CharField` now includes
  a ``minlength`` attribute if the field has a ``min_length``.
  
  * Required form fields now have the ``required`` HTML attribute. Set the new
  :attr:`Form.use_required_attribute <django.forms.Form.use_required_attribute>`
  attribute to ``False`` to disable it. The ``required`` attribute isn't
  included on forms of formsets because the browser validation may not be
  correct when adding and deleting formsets.
  
  Generic Views
  ~~~~~~~~~~~~~
  
  * The :class:`~django.views.generic.base.View` class can now be imported from
  ``django.views``.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * The :func:`~django.conf.urls.i18n.i18n_patterns` helper function can now be
  used in a root URLConf specified using :attr:`request.urlconf
  <django.http.HttpRequest.urlconf>`.
  
  * By setting the new ``prefix_default_language`` parameter for
  :func:`~django.conf.urls.i18n.i18n_patterns` to ``False``, you can allow
  accessing the default language without a URL prefix.
  
  * :func:`~django.views.i18n.set_language` now returns a 204 status code (No
  Content) for AJAX requests when there is no ``next`` parameter in ``POST`` or
  ``GET``.
  
  * The :class:`~django.views.i18n.JavaScriptCatalog` and
  :class:`~django.views.i18n.JSONCatalog` class-based views supersede the
  deprecated ``javascript_catalog()`` and ``json_catalog()`` function-based
  views. The new views are almost equivalent to the old ones except that by
  default the new views collect all JavaScript strings in the ``djangojs``
  translation domain from all installed apps rather than only the JavaScript
  strings from :setting:`LOCALE_PATHS`.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * :func:`~django.core.management.call_command` now returns the value returned
  from the ``command.handle()`` method.
  
  * The new :option:`check --fail-level` option allows specifying the message
  level that will cause the command to exit with a non-zero status.
  
  * The new :option:`makemigrations --check` option makes the command exit
  with a non-zero status when model changes without migrations are detected.
  
  * :djadmin:`makemigrations` now displays the path to the migration files that
  it generates.
  
  * The :option:`shell --interface` option now accepts ``python`` to force use of
  the "plain" Python interpreter.
  
  * The new :option:`shell --command` option lets you run a command as Django and
  exit, instead of opening the interactive shell.
  
  * Added a warning to :djadmin:`dumpdata` if a proxy model is specified (which
  results in no output) without its concrete parent.
  
  * The new :attr:`BaseCommand.requires_migrations_checks
  <django.core.management.BaseCommand.requires_migrations_checks>` attribute
  may be set to ``True`` if you want your command to print a warning, like
  :djadmin:`runserver` does, if the set of migrations on disk don't match the
  migrations in the database.
  
  * To assist with testing, :func:`~django.core.management.call_command` now
  accepts a command object as the first argument.
  
  * The :djadmin:`shell` command supports tab completion on systems using
  ``libedit``, e.g. macOS.
  
  * The :djadmin:`inspectdb` command lets you choose what tables should be
  inspected by specifying their names as arguments.
  
  Migrations
  ~~~~~~~~~~
  
  * Added support for serialization of ``enum.Enum`` objects.
  
  * Added the ``elidable`` argument to the
  :class:`~django.db.migrations.operations.RunSQL` and
  :class:`~django.db.migrations.operations.RunPython` operations to allow them
  to be removed when squashing migrations.
  
  * Added support for :ref:`non-atomic migrations <non-atomic-migrations>` by
  setting the ``atomic`` attribute on a ``Migration``.
  
  * The ``migrate`` and ``makemigrations`` commands now :ref:`check for a
  consistent migration history <migration-history-consistency>`. If they find
  some unapplied dependencies of an applied migration,
  ``InconsistentMigrationHistory`` is raised.
  
  * The :func:`~django.db.models.signals.pre_migrate` and
  :func:`~django.db.models.signals.post_migrate` signals now dispatch their
  migration ``plan`` and ``apps``.
  
  Models
  ~~~~~~
  
  * Reverse foreign keys from proxy models are now propagated to their
  concrete class. The reverse relation attached by a
  :class:`~django.db.models.ForeignKey` pointing to a proxy model is now
  accessible as a descriptor on the proxied model class and may be referenced in
  queryset filtering.
  
  * The new :meth:`Field.rel_db_type() <django.db.models.Field.rel_db_type>`
  method returns the database column data type for fields such as ``ForeignKey``
  and ``OneToOneField`` that point to another field.
  
  * The :attr:`~django.db.models.Func.arity` class attribute is added to
  :class:`~django.db.models.Func`. This attribute can be used to set the number
  of arguments the function accepts.
  
  * Added :class:`~django.db.models.BigAutoField` which acts much like an
  :class:`~django.db.models.AutoField` except that it is guaranteed
  to fit numbers from ``1`` to ``9223372036854775807``.
  
  * :meth:`QuerySet.in_bulk() <django.db.models.query.QuerySet.in_bulk>`
  may be called without any arguments to return all objects in the queryset.
  
  * :attr:`~django.db.models.ForeignKey.related_query_name` now supports
  app label and class interpolation using the ``'%(app_label)s'`` and
  ``'%(class)s'`` strings.
  
  * Allowed overriding model fields inherited from abstract base classes.
  
  * The :func:`~django.db.models.prefetch_related_objects` function is now a
  public API.
  
  * :meth:`QuerySet.bulk_create() <django.db.models.query.QuerySet.bulk_create>`
  sets the primary key on objects when using PostgreSQL.
  
  * Added the :class:`~django.db.models.functions.Cast` database function.
  
  * A proxy model may now inherit multiple proxy models that share a common
  non-abstract parent class.
  
  * Added :class:`~django.db.models.functions.Extract` functions to extract
  datetime components as integers, such as year and hour.
  
  * Added :class:`~django.db.models.functions.Trunc` functions to truncate a date
  or datetime to a significant component. They enable queries like
  sales-per-day or sales-per-hour.
  
  * ``Model.__init__()`` now sets values of virtual fields from its keyword
  arguments.
  
  * The new :attr:`Meta.base_manager_name
  <django.db.models.Options.base_manager_name>` and
  :attr:`Meta.default_manager_name
  <django.db.models.Options.default_manager_name>` options allow controlling
  the :attr:`~django.db.models.Model._base_manager` and
  :attr:`~django.db.models.Model._default_manager`, respectively.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Added ``request.user`` to the debug view.
  
  * Added :class:`~django.http.HttpResponse` methods
  :meth:`~django.http.HttpResponse.readable()` and
  :meth:`~django.http.HttpResponse.seekable()` to make an instance a
  stream-like object and allow wrapping it with :py:class:`io.TextIOWrapper`.
  
  * Added the :attr:`HttpRequest.content_type
  <django.http.HttpRequest.content_type>` and
  :attr:`~django.http.HttpRequest.content_params` attributes which are
  parsed from the ``CONTENT_TYPE`` header.
  
  * The parser for ``request.COOKIES`` is simplified to better match the behavior
  of browsers. ``request.COOKIES`` may now contain cookies that are invalid
  according to :rfc:`6265` but are possible to set via ``document.cookie``.
  
  Serialization
  ~~~~~~~~~~~~~
  
  * The ``django.core.serializers.json.DjangoJSONEncoder`` now knows how to
  serialize lazy strings, typically used for translatable content.
  
  Templates
  ~~~~~~~~~
  
  * Added the ``autoescape`` option to the
  :class:`~django.template.backends.django.DjangoTemplates` backend and the
  :class:`~django.template.Engine` class.
  
  * Added the ``is`` and ``is not`` comparison operators to the :ttag:`if` tag.
  
  * Allowed :tfilter:`dictsort` to order a list of lists by an element at a
  specified index.
  
  * The :func:`~django.template.context_processors.debug` context processor
  contains queries for all database aliases instead of only the default alias.
  
  * Added relative path support for string arguments of the :ttag:`extends` and
  :ttag:`include` template tags.
  
  Tests
  ~~~~~
  
  * To better catch bugs, :class:`~django.test.TestCase` now checks deferrable
  database constraints at the end of each test.
  
  * Tests and test cases can be :ref:`marked with tags <topics-tagging-tests>`
  and run selectively with the new :option:`test --tag` and :option:`test
  --exclude-tag` options.
  
  * You can now login and use sessions with the test client even if
  :mod:`django.contrib.sessions` is not in :setting:`INSTALLED_APPS`.
  
  URLs
  ~~~~
  
  * An addition in :func:`django.setup()` allows URL resolving that happens
  outside of the request/response cycle (e.g. in management commands and
  standalone scripts) to take :setting:`FORCE_SCRIPT_NAME` into account when it
  is set.
  
  Validators
  ~~~~~~~~~~
  
  * :class:`~django.core.validators.URLValidator` now limits the length of
  domain name labels to 63 characters and the total length of domain
  names to 253 characters per :rfc:`1034`.
  
  * :func:`~django.core.validators.int_list_validator` now accepts an optional
  ``allow_negative`` boolean parameter, defaulting to ``False``, to allow
  negative integers.
  
  .. _backwards-incompatible-1.10:
  
  Backwards incompatible changes in 1.10
  ======================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`removed-features-1.10` for the features that have reached the end of
  their deprecation cycle and therefore been removed. If you haven't updated
  your code within the deprecation timeline for a given feature, its removal
  may appear as a backwards incompatible change.
  
  Database backend API
  --------------------
  
  * GIS's ``AreaField`` uses an unspecified underlying numeric type that could in
  practice be any numeric Python type. ``decimal.Decimal`` values retrieved
  from the database are now converted to ``float`` to make it easier to combine
  them with values used by the GIS libraries.
  
  * In order to enable temporal subtraction you must set the
  ``supports_temporal_subtraction`` database feature flag to ``True`` and
  implement the ``DatabaseOperations.subtract_temporals()`` method. This
  method should return the SQL and parameters required to compute the
  difference in microseconds between the ``lhs`` and ``rhs`` arguments in the
  datatype used to store :class:`~django.db.models.DurationField`.
  
  ``select_related()`` prohibits non-relational fields for nested relations
  -------------------------------------------------------------------------
  
  Django 1.8 added validation for non-relational fields in ``select_related()``::
  
  >>> Book.objects.select_related('title')
  Traceback (most recent call last):
  ...
  FieldError: Non-relational field given in select_related: 'title'
  
  But it didn't prohibit nested non-relation fields as it does now::
  
  >>> Book.objects.select_related('author__name')
  Traceback (most recent call last):
  ...
  FieldError: Non-relational field given in select_related: 'name'
  
  ``_meta.get_fields()`` returns consistent reverse fields for proxy models
  -------------------------------------------------------------------------
  
  Before Django 1.10, the :meth:`~django.db.models.options.Options.get_fields`
  method returned different reverse fields when called on a proxy model compared
  to its proxied concrete class. This inconsistency was fixed by returning the
  full set of fields pointing to a concrete class or one of its proxies in both
  cases.
  
  :attr:`AbstractUser.username <django.contrib.auth.models.User.username>` ``max_length`` increased to 150
  --------------------------------------------------------------------------------------------------------
  
  A migration for :attr:`django.contrib.auth.models.User.username` is included.
  If you have a custom user model inheriting from ``AbstractUser``, you'll need
  to generate and apply a database migration for your user model.
  
  We considered an increase to 254 characters to more easily allow the use of
  email addresses (which are limited to 254 characters) as usernames but rejected
  it due to a MySQL limitation.  When using the ``utf8mb4`` encoding (recommended
  for proper Unicode support), MySQL can only create unique indexes with 191
  characters by default. Therefore, if you need a longer length, please use a
  custom user model.
  
  If you want to preserve the 30 character limit for usernames, use a custom form
  when creating a user or changing usernames::
  
  from django.contrib.auth.forms import UserCreationForm
  
  class MyUserCreationForm(UserCreationForm):
  username = forms.CharField(
  max_length=30,
  help_text='Required. 30 characters or fewer. Letters, digits and /./+/-/_ only.',
  )
  
  If you wish to keep this restriction in the admin, set ``UserAdmin.add_form``
  to use this form::
  
  from django.contrib.auth.admin import UserAdmin as BaseUserAdmin
  from django.contrib.auth.models import User
  
  class UserAdmin(BaseUserAdmin):
  add_form = MyUserCreationForm
  
  admin.site.unregister(User)
  admin.site.register(User, UserAdmin)
  
  Dropped support for PostgreSQL 9.1
  ----------------------------------
  
  Upstream support for PostgreSQL 9.1 ends in September 2016. As a consequence,
  Django 1.10 sets PostgreSQL 9.2 as the minimum version it officially supports.
  
  ``runserver`` output goes through logging
  -----------------------------------------
  
  Request and response handling of the ``runserver`` command is sent to the
  :ref:`django-server-logger` logger instead of to ``sys.stderr``. If you
  disable Django's logging configuration or override it with your own, you'll
  need to add the appropriate logging configuration if you want to see that
  output::
  
  'formatters': {
  'django.server': {
  '()': 'django.utils.log.ServerFormatter',
  'format': '[%(server_time)s] %(message)s',
  }
  },
  'handlers': {
  'django.server': {
  'level': 'INFO',
  'class': 'logging.StreamHandler',
  'formatter': 'django.server',
  },
  },
  'loggers': {
  'django.server': {
  'handlers': ['django.server'],
  'level': 'INFO',
  'propagate': False,
  }
  }
  
  ``auth.CustomUser`` and ``auth.ExtensionUser`` test models were removed
  -----------------------------------------------------------------------
  
  Since the introduction of migrations for the contrib apps in Django 1.8, the
  tables of these custom user test models were not created anymore making them
  unusable in a testing context.
  
  Apps registry is no longer auto-populated when unpickling models outside of Django
  ----------------------------------------------------------------------------------
  
  The apps registry is no longer auto-populated when unpickling models. This was
  added in Django 1.7.2 as an attempt to allow unpickling models outside of
  Django, such as in an RQ worker, without calling ``django.setup()``, but it
  creates the possibility of a deadlock. To adapt your code in the case of RQ,
  you can `provide your own worker script <https://python-rq.org/docs/workers/>`_
  that calls ``django.setup()``.
  
  Removed null assignment check for non-null foreign key fields
  -------------------------------------------------------------
  
  In older versions, assigning ``None`` to a non-nullable ``ForeignKey`` or
  ``OneToOneField`` raised ``ValueError('Cannot assign None: "model.field" does
  not allow null values.')``. For consistency with other model fields which don't
  have a similar check, this check is removed.
  
  Removed weak password hashers from the default ``PASSWORD_HASHERS`` setting
  ---------------------------------------------------------------------------
  
  Django 0.90 stored passwords as unsalted MD5. Django 0.91 added support for
  salted SHA1 with automatic upgrade of passwords when a user logs in. Django 1.4
  added PBKDF2 as the default password hasher.
  
  If you have an old Django project with MD5 or SHA1 (even salted) encoded
  passwords, be aware that these can be cracked fairly easily with today's
  hardware. To make Django users acknowledge continued use of weak hashers, the
  following hashers are removed from the default :setting:`PASSWORD_HASHERS`
  setting::
  
  'django.contrib.auth.hashers.SHA1PasswordHasher'
  'django.contrib.auth.hashers.MD5PasswordHasher'
  'django.contrib.auth.hashers.UnsaltedSHA1PasswordHasher'
  'django.contrib.auth.hashers.UnsaltedMD5PasswordHasher'
  'django.contrib.auth.hashers.CryptPasswordHasher'
  
  Consider using a :ref:`wrapped password hasher <wrapping-password-hashers>` to
  strengthen the hashes in your database. If that's not feasible, add the
  :setting:`PASSWORD_HASHERS` setting to your project and add back any hashers
  that you need.
  
  You can check if your database has any of the removed hashers like this::
  
  from django.contrib.auth import get_user_model
  User = get_user_model()
  
  Unsalted MD5/SHA1:
  User.objects.filter(password__startswith='md5$$')
  User.objects.filter(password__startswith='sha1$$')
  Salted MD5/SHA1:
  User.objects.filter(password__startswith='md5$').exclude(password__startswith='md5$$')
  User.objects.filter(password__startswith='sha1$').exclude(password__startswith='sha1$$')
  Crypt hasher:
  User.objects.filter(password__startswith='crypt$$')
  
  from django.db.models import CharField
  from django.db.models.functions import Length
  CharField.register_lookup(Length)
  Unsalted MD5 passwords might not have an 'md5$$' prefix:
  User.objects.filter(password__length=32)
  
  ``Field.get_prep_lookup()`` and ``Field.get_db_prep_lookup()`` methods are removed
  ----------------------------------------------------------------------------------
  
  If you have a custom field that implements either of these methods, register a
  custom lookup for it. For example::
  
  from django.db.models import Field
  from django.db.models.lookups import Exact
  
  class MyField(Field):
  ...
  
  class MyFieldExact(Exact):
  def get_prep_lookup(self):
  do_custom_stuff_for_myfield
  ....
  
  MyField.register_lookup(MyFieldExact)
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * Support for SpatiaLite < 3.0 and GEOS < 3.3 is dropped.
  
  * The ``add_postgis_srs()`` backwards compatibility alias for
  ``django.contrib.gis.utils.add_srs_entry()`` is removed.
  
  * On Oracle/GIS, the :class:`~django.contrib.gis.db.models.functions.Area`
  aggregate function now returns a ``float`` instead of ``decimal.Decimal``.
  (It's still wrapped in a measure of square meters.)
  
  * The default :class:`~django.contrib.gis.geos.GEOSGeometry` representation (WKT
  output) is trimmed by default. That is, instead of
  ``POINT (23.0000000000000000 5.5000000000000000)``, you'll get
  ``POINT (23 5.5)``.
  
  Maximum size of a request body and the number of GET/POST parameters is limited
  -------------------------------------------------------------------------------
  
  Two new settings help mitigate denial-of-service attacks via large requests:
  
  * :setting:`DATA_UPLOAD_MAX_MEMORY_SIZE` limits the size that a request body
  may be. File uploads don't count towards this limit.
  * :setting:`DATA_UPLOAD_MAX_NUMBER_FIELDS` limits the number of GET/POST
  parameters that are parsed.
  
  Applications that receive unusually large form posts may need to tune these
  settings.
  
  Miscellaneous
  -------------
  
  * The ``repr()`` of a ``QuerySet`` is wrapped in ``<QuerySet >`` to
  disambiguate it from a plain list when debugging.
  
  * ``utils.version.get_version()`` returns :pep:`440` compliant release
  candidate versions (e.g. '1.10rc1' instead of '1.10c1').
  
  * CSRF token values are now required to be strings of 64 alphanumerics; values
  of 32 alphanumerics, as set by older versions of Django by default, are
  automatically replaced by strings of 64 characters. Other values are
  considered invalid. This should only affect developers or users who replace
  these tokens.
  
  * The ``LOGOUT_URL`` setting is removed as Django hasn't made use of it
  since pre-1.0. If you use it in your project, you can add it to your
  project's settings. The default value was ``'/accounts/logout/'``.
  
  * Objects with a ``close()`` method such as files and generators passed to
  :class:`~django.http.HttpResponse` are now closed immediately instead of when
  the WSGI server calls ``close()`` on the response.
  
  * A redundant ``transaction.atomic()`` call in ``QuerySet.update_or_create()``
  is removed. This may affect query counts tested by
  ``TransactionTestCase.assertNumQueries()``.
  
  * Support for ``skip_validation`` in ``BaseCommand.execute(**options)`` is
  removed. Use ``skip_checks`` (added in Django 1.7) instead.
  
  * :djadmin:`loaddata` now raises a ``CommandError`` instead of showing a
  warning when the specified fixture file is not found.
  
  * Instead of directly accessing the ``LogEntry.change_message`` attribute, it's
  now better to call the ``LogEntry.get_change_message()`` method which will
  provide the message in the current language.
  
  * The default error views now raise ``TemplateDoesNotExist`` if a nonexistent
  ``template_name`` is specified.
  
  * The unused ``choices`` keyword argument of the ``Select`` and
  ``SelectMultiple`` widgets' ``render()`` method is removed. The ``choices``
  argument of the ``render_options()`` method is also removed, making
  ``selected_choices`` the first argument.
  
  * Tests that violate deferrable database constraints will now error when run on
  a database that supports deferrable constraints.
  
  * Built-in management commands now use indexing of keys in ``options``, e.g.
  ``options['verbosity']``, instead of ``options.get()`` and no longer perform
  any type coercion. This could be a problem if you're calling commands using
  ``Command.execute()`` (which bypasses the argument parser that sets a default
  value) instead of :func:`~django.core.management.call_command`. Instead of
  calling ``Command.execute()``, pass the command object as the first argument
  to ``call_command()``.
  
  * :class:`~django.contrib.auth.backends.ModelBackend` and
  :class:`~django.contrib.auth.backends.RemoteUserBackend` now reject inactive
  users. This means that inactive users can't login and will be logged
  out if they are switched from ``is_active=True`` to ``False``. If you need
  the previous behavior, use the new
  :class:`~django.contrib.auth.backends.AllowAllUsersModelBackend` or
  :class:`~django.contrib.auth.backends.AllowAllUsersRemoteUserBackend`
  in :setting:`AUTHENTICATION_BACKENDS` instead.
  
  * In light of the previous change, the test client's
  :meth:`~django.test.Client.login()` method no longer always rejects inactive
  users but instead delegates this decision to the authentication backend.
  :meth:`~django.test.Client.force_login()` also delegates the decision to the
  authentication backend, so if you're using the default backends, you need to
  use an active user.
  
  * :func:`django.views.i18n.set_language` may now return a 204 status code for
  AJAX requests.
  
  * The ``base_field`` attribute of
  :class:`~django.contrib.postgres.fields.RangeField` is now a type of field,
  not an instance of a field.  If you have created a custom subclass of
  :class:`~django.contrib.postgres.fields.RangeField`, you should change the
  ``base_field`` attribute.
  
  * Middleware classes are now initialized when the server starts rather than
  during the first request.
  
  * If you override ``is_authenticated()`` or ``is_anonymous()`` in a custom user
  model, you must convert them to attributes or properties as described in
  :ref:`the deprecation note <user-is-auth-anon-deprecation>`.
  
  * When using :attr:`ModelAdmin.save_as=True
  <django.contrib.admin.ModelAdmin.save_as>`, the "Save as new" button now
  redirects to the change view for the new object instead of to the model's
  changelist. If you need the previous behavior, set the new
  :attr:`ModelAdmin.save_as_continue
  <django.contrib.admin.ModelAdmin.save_as_continue>` attribute to ``False``.
  
  * Required form fields now have the ``required`` HTML attribute. Set the
  :attr:`Form.use_required_attribute <django.forms.Form.use_required_attribute>`
  attribute to ``False`` to disable it. You could also add the ``novalidate``
  attribute to ``<form>`` if you don't want browser validation. To disable
  the ``required`` attribute on custom widgets, override the
  :meth:`Widget.use_required_attribute() <django.forms.Widget.use_required_attribute>`
  method.
  
  * The WSGI handler no longer removes content of responses from ``HEAD``
  requests or responses with a ``status_code`` of 100-199, 204, or 304. Most
  Web servers already implement this behavior. Responses retrieved using the
  Django test client continue to have these "response fixes" applied.
  
  * ``Model.__init__()`` now receives ``django.db.models.DEFERRED`` as the value
  of deferred fields.
  
  * The ``Model._deferred`` attribute is removed as dynamic model classes when
  using ``QuerySet.defer()`` and ``only()`` is removed.
  
  * :meth:`Storage.save() <django.core.files.storage.Storage.save>` no longer
  replaces ``'\'`` with ``'/'``. This behavior is moved to
  :class:`~django.core.files.storage.FileSystemStorage` since this is a storage
  specific implementation detail. Any Windows user with a custom storage
  implementation that relies on this behavior will need to implement it in the
  custom storage's ``save()`` method.
  
  * Private :class:`~django.db.models.FileField` methods ``get_directory_name()``
  and ``get_filename()`` are no longer called (and are now deprecated) which is
  a backwards incompatible change for users overriding those methods on custom
  fields. To adapt such code, override ``FileField.generate_filename()`` or
  :meth:`Storage.generate_filename()
  <django.core.files.storage.Storage.generate_filename>` instead. It
  might be possible to use :attr:`~django.db.models.FileField.upload_to` also.
  
  * The subject of mail sent by ``AdminEmailHandler`` is no longer truncated at
  989 characters. If you were counting on a limited length, truncate the subject
  yourself.
  
  * Private expressions ``django.db.models.expressions.Date`` and ``DateTime``
  are removed. The new :class:`~django.db.models.functions.Trunc` expressions
  provide the same functionality.
  
  * The ``_base_manager`` and ``_default_manager`` attributes are removed from
  model instances. They remain accessible on the model class.
  
  * Accessing a deleted field on a model instance, e.g. after ``del obj.field``,
  reloads the field's value instead of raising ``AttributeError``.
  
  * If you subclass ``AbstractBaseUser`` and override ``clean()``, be sure it
  calls ``super()``. :meth:`.AbstractBaseUser.normalize_username` is called in
  a new :meth:`.AbstractBaseUser.clean` method.
  
  * Private API ``django.forms.models.model_to_dict()`` returns a queryset rather
  than a list of primary keys for ``ManyToManyField``\s.
  
  * If ``django.contrib.staticfiles`` is
  installed, the :ttag:`static`  template tag uses the ``staticfiles`` storage
  to construct the URL rather than simply joining the value with
  ``STATIC_ROOT``. The new approach encodes the URL, which could be
  backwards-incompatible in cases such as including a fragment in a path, e.g.
  ``{% static 'img.svgfragment' %}``, since the ` is encoded as ``%23``.
  To adapt, move the fragment outside the template tag:
  ``{% static 'img.svg' %}fragment``.
  
  * When :setting:`USE_L10N` is ``True``, localization is now applied for the
  :tfilter:`date` and :tfilter:`time` filters when no format string is
  specified. The ``DATE_FORMAT`` and ``TIME_FORMAT`` specifiers from the active
  locale are used instead of the settings of the same name.
  
  .. _deprecated-features-1.10:
  
  Features deprecated in 1.10
  ===========================
  
  Direct assignment to a reverse foreign key or many-to-many relation
  -------------------------------------------------------------------
  
  Instead of assigning related objects using direct assignment::
  
  >>> new_list = [obj1, obj2, obj3]
  >>> e.related_set = new_list
  
  Use the :meth:`~django.db.models.fields.related.RelatedManager.set` method
  added in Django 1.9::
  
  >>> e.related_set.set([obj1, obj2, obj3])
  
  This prevents confusion about an assignment resulting in an implicit save.
  
  Non-timezone-aware :class:`~django.core.files.storage.Storage` API
  ------------------------------------------------------------------
  
  The old, non-timezone-aware methods ``accessed_time()``, ``created_time()``,
  and ``modified_time()`` are deprecated in favor of the new ``get_*_time()``
  methods.
  
  Third-party storage backends should implement the new methods and mark the old
  ones as deprecated. Until then, the new ``get_*_time()`` methods on the base
  :class:`~django.core.files.storage.Storage` class convert ``datetime``\s from
  the old methods as required and emit a deprecation warning as they do so.
  
  Third-party storage backends may retain the old methods as long as they
  wish to support earlier versions of Django.
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * The ``get_srid()`` and ``set_srid()`` methods of
  :class:`~django.contrib.gis.geos.GEOSGeometry` are deprecated in favor
  of the :attr:`~django.contrib.gis.geos.GEOSGeometry.srid` property.
  
  * The ``get_x()``, ``set_x()``, ``get_y()``, ``set_y()``, ``get_z()``, and
  ``set_z()`` methods of :class:`~django.contrib.gis.geos.Point` are deprecated
  in favor of the ``x``, ``y``, and ``z`` properties.
  
  * The ``get_coords()`` and ``set_coords()`` methods of
  :class:`~django.contrib.gis.geos.Point` are deprecated in favor of the
  ``tuple`` property.
  
  * The ``cascaded_union`` property of
  :class:`~django.contrib.gis.geos.MultiPolygon` is deprecated in favor of the
  :attr:`~django.contrib.gis.geos.GEOSGeometry.unary_union` property.
  
  * The ``django.contrib.gis.utils.precision_wkt()`` function is deprecated in
  favor of :class:`~django.contrib.gis.geos.WKTWriter`.
  
  ``CommaSeparatedIntegerField`` model field
  ------------------------------------------
  
  ``CommaSeparatedIntegerField`` is deprecated in favor of
  :class:`~django.db.models.CharField` with the
  :func:`~django.core.validators.validate_comma_separated_integer_list`
  validator::
  
  from django.core.validators import validate_comma_separated_integer_list
  from django.db import models
  
  class MyModel(models.Model):
  numbers = models.CharField(..., validators=[validate_comma_separated_integer_list])
  
  If you're using Oracle, ``CharField`` uses a different database field  type
  (``NVARCHAR2``) than ``CommaSeparatedIntegerField`` (``VARCHAR2``). Depending
  on your database settings, this might imply a different encoding, and thus a
  different length (in bytes) for the same contents. If your stored values are
  longer than the 4000 byte limit of ``NVARCHAR2``, you should use ``TextField``
  (``NCLOB``) instead. In this case, if you have any queries that group by the
  field (e.g. annotating the model with an aggregation or using ``distinct()``)
  you'll need to change them (to defer the field).
  
  Using a model name as a query lookup when ``default_related_name`` is set
  -------------------------------------------------------------------------
  
  Assume the following models::
  
  from django.db import models
  
  class Foo(models.Model):
  pass
  
  class Bar(models.Model):
  foo = models.ForeignKey(Foo)
  
  class Meta:
  default_related_name = 'bars'
  
  In older versions, :attr:`~django.db.models.Options.default_related_name`
  couldn't be used as a query lookup. This is fixed and support for the old
  lookup name is deprecated. For example, since ``default_related_name`` is set
  in model ``Bar``, instead of using the model name ``bar`` as the lookup::
  
  >>> bar = Bar.objects.get(pk=1)
  >>> Foo.objects.get(bar=bar)
  
  use the default_related_name ``bars``::
  
  >>> Foo.objects.get(bars=bar)
  
  .. _search-lookup-replacement:
  
  ``__search`` query lookup
  -------------------------
  
  The ``search`` lookup, which supports MySQL only and is extremely limited in
  features, is deprecated. Replace it with a custom lookup::
  
  from django.db import models
  
  class Search(models.Lookup):
  lookup_name = 'search'
  
  def as_mysql(self, compiler, connection):
  lhs, lhs_params = self.process_lhs(compiler, connection)
  rhs, rhs_params = self.process_rhs(compiler, connection)
  params = lhs_params + rhs_params
  return 'MATCH (%s) AGAINST (%s IN BOOLEAN MODE)' % (lhs, rhs), params
  
  models.CharField.register_lookup(Search)
  models.TextField.register_lookup(Search)
  
  .. _user-is-auth-anon-deprecation:
  
  Using ``User.is_authenticated()`` and ``User.is_anonymous()`` as methods
  ------------------------------------------------------------------------
  
  The ``is_authenticated()`` and ``is_anonymous()`` methods of
  :class:`~django.contrib.auth.models.AbstractBaseUser` and
  :class:`~django.contrib.auth.models.AnonymousUser` classes are now
  properties. They will still work as methods until Django 2.0, but all usage
  in Django now uses attribute access.
  
  For example, if you use
  :class:`~django.contrib.auth.middleware.AuthenticationMiddleware` and want
  to know whether the user is currently logged-in you would use::
  
  if request.user.is_authenticated:
  ...  Do something for logged-in users.
  else:
  ...  Do something for anonymous users.
  
  instead of ``request.user.is_authenticated()``.
  
  This change avoids accidental information leakage if you forget to call the
  method, e.g.::
  
  if request.user.is_authenticated:
  return sensitive_information
  
  If you override these methods in a custom user model, you must change them to
  properties or attributes.
  
  Django uses a ``CallableBool`` object to allow these attributes to work as both
  a property and a method. Thus, until the deprecation period ends, you cannot
  compare these properties using the ``is`` operator. That is, the following
  won't work::
  
  if request.user.is_authenticated is True:
  ...
  
  Custom manager classes available through ``prefetch_related`` must define a ``_apply_rel_filters()`` method
  -----------------------------------------------------------------------------------------------------------
  
  If you defined a custom manager class available through
  :meth:`~django.db.models.query.QuerySet.prefetch_related` you must make sure
  it defines a ``_apply_rel_filters()`` method.
  
  This method must accept a :class:`~django.db.models.query.QuerySet` instance
  as its single argument and return a filtered version of the queryset for the
  model instance the manager is bound to.
  
  The "escape" half of ``django.utils.safestring``
  ------------------------------------------------
  
  The ``mark_for_escaping()`` function and the classes it uses: ``EscapeData``,
  ``EscapeBytes``, ``EscapeText``, ``EscapeString``, and ``EscapeUnicode`` are
  deprecated.
  
  As a result, the "lazy" behavior of the ``escape`` filter (where it would
  always be applied as the last filter no matter where in the filter chain it
  appeared) is deprecated. The filter will change to immediately apply
  :func:`~django.utils.html.conditional_escape` in Django 2.0.
  
  ``Manager.use_for_related_fields`` and inheritance changes
  ----------------------------------------------------------
  
  ``Manager.use_for_related_fields`` is deprecated in favor of setting
  :attr:`Meta.base_manager_name <django.db.models.Options.base_manager_name>` on
  the model.
  
  Model ``Manager`` inheritance will follow MRO inheritance rules in Django 2.0,
  changing the current behavior where managers defined on non-abstract base
  classes aren't inherited by child classes. A deprecating warning with
  instructions on how to adapt your code is raised if you have any affected
  managers. You'll either redeclare a manager from an abstract model on the child
  class to override the manager from the concrete model, or you'll set the
  model's ``Meta.manager_inheritance_from_future=True`` option to opt-in to the
  new inheritance behavior.
  
  During the deprecation period, ``use_for_related_fields`` will be honored and
  raise a warning, even if a ``base_manager_name`` is set. This allows
  third-party code to preserve legacy behavior while transitioning to the new
  API. The warning can be silenced by setting
  ``silence_use_for_related_fields_deprecation=True`` on the manager.
  
  Miscellaneous
  -------------
  
  * The ``makemigrations --exit`` option is deprecated in favor of the
  :option:`makemigrations --check` option.
  
  * ``django.utils.functional.allow_lazy()`` is deprecated in favor of the new
  :func:`~django.utils.functional.keep_lazy` function which can be used with a
  more natural decorator syntax.
  
  * The ``shell --plain`` option is deprecated in favor of ``-i python`` or
  ``--interface python``.
  
  * Importing from the ``django.core.urlresolvers`` module is deprecated in
  favor of its new location, :mod:`django.urls`.
  
  * The template ``Context.has_key()`` method is deprecated in favor of ``in``.
  
  * The private attribute ``virtual_fields`` of ``Model._meta`` is
  deprecated in favor of ``private_fields``.
  
  * The private keyword arguments ``virtual_only`` in
  ``Field.contribute_to_class()`` and ``virtual`` in
  ``Model._meta.add_field()`` are deprecated in favor of ``private_only``
  and ``private``, respectively.
  
  * The ``javascript_catalog()`` and ``json_catalog()`` views are deprecated in
  favor of class-based views :class:`~django.views.i18n.JavaScriptCatalog`
  and :class:`~django.views.i18n.JSONCatalog`.
  
  * In multi-table inheritance, implicit promotion of a ``OneToOneField`` to a
  ``parent_link`` is deprecated. Add ``parent_link=True`` to such fields.
  
  * The private API ``Widget._format_value()`` is made public and renamed to
  :meth:`~django.forms.Widget.format_value`. The old name will work
  through a deprecation period.
  
  * Private ``FileField`` methods ``get_directory_name()`` and ``get_filename()``
  are deprecated in favor of performing this work in
  :meth:`Storage.generate_filename()
  <django.core.files.storage.Storage.generate_filename>`).
  
  * Old-style middleware that uses  ``settings.MIDDLEWARE_CLASSES`` are
  deprecated. :ref:`Adapt old, custom middleware <upgrading-middleware>` and
  use the new :setting:`MIDDLEWARE` setting.
  
  .. _removed-features-1.10:
  
  Features removed in 1.10
  ========================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 1.10. See :ref:`deprecated-features-1.8` for details, including how
  to remove usage of these features.
  
  * Support for calling a ``SQLCompiler`` directly as an alias for calling its
  ``quote_name_unless_alias`` method is removed.
  
  * The ``cycle`` and ``firstof`` template tags are removed from the ``future``
  template tag library.
  
  * ``django.conf.urls.patterns()`` is removed.
  
  * Support for the ``prefix`` argument to
  ``django.conf.urls.i18n.i18n_patterns()`` is removed.
  
  * ``SimpleTestCase.urls`` is removed.
  
  * Using an incorrect count of unpacked values in the ``for`` template tag
  raises an exception rather than failing silently.
  
  * The ability to :func:`~django.urls.reverse` URLs using a dotted Python path
  is removed.
  
  * The ability to use a dotted Python path for the ``LOGIN_URL`` and
  ``LOGIN_REDIRECT_URL`` settings is removed.
  
  * Support for ``optparse`` is dropped for custom management commands.
  
  * The class ``django.core.management.NoArgsCommand`` is removed.
  
  * ``django.core.context_processors`` module is removed.
  
  * ``django.db.models.sql.aggregates`` module is removed.
  
  * ``django.contrib.gis.db.models.sql.aggregates`` module is removed.
  
  * The following methods and properties of ``django.db.sql.query.Query`` are
  removed:
  
  * Properties: ``aggregates`` and ``aggregate_select``
  * Methods: ``add_aggregate``, ``set_aggregate_mask``, and
  ``append_aggregate_mask``.
  
  * ``django.template.resolve_variable`` is removed.
  
  * The following private APIs are removed from
  :class:`django.db.models.options.Options` (``Model._meta``):
  
  * ``get_field_by_name()``
  * ``get_all_field_names()``
  * ``get_fields_with_model()``
  * ``get_concrete_fields_with_model()``
  * ``get_m2m_with_model()``
  * ``get_all_related_objects()``
  * ``get_all_related_objects_with_model()``
  * ``get_all_related_many_to_many_objects()``
  * ``get_all_related_m2m_objects_with_model()``
  
  * The ``error_message`` argument of ``django.forms.RegexField`` is removed.
  
  * The ``unordered_list`` filter no longer supports old style lists.
  
  * Support for string ``view`` arguments to ``url()`` is removed.
  
  * The backward compatible shim  to rename ``django.forms.Form._has_changed()``
  to ``has_changed()`` is removed.
  
  * The ``removetags`` template filter is removed.
  
  * The ``remove_tags()`` and ``strip_entities()`` functions in
  ``django.utils.html`` is removed.
  
  * The ``is_admin_site`` argument to
  ``django.contrib.auth.views.password_reset()`` is removed.
  
  * ``django.db.models.field.subclassing.SubfieldBase`` is removed.
  
  * ``django.utils.checksums`` is removed.
  
  * The ``original_content_type_id`` attribute on
  ``django.contrib.admin.helpers.InlineAdminForm`` is removed.
  
  * The backwards compatibility shim to allow ``FormMixin.get_form()`` to be
  defined with no default value for its ``form_class`` argument is removed.
  
  * The following settings are removed, and you must upgrade to the
  :setting:`TEMPLATES` setting:
  
  * ``ALLOWED_INCLUDE_ROOTS``
  * ``TEMPLATE_CONTEXT_PROCESSORS``
  * ``TEMPLATE_DEBUG``
  * ``TEMPLATE_DIRS``
  * ``TEMPLATE_LOADERS``
  * ``TEMPLATE_STRING_IF_INVALID``
  
  * The backwards compatibility alias ``django.template.loader.BaseLoader`` is
  removed.
  
  * Django template objects returned by
  :func:`~django.template.loader.get_template` and
  :func:`~django.template.loader.select_template` no longer accept a
  :class:`~django.template.Context` in their
  :meth:`~django.template.backends.base.Template.render()` method.
  
  * :doc:`Template response APIs </ref/template-response>` enforce the use of
  :class:`dict` and backend-dependent template objects instead of
  :class:`~django.template.Context` and :class:`~django.template.Template`
  respectively.
  
  * The ``current_app`` parameter for the following function and classes is
  removed:
  
  * ``django.shortcuts.render()``
  * ``django.template.Context()``
  * ``django.template.RequestContext()``
  * ``django.template.response.TemplateResponse()``
  
  * The ``dictionary`` and ``context_instance`` parameters for the following
  functions are removed:
  
  * ``django.shortcuts.render()``
  * ``django.shortcuts.render_to_response()``
  * ``django.template.loader.render_to_string()``
  
  * The ``dirs`` parameter for the following functions is removed:
  
  * ``django.template.loader.get_template()``
  * ``django.template.loader.select_template()``
  * ``django.shortcuts.render()``
  * ``django.shortcuts.render_to_response()``
  
  * Session verification is enabled regardless of whether or not
  ``'django.contrib.auth.middleware.SessionAuthenticationMiddleware'`` is in
  ``MIDDLEWARE_CLASSES``. ``SessionAuthenticationMiddleware`` no longer has
  any purpose and can be removed from ``MIDDLEWARE_CLASSES``. It's kept as
  a stub until Django 2.0 as a courtesy for users who don't read this note.
  
  * Private attribute ``django.db.models.Field.related`` is removed.
  
  * The ``--list`` option of the ``migrate`` management command is removed.
  
  * The ``ssi`` template tag is removed.
  
  * Support for the ``=`` comparison operator in the ``if`` template tag is
  removed.
  
  * The backwards compatibility shims to allow ``Storage.get_available_name()``
  and ``Storage.save()`` to be defined without a ``max_length`` argument are
  removed.
  
  * Support for the legacy ``%(<foo>)s`` syntax in ``ModelFormMixin.success_url``
  is removed.
  
  * ``GeoQuerySet`` aggregate methods ``collect()``, ``extent()``, ``extent3d()``,
  ``make_line()``, and ``unionagg()`` are removed.
  
  * The ability to specify ``ContentType.name`` when creating a content type
  instance is removed.
  
  * Support for the old signature of ``allow_migrate`` is removed.
  
  * Support for the syntax of ``{% cycle %}`` that uses comma-separated arguments
  is removed.
  
  * The warning that :class:`~django.core.signing.Signer` issued when given an
  invalid separator is now a ``ValueError``.
  
  
  ===========================

1.9.13 not secure

===========================
  
  *April 4, 2017*
  
  Django 1.9.13 fixes two security issues and a bug in 1.9.12. This is the final
  release of the 1.9.x series.
  
  CVE-2017-7233: Open redirect and possible XSS attack via user-supplied numeric redirect URLs
  ============================================================================================
  
  Django relies on user input in some cases  (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security check for these
  redirects (namely ``django.utils.http.is_safe_url()``) considered some numeric
  URLs (e.g. ``http:999999999``) "safe" when they shouldn't be.
  
  Also, if a developer relies on ``is_safe_url()`` to provide safe redirect
  targets and puts such a URL into a link, they could suffer from an XSS attack.
  
  CVE-2017-7234: Open redirect vulnerability in ``django.views.static.serve()``
  =============================================================================
  
  A maliciously crafted URL to a Django site using the
  :func:`~django.views.static.serve` view could redirect to any other domain. The
  view no longer does any redirects as they don't provide any known, useful
  functionality.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid.
  
  Bugfixes
  ========
  
  * Fixed a regression in the ``timesince`` and ``timeuntil`` filters that caused
  incorrect results for dates in a leap year (:ticket:`27637`).
  
  
  ===========================

1.9.12 not secure

===========================
  
  *December 1, 2016*
  
  Django 1.9.12 fixes a regression in 1.9.11.
  
  Bugfixes
  ========
  
  * Quoted the Oracle test user's password in queries to fix the "ORA-00922:
  missing or invalid option" error when the password starts with a number or
  special character (:ticket:`27420`).
  
  
  ===========================

1.9.11 not secure

===========================
  
  *November 1, 2016*
  
  Django 1.9.11 fixes two security issues in 1.9.10.
  
  User with hardcoded password created when running tests on Oracle
  =================================================================
  
  When running tests with an Oracle database, Django creates a temporary database
  user. In older versions, if a password isn't manually specified in the database
  settings ``TEST`` dictionary, a hardcoded password is used. This could allow
  an attacker with network access to the database server to connect.
  
  This user is usually dropped after the test suite completes, but not when using
  the ``manage.py test --keepdb`` option or if the user has an active session
  (such as an attacker's connection).
  
  A randomly generated password is now used for each test run.
  
  DNS rebinding vulnerability when ``DEBUG=True``
  ===============================================
  
  Older versions of Django don't validate the ``Host`` header against
  ``settings.ALLOWED_HOSTS`` when ``settings.DEBUG=True``. This makes them
  vulnerable to a `DNS rebinding attack
  <https://benmmurphy.github.io/blog/2016/07/11/rails-webconsole-dns-rebinding/>`_.
  
  While Django doesn't ship a module that allows remote code execution, this is
  at least a cross-site scripting vector, which could be quite serious if
  developers load a copy of the production database in development or connect to
  some production services for which there's no development instance, for
  example. If a project uses a package like the ``django-debug-toolbar``, then
  the attacker could execute arbitrary SQL, which could be especially bad if the
  developers connect to the database with a superuser account.
  
  ``settings.ALLOWED_HOSTS`` is now validated regardless of ``DEBUG``. For
  convenience, if ``ALLOWED_HOSTS`` is empty and ``DEBUG=True``, the following
  variations of localhost are allowed ``['localhost', '127.0.0.1', '::1']``. If
  your local settings file has your production ``ALLOWED_HOSTS`` value, you must
  now omit it to get those fallback values.
  
  
  ===========================

1.9.10 not secure

===========================
  
  *September 26, 2016*
  
  Django 1.9.10 fixes a security issue in 1.9.9.
  
  CSRF protection bypass on a site with Google Analytics
  ======================================================
  
  An interaction between Google Analytics and Django's cookie parsing could allow
  an attacker to set arbitrary cookies leading to a bypass of CSRF protection.
  
  The parser for ``request.COOKIES`` is simplified to better match the behavior
  of browsers and to mitigate this attack. ``request.COOKIES`` may now contain
  cookies that are invalid according to :rfc:`6265` but are possible to set via
  ``document.cookie``.
  
  
  ==========================

1.9.9 not secure

==========================
  
  *August 1, 2016*
  
  Django 1.9.9 fixes several bugs in 1.9.8.
  
  Bugfixes
  ========
  
  * Fixed invalid HTML in template postmortem on the debug page
  (:ticket:`26938`).
  
  * Fixed some GIS database function crashes on MySQL 5.7 (:ticket:`26657`).
  
  
  ==========================

1.9.8 not secure

==========================
  
  *July 18, 2016*
  
  Django 1.9.8 fixes a security issue and several bugs in 1.9.7.
  
  XSS in admin's add/change related popup
  =======================================
  
  Unsafe usage of JavaScript's ``Element.innerHTML`` could result in XSS in the
  admin's add/change related popup. ``Element.textContent`` is now used to
  prevent execution of the data.
  
  The debug view also used ``innerHTML``. Although a security issue wasn't
  identified there, out of an abundance of caution it's also updated to use
  ``textContent``.
  
  Bugfixes
  ========
  
  * Fixed missing ``varchar/text_pattern_ops`` index on ``CharField`` and
  ``TextField`` respectively when using ``AddField`` on PostgreSQL
  (:ticket:`26889`).
  
  * Fixed ``makemessages`` crash on Python 2 with non-ASCII file names
  (:ticket:`26897`).
  
  
  ==========================

1.9.7 not secure

==========================
  
  *June 4, 2016*
  
  Django 1.9.7 fixes several bugs in 1.9.6.
  
  Bugfixes
  ========
  
  * Removed the need for the ``request`` context processor on the admin login
  page to fix a regression in 1.9 (:ticket:`26558`).
  
  * Fixed translation of password validators' ``help_text`` in forms
  (:ticket:`26544`).
  
  * Fixed a regression causing the cached template loader to crash when using
  lazy template names (:ticket:`26603`).
  
  * Fixed ``on_commit`` callbacks execution order when callbacks make
  transactions (:ticket:`26627`).
  
  * Fixed ``HStoreField`` to raise a ``ValidationError`` instead of crashing on
  non-dictionary JSON input (:ticket:`26672`).
  
  * Fixed ``dbshell`` crash on PostgreSQL with an empty database name
  (:ticket:`26698`).
  
  * Fixed a regression in queries on a ``OneToOneField`` that has ``to_field``
  and ``primary_key=True`` (:ticket:`26667`).
  
  
  ==========================

1.9.6 not secure

==========================
  
  *May 2, 2016*
  
  Django 1.9.6 fixes several bugs in 1.9.5.
  
  Bugfixes
  ========
  
  * Added support for relative path redirects to the test client and to
  ``SimpleTestCase.assertRedirects()`` because Django 1.9 no longer converts
  redirects to absolute URIs (:ticket:`26428`).
  
  * Fixed ``TimeField`` microseconds round-tripping on MySQL and SQLite
  (:ticket:`26498`).
  
  * Prevented ``makemigrations`` from generating infinite migrations for a model
  field that references a ``functools.partial`` (:ticket:`26475`).
  
  * Fixed a regression where ``SessionBase.pop()`` returned ``None`` rather than
  raising a ``KeyError`` for nonexistent values (:ticket:`26520`).
  
  * Fixed a regression causing the cached template loader to crash when using
  template names starting with a dash (:ticket:`26536`).
  
  * Restored conversion of an empty string to null when saving values of
  ``GenericIPAddressField`` on SQLite and MySQL (:ticket:`26557`).
  
  * Fixed a ``makemessages`` regression where temporary ``.py`` extensions were
  leaked in source file paths (:ticket:`26341`).
  
  
  ==========================

1.9.5 not secure

==========================
  
  *April 1, 2016*
  
  Django 1.9.5 fixes several bugs in 1.9.4.
  
  Bugfixes
  ========
  
  * Made ``MultiPartParser`` ignore filenames that normalize to an empty string
  to fix crash in ``MemoryFileUploadHandler`` on specially crafted user input
  (:ticket:`26325`).
  
  * Fixed a race condition in ``BaseCache.get_or_set()`` (:ticket:`26332`). It
  now returns the ``default`` value instead of ``False`` if there's an error
  when trying to add the value to the cache.
  
  * Fixed data loss on SQLite where ``DurationField`` values with fractional
  seconds could be saved as ``None`` (:ticket:`26324`).
  
  * The forms in ``contrib.auth`` no longer strip trailing and leading whitespace
  from the password fields (:ticket:`26334`). The change requires users who set
  their password to something with such whitespace after a site updated to
  Django 1.9 to reset their password. It provides backwards-compatibility for
  earlier versions of Django.
  
  * Fixed a memory leak in the cached template loader (:ticket:`26306`).
  
  * Fixed a regression that caused ``collectstatic --clear`` to fail if the
  storage doesn't implement ``path()`` (:ticket:`26297`).
  
  * Fixed a crash when using a reverse lookup with a subquery when a
  ``ForeignKey`` has a ``to_field`` set to something other than the primary key
  (:ticket:`26373`).
  
  * Fixed a regression in ``CommonMiddleware`` that caused spurious warnings in
  logs on requests missing a trailing slash (:ticket:`26293`).
  
  * Restored the functionality of the admin's ``raw_id_fields`` in
  ``list_editable`` (:ticket:`26387`).
  
  * Fixed a regression with abstract model inheritance and explicit parent links
  (:ticket:`26413`).
  
  * Fixed a migrations crash on SQLite when renaming the primary key of a model
  containing a ``ForeignKey`` to ``'self'`` (:ticket:`26384`).
  
  * Fixed ``JSONField`` inadvertently escaping its contents when displaying values
  after failed form validation (:ticket:`25532`).
  
  
  ==========================

1.9.4 not secure

==========================
  
  *March 5, 2016*
  
  Django 1.9.4 fixes a regression on Python 2 in the 1.9.3 security release
  where ``utils.http.is_safe_url()`` crashes on bytestring URLs (:ticket:`26308`).
  
  
  ==========================

1.9.3 not secure

==========================
  
  *March 1, 2016*
  
  Django 1.9.3 fixes two security issues and several bugs in 1.9.2.
  
  CVE-2016-2512: Malicious redirect and possible XSS attack via user-supplied redirect URLs containing basic auth
  ===============================================================================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security check for these
  redirects (namely ``django.utils.http.is_safe_url()``) considered some URLs
  with basic authentication credentials "safe" when they shouldn't be.
  
  For example, a URL like ``http://mysite.example.com\attacker.com`` would be
  considered safe if the request's host is ``http://mysite.example.com``, but
  redirecting to this URL sends the user to ``attacker.com``.
  
  Also, if a developer relies on ``is_safe_url()`` to provide safe redirect
  targets and puts such a URL into a link, they could suffer from an XSS attack.
  
  CVE-2016-2513: User enumeration through timing difference on password hasher work factor upgrade
  ================================================================================================
  
  In each major version of Django since 1.6, the default number of iterations for
  the ``PBKDF2PasswordHasher`` and its subclasses has increased. This improves
  the security of the password as the speed of hardware increases, however, it
  also creates a timing difference between a login request for a user with a
  password encoded in an older number of iterations and login request for a
  nonexistent user (which runs the default hasher's default number of iterations
  since Django 1.6).
  
  This only affects users who haven't logged in since the iterations were
  increased. The first time a user logs in after an iterations increase, their
  password is updated with the new iterations and there is no longer a timing
  difference.
  
  The new ``BasePasswordHasher.harden_runtime()`` method allows hashers to bridge
  the runtime gap between the work factor (e.g. iterations) supplied in existing
  encoded passwords and the default work factor of the hasher. This method
  is implemented for ``PBKDF2PasswordHasher``  and ``BCryptPasswordHasher``.
  The number of rounds for the latter hasher hasn't changed since Django 1.4, but
  some projects may subclass it and increase the work factor as needed.
  
  A warning will be emitted for any :ref:`third-party password hashers that don't
  implement <write-your-own-password-hasher>` a ``harden_runtime()`` method.
  
  If you have different password hashes in your database (such as SHA1 hashes
  from users who haven't logged in since the default hasher switched to PBKDF2
  in Django 1.4), the timing difference on a login request for these users may be
  even greater and this fix doesn't remedy that difference (or any difference
  when changing hashers). You may be able to :ref:`upgrade those hashes
  <wrapping-password-hashers>` to prevent a timing attack for that case.
  
  Bugfixes
  ========
  
  * Skipped URL checks (new in 1.9) if the ``ROOT_URLCONF`` setting isn't defined
  (:ticket:`26155`).
  
  * Fixed a crash on PostgreSQL that prevented using ``TIME_ZONE=None`` and
  ``USE_TZ=False`` (:ticket:`26177`).
  
  * Added system checks for query name clashes of hidden relationships
  (:ticket:`26162`).
  
  * Fixed a regression for cases where
  ``ForeignObject.get_extra_descriptor_filter()`` returned a ``Q`` object
  (:ticket:`26153`).
  
  * Fixed regression with an ``__in=qs`` lookup for a ``ForeignKey`` with
  ``to_field`` set (:ticket:`26196`).
  
  * Made ``forms.FileField`` and ``utils.translation.lazy_number()`` picklable
  (:ticket:`26212`).
  
  * Fixed :class:`~django.contrib.postgres.fields.RangeField` and
  :class:`~django.contrib.postgres.fields.ArrayField` serialization with
  ``None`` values (:ticket:`26215`).
  
  * Fixed a crash when filtering by a ``Decimal`` in ``RawQuery``
  (:ticket:`26219`).
  
  * Reallowed dashes in top-level domain names of URLs checked by
  ``URLValidator`` to fix a regression in Django 1.8 (:ticket:`26204`).
  
  * Fixed some crashing deprecation shims in ``SimpleTemplateResponse`` that
  regressed in Django 1.9 (:ticket:`26253`).
  
  * Fixed ``BoundField`` to reallow slices of subwidgets (:ticket:`26267`).
  
  * Changed the admin's "permission denied" message in the login template to use
  ``get_username`` instead of ``username`` to support custom user models
  (:ticket:`26231`).
  
  * Fixed a crash when passing a nonexistent template name to the cached template
  loader's ``load_template()`` method (:ticket:`26280`).
  
  * Prevented ``ContentTypeManager`` instances from sharing their cache
  (:ticket:`26286`).
  
  * Reverted a change in Django 1.9.2 (:ticket:`25858`) that prevented relative
  lazy relationships defined on abstract models to be resolved according to
  their concrete model's ``app_label`` (:ticket:`26186`).
  
  
  ==========================

1.9.2 not secure

==========================
  
  *February 1, 2016*
  
  Django 1.9.2 fixes a security regression in 1.9 and several bugs in 1.9.1. It
  also makes a small backwards incompatible change that hopefully doesn't affect
  any users.
  
  Security issue: User with "change" but not "add" permission can create objects for ``ModelAdmin``’s with ``save_as=True``
  =========================================================================================================================
  
  If a ``ModelAdmin`` uses ``save_as=True`` (not the default), the admin
  provides an option when editing objects to "Save as new". A regression in
  Django 1.9 prevented that form submission from raising a "Permission Denied"
  error for users without the "add" permission.
  
  Backwards incompatible change: ``.py-tpl`` files rewritten in project/app templates
  ===================================================================================
  
  The addition of some Django template language syntax to the default app
  template in Django 1.9 means those files now have some invalid Python syntax.
  This causes difficulties for packaging systems that unconditionally
  byte-compile ``*.py`` files.
  
  To remedy this, a ``.py-tpl`` suffix is now used for the project and app
  template files included in Django. The ``.py-tpl`` suffix is replaced with
  ``.py`` by the ``startproject`` and ``startapp`` commands. For example, a
  template with the filename ``manage.py-tpl`` will be created as ``manage.py``.
  
  Please file a ticket if you have a custom project template containing
  ``.py-tpl`` files and find this behavior problematic.
  
  Bugfixes
  ========
  
  * Fixed a regression in ``ConditionalGetMiddleware`` causing ``If-None-Match``
  checks to always return HTTP 200 (:ticket:`26024`).
  
  * Fixed a regression that caused the "user-tools" items to display on the
  admin's logout page (:ticket:`26035`).
  
  * Fixed a crash in the translations system when the current language has no
  translations (:ticket:`26046`).
  
  * Fixed a regression that caused the incorrect day to be selected when opening
  the admin calendar widget for timezones from GMT+0100 to GMT+1200
  (:ticket:`24980`).
  
  * Fixed a regression in the admin's edit related model popup that caused an
  escaped value to be displayed in the select dropdown of the parent window
  (:ticket:`25997`).
  
  * Fixed a regression in 1.8.8 causing incorrect index handling in migrations on
  PostgreSQL when adding ``db_index=True`` or ``unique=True`` to a
  ``CharField`` or ``TextField`` that already had the other specified, or when
  removing one of them from a field that had both, or when adding
  ``unique=True`` to a field already listed in ``unique_together``
  (:ticket:`26034`).
  
  * Fixed a regression where defining a relation on an abstract model's field
  using a string model name without an app_label no longer resolved that
  reference to the abstract model's app if using that model in another
  application (:ticket:`25858`).
  
  * Fixed a crash when destroying an existing test database on MySQL or
  PostgreSQL (:ticket:`26096`).
  
  * Fixed CSRF cookie check on POST requests when ``USE_X_FORWARDED_PORT=True``
  (:ticket:`26094`).
  
  * Fixed a ``QuerySet.order_by()`` crash when ordering by a relational field of
  a ``ManyToManyField`` ``through`` model (:ticket:`26092`).
  
  * Fixed a regression that caused an exception when making database queries on
  SQLite with more than 2000 parameters when :setting:`DEBUG` is ``True`` on
  distributions that increase the ``SQLITE_MAX_VARIABLE_NUMBER`` compile-time
  limit to over 2000, such as Debian (:ticket:`26063`).
  
  * Fixed a crash when using a reverse ``OneToOneField`` in
  ``ModelAdmin.readonly_fields`` (:ticket:`26060`).
  
  * Fixed a crash when calling the ``migrate`` command in a test case with the
  ``available_apps`` attribute pointing to an application with migrations
  disabled using the ``MIGRATION_MODULES`` setting (:ticket:`26135`).
  
  * Restored the ability for testing and debugging tools to determine the
  template from which a node came from, even during template inheritance or
  inclusion. Prior to Django 1.9, debugging tools could access the template
  origin from the node via ``Node.token.source[0]``. This was an undocumented,
  private API. The origin is now available directly on each node using the
  ``Node.origin`` attribute (:ticket:`25848`).
  
  * Fixed a regression in Django 1.8.5 that broke copying a ``SimpleLazyObject``
  with ``copy.copy()`` (:ticket:`26122`).
  
  * Always included ``geometry_field`` in the GeoJSON serializer output regardless
  of the ``fields`` parameter (:ticket:`26138`).
  
  * Fixed the ``contrib.gis`` map widgets when using
  ``USE_THOUSAND_SEPARATOR=True`` (:ticket:`20415`).
  
  * Made invalid forms display the initial of values of their disabled fields
  (:ticket:`26129`).
  
  
  ==========================

1.9.1 not secure

==========================
  
  *January 2, 2016*
  
  Django 1.9.1 fixes several bugs in 1.9.
  
  Bugfixes
  ========
  
  * Fixed ``BaseCache.get_or_set()`` with the ``DummyCache`` backend
  (:ticket:`25840`).
  
  * Fixed a regression in ``FormMixin`` causing forms to be validated twice
  (:ticket:`25548`, :ticket:`26018`).
  
  * Fixed a system check crash with nested ``ArrayField``\s (:ticket:`25867`).
  
  * Fixed a state bug when migrating a ``SeparateDatabaseAndState`` operation
  backwards (:ticket:`25896`).
  
  * Fixed a regression in ``CommonMiddleware`` causing ``If-None-Match`` checks
  to always return HTTP 200 (:ticket:`25900`).
  
  * Fixed missing ``varchar/text_pattern_ops`` index on ``CharField`` and
  ``TextField`` respectively when using ``AlterField`` on PostgreSQL
  (:ticket:`25412`).
  
  * Fixed admin's delete confirmation page's summary counts of related objects
  (:ticket:`25883`).
  
  * Added ``from __future__ import unicode_literals`` to the default ``apps.py``
  created by ``startapp`` on Python 2 (:ticket:`25909`). Add this line to your
  own ``apps.py`` files created using Django 1.9 if you want your migrations
  to work on both Python 2 and Python 3.
  
  * Prevented ``QuerySet.delete()`` from crashing on MySQL when querying across
  relations (:ticket:`25882`).
  
  * Fixed evaluation of zero-length slices of ``QuerySet.values()``
  (:ticket:`25894`).
  
  * Fixed a state bug when using an ``AlterModelManagers`` operation
  (:ticket:`25852`).
  
  * Fixed ``TypedChoiceField`` change detection with nullable fields
  (:ticket:`25942`).
  
  * Fixed incorrect timezone warnings in custom admin templates that don't have
  a ``data-admin-utc-offset`` attribute in the ``body`` tag.
  (:ticket:`25845`).
  
  * Fixed a regression which prevented using a language not in Django's default
  language list (:setting:`LANGUAGES`) (:ticket:`25915`).
  
  * Avoided hiding some exceptions, like an invalid ``INSTALLED_APPS`` setting,
  behind ``AppRegistryNotReady`` when starting ``runserver`` (:ticket:`25510`).
  This regression appeared in 1.8.5 as a side effect of fixing :ticket:`24704`
  and by mistake the fix wasn't applied to the ``stable/1.9.x`` branch.
  
  * Fixed ``migrate --fake-initial`` detection of many-to-many tables
  (:ticket:`25922`).
  
  * Restored the functionality of the admin's ``list_editable`` add and change
  buttons (:ticket:`25903`).
  
  * Fixed ``isnull`` query lookup for ``ForeignObject``
  (:ticket:`25972`).
  
  * Fixed a regression in the admin which ignored line breaks in read-only fields
  instead of converting them to ``<br>`` (:ticket:`25465`).
  
  * Fixed incorrect object reference in
  ``SingleObjectMixin.get_context_object_name()`` (:ticket:`26006`).
  
  * Made ``loaddata`` skip disabling and enabling database constraints when it
  doesn't load any fixtures (:ticket:`23372`).
  
  * Restored ``contrib.auth`` hashers compatibility with py-bcrypt
  (:ticket:`26016`).
  
  * Fixed a crash in ``QuerySet.values()/values_list()`` after an ``annotate()``
  and ``order_by()`` when ``values()/values_list()`` includes a field not in
  the ``order_by()`` (:ticket:`25316`).
  
  
  ========================

1.9 not secure

========================
  
  *December 1, 2015*
  
  Welcome to Django 1.9!
  
  These release notes cover the :ref:`new features <whats-new-1.9>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.9>` you'll
  want to be aware of when upgrading from Django 1.8 or older versions. We've
  :ref:`dropped some features<removed-features-1.9>` that have reached the end of
  their deprecation cycle, and we've :ref:`begun the deprecation process for some
  features <deprecated-features-1.9>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Python compatibility
  ====================
  
  Django 1.9 requires Python 2.7, 3.4, or 3.5. We **highly recommend** and only
  officially support the latest release of each series.
  
  The Django 1.8 series is the last to support Python 3.2 and 3.3.
  
  .. _whats-new-1.9:
  
  What's new in Django 1.9
  ========================
  
  Performing actions after a transaction commit
  ---------------------------------------------
  
  The new :func:`~django.db.transaction.on_commit` hook allows performing actions
  after a database transaction is successfully committed. This is useful for
  tasks such as sending notification emails, creating queued tasks, or
  invalidating caches.
  
  This functionality from the `django-transaction-hooks`_ package has been
  integrated into Django.
  
  .. _django-transaction-hooks: https://pypi.org/project/django-transaction-hooks/
  
  Password validation
  -------------------
  
  Django now offers password validation to help prevent the usage of weak
  passwords by users. The validation is integrated in the included password
  change and reset forms and is simple to integrate in any other code.
  Validation is performed by one or more validators, configured in the new
  :setting:`AUTH_PASSWORD_VALIDATORS` setting.
  
  Four validators are included in Django, which can enforce a minimum length,
  compare the password to the user's attributes like their name, ensure
  passwords aren't entirely numeric, or check against an included list of common
  passwords. You can combine multiple validators, and some validators have
  custom configuration options. For example, you can choose to provide a custom
  list of common passwords. Each validator provides a help text to explain its
  requirements to the user.
  
  By default, no validation is performed and all passwords are accepted, so if
  you don't set :setting:`AUTH_PASSWORD_VALIDATORS`, you will not see any
  change. In new projects created with the default :djadmin:`startproject`
  template, a simple set of validators is enabled. To enable basic validation in
  the included auth forms for your project, you could set, for example::
  
  AUTH_PASSWORD_VALIDATORS = [
  {
  'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
  },
  {
  'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
  },
  {
  'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
  },
  {
  'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
  },
  ]
  
  See :ref:`password-validation` for more details.
  
  Permission mixins for class-based views
  ---------------------------------------
  
  Django now ships with the mixins
  :class:`~django.contrib.auth.mixins.AccessMixin`,
  :class:`~django.contrib.auth.mixins.LoginRequiredMixin`,
  :class:`~django.contrib.auth.mixins.PermissionRequiredMixin`, and
  :class:`~django.contrib.auth.mixins.UserPassesTestMixin` to provide the
  functionality of the ``django.contrib.auth.decorators`` for class-based views.
  These mixins have been taken from, or are at least inspired by, the
  `django-braces`_ project.
  
  There are a few differences between Django's and ``django-braces``\'
  implementation, though:
  
  * The :attr:`~django.contrib.auth.mixins.AccessMixin.raise_exception` attribute
  can only be ``True`` or ``False``. Custom exceptions or callables are not
  supported.
  
  * The :meth:`~django.contrib.auth.mixins.AccessMixin.handle_no_permission`
  method does not take a ``request`` argument. The current request is available
  in ``self.request``.
  
  * The custom ``test_func()`` of :class:`~django.contrib.auth.mixins.UserPassesTestMixin`
  does not take a ``user`` argument. The current user is available in
  ``self.request.user``.
  
  * The :attr:`permission_required <django.contrib.auth.mixins.PermissionRequiredMixin>`
  attribute supports a string (defining one permission) or a list/tuple of
  strings (defining multiple permissions) that need to be fulfilled to grant
  access.
  
  * The new :attr:`~django.contrib.auth.mixins.AccessMixin.permission_denied_message`
  attribute allows passing a message to the ``PermissionDenied`` exception.
  
  .. _django-braces: https://django-braces.readthedocs.io/en/latest/index.html
  
  New styling for ``contrib.admin``
  ---------------------------------
  
  The admin sports a modern, flat design with new SVG icons which look perfect
  on HiDPI screens. It still provides a fully-functional experience to `YUI's
  A-grade`_ browsers. Older browser may experience varying levels of graceful
  degradation.
  
  .. _YUI's A-grade: https://github.com/yui/yui3/wiki/Graded-Browser-Support
  
  Running tests in parallel
  -------------------------
  
  The :djadmin:`test` command now supports a :option:`--parallel <test
  --parallel>` option to run a project's tests in multiple processes in parallel.
  
  Each process gets its own database. You must ensure that different test cases
  don't access the same resources. For instance, test cases that touch the
  filesystem should create a temporary directory for their own use.
  
  This option is enabled by default for Django's own test suite provided:
  
  - the OS supports it (all but Windows)
  - the database backend supports it (all the built-in backends but Oracle)
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Admin views now have ``model_admin`` or ``admin_site`` attributes.
  
  * The URL of the admin change view has been changed (was at
  ``/admin/<app>/<model>/<pk>/`` by default and is now at
  ``/admin/<app>/<model>/<pk>/change/``). This should not affect your
  application unless you have hardcoded admin URLs. In that case, replace those
  links by :ref:`reversing admin URLs <admin-reverse-urls>` instead. Note that
  the old URL still redirects to the new one for backwards compatibility, but
  it may be removed in a future version.
  
  * :meth:`ModelAdmin.get_list_select_related()
  <django.contrib.admin.ModelAdmin.get_list_select_related>` was added to allow
  changing the ``select_related()`` values used in the admin's changelist query
  based on the request.
  
  * The ``available_apps`` context variable, which lists the available
  applications for the current user, has been added to the
  :meth:`AdminSite.each_context() <django.contrib.admin.AdminSite.each_context>`
  method.
  
  * :attr:`AdminSite.empty_value_display
  <django.contrib.admin.AdminSite.empty_value_display>` and
  :attr:`ModelAdmin.empty_value_display
  <django.contrib.admin.ModelAdmin.empty_value_display>` were added to override
  the display of empty values in admin change list. You can also customize the
  value for each field.
  
  * Added jQuery events :ref:`when an inline form is added or removed
  <admin-javascript-inline-form-events>` on the change form page.
  
  * The time picker widget includes a '6 p.m' option for consistency of having
  predefined options every 6 hours.
  
  * JavaScript slug generation now supports Romanian characters.
  
  :mod:`django.contrib.admindocs`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The model section of the ``admindocs`` now also describes methods that take
  arguments, rather than ignoring them.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The default iteration count for the PBKDF2 password hasher has been increased
  by 20%. This backwards compatible change will not affect users who have
  subclassed ``django.contrib.auth.hashers.PBKDF2PasswordHasher`` to change the
  default value.
  
  * The ``BCryptSHA256PasswordHasher`` will now update passwords if its
  ``rounds`` attribute is changed.
  
  * ``AbstractBaseUser`` and ``BaseUserManager`` were moved to a new
  ``django.contrib.auth.base_user`` module so that they can be imported without
  including ``django.contrib.auth`` in :setting:`INSTALLED_APPS` (doing so
  raised a deprecation warning in older versions and is no longer supported in
  Django 1.9).
  
  * The permission argument of
  :func:`~django.contrib.auth.decorators.permission_required()` accepts all
  kinds of iterables, not only list and tuples.
  
  * The new :class:`~django.contrib.auth.middleware.PersistentRemoteUserMiddleware`
  makes it possible to use ``REMOTE_USER`` for setups where the header is only
  populated on login pages instead of every request in the session.
  
  * The ``django.contrib.auth.views.password_reset()`` view accepts an
  ``extra_email_context`` parameter.
  
  :mod:`django.contrib.contenttypes`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * It's now possible to use
  :attr:`~django.db.models.Options.order_with_respect_to` with a
  ``GenericForeignKey``.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * All ``GeoQuerySet`` methods have been deprecated and replaced by
  :doc:`equivalent database functions </ref/contrib/gis/functions>`. As soon
  as the legacy methods have been replaced in your code, you should even be
  able to remove the special ``GeoManager`` from your GIS-enabled classes.
  
  * The GDAL interface now supports instantiating file-based and in-memory
  :ref:`GDALRaster objects <raster-data-source-objects>` from raw data.
  Setters for raster properties such as projection or pixel values have
  been added.
  
  * For PostGIS users, the new :class:`~django.contrib.gis.db.models.RasterField`
  allows :ref:`storing GDALRaster objects <creating-and-saving-raster-models>`.
  It supports automatic spatial index creation and reprojection when saving a
  model. It does not yet support spatial querying.
  
  * The new :meth:`GDALRaster.warp() <django.contrib.gis.gdal.GDALRaster.warp>`
  method allows warping a raster by specifying target raster properties such as
  origin, width, height, or pixel size (among others).
  
  * The new :meth:`GDALRaster.transform()
  <django.contrib.gis.gdal.GDALRaster.transform>` method allows transforming a
  raster into a different spatial reference system by specifying a target
  ``srid``.
  
  * The new :class:`~django.contrib.gis.geoip2.GeoIP2` class allows using
  MaxMind's GeoLite2 databases which includes support for IPv6 addresses.
  
  * The default OpenLayers library version included in widgets has been updated
  from 2.13 to 2.13.1.
  
  :mod:`django.contrib.postgres`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Added support for the :lookup:`rangefield.contained_by` lookup for some built
  in fields which correspond to the range fields.
  
  * Added :class:`~django.contrib.postgres.fields.JSONField`.
  
  * Added :doc:`/ref/contrib/postgres/aggregates`.
  
  * Added the :class:`~django.contrib.postgres.functions.TransactionNow` database
  function.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The session model and ``SessionStore`` classes for the ``db`` and
  ``cached_db`` backends are refactored to allow a custom database session
  backend to build upon them. See
  :ref:`extending-database-backed-session-engines` for more details.
  
  :mod:`django.contrib.sites`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :func:`~django.contrib.sites.shortcuts.get_current_site` now handles the case
  where ``request.get_host()`` returns ``domain:port``, e.g.
  ``example.com:80``. If the lookup fails because the host does not match a
  record in the database and the host has a port, the port is stripped and the
  lookup is retried with the domain part only.
  
  :mod:`django.contrib.syndication`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Support for multiple enclosures per feed item has been added. If multiple
  enclosures are defined on a RSS feed, an exception is raised as RSS feeds,
  unlike Atom feeds, do not support multiple enclosures per feed item.
  
  Cache
  ~~~~~
  
  * ``django.core.cache.backends.base.BaseCache`` now has a ``get_or_set()``
  method.
  
  * :func:`django.views.decorators.cache.never_cache` now sends more persuasive
  headers (added ``no-cache, no-store, must-revalidate`` to ``Cache-Control``)
  to better prevent caching. This was also added in Django 1.8.8.
  
  CSRF
  ~~~~
  
  * The request header's name used for CSRF authentication can be customized
  with :setting:`CSRF_HEADER_NAME`.
  
  * The CSRF referer header is now validated against the
  :setting:`CSRF_COOKIE_DOMAIN` setting if set. See :ref:`how-csrf-works` for
  details.
  
  * The new :setting:`CSRF_TRUSTED_ORIGINS` setting provides a way to allow
  cross-origin unsafe requests (e.g. ``POST``) over HTTPS.
  
  Database backends
  ~~~~~~~~~~~~~~~~~
  
  * The PostgreSQL backend (``django.db.backends.postgresql_psycopg2``) is also
  available as ``django.db.backends.postgresql``. The old name will continue to
  be available for backwards compatibility.
  
  File Storage
  ~~~~~~~~~~~~
  
  * :meth:`Storage.get_valid_name()
  <django.core.files.storage.Storage.get_valid_name>` is now called when
  the :attr:`~django.db.models.FileField.upload_to` is a callable.
  
  * :class:`~django.core.files.File` now has the ``seekable()`` method when using
  Python 3.
  
  Forms
  ~~~~~
  
  * :class:`~django.forms.ModelForm` accepts the new ``Meta`` option
  ``field_classes`` to customize the type of the fields. See
  :ref:`modelforms-overriding-default-fields` for details.
  
  * You can now specify the order in which form fields are rendered with the
  :attr:`~django.forms.Form.field_order` attribute, the ``field_order``
  constructor argument , or the :meth:`~django.forms.Form.order_fields` method.
  
  * A form prefix can be specified inside a form class, not only when
  instantiating a form. See :ref:`form-prefix` for details.
  
  * You can now :ref:`specify keyword arguments <custom-formset-form-kwargs>`
  that you want to pass to the constructor of forms in a formset.
  
  * :class:`~django.forms.SlugField` now accepts an
  :attr:`~django.forms.SlugField.allow_unicode` argument to allow Unicode
  characters in slugs.
  
  * :class:`~django.forms.CharField` now accepts a
  :attr:`~django.forms.CharField.strip` argument to strip input data of leading
  and trailing whitespace.  As this defaults to ``True`` this is different
  behavior from previous releases.
  
  * Form fields now support the :attr:`~django.forms.Field.disabled` argument,
  allowing the field widget to be displayed disabled by browsers.
  
  * It's now possible to customize bound fields by overriding a field's
  :meth:`~django.forms.Field.get_bound_field()` method.
  
  Generic Views
  ~~~~~~~~~~~~~
  
  * Class-based views generated using ``as_view()`` now have ``view_class``
  and ``view_initkwargs`` attributes.
  
  * :func:`~django.utils.decorators.method_decorator` can now be used with a list
  or tuple of decorators. It can also be used to :ref:`decorate classes instead
  of methods <decorating-class-based-views>`.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * The :func:`django.views.i18n.set_language` view now properly redirects to
  :ref:`translated URLs <url-internationalization>`, when available.
  
  * The ``django.views.i18n.javascript_catalog()`` view now works correctly
  if used multiple times with different configurations on the same page.
  
  * The :func:`django.utils.timezone.make_aware` function gained an ``is_dst``
  argument to help resolve ambiguous times during DST transitions.
  
  * You can now use locale variants supported by gettext. These are usually used
  for languages which can be written in different scripts, for example Latin
  and Cyrillic (e.g. ``belatin``).
  
  * Added the ``django.views.i18n.json_catalog()`` view to help build a custom
  client-side i18n library upon Django translations. It returns a JSON object
  containing a translations catalog, formatting settings, and a plural rule.
  
  * Added the ``name_translated`` attribute to the object returned by the
  :ttag:`get_language_info` template tag. Also added a corresponding template
  filter: :tfilter:`language_name_translated`.
  
  * You can now run :djadmin:`compilemessages` from the root directory of your
  project and it will find all the app message files that were created by
  :djadmin:`makemessages`.
  
  * :djadmin:`makemessages` now calls xgettext once per locale directory rather
  than once per translatable file. This speeds up localization builds.
  
  * :ttag:`blocktrans` supports assigning its output to a variable using
  ``asvar``.
  
  * Two new languages are available: Colombian Spanish and Scottish Gaelic.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :djadmin:`sendtestemail` command lets you send a test email to
  easily confirm that email sending through Django is working.
  
  * To increase the readability of the SQL code generated by
  :djadmin:`sqlmigrate`, the SQL code generated for each migration operation is
  preceded by the operation's description.
  
  * The :djadmin:`dumpdata` command output is now deterministically ordered.
  Moreover, when the ``--output`` option is specified, it also shows a progress
  bar in the terminal.
  
  * The :djadmin:`createcachetable` command now has a ``--dry-run`` flag to
  print out the SQL rather than execute it.
  
  * The :djadmin:`startapp` command creates an ``apps.py`` file. Since it doesn't
  use ``default_app_config`` (:ref:`a discouraged API
  <configuring-applications-ref>`), you must specify the app config's path,
  e.g. ``'polls.apps.PollsConfig'``, in :setting:`INSTALLED_APPS` for it to be
  used (instead of just ``'polls'``).
  
  * When using the PostgreSQL backend, the :djadmin:`dbshell` command can connect
  to the database using the password from your settings file (instead of
  requiring it to be manually entered).
  
  * The ``django`` package may be run as a script, i.e. ``python -m django``,
  which will behave the same as ``django-admin``.
  
  * Management commands that have the ``--noinput`` option now also take
  ``--no-input`` as an alias for that option.
  
  Migrations
  ~~~~~~~~~~
  
  * Initial migrations are now marked with an :attr:`initial = True
  <django.db.migrations.Migration.initial>` class attribute which allows
  :option:`migrate --fake-initial` to more easily detect initial migrations.
  
  * Added support for serialization of ``functools.partial`` and ``LazyObject``
  instances.
  
  * When supplying ``None`` as a value in :setting:`MIGRATION_MODULES`, Django
  will consider the app an app without migrations.
  
  * When applying migrations, the "Rendering model states" step that's displayed
  when running migrate with verbosity 2 or higher now computes only the states
  for the migrations that have already been applied. The model states for
  migrations being applied are generated on demand, drastically reducing the
  amount of required memory.
  
  However, this improvement is not available when unapplying migrations and
  therefore still requires the precomputation and storage of the intermediate
  migration states.
  
  This improvement also requires that Django no longer supports mixed migration
  plans. Mixed plans consist of a list of migrations where some are being
  applied and others are being unapplied. This was never officially supported
  and never had a public API that supports this behavior.
  
  * The :djadmin:`squashmigrations` command now supports specifying the starting
  migration from which migrations will be squashed.
  
  Models
  ~~~~~~
  
  * :meth:`QuerySet.bulk_create() <django.db.models.query.QuerySet.bulk_create>`
  now works on proxy models.
  
  * Database configuration gained a :setting:`TIME_ZONE <DATABASE-TIME_ZONE>`
  option for interacting with databases that store datetimes in local time and
  don't support time zones when :setting:`USE_TZ` is ``True``.
  
  * Added the :meth:`RelatedManager.set()
  <django.db.models.fields.related.RelatedManager.set()>` method to the related
  managers created by ``ForeignKey``, ``GenericForeignKey``, and
  ``ManyToManyField``.
  
  * The :meth:`~django.db.models.fields.related.RelatedManager.add` method on
  a reverse foreign key now has a ``bulk`` parameter to allow executing one
  query regardless of the number of objects being added rather than one query
  per object.
  
  * Added the ``keep_parents`` parameter to :meth:`Model.delete()
  <django.db.models.Model.delete>` to allow deleting only a child's data in a
  model that uses multi-table inheritance.
  
  * :meth:`Model.delete() <django.db.models.Model.delete>`
  and :meth:`QuerySet.delete() <django.db.models.query.QuerySet.delete>` return
  the number of objects deleted.
  
  * Added a system check to prevent defining both ``Meta.ordering`` and
  ``order_with_respect_to`` on the same model.
  
  * :lookup:`Date and time <year>` lookups can be chained with other lookups
  (such as :lookup:`exact`, :lookup:`gt`, :lookup:`lt`, etc.). For example:
  ``Entry.objects.filter(pub_date__month__gt=6)``.
  
  * Time lookups (hour, minute, second) are now supported by
  :class:`~django.db.models.TimeField` for all database backends. Support for
  backends other than SQLite was added but undocumented in Django 1.7.
  
  * You can specify the ``output_field`` parameter of the
  :class:`~django.db.models.Avg` aggregate in order to aggregate over
  non-numeric columns, such as ``DurationField``.
  
  * Added the :lookup:`date` lookup to :class:`~django.db.models.DateTimeField`
  to allow querying the field by only the date portion.
  
  * Added the :class:`~django.db.models.functions.Greatest` and
  :class:`~django.db.models.functions.Least` database functions.
  
  * Added the :class:`~django.db.models.functions.Now` database function, which
  returns the current date and time.
  
  * :class:`~django.db.models.Transform` is now a subclass of
  :ref:`Func() <func-expressions>` which allows ``Transform``\s to be used on
  the right hand side of an expression, just like regular ``Func``\s. This
  allows registering some database functions like
  :class:`~django.db.models.functions.Length`,
  :class:`~django.db.models.functions.Lower`, and
  :class:`~django.db.models.functions.Upper` as transforms.
  
  * :class:`~django.db.models.SlugField` now accepts an
  :attr:`~django.db.models.SlugField.allow_unicode` argument to allow Unicode
  characters in slugs.
  
  * Added support for referencing annotations in ``QuerySet.distinct()``.
  
  * ``connection.queries`` shows queries with substituted parameters on SQLite.
  
  * :doc:`Query expressions </ref/models/expressions>` can now be used when
  creating new model instances using ``save()``, ``create()``, and
  ``bulk_create()``.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * Unless :attr:`HttpResponse.reason_phrase
  <django.http.HttpResponse.reason_phrase>` is explicitly set, it now is
  determined by the current value of :attr:`HttpResponse.status_code
  <django.http.HttpResponse.status_code>`. Modifying the value of
  ``status_code`` outside of the constructor will also modify the value of
  ``reason_phrase``.
  
  * The debug view now shows details of chained exceptions on Python 3.
  
  * The default 40x error views now accept a second positional parameter, the
  exception that triggered the view.
  
  * View error handlers now support
  :class:`~django.template.response.TemplateResponse`, commonly used with
  class-based views.
  
  * Exceptions raised by the ``render()`` method are now passed to the
  ``process_exception()`` method of each middleware.
  
  * Request middleware can now set :attr:`HttpRequest.urlconf
  <django.http.HttpRequest.urlconf>` to ``None`` to revert any changes made
  by previous middleware and return to using the :setting:`ROOT_URLCONF`.
  
  * The :setting:`DISALLOWED_USER_AGENTS` check in
  :class:`~django.middleware.common.CommonMiddleware` now raises a
  :class:`~django.core.exceptions.PermissionDenied` exception as opposed to
  returning an :class:`~django.http.HttpResponseForbidden` so that
  :data:`~django.conf.urls.handler403` is invoked.
  
  * Added :meth:`HttpRequest.get_port() <django.http.HttpRequest.get_port>` to
  fetch the originating port of the request.
  
  * Added the ``json_dumps_params`` parameter to
  :class:`~django.http.JsonResponse` to allow passing keyword arguments to the
  ``json.dumps()`` call used to generate the response.
  
  * The :class:`~django.middleware.common.BrokenLinkEmailsMiddleware` now
  ignores 404s when the referer is equal to the requested URL. To circumvent
  the empty referer check already implemented, some Web bots set the referer to
  the requested URL.
  
  Templates
  ~~~~~~~~~
  
  * Template tags created with the :meth:`~django.template.Library.simple_tag`
  helper can now store results in a template variable by using the ``as``
  argument.
  
  * Added a :meth:`Context.setdefault() <django.template.Context.setdefault>`
  method.
  
  * The :ref:`django.template <django-template-logger>` logger was added and
  includes the following messages:
  
  * A ``DEBUG`` level message for missing context variables.
  
  * A ``WARNING`` level message for uncaught exceptions raised
  during the rendering of an ``{% include %}`` when debug mode is off
  (helpful since ``{% include %}`` silences the exception and returns an
  empty string).
  
  * The :ttag:`firstof` template tag supports storing the output in a variable
  using 'as'.
  
  * :meth:`Context.update() <django.template.Context.update>` can now be used as
  a context manager.
  
  * Django template loaders can now extend templates recursively.
  
  * The debug page template postmortem now include output from each engine that
  is installed.
  
  * :ref:`Debug page integration <template-debug-integration>` for custom
  template engines was added.
  
  * The :class:`~django.template.backends.django.DjangoTemplates` backend gained
  the ability to register libraries and builtins explicitly through the
  template :setting:`OPTIONS <TEMPLATES-OPTIONS>`.
  
  * The ``timesince`` and ``timeuntil`` filters were improved to deal with leap
  years when given large time spans.
  
  * The ``include`` tag now caches parsed templates objects during template
  rendering, speeding up reuse in places such as for loops.
  
  Tests
  ~~~~~
  
  * Added the :meth:`json() <django.test.Response.json>` method to test client
  responses to give access to the response body as JSON.
  
  * Added the :meth:`~django.test.Client.force_login()` method to the test
  client. Use this method to simulate the effect of a user logging into the
  site while skipping the authentication and verification steps of
  :meth:`~django.test.Client.login()`.
  
  URLs
  ~~~~
  
  * Regular expression lookaround assertions are now allowed in URL patterns.
  
  * The application namespace can now be set using an ``app_name`` attribute
  on the included module or object. It can also be set by passing a 2-tuple
  of (<list of patterns>, <application namespace>) as the first argument to
  ``include()``.
  
  * System checks have been added for common URL pattern mistakes.
  
  Validators
  ~~~~~~~~~~
  
  * Added :func:`django.core.validators.int_list_validator` to generate
  validators of strings containing integers separated with a custom character.
  
  * :class:`~django.core.validators.EmailValidator` now limits the length of
  domain name labels to 63 characters per :rfc:`1034`.
  
  * Added :func:`~django.core.validators.validate_unicode_slug` to validate slugs
  that may contain Unicode characters.
  
  .. _backwards-incompatible-1.9:
  
  Backwards incompatible changes in 1.9
  =====================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`removed-features-1.9` for the features that have reached the end of
  their deprecation cycle and therefore been removed. If you haven't updated
  your code within the deprecation timeline for a given feature, its removal
  may appear as a backwards incompatible change.
  
  Database backend API
  --------------------
  
  * A couple of new tests rely on the ability of the backend to introspect column
  defaults (returning the result as ``Field.default``). You can set the
  ``can_introspect_default`` database feature to ``False`` if your backend
  doesn't implement this. You may want to review the implementation on the
  backends that Django includes for reference (:ticket:`24245`).
  
  * Registering a global adapter or converter at the level of the DB-API module
  to handle time zone information of :class:`~datetime.datetime` values passed
  as query parameters or returned as query results on databases that don't
  support time zones is discouraged. It can conflict with other libraries.
  
  The recommended way to add a time zone to :class:`~datetime.datetime` values
  fetched from the database is to register a converter for ``DateTimeField``
  in ``DatabaseOperations.get_db_converters()``.
  
  The ``needs_datetime_string_cast`` database feature was removed. Database
  backends that set it must register a converter instead, as explained above.
  
  * The ``DatabaseOperations.value_to_db_<type>()`` methods were renamed to
  ``adapt_<type>field_value()`` to mirror the ``convert_<type>field_value()``
  methods.
  
  * To use the new ``date`` lookup, third-party database backends may need to
  implement the ``DatabaseOperations.datetime_cast_date_sql()`` method.
  
  * The ``DatabaseOperations.time_extract_sql()`` method was added. It calls the
  existing ``date_extract_sql()`` method. This method is overridden by the
  SQLite backend to add time lookups (hour, minute, second) to
  :class:`~django.db.models.TimeField`, and may be needed by third-party
  database backends.
  
  * The ``DatabaseOperations.datetime_cast_sql()`` method (not to be confused
  with ``DatabaseOperations.datetime_cast_date_sql()`` mentioned above)
  has been removed. This method served to format dates on Oracle long
  before 1.0, but hasn't been overridden by any core backend in years
  and hasn't been called anywhere in Django's code or tests.
  
  * In order to support test parallelization, you must implement the
  ``DatabaseCreation._clone_test_db()`` method and set
  ``DatabaseFeatures.can_clone_databases = True``. You may have to adjust
  ``DatabaseCreation.get_test_db_clone_settings()``.
  
  Default settings that were tuples are now lists
  -----------------------------------------------
  
  The default settings in ``django.conf.global_settings`` were a combination of
  lists and tuples. All settings that were formerly tuples are now lists.
  
  ``is_usable`` attribute on template loaders is removed
  ------------------------------------------------------
  
  Django template loaders previously required an ``is_usable`` attribute to be
  defined. If a loader was configured in the template settings and this attribute
  was ``False``, the loader would be silently ignored. In practice, this was only
  used by the egg loader to detect if setuptools was installed. The ``is_usable``
  attribute is now removed and the egg loader instead fails at runtime if
  setuptools is not installed.
  
  Related set direct assignment
  -----------------------------
  
  Direct assignment of related objects in the ORM used to perform a ``clear()``
  followed by a call to ``add()``. This caused needlessly large data changes and
  prevented using the :data:`~django.db.models.signals.m2m_changed` signal to
  track individual changes in many-to-many relations.
  
  Direct assignment now relies on the new
  :meth:`~django.db.models.fields.related.RelatedManager.set` method on related
  managers which by default only processes changes between the existing related
  set and the one that's newly assigned. The previous behavior can be restored by
  replacing direct assignment by a call to ``set()`` with the keyword argument
  ``clear=True``.
  
  ``ModelForm``, and therefore ``ModelAdmin``, internally rely on direct
  assignment for many-to-many relations and as a consequence now use the new
  behavior.
  
  Filesystem-based template loaders catch more specific exceptions
  ----------------------------------------------------------------
  
  When using the :class:`filesystem.Loader <django.template.loaders.filesystem.Loader>`
  or :class:`app_directories.Loader <django.template.loaders.app_directories.Loader>`
  template loaders, earlier versions of Django raised a
  :exc:`~django.template.TemplateDoesNotExist` error if a template source existed
  but was unreadable. This could happen under many circumstances, such as if
  Django didn't have permissions to open the file, or if the template source was
  a directory. Now, Django only silences the exception if the template source
  does not exist. All other situations result in the original ``IOError`` being
  raised.
  
  HTTP redirects no longer forced to absolute URIs
  ------------------------------------------------
  
  Relative redirects are no longer converted to absolute URIs. :rfc:`2616`
  required the ``Location`` header in redirect responses to be an absolute URI,
  but it has been superseded by :rfc:`7231` which allows relative URIs in
  ``Location``, recognizing the actual practice of user agents, almost all of
  which support them.
  
  Consequently, the expected URLs passed to ``assertRedirects`` should generally
  no longer include the scheme and domain part of the URLs. For example,
  ``self.assertRedirects(response, 'http://testserver/some-url/')`` should be
  replaced by ``self.assertRedirects(response, '/some-url/')`` (unless the
  redirection specifically contained an absolute URL).
  
  In the rare case that you need the old behavior (discovered with an ancient
  version of Apache with ``mod_scgi`` that interprets a relative redirect as an
  "internal redirect"), you can restore it by writing a custom middleware::
  
  class LocationHeaderFix(object):
  def process_response(self, request, response):
  if 'Location' in response:
  response['Location'] = request.build_absolute_uri(response['Location'])
  return response
  
  Dropped support for PostgreSQL 9.0
  ----------------------------------
  
  Upstream support for PostgreSQL 9.0 ended in September 2015. As a consequence,
  Django 1.9 sets 9.1 as the minimum PostgreSQL version it officially supports.
  
  Dropped support for Oracle 11.1
  -------------------------------
  
  Upstream support for Oracle 11.1 ended in August 2015. As a consequence, Django
  1.9 sets 11.2 as the minimum Oracle version it officially supports.
  
  Bulk behavior of ``add()`` method of related managers
  -----------------------------------------------------
  
  To improve performance, the ``add()`` methods of the related managers created
  by ``ForeignKey`` and ``GenericForeignKey`` changed from a series of
  ``Model.save()`` calls to a single ``QuerySet.update()`` call. The change means
  that ``pre_save`` and ``post_save`` signals aren't sent anymore. You can use
  the ``bulk=False`` keyword argument to revert to the previous behavior.
  
  Template ``LoaderOrigin`` and ``StringOrigin`` are removed
  ----------------------------------------------------------
  
  In previous versions of Django, when a template engine was initialized with
  debug as ``True``, an instance of ``django.template.loader.LoaderOrigin`` or
  ``django.template.base.StringOrigin`` was set as the origin attribute on the
  template object. These classes have been combined into
  :class:`~django.template.base.Origin` and is now always set regardless of the
  engine debug setting. For a minimal level of backwards compatibility, the old
  class names will be kept as aliases to the new ``Origin`` class until
  Django 2.0.
  
  .. _default-logging-changes-19:
  
  Changes to the default logging configuration
  --------------------------------------------
  
  To make it easier to write custom logging configurations, Django's default
  logging configuration no longer defines ``django.request`` and
  ``django.security`` loggers. Instead, it defines a single ``django`` logger,
  filtered at the ``INFO`` level, with two handlers:
  
  * ``console``: filtered at the ``INFO`` level and only active if ``DEBUG=True``.
  * ``mail_admins``: filtered at the ``ERROR`` level and only active if
  ``DEBUG=False``.
  
  If you aren't overriding Django's default logging, you should see minimal
  changes in behavior, but you might see some new logging to the ``runserver``
  console, for example.
  
  If you are overriding Django's default logging, you should check to see how
  your configuration merges with the new defaults.
  
  ``HttpRequest`` details in error reporting
  ------------------------------------------
  
  It was redundant to display the full details of the
  :class:`~django.http.HttpRequest` each time it appeared as a stack frame
  variable in the HTML version of the debug page and error email. Thus, the HTTP
  request will now display the same standard representation as other variables
  (``repr(request)``). As a result, the
  ``ExceptionReporterFilter.get_request_repr()`` method and the undocumented
  ``django.http.build_request_repr()`` function were removed.
  
  The contents of the text version of the email were modified to provide a
  traceback of the same structure as in the case of AJAX requests. The traceback
  details are rendered by the ``ExceptionReporter.get_traceback_text()`` method.
  
  Removal of time zone aware global adapters and converters for datetimes
  -----------------------------------------------------------------------
  
  Django no longer registers global adapters and converters for managing time
  zone information on :class:`~datetime.datetime` values sent to the database as
  query parameters or read from the database in query results. This change
  affects projects that meet all the following conditions:
  
  * The :setting:`USE_TZ` setting is ``True``.
  * The database is SQLite, MySQL, Oracle, or a third-party database that
  doesn't support time zones. In doubt, you can check the value of
  ``connection.features.supports_timezones``.
  * The code queries the database outside of the ORM, typically with
  ``cursor.execute(sql, params)``.
  
  If you're passing aware :class:`~datetime.datetime` parameters to such
  queries, you should turn them into naive datetimes in UTC::
  
  from django.utils import timezone
  param = timezone.make_naive(param, timezone.utc)
  
  If you fail to do so, the conversion will be performed as in earlier versions
  (with a deprecation warning) up until Django 1.11. Django 2.0 won't perform any
  conversion, which may result in data corruption.
  
  If you're reading :class:`~datetime.datetime` values from the results, they
  will be naive instead of aware. You can compensate as follows::
  
  from django.utils import timezone
  value = timezone.make_aware(value, timezone.utc)
  
  You don't need any of this if you're querying the database through the ORM,
  even if you're using :meth:`raw() <django.db.models.query.QuerySet.raw>`
  queries. The ORM takes care of managing time zone information.
  
  Template tag modules are imported when templates are configured
  ---------------------------------------------------------------
  
  The :class:`~django.template.backends.django.DjangoTemplates` backend now
  performs discovery on installed template tag modules when instantiated. This
  update enables libraries to be provided explicitly via the ``'libraries'``
  key of :setting:`OPTIONS <TEMPLATES-OPTIONS>` when defining a
  :class:`~django.template.backends.django.DjangoTemplates` backend. Import
  or syntax errors in template tag modules now fail early at instantiation time
  rather than when a template with a :ttag:`{% load %}<load>` tag is first
  compiled.
  
  ``django.template.base.add_to_builtins()`` is removed
  -----------------------------------------------------
  
  Although it was a private API, projects commonly used ``add_to_builtins()`` to
  make template tags and filters available without using the
  :ttag:`{% load %}<load>` tag. This API has been formalized. Projects should now
  define built-in libraries via the ``'builtins'`` key of :setting:`OPTIONS
  <TEMPLATES-OPTIONS>` when defining a
  :class:`~django.template.backends.django.DjangoTemplates` backend.
  
  .. _simple-tag-conditional-escape-fix:
  
  ``simple_tag`` now wraps tag output in ``conditional_escape``
  -------------------------------------------------------------
  
  In general, template tags do not autoescape their contents, and this behavior is
  :ref:`documented <tags-auto-escaping>`. For tags like
  :class:`~django.template.Library.inclusion_tag`, this is not a problem because
  the included template will perform autoescaping. For ``assignment_tag()``,
  the output will be escaped when it is used as a variable in the template.
  
  For the intended use cases of :class:`~django.template.Library.simple_tag`,
  however, it is very easy to end up with incorrect HTML and possibly an XSS
  exploit. For example::
  
  register.simple_tag(takes_context=True)
  def greeting(context):
  return "Hello {0}!".format(context['request'].user.first_name)
  
  In older versions of Django, this will be an XSS issue because
  ``user.first_name`` is not escaped.
  
  In Django 1.9, this is fixed: if the template context has ``autoescape=True``
  set (the default), then ``simple_tag`` will wrap the output of the tag function
  with :func:`~django.utils.html.conditional_escape`.
  
  To fix your ``simple_tag``\s, it is best to apply the following practices:
  
  * Any code that generates HTML should use either the template system or
  :func:`~django.utils.html.format_html`.
  
  * If the output of a ``simple_tag`` needs escaping, use
  :func:`~django.utils.html.escape` or
  :func:`~django.utils.html.conditional_escape`.
  
  * If you are absolutely certain that you are outputting HTML from a trusted
  source (e.g. a CMS field that stores HTML entered by admins), you can mark it
  as such using :func:`~django.utils.safestring.mark_safe`.
  
  Tags that follow these rules will be correct and safe whether they are run on
  Django 1.9+ or earlier.
  
  ``Paginator.page_range``
  ------------------------
  
  :attr:`Paginator.page_range <django.core.paginator.Paginator.page_range>` is
  now an iterator instead of a list.
  
  In versions of Django previous to 1.8, ``Paginator.page_range`` returned a
  ``list`` in Python 2 and a ``range`` in Python 3. Django 1.8 consistently
  returned a list, but an iterator is more efficient.
  
  Existing code that depends on ``list`` specific features, such as indexing,
  can be ported by converting the iterator into a ``list`` using ``list()``.
  
  Implicit ``QuerySet`` ``__in`` lookup removed
  ---------------------------------------------
  
  In earlier versions, queries such as::
  
  Model.objects.filter(related_id=RelatedModel.objects.all())
  
  would implicitly convert to::
  
  Model.objects.filter(related_id__in=RelatedModel.objects.all())
  
  resulting in SQL like ``"related_id IN (SELECT id FROM ...)"``.
  
  This implicit ``__in`` no longer happens so the "IN" SQL is now "=", and if the
  subquery returns multiple results, at least some databases will throw an error.
  
  .. _admin-browser-support-19:
  
  ``contrib.admin`` browser support
  ---------------------------------
  
  The admin no longer supports Internet Explorer 8 and below, as these browsers
  have reached end-of-life.
  
  CSS and images to support Internet Explorer 6 and 7 have been removed. PNG and
  GIF icons have been replaced with SVG icons, which are not supported by
  Internet Explorer 8 and earlier.
  
  The jQuery library embedded in the admin has been upgraded from version 1.11.2
  to 2.1.4. jQuery 2.x has the same API as jQuery 1.x, but does not support
  Internet Explorer 6, 7, or 8, allowing for better performance and a smaller
  file size. If you need to support IE8 and must also use the latest version of
  Django, you can override the admin's copy of jQuery with your own by creating
  a Django application with this structure::
  
  app/static/admin/js/vendor/
  jquery.js
  jquery.min.js
  
  .. _syntax-error-old-setuptools-django-19:
  
  ``SyntaxError`` when installing Django setuptools 5.5.x
  -------------------------------------------------------
  
  When installing Django 1.9 or 1.9.1 with setuptools 5.5.x, you'll see::
  
  Compiling django/conf/app_template/apps.py ...
  File "django/conf/app_template/apps.py", line 4
  class {{ camel_case_app_name }}Config(AppConfig):
  ^
  SyntaxError: invalid syntax
  
  Compiling django/conf/app_template/models.py ...
  File "django/conf/app_template/models.py", line 1
  {{ unicode_literals }}from django.db import models
  ^
  SyntaxError: invalid syntax
  
  It's safe to ignore these errors (Django will still install just fine), but you
  can avoid them by upgrading setuptools to a more recent version. If you're
  using pip, you can upgrade pip using ``python -m pip install -U pip`` which
  will also upgrade setuptools. This is resolved in later versions of Django as
  described in the :doc:`/releases/1.9.2`.
  
  Miscellaneous
  -------------
  
  * The jQuery static files in ``contrib.admin`` have been moved into a
  ``vendor/jquery`` subdirectory.
  
  * The text displayed for null columns in the admin changelist ``list_display``
  cells has changed from ``(None)`` (or its translated equivalent) to ``-`` (a
  dash).
  
  * ``django.http.responses.REASON_PHRASES`` and
  ``django.core.handlers.wsgi.STATUS_CODE_TEXT`` have been removed. Use
  Python's stdlib instead: :data:`http.client.responses` for Python 3 and
  `httplib.responses`_ for Python 2.
  
  .. _`httplib.responses`: https://docs.python.org/2/library/httplib.htmlhttplib.responses
  
  * ``ValuesQuerySet`` and ``ValuesListQuerySet`` have been removed.
  
  * The ``admin/base.html`` template no longer sets
  ``window.__admin_media_prefix__`` or ``window.__admin_utc_offset__``. Image
  references in JavaScript that used that value to construct absolute URLs have
  been moved to CSS for easier customization. The UTC offset is stored on a
  data attribute of the ``<body>`` tag.
  
  * ``CommaSeparatedIntegerField`` validation has been refined to forbid values
  like ``','``, ``',1'``, and ``'1,,2'``.
  
  * Form initialization was moved from the :meth:`ProcessFormView.get()
  <django.views.generic.edit.ProcessFormView.get>` method to the new
  :meth:`FormMixin.get_context_data()
  <django.views.generic.edit.FormMixin.get_context_data>` method. This may be
  backwards incompatible if you have overridden the ``get_context_data()``
  method without calling ``super()``.
  
  * Support for PostGIS 1.5 has been dropped.
  
  * The ``django.contrib.sites.models.Site.domain`` field was changed to be
  :attr:`~django.db.models.Field.unique`.
  
  * In order to enforce test isolation, database queries are not allowed
  by default in :class:`~django.test.SimpleTestCase` tests anymore. You
  can disable this behavior by setting the ``allow_database_queries`` class
  attribute to ``True`` on your test class.
  
  * ``ResolverMatch.app_name`` was changed to contain the full namespace path in
  the case of nested namespaces. For consistency with
  ``ResolverMatch.namespace``, the empty value is now an empty string instead
  of ``None``.
  
  * For security hardening, session keys must be at least 8 characters.
  
  * Private function ``django.utils.functional.total_ordering()`` has been
  removed. It contained a workaround for a ``functools.total_ordering()`` bug
  in Python versions older than 2.7.3.
  
  * XML serialization (either through :djadmin:`dumpdata` or the syndication
  framework) used to output any characters it received. Now if the content to
  be serialized contains any control characters not allowed in the XML 1.0
  standard, the serialization will fail with a :exc:`ValueError`.
  
  * :class:`~django.forms.CharField` now strips input of leading and trailing
  whitespace by default. This can be disabled by setting the new
  :attr:`~django.forms.CharField.strip` argument to ``False``.
  
  * Template text that is translated and uses two or more consecutive percent
  signs, e.g. ``"%%"``, may have a new ``msgid`` after ``makemessages`` is run
  (most likely the translation will be marked fuzzy). The new ``msgid`` will be
  marked ``", python-format"``.
  
  * If neither :attr:`request.current_app <django.http.HttpRequest.current_app>`
  nor :class:`Context.current_app <django.template.Context>` are set, the
  :ttag:`url` template tag will now use the namespace of the current request.
  Set ``request.current_app`` to ``None`` if you don't want to use a namespace
  hint.
  
  * The :setting:`SILENCED_SYSTEM_CHECKS` setting now silences messages of all
  levels. Previously, messages of ``ERROR`` level or higher were printed to the
  console.
  
  * The ``FlatPage.enable_comments`` field is removed from the ``FlatPageAdmin``
  as it's unused by the application. If your project or a third-party app makes
  use of it, :ref:`create a custom ModelAdmin <flatpages-admin>` to add it back.
  
  * The return value of
  :meth:`~django.test.runner.DiscoverRunner.setup_databases` and the first
  argument of :meth:`~django.test.runner.DiscoverRunner.teardown_databases`
  changed. They used to be ``(old_names, mirrors)`` tuples. Now they're just
  the first item, ``old_names``.
  
  * By default :class:`~django.test.LiveServerTestCase` attempts to find an
  available port in the 8081-8179 range instead of just trying port 8081.
  
  * The system checks for :class:`~django.contrib.admin.ModelAdmin` now check
  instances rather than classes.
  
  * The private API to apply mixed migration plans has been dropped for
  performance reasons. Mixed plans consist of a list of migrations where some
  are being applied and others are being unapplied.
  
  * The related model object descriptor classes in
  ``django.db.models.fields.related`` (private API) are moved from the
  ``related`` module to ``related_descriptors`` and renamed as follows:
  
  * ``ReverseSingleRelatedObjectDescriptor`` is ``ForwardManyToOneDescriptor``
  * ``SingleRelatedObjectDescriptor`` is ``ReverseOneToOneDescriptor``
  * ``ForeignRelatedObjectsDescriptor`` is ``ReverseManyToOneDescriptor``
  * ``ManyRelatedObjectsDescriptor`` is ``ManyToManyDescriptor``
  
  * If you implement a custom :data:`~django.conf.urls.handler404` view, it must
  return a response with an HTTP 404 status code. Use
  :class:`~django.http.HttpResponseNotFound` or pass ``status=404`` to the
  :class:`~django.http.HttpResponse`. Otherwise, :setting:`APPEND_SLASH` won't
  work correctly with ``DEBUG=False``.
  
  .. _deprecated-features-1.9:
  
  Features deprecated in 1.9
  ==========================
  
  ``assignment_tag()``
  --------------------
  
  Django 1.4 added the ``assignment_tag`` helper to ease the creation of
  template tags that store results in a template variable. The
  :meth:`~django.template.Library.simple_tag` helper has gained this same
  ability, making the ``assignment_tag`` obsolete. Tags that use
  ``assignment_tag`` should be updated to use ``simple_tag``.
  
  ``{% cycle %}`` syntax with comma-separated arguments
  -----------------------------------------------------
  
  The :ttag:`cycle` tag supports an inferior old syntax from previous Django
  versions:
  
  .. code-block:: html+django
  
  {% cycle row1,row2,row3 %}
  
  Its parsing caused bugs with the current syntax, so support for the old syntax
  will be removed in Django 1.10 following an accelerated deprecation.
  
  ``ForeignKey`` and ``OneToOneField`` ``on_delete`` argument
  -----------------------------------------------------------
  
  In order to increase awareness about cascading model deletion, the
  ``on_delete`` argument of ``ForeignKey`` and ``OneToOneField`` will be required
  in Django 2.0.
  
  Update models and existing migrations to explicitly set the argument. Since the
  default is ``models.CASCADE``, add ``on_delete=models.CASCADE`` to all
  ``ForeignKey`` and ``OneToOneField``\s that don't use a different option. You
  can also pass it as the second positional argument if you don't care about
  compatibility with older versions of Django.
  
  ``Field.rel`` changes
  ---------------------
  
  ``Field.rel`` and its methods and attributes have changed to match the related
  fields API. The ``Field.rel`` attribute is renamed to ``remote_field`` and many
  of its methods and attributes are either changed or renamed.
  
  The aim of these changes is to provide a documented API for relation fields.
  
  ``GeoManager`` and ``GeoQuerySet`` custom methods
  -------------------------------------------------
  
  All custom ``GeoQuerySet`` methods (``area()``, ``distance()``, ``gml()``, ...)
  have been replaced by equivalent geographic expressions in annotations (see in
  new features). Hence the need to set a custom ``GeoManager`` to GIS-enabled
  models is now obsolete. As soon as your code doesn't call any of the deprecated
  methods, you can simply remove the ``objects = GeoManager()`` lines from your
  models.
  
  Template loader APIs have changed
  ---------------------------------
  
  Django template loaders have been updated to allow recursive template
  extending. This change necessitated a new template loader API. The old
  ``load_template()`` and ``load_template_sources()`` methods are now deprecated.
  Details about the new API can be found :ref:`in the template loader
  documentation <custom-template-loaders>`.
  
  Passing a 3-tuple or an ``app_name`` to ``include()``
  -----------------------------------------------------
  
  The instance namespace part of passing a tuple as an argument to ``include()``
  has been replaced by passing the ``namespace`` argument to ``include()``. For
  example::
  
  polls_patterns = [
  url(...),
  ]
  
  urlpatterns = [
  url(r'^polls/', include((polls_patterns, 'polls', 'author-polls'))),
  ]
  
  becomes::
  
  polls_patterns = ([
  url(...),
  ], 'polls')   'polls' is the app_name
  
  urlpatterns = [
  url(r'^polls/', include(polls_patterns, namespace='author-polls')),
  ]
  
  The ``app_name`` argument to ``include()`` has been replaced by passing a
  2-tuple (as above), or passing an object or module with an ``app_name``
  attribute (as below). If the ``app_name`` is set in this new way, the
  ``namespace`` argument is no longer required. It will default to the value of
  ``app_name``. For example, the URL patterns in the tutorial are changed from:
  
  .. code-block:: python
  :caption: mysite/urls.py
  
  urlpatterns = [
  url(r'^polls/', include('polls.urls', namespace="polls")),
  ...
  ]
  
  to:
  
  .. code-block:: python
  :caption: mysite/urls.py
  
  urlpatterns = [
  url(r'^polls/', include('polls.urls')),   'namespace="polls"' removed
  ...
  ]
  
  .. code-block:: python
  :caption: polls/urls.py
  
  app_name = 'polls'   added
  urlpatterns = [...]
  
  This change also means that the old way of including an ``AdminSite`` instance
  is deprecated. Instead, pass ``admin.site.urls`` directly to
  ``django.conf.urls.url()``:
  
  .. code-block:: python
  :caption: urls.py
  
  from django.conf.urls import url
  from django.contrib import admin
  
  urlpatterns = [
  url(r'^admin/', admin.site.urls),
  ]
  
  URL application namespace required if setting an instance namespace
  -------------------------------------------------------------------
  
  In the past, an instance namespace without an application namespace
  would serve the same purpose as the application namespace, but it was
  impossible to reverse the patterns if there was an application namespace
  with the same name. Includes that specify an instance namespace require that
  the included URLconf sets an application namespace.
  
  ``current_app`` parameter to ``contrib.auth`` views
  ---------------------------------------------------
  
  All views in ``django.contrib.auth.views`` have the following structure::
  
  def view(request, ..., current_app=None, ...):
  
  ...
  
  if current_app is not None:
  request.current_app = current_app
  
  return TemplateResponse(request, template_name, context)
  
  As of Django 1.8, ``current_app`` is set on the ``request`` object. For
  consistency, these views will require the caller to set ``current_app`` on the
  ``request`` instead of passing it in a separate argument.
  
  ``django.contrib.gis.geoip``
  ----------------------------
  
  The :mod:`django.contrib.gis.geoip2` module supersedes
  ``django.contrib.gis.geoip``. The new module provides a similar API except that
  it doesn't provide the legacy GeoIP-Python API compatibility methods.
  
  Miscellaneous
  -------------
  
  * The ``weak`` argument to ``django.dispatch.signals.Signal.disconnect()`` has
  been deprecated as it has no effect.
  
  * The ``check_aggregate_support()`` method of
  ``django.db.backends.base.BaseDatabaseOperations`` has been deprecated and
  will be removed in Django 2.0. The more general ``check_expression_support()``
  should be used instead.
  
  * ``django.forms.extras`` is deprecated. You can find
  :class:`~django.forms.SelectDateWidget` in ``django.forms.widgets``
  (or simply ``django.forms``) instead.
  
  * Private API ``django.db.models.fields.add_lazy_relation()`` is deprecated.
  
  * The ``django.contrib.auth.tests.utils.skipIfCustomUser()`` decorator is
  deprecated. With the test discovery changes in Django 1.6, the tests for
  ``django.contrib`` apps are no longer run as part of the user's project.
  Therefore, the ``skipIfCustomUser`` decorator is no longer needed to
  decorate tests in ``django.contrib.auth``.
  
  * If you customized some :ref:`error handlers <error-views>`, the view
  signatures with only one request parameter are deprecated. The views should
  now also accept a second ``exception`` positional parameter.
  
  * The ``django.utils.feedgenerator.Atom1Feed.mime_type`` and
  ``django.utils.feedgenerator.RssFeed.mime_type`` attributes are deprecated in
  favor of ``content_type``.
  
  * :class:`~django.core.signing.Signer` now issues a warning if an invalid
  separator is used. This will become an exception in Django 1.10.
  
  * ``django.db.models.Field._get_val_from_obj()`` is deprecated in favor of
  ``Field.value_from_object()``.
  
  * ``django.template.loaders.eggs.Loader`` is deprecated as distributing
  applications as eggs is not recommended.
  
  * The ``callable_obj`` keyword argument to
  ``SimpleTestCase.assertRaisesMessage()`` is deprecated. Pass the callable as
  a positional argument instead.
  
  * The ``allow_tags`` attribute on methods of ``ModelAdmin`` has been
  deprecated. Use :func:`~django.utils.html.format_html`,
  :func:`~django.utils.html.format_html_join`, or
  :func:`~django.utils.safestring.mark_safe` when constructing the method's
  return value instead.
  
  * The ``enclosure`` keyword argument to ``SyndicationFeed.add_item()`` is
  deprecated. Use the new ``enclosures`` argument which accepts a list of
  ``Enclosure`` objects instead of a single one.
  
  * The ``django.template.loader.LoaderOrigin`` and
  ``django.template.base.StringOrigin`` aliases for
  ``django.template.base.Origin`` are deprecated.
  
  .. _removed-features-1.9:
  
  Features removed in 1.9
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 1.9. See :ref:`deprecated-features-1.7` for details, including how to
  remove usage of these features.
  
  * ``django.utils.dictconfig`` is removed.
  
  * ``django.utils.importlib`` is removed.
  
  * ``django.utils.tzinfo`` is removed.
  
  * ``django.utils.unittest`` is removed.
  
  * The ``syncdb`` command is removed.
  
  * ``django.db.models.signals.pre_syncdb`` and
  ``django.db.models.signals.post_syncdb`` is removed.
  
  * Support for ``allow_syncdb`` on database routers is removed.
  
  * Automatic syncing of apps without migrations is removed. Migrations are
  compulsory for all apps unless you pass the :option:`migrate --run-syncdb`
  option.
  
  * The SQL management commands for apps without migrations, ``sql``, ``sqlall``,
  ``sqlclear``, ``sqldropindexes``, and ``sqlindexes``, are removed.
  
  * Support for automatic loading of ``initial_data`` fixtures and initial SQL
  data is removed.
  
  * All models need to be defined inside an installed application or declare an
  explicit :attr:`~django.db.models.Options.app_label`. Furthermore, it isn't
  possible to import them before their application is loaded. In particular, it
  isn't possible to import models inside the root package of an application.
  
  * The model and form ``IPAddressField`` is removed. A stub field remains for
  compatibility with historical migrations.
  
  * ``AppCommand.handle_app()`` is no longer supported.
  
  * ``RequestSite`` and ``get_current_site()`` are no longer importable from
  ``django.contrib.sites.models``.
  
  * FastCGI support via the ``runfcgi`` management command is removed.
  
  * ``django.utils.datastructures.SortedDict`` is removed.
  
  * ``ModelAdmin.declared_fieldsets`` is removed.
  
  * The ``util`` modules that provided backwards compatibility are removed:
  
  * ``django.contrib.admin.util``
  * ``django.contrib.gis.db.backends.util``
  * ``django.db.backends.util``
  * ``django.forms.util``
  
  * ``ModelAdmin.get_formsets`` is removed.
  
  * The backward compatible shims introduced to rename the
  ``BaseMemcachedCache._get_memcache_timeout()`` method to
  ``get_backend_timeout()`` is removed.
  
  * The ``--natural`` and ``-n`` options for :djadmin:`dumpdata` are removed.
  
  * The ``use_natural_keys`` argument for ``serializers.serialize()`` is removed.
  
  * Private API ``django.forms.forms.get_declared_fields()`` is removed.
  
  * The ability to use a ``SplitDateTimeWidget`` with ``DateTimeField`` is
  removed.
  
  * The ``WSGIRequest.REQUEST`` property is removed.
  
  * The class ``django.utils.datastructures.MergeDict`` is removed.
  
  * The ``zh-cn`` and ``zh-tw`` language codes are removed.
  
  * The internal ``django.utils.functional.memoize()`` is removed.
  
  * ``django.core.cache.get_cache`` is removed.
  
  * ``django.db.models.loading`` is removed.
  
  * Passing callable arguments to querysets is no longer possible.
  
  * ``BaseCommand.requires_model_validation`` is removed in favor of
  ``requires_system_checks``. Admin validators is replaced by admin checks.
  
  * The ``ModelAdmin.validator_class`` and ``default_validator_class`` attributes
  are removed.
  
  * ``ModelAdmin.validate()`` is removed.
  
  * ``django.db.backends.DatabaseValidation.validate_field`` is removed in
  favor of the ``check_field`` method.
  
  * The ``validate`` management command is removed.
  
  * ``django.utils.module_loading.import_by_path`` is removed in favor of
  ``django.utils.module_loading.import_string``.
  
  * ``ssi`` and ``url`` template tags are removed from the ``future`` template
  tag library.
  
  * ``django.utils.text.javascript_quote()`` is removed.
  
  * Database test settings as independent entries in the database settings,
  prefixed by ``TEST_``, are no longer supported.
  
  * The ``cache_choices`` option to :class:`~django.forms.ModelChoiceField` and
  :class:`~django.forms.ModelMultipleChoiceField` is removed.
  
  * The default value of the
  :attr:`RedirectView.permanent <django.views.generic.base.RedirectView.permanent>`
  attribute has changed from ``True`` to ``False``.
  
  * ``django.contrib.sitemaps.FlatPageSitemap`` is removed in favor of
  ``django.contrib.flatpages.sitemaps.FlatPageSitemap``.
  
  * Private API ``django.test.utils.TestTemplateLoader`` is removed.
  
  * The ``django.contrib.contenttypes.generic`` module is removed.
  
  
  ===========================

1.8.19 not secure

===========================
  
  *March 6, 2018*
  
  Django 1.8.19 fixes two security issues in 1.18.18.
  
  CVE-2018-7536: Denial-of-service possibility in ``urlize`` and ``urlizetrunc`` template filters
  ===============================================================================================
  
  The ``django.utils.html.urlize()`` function was extremely slow to evaluate
  certain inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``urlize()`` function is used to implement the ``urlize`` and
  ``urlizetrunc`` template filters, which were thus vulnerable.
  
  The problematic regular expression is replaced with parsing logic that behaves
  similarly.
  
  CVE-2018-7537: Denial-of-service possibility in ``truncatechars_html`` and ``truncatewords_html`` template filters
  ==================================================================================================================
  
  If ``django.utils.text.Truncator``'s ``chars()`` and ``words()`` methods were
  passed the ``html=True`` argument, they were extremely slow to evaluate certain
  inputs due to a catastrophic backtracking vulnerability in a regular
  expression. The ``chars()`` and ``words()`` methods are used to implement the
  ``truncatechars_html`` and ``truncatewords_html`` template filters, which were
  thus vulnerable.
  
  The backtracking problem in the regular expression is fixed.
  
  
  ===========================

1.8.18 not secure

===========================
  
  *April 4, 2017*
  
  Django 1.8.18 fixes two security issues in 1.8.17.
  
  CVE-2017-7233: Open redirect and possible XSS attack via user-supplied numeric redirect URLs
  ============================================================================================
  
  Django relies on user input in some cases  (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security check for these
  redirects (namely ``django.utils.http.is_safe_url()``) considered some numeric
  URLs (e.g. ``http:999999999``) "safe" when they shouldn't be.
  
  Also, if a developer relies on ``is_safe_url()`` to provide safe redirect
  targets and puts such a URL into a link, they could suffer from an XSS attack.
  
  CVE-2017-7234: Open redirect vulnerability in ``django.views.static.serve()``
  =============================================================================
  
  A maliciously crafted URL to a Django site using the
  :func:`~django.views.static.serve` view could redirect to any other domain. The
  view no longer does any redirects as they don't provide any known, useful
  functionality.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid.
  
  
  ===========================

1.8.17 not secure

===========================
  
  *December 1, 2016*
  
  Django 1.8.17 fixes a regression in 1.8.16.
  
  Bugfixes
  ========
  
  * Quoted the Oracle test user's password in queries to fix the "ORA-00922:
  missing or invalid option" error when the password starts with a number or
  special character (:ticket:`27420`).
  
  
  ===========================

1.8.16 not secure

===========================
  
  *November 1, 2016*
  
  Django 1.8.16 fixes two security issues in 1.8.15.
  
  User with hardcoded password created when running tests on Oracle
  =================================================================
  
  When running tests with an Oracle database, Django creates a temporary database
  user. In older versions, if a password isn't manually specified in the database
  settings ``TEST`` dictionary, a hardcoded password is used. This could allow
  an attacker with network access to the database server to connect.
  
  This user is usually dropped after the test suite completes, but not when using
  the ``manage.py test --keepdb`` option or if the user has an active session
  (such as an attacker's connection).
  
  A randomly generated password is now used for each test run.
  
  DNS rebinding vulnerability when ``DEBUG=True``
  ===============================================
  
  Older versions of Django don't validate the ``Host`` header against
  ``settings.ALLOWED_HOSTS`` when ``settings.DEBUG=True``. This makes them
  vulnerable to a `DNS rebinding attack
  <https://benmmurphy.github.io/blog/2016/07/11/rails-webconsole-dns-rebinding/>`_.
  
  While Django doesn't ship a module that allows remote code execution, this is
  at least a cross-site scripting vector, which could be quite serious if
  developers load a copy of the production database in development or connect to
  some production services for which there's no development instance, for
  example. If a project uses a package like the ``django-debug-toolbar``, then
  the attacker could execute arbitrary SQL, which could be especially bad if the
  developers connect to the database with a superuser account.
  
  ``settings.ALLOWED_HOSTS`` is now validated regardless of ``DEBUG``. For
  convenience, if ``ALLOWED_HOSTS`` is empty and ``DEBUG=True``, the following
  variations of localhost are allowed ``['localhost', '127.0.0.1', '::1']``. If
  your local settings file has your production ``ALLOWED_HOSTS`` value, you must
  now omit it to get those fallback values.
  
  
  ===========================

1.8.15 not secure

===========================
  
  *September 26, 2016*
  
  Django 1.8.15 fixes a security issue in 1.8.14.
  
  CSRF protection bypass on a site with Google Analytics
  ======================================================
  
  An interaction between Google Analytics and Django's cookie parsing could allow
  an attacker to set arbitrary cookies leading to a bypass of CSRF protection.
  
  The parser for ``request.COOKIES`` is simplified to better match the behavior
  of browsers and to mitigate this attack. ``request.COOKIES`` may now contain
  cookies that are invalid according to :rfc:`6265` but are possible to set via
  ``document.cookie``.
  
  
  ===========================

1.8.14 not secure

===========================
  
  *July 18, 2016*
  
  Django 1.8.14 fixes a security issue and a bug in 1.8.13.
  
  XSS in admin's add/change related popup
  =======================================
  
  Unsafe usage of JavaScript's ``Element.innerHTML`` could result in XSS in the
  admin's add/change related popup. ``Element.textContent`` is now used to
  prevent execution of the data.
  
  The debug view also used ``innerHTML``. Although a security issue wasn't
  identified there, out of an abundance of caution it's also updated to use
  ``textContent``.
  
  Bugfixes
  ========
  
  * Fixed missing ``varchar/text_pattern_ops`` index on ``CharField`` and
  ``TextField`` respectively when using ``AddField`` on PostgreSQL
  (:ticket:`26889`).
  
  
  ===========================

1.8.13 not secure

===========================
  
  *May 2, 2016*
  
  Django 1.8.13 fixes several bugs in 1.8.12.
  
  Bugfixes
  ========
  
  * Fixed ``TimeField`` microseconds round-tripping on MySQL and SQLite
  (:ticket:`26498`).
  
  * Restored conversion of an empty string to null when saving values of
  ``GenericIPAddressField`` on SQLite and MySQL (:ticket:`26557`).
  
  
  ===========================

1.8.12 not secure

===========================
  
  *April 1, 2016*
  
  Django 1.8.12 fixes several bugs in 1.8.11.
  
  Bugfixes
  ========
  
  * Made ``MultiPartParser`` ignore filenames that normalize to an empty string
  to fix crash in ``MemoryFileUploadHandler`` on specially crafted user input
  (:ticket:`26325`).
  
  * Fixed data loss on SQLite where ``DurationField`` values with fractional
  seconds could be saved as ``None`` (:ticket:`26324`).
  
  * Restored the functionality of the admin's ``raw_id_fields`` in
  ``list_editable`` (:ticket:`26387`).
  
  
  ===========================

1.8.11 not secure

===========================
  
  *March 5, 2016*
  
  Django 1.8.11 fixes a regression on Python 2 in the 1.8.10 security release
  where ``utils.http.is_safe_url()`` crashes on bytestring URLs (:ticket:`26308`).
  
  
  ===========================

1.8.10 not secure

===========================
  
  *March 1, 2016*
  
  Django 1.8.10 fixes two security issues and several bugs in 1.8.9.
  
  CVE-2016-2512: Malicious redirect and possible XSS attack via user-supplied redirect URLs containing basic auth
  ===============================================================================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security check for these
  redirects (namely ``django.utils.http.is_safe_url()``) considered some URLs
  with basic authentication credentials "safe" when they shouldn't be.
  
  For example, a URL like ``http://mysite.example.com\attacker.com`` would be
  considered safe if the request's host is ``http://mysite.example.com``, but
  redirecting to this URL sends the user to ``attacker.com``.
  
  Also, if a developer relies on ``is_safe_url()`` to provide safe redirect
  targets and puts such a URL into a link, they could suffer from an XSS attack.
  
  CVE-2016-2513: User enumeration through timing difference on password hasher work factor upgrade
  ================================================================================================
  
  In each major version of Django since 1.6, the default number of iterations for
  the ``PBKDF2PasswordHasher`` and its subclasses has increased. This improves
  the security of the password as the speed of hardware increases, however, it
  also creates a timing difference between a login request for a user with a
  password encoded in an older number of iterations and login request for a
  nonexistent user (which runs the default hasher's default number of iterations
  since Django 1.6).
  
  This only affects users who haven't logged in since the iterations were
  increased. The first time a user logs in after an iterations increase, their
  password is updated with the new iterations and there is no longer a timing
  difference.
  
  The new ``BasePasswordHasher.harden_runtime()`` method allows hashers to bridge
  the runtime gap between the work factor (e.g. iterations) supplied in existing
  encoded passwords and the default work factor of the hasher. This method
  is implemented for ``PBKDF2PasswordHasher``  and ``BCryptPasswordHasher``.
  The number of rounds for the latter hasher hasn't changed since Django 1.4, but
  some projects may subclass it and increase the work factor as needed.
  
  A warning will be emitted for any :ref:`third-party password hashers that don't
  implement <write-your-own-password-hasher>` a ``harden_runtime()`` method.
  
  If you have different password hashes in your database (such as SHA1 hashes
  from users who haven't logged in since the default hasher switched to PBKDF2
  in Django 1.4), the timing difference on a login request for these users may be
  even greater and this fix doesn't remedy that difference (or any difference
  when changing hashers). You may be able to :ref:`upgrade those hashes
  <wrapping-password-hashers>` to prevent a timing attack for that case.
  
  Bugfixes
  ========
  
  * Fixed a crash on PostgreSQL that prevented using ``TIME_ZONE=None`` and
  ``USE_TZ=False`` (:ticket:`26177`).
  
  * Added system checks for query name clashes of hidden relationships
  (:ticket:`26162`).
  
  * Made ``forms.FileField`` and ``utils.translation.lazy_number()`` picklable
  (:ticket:`26212`).
  
  * Fixed :class:`~django.contrib.postgres.fields.RangeField` and
  :class:`~django.contrib.postgres.fields.ArrayField` serialization with
  ``None`` values (:ticket:`26215`).
  
  * Reallowed dashes in top-level domain names of URLs checked by
  ``URLValidator`` to fix a regression in Django 1.8 (:ticket:`26204`).
  
  * Fixed ``BoundField`` to reallow slices of subwidgets (:ticket:`26267`).
  
  * Prevented ``ContentTypeManager`` instances from sharing their cache
  (:ticket:`26286`).
  
  
  ==========================

1.8.9 not secure

==========================
  
  *February 1, 2016*
  
  Django 1.8.9 fixes several bugs in 1.8.8.
  
  Bugfixes
  ========
  
  * Fixed a regression that caused the "user-tools" items to display on the
  admin's logout page (:ticket:`26035`).
  
  * Fixed a crash in the translations system when the current language has no
  translations (:ticket:`26046`).
  
  * Fixed a regression that caused the incorrect day to be selected when opening
  the admin calendar widget for timezones from GMT+0100 to GMT+1200
  (:ticket:`24980`).
  
  * Fixed a regression in 1.8.8 causing incorrect index handling in migrations on
  PostgreSQL when adding ``db_index=True`` or ``unique=True`` to a
  ``CharField`` or ``TextField`` that already had the other specified, or when
  removing one of them from a field that had both, or when adding
  ``unique=True`` to a field already listed in ``unique_together``
  (:ticket:`26034`).
  
  * Fixed a crash when using an ``__in`` lookup inside a ``Case`` expression
  (:ticket:`26071`).
  
  * Fixed a crash when using a reverse ``OneToOneField`` in
  ``ModelAdmin.readonly_fields`` (:ticket:`26060`).
  
  * Fixed a regression in Django 1.8.5 that broke copying a ``SimpleLazyObject``
  with ``copy.copy()`` (:ticket:`26122`).
  
  * Fixed the ``contrib.gis`` map widgets when using
  ``USE_THOUSAND_SEPARATOR=True`` (:ticket:`20415`).
  
  
  ==========================

1.8.8 not secure

==========================
  
  *January 2, 2016*
  
  Django 1.8.8 fixes several bugs in 1.8.7.
  
  Python 3.2 users, please be advised that we've decided to drop support for
  Python 3.2 in Django 1.8.x at the end of 2016. We won't break things
  intentionally after that, but we won't test subsequent releases against Python
  3.2 either. Upstream support for Python 3.2 ends February 2016 so we don't find
  much value in providing security updates for a version of Python that could be
  insecure. To read more about the decision and to let us know if this will be
  problematic for you, please read the `django-developers thread
  <https://groups.google.com/d/topic/django-developers/eMu5UQpUdWs/discussion>`_.
  
  Bugfixes
  ========
  
  * Fixed incorrect ``unique_together`` field name generation by ``inspectdb``
  (:ticket:`25274`).
  
  * Corrected ``__len`` query lookup on ``ArrayField`` for empty arrays
  (:ticket:`25772`).
  
  * Restored the ability to use custom formats from ``formats.py`` with
  ``django.utils.formats.get_format()`` and the ``date`` template filter
  (:ticket:`25812`).
  
  * Fixed a state bug when migrating a ``SeparateDatabaseAndState`` operation
  backwards (:ticket:`25896`).
  
  * Fixed missing ``varchar/text_pattern_ops`` index on ``CharField`` and
  ``TextField`` respectively when using ``AlterField`` on PostgreSQL
  (:ticket:`25412`).
  
  * Fixed a state bug when using an ``AlterModelManagers`` operation
  (:ticket:`25852`).
  
  * Fixed a regression which prevented using a language not in Django's default
  language list (:setting:`LANGUAGES`) (:ticket:`25915`).
  
  * ``django.views.decorators.cache.never_cache()`` now sends more persuasive
  headers (added ``no-cache, no-store, must-revalidate`` to ``Cache-Control``)
  to better prevent caching (:ticket:`13008`). This fixes a problem where a
  page refresh in Firefox cleared the selected entries in the admin's
  ``filter_horizontal`` and ``filter_vertical`` widgets, which could result
  in inadvertent data loss if a user didn't notice that and then submitted the
  form (:ticket:`22955`).
  
  * Fixed a regression in the admin which ignored line breaks in read-only fields
  instead of converting them to ``<br>`` (:ticket:`25465`).
  
  * Made ``loaddata`` skip disabling and enabling database constraints when it
  doesn't load any fixtures (:ticket:`23372`).
  
  * Fixed a crash in ``QuerySet.values()/values_list()`` after an ``annotate()``
  and ``order_by()`` when ``values()/values_list()`` includes a field not in
  the ``order_by()`` (:ticket:`25316`).
  
  
  ==========================

1.8.7 not secure

==========================
  
  *November 24, 2015*
  
  Django 1.8.7 fixes a security issue and several bugs in 1.8.6.
  
  Additionally, Django's vendored version of six, ``django.utils.six``, has
  been upgraded to the latest release (1.10.0).
  
  Fixed settings leak possibility in ``date`` template filter
  ===========================================================
  
  If an application allows users to specify an unvalidated format for dates and
  passes this format to the :tfilter:`date` filter, e.g.
  ``{{ last_updated|date:user_date_format }}``, then a malicious user could
  obtain any secret in the application's settings by specifying a settings key
  instead of a date format. e.g. ``"SECRET_KEY"`` instead of ``"j/m/Y"``.
  
  To remedy this, the underlying function used by the ``date`` template filter,
  ``django.utils.formats.get_format()``, now only allows accessing the date/time
  formatting settings.
  
  Bugfixes
  ========
  
  * Fixed a crash of the debug view during the autumn DST change when
  :setting:`USE_TZ` is ``False`` and ``pytz`` is installed.
  
  * Fixed a regression in 1.8.6 that caused database routers without an
  ``allow_migrate()`` method to crash (:ticket:`25686`).
  
  * Fixed a regression in 1.8.6 by restoring the ability to use ``Manager``
  objects for the ``queryset`` argument of ``ModelChoiceField``
  (:ticket:`25683`).
  
  * Fixed a regression in 1.8.6 that caused an application with South migrations
  in the ``migrations`` directory to fail (:ticket:`25618`).
  
  * Fixed a data loss possibility with :class:`~django.db.models.Prefetch` if
  ``to_attr`` is set to a ``ManyToManyField`` (:ticket:`25693`).
  
  * Fixed a regression in 1.8 by making ``gettext()`` once again return UTF-8
  bytestrings on Python 2 if the input is a bytestring (:ticket:`25720`).
  
  * Fixed serialization of
  :class:`~django.contrib.postgres.fields.DateRangeField` and
  :class:`~django.contrib.postgres.fields.DateTimeRangeField` (:ticket:`24937`).
  
  * Fixed the exact lookup of ``ArrayField`` (:ticket:`25666`).
  
  * Fixed ``Model.refresh_from_db()`` updating of ``ForeignKey`` fields with
  ``on_delete=models.SET_NULL`` (:ticket:`25715`).
  
  * Fixed a duplicate query regression in 1.8 on proxied model deletion
  (:ticket:`25685`).
  
  * Fixed ``set_FOO_order()`` crash when the ``ForeignKey`` of a model with
  ``order_with_respect_to`` references a model with a ``OneToOneField``
  primary key (:ticket:`25786`).
  
  * Fixed incorrect validation for ``PositiveIntegerField`` and
  ``PositiveSmallIntegerField`` on MySQL resulting in values greater than
  4294967295 or 65535, respectively, passing validation and being silently
  truncated by the database (:ticket:`25767`).
  
  
  ==========================

1.8.6 not secure

==========================
  
  *November 4, 2015*
  
  Django 1.8.6 adds official support for Python 3.5 and fixes several bugs in
  1.8.5.
  
  Bugfixes
  ========
  
  * Fixed a regression causing ``ModelChoiceField`` to ignore
  ``prefetch_related()`` on its queryset (:ticket:`25496`).
  
  * Allowed "mode=memory" in SQLite test database name if supported
  (:ticket:`12118`).
  
  * Fixed system check crash on ``ForeignKey`` to abstract model
  (:ticket:`25503`).
  
  * Fixed incorrect queries when you have multiple ``ManyToManyField``\s on
  different models that have the same field name, point to the same model, and
  have their reverse relations disabled (:ticket:`25545`).
  
  * Allowed filtering over a ``RawSQL`` annotation (:ticket:`25506`).
  
  * Made the ``Concat`` database function idempotent on SQLite (:ticket:`25517`).
  
  * Avoided a confusing stack trace when starting :djadmin:`runserver` with an
  invalid :setting:`INSTALLED_APPS` setting (:ticket:`25510`). This regression
  appeared in 1.8.5 as a side effect of fixing :ticket:`24704`.
  
  * Made deferred models use their proxied model's ``_meta.apps`` for caching
  and retrieval (:ticket:`25563`). This prevents any models generated in data
  migrations using ``QuerySet.defer()`` from leaking to test and application
  code.
  
  * Fixed a typo in the name of the ``strictly_above`` PostGIS lookup
  (:ticket:`25592`).
  
  * Fixed crash with ``contrib.postgres.forms.SplitArrayField`` and
  ``IntegerField`` on invalid value (:ticket:`25597`).
  
  * Added a helpful error message when Django and South migrations exist in the
  same directory (:ticket:`25618`).
  
  * Fixed a regression in ``URLValidator`` that allowed URLs with consecutive
  dots in the domain section (like ``http://example..com/``) to pass
  (:ticket:`25620`).
  
  * Fixed a crash with ``GenericRelation`` and
  ``BaseModelAdmin.to_field_allowed`` (:ticket:`25622`).
  
  
  ==========================

1.8.5 not secure

==========================
  
  *October 3, 2015*
  
  Django 1.8.5 fixes several bugs in 1.8.4.
  
  Bugfixes
  ========
  
  * Made the development server's autoreload more robust (:ticket:`24704`).
  
  * Fixed ``AssertionError`` in some delete queries with a model containing a
  field that is both a foreign and primary key (:ticket:`24951`).
  
  * Fixed ``AssertionError`` in some complex queries (:ticket:`24525`).
  
  * Fixed a migrations crash with ``GenericForeignKey`` (:ticket:`25040`).
  
  * Made ``translation.override()`` clear the overridden language when a
  translation isn't initially active (:ticket:`25295`).
  
  * Fixed crash when using a value in ``ModelAdmin.list_display`` that clashed
  with a reverse field on the model (:ticket:`25299`).
  
  * Fixed autocompletion for options of non-``argparse`` management commands
  (:ticket:`25372`).
  
  * Alphabetized ordering of imports in ``from django.db import migrations,
  models`` statement in newly created migrations (:ticket:`25384`).
  
  * Fixed migrations crash on MySQL when adding a text or a blob field with an
  unhashable default (:ticket:`25393`).
  
  * Changed ``Count`` queries to execute ``COUNT(*)`` instead of ``COUNT('*')``
  as versions of Django before 1.8 did (:ticket:`25377`). This may fix a
  performance regression on some databases.
  
  * Fixed custom queryset chaining with ``values()`` and ``values_list()``
  (:ticket:`20625`).
  
  * Moved the :ref:`unsaved model instance assignment data loss check
  <unsaved-model-instance-check-18>` on reverse relations to ``Model.save()``
  (:ticket:`25160`).
  
  * Readded inline foreign keys to form instances when validating model formsets
  (:ticket:`25431`).
  
  * Allowed using ORM write methods after disabling autocommit with
  :func:`set_autocommit(False) <django.db.transaction.set_autocommit>`
  (:ticket:`24921`).
  
  * Fixed the ``manage.py test --keepdb`` option on Oracle (:ticket:`25421`).
  
  * Fixed incorrect queries with multiple many-to-many fields on a model with the
  same 'to' model and with ``related_name`` set to '+' (:ticket:`24505`,
  :ticket:`25486`).
  
  * Fixed pickling a ``SimpleLazyObject`` wrapping a model (:ticket:`25389`).
  
  
  ==========================

1.8.4 not secure

==========================
  
  *August 18, 2015*
  
  Django 1.8.4 fixes a security issue and several bugs in 1.8.3.
  
  Denial-of-service possibility in ``logout()`` view by filling session store
  ===========================================================================
  
  Previously, a session could be created when anonymously accessing the
  ``django.contrib.auth.views.logout()`` view (provided it wasn't decorated
  with :func:`~django.contrib.auth.decorators.login_required` as done in the
  admin). This could allow an attacker to easily create many new session records
  by sending repeated requests, potentially filling up the session store or
  causing other users' session records to be evicted.
  
  The :class:`~django.contrib.sessions.middleware.SessionMiddleware` has been
  modified to no longer create empty session records, including when
  :setting:`SESSION_SAVE_EVERY_REQUEST` is active.
  
  Bugfixes
  ========
  
  * Added the ability to serialize values from the newly added
  :class:`~django.db.models.UUIDField` (:ticket:`25019`).
  
  * Added a system check warning if the old ``TEMPLATE_*`` settings are defined
  in addition to the new ``TEMPLATES`` setting.
  
  * Fixed ``QuerySet.raw()`` so ``InvalidQuery`` is not raised when using the
  ``db_column`` name of a ``ForeignKey`` field with ``primary_key=True``
  (:ticket:`12768`).
  
  * Prevented an exception in ``TestCase.setUpTestData()`` from leaking the
  transaction (:ticket:`25176`).
  
  * Fixed ``has_changed()`` method in ``contrib.postgres.forms.HStoreField``
  (:ticket:`25215`, :ticket:`25233`).
  
  * Fixed the recording of squashed migrations when running the ``migrate``
  command (:ticket:`25231`).
  
  * Moved the :ref:`unsaved model instance assignment data loss check
  <unsaved-model-instance-check-18>` to ``Model.save()`` to allow easier usage
  of in-memory models (:ticket:`25160`).
  
  * Prevented ``varchar_patterns_ops`` and ``text_patterns_ops`` indexes for
  ``ArrayField`` (:ticket:`25180`).
  
  
  ==========================

1.8.3 not secure

==========================
  
  *July 8, 2015*
  
  Django 1.8.3 fixes several security issues and bugs in 1.8.2.
  
  Also, ``django.utils.deprecation.RemovedInDjango20Warning`` was renamed to
  ``RemovedInDjango110Warning`` as the version roadmap was revised to 1.9, 1.10,
  1.11 (LTS), 2.0 (drops Python 2 support). For backwards compatibility,
  ``RemovedInDjango20Warning`` remains as an importable alias.
  
  Denial-of-service possibility by filling session store
  ======================================================
  
  In previous versions of Django, the session backends created a new empty record
  in the session storage anytime ``request.session`` was accessed and there was a
  session key provided in the request cookies that didn't already have a session
  record. This could allow an attacker to easily create many new session records
  simply by sending repeated requests with unknown session keys, potentially
  filling up the session store or causing other users' session records to be
  evicted.
  
  The built-in session backends now create a session record only if the session
  is actually modified; empty session records are not created. Thus this
  potential DoS is now only possible if the site chooses to expose a
  session-modifying view to anonymous users.
  
  As each built-in session backend was fixed separately (rather than a fix in the
  core sessions framework), maintainers of third-party session backends should
  check whether the same vulnerability is present in their backend and correct
  it if so.
  
  Header injection possibility since validators accept newlines in input
  ======================================================================
  
  Some of Django's built-in validators
  (:class:`~django.core.validators.EmailValidator`, most seriously) didn't
  prohibit newline characters (due to the usage of ``$`` instead of ``\Z`` in the
  regular expressions). If you use values with newlines in HTTP response or email
  headers, you can suffer from header injection attacks. Django itself isn't
  vulnerable because :class:`~django.http.HttpResponse` and the mail sending
  utilities in :mod:`django.core.mail` prohibit newlines in HTTP and SMTP
  headers, respectively. While the validators have been fixed in Django, if
  you're creating HTTP responses or email messages in other ways, it's a good
  idea to ensure that those methods prohibit newlines as well. You might also
  want to validate that any existing data in your application doesn't contain
  unexpected newlines.
  
  :func:`~django.core.validators.validate_ipv4_address`,
  :func:`~django.core.validators.validate_slug`, and
  :class:`~django.core.validators.URLValidator` are also affected, however, as
  of Django 1.6 the ``GenericIPAddresseField``, ``IPAddressField``, ``SlugField``,
  and ``URLField`` form fields which use these validators all strip the input, so
  the possibility of newlines entering your data only exists if you are using
  these validators outside of the form fields.
  
  The undocumented, internally unused ``validate_integer()`` function is now
  stricter as it validates using a regular expression instead of simply casting
  the value using ``int()`` and checking if an exception was raised.
  
  Denial-of-service possibility in URL validation
  ===============================================
  
  :class:`~django.core.validators.URLValidator` included a regular expression
  that was extremely slow to evaluate against certain invalid inputs. This regular
  expression has been simplified and optimized.
  
  Bugfixes
  ========
  
  * Fixed ``BaseRangeField.prepare_value()`` to use each ``base_field``’s
  ``prepare_value()`` method (:ticket:`24841`).
  
  * Fixed crash during :djadmin:`makemigrations` if a migrations module either
  is missing ``__init__.py`` or is a file (:ticket:`24848`).
  
  * Fixed ``QuerySet.exists()`` returning incorrect results after annotation with
  ``Count()`` (:ticket:`24835`).
  
  * Corrected ``HStoreField.has_changed()`` (:ticket:`24844`).
  
  * Reverted an optimization to the CSRF template context processor which caused
  a regression (:ticket:`24836`).
  
  * Fixed a regression which caused template context processors to overwrite
  variables set on a ``RequestContext`` after it's created (:ticket:`24847`).
  
  * Prevented the loss of ``null``/``not null`` column properties during field
  renaming of MySQL databases (:ticket:`24817`).
  
  * Fixed a crash when using a reverse one-to-one relation in
  ``ModelAdmin.list_display`` (:ticket:`24851`).
  
  * Fixed quoting of SQL when renaming a field to ``AutoField`` in PostgreSQL
  (:ticket:`24892`).
  
  * Fixed lack of unique constraint when changing a field from
  ``primary_key=True`` to ``unique=True`` (:ticket:`24893`).
  
  * Fixed queryset pickling when using ``prefetch_related()`` after deleting
  objects (:ticket:`24831`).
  
  * Allowed using ``choices`` longer than 1 day with ``DurationField``
  (:ticket:`24897`).
  
  * Fixed a crash when loading squashed migrations from two apps with a
  dependency between them, where the dependent app's replaced migrations are
  partially applied (:ticket:`24895`).
  
  * Fixed recording of applied status for squashed (replacement) migrations
  (:ticket:`24628`).
  
  * Fixed queryset annotations when using ``Case`` expressions with ``exclude()``
  (:ticket:`24833`).
  
  * Corrected join promotion for multiple ``Case`` expressions. Annotating a
  query with multiple  ``Case`` expressions could unexpectedly filter out
  results (:ticket:`24924`).
  
  * Fixed usage of transforms in subqueries (:ticket:`24744`).
  
  * Fixed ``SimpleTestCase.assertRaisesMessage()`` on Python 2.7.10
  (:ticket:`24903`).
  
  * Provided better backwards compatibility for the ``verbosity`` argument in
  ``optparse`` management commands by casting it to an integer
  (:ticket:`24769`).
  
  * Fixed ``prefetch_related()`` on databases other than PostgreSQL for models
  using UUID primary keys (:ticket:`24912`).
  
  * Fixed removing ``unique_together`` constraints on MySQL (:ticket:`24972`).
  
  * Fixed crash when uploading images with MIME types that Pillow doesn't detect,
  such as bitmap, in ``forms.ImageField`` (:ticket:`24948`).
  
  * Fixed a regression when deleting a model through the admin that has a
  ``GenericRelation`` with a ``related_query_name`` (:ticket:`24940`).
  
  * Reallowed non-ASCII values for ``ForeignKey.related_name`` on Python 3 by
  fixing the false positive system check (:ticket:`25016`).
  
  * Fixed inline forms that use a parent object that has a ``UUIDField`` primary
  key and a child object that has an ``AutoField`` primary key
  (:ticket:`24958`).
  
  * Fixed a regression in the ``unordered_list`` template filter on certain
  inputs (:ticket:`25031`).
  
  * Fixed a regression in ``URLValidator`` that invalidated Punycode TLDs
  (:ticket:`25059`).
  
  * Improved ``pyinotify`` ``runserver`` polling (:ticket:`23882`).
  
  
  ==========================

1.8.2 not secure

==========================
  
  *May 20, 2015*
  
  Django 1.8.2 fixes a security issue and several bugs in 1.8.1.
  
  Fixed session flushing in the ``cached_db`` backend
  ===================================================
  
  A change to ``session.flush()`` in the ``cached_db`` session backend in Django
  1.8 mistakenly sets the session key to an empty string rather than ``None``. An
  empty string is treated as a valid session key and the session cookie is set
  accordingly. Any users with an empty string in their session cookie will use
  the same session store. ``session.flush()`` is called by
  ``django.contrib.auth.logout()`` and, more seriously, by
  ``django.contrib.auth.login()`` when a user switches accounts. If a user is
  logged in and logs in again to a different account (without logging out) the
  session is flushed to avoid reuse. After the session is flushed (and its
  session key becomes ``''``) the account details are set on the session and the
  session is saved. Any users with an empty string in their session cookie will
  now be logged into that account.
  
  Bugfixes
  ========
  
  * Fixed check for template engine alias uniqueness (:ticket:`24685`).
  
  * Fixed crash when reusing the same ``Case`` instance in a query
  (:ticket:`24752`).
  
  * Corrected join promotion for ``Case`` expressions. For example, annotating a
  query with a  ``Case`` expression could unexpectedly filter out results
  (:ticket:`24766`).
  
  * Fixed negated ``Q`` objects in expressions. Cases like
  ``Case(When(~Q(friends__age__lte=30)))`` tried to generate a subquery which
  resulted in a crash (:ticket:`24705`).
  
  * Fixed incorrect GROUP BY clause generation on MySQL when the query's model
  has a self-referential foreign key (:ticket:`24748`).
  
  * Implemented ``ForeignKey.get_db_prep_value()`` so that ``ForeignKey``\s
  pointing to :class:`~django.db.models.UUIDField` and inheritance on models
  with ``UUIDField`` primary keys work correctly (:ticket:`24698`,
  :ticket:`24712`).
  
  * Fixed ``isnull`` lookup for ``HStoreField`` (:ticket:`24751`).
  
  * Fixed a MySQL crash when a migration removes a combined index (unique_together
  or index_together) containing a foreign key (:ticket:`24757`).
  
  * Fixed session cookie deletion when using :setting:`SESSION_COOKIE_DOMAIN`
  (:ticket:`24799`).
  
  * On PostgreSQL, when no access is granted for the ``postgres`` database,
  Django now falls back to the default database when it normally requires a
  "no database" connection (:ticket:`24791`).
  
  * Fixed display of ``contrib.admin``’s ``ForeignKey`` widget when it's used
  in a row with other fields (:ticket:`24784`).
  
  
  ==========================

1.8.1 not secure

==========================
  
  *May 1, 2015*
  
  Django 1.8.1 fixes several bugs in 1.8 and includes some optimizations in the
  migrations framework.
  
  Bugfixes
  ========
  
  * Added support for serializing :class:`~datetime.timedelta` objects in
  migrations (:ticket:`24566`).
  
  * Restored proper parsing of the :djadmin:`testserver` command's positional
  arguments (fixture names) (:ticket:`24571`).
  
  * Prevented ``TypeError`` in translation functions ``check_for_language()`` and
  ``get_language_bidi()`` when translations are deactivated (:ticket:`24569`).
  
  * Fixed :djadmin:`squashmigrations` command when using
  :class:`~django.db.migrations.operations.SeparateDatabaseAndState`
  (:ticket:`24278`).
  
  * Stripped microseconds from ``datetime`` values when using an older version of
  the MySQLdb DB API driver as it does not support fractional seconds
  (:ticket:`24584`).
  
  * Fixed a migration crash when altering
  :class:`~django.db.models.ManyToManyField`\s (:ticket:`24513`).
  
  * Fixed a crash with ``QuerySet.update()`` on foreign keys to one-to-one fields
  (:ticket:`24578`).
  
  * Fixed a regression in the model detail view of
  :mod:`~django.contrib.admindocs` when a model has a reverse foreign key
  relation (:ticket:`24624`).
  
  * Prevented arbitrary file inclusions in :mod:`~django.contrib.admindocs`
  (:ticket:`24625`).
  
  * Fixed a crash with ``QuerySet.update()`` on foreign keys to instances with
  ``uuid`` primary keys (:ticket:`24611`).
  
  * Fixed database introspection with SQLite 3.8.9 (released April 8, 2015)
  (:ticket:`24637`).
  
  * Updated ``urlpatterns`` examples generated by :djadmin:`startproject` to
  remove usage of referencing views by dotted path in
  ``django.conf.urls.url()`` which is deprecated in Django 1.8
  (:ticket:`24635`).
  
  * Fixed queries where an expression was referenced in ``order_by()``, but wasn't
  part of the select clause. An example query is
  ``qs.annotate(foo=F('field')).values('pk').order_by('foo'))`` (:ticket:`24615`).
  
  * Fixed a database table name quoting regression (:ticket:`24605`).
  
  * Prevented the loss of ``null``/``not null`` column properties during field
  alteration of MySQL databases (:ticket:`24595`).
  
  * Fixed JavaScript path of ``contrib.admin``’s related field widget when using
  alternate static file storages (:ticket:`24655`).
  
  * Fixed a migration crash when adding new relations to models
  (:ticket:`24573`).
  
  * Fixed a migration crash when applying migrations with model managers on
  Python 3 that were generated on Python 2 (:ticket:`24701`).
  
  * Restored the ability to use iterators as queryset filter arguments
  (:ticket:`24719`).
  
  * Fixed a migration crash when renaming the target model of a many-to-many
  relation (:ticket:`24725`).
  
  * Removed flushing of the test database with :option:`test --keepdb`, which
  prevented apps with data migrations from using the option (:ticket:`24729`).
  
  * Fixed ``makemessages`` crash in some locales (:ticket:`23271`).
  
  * Fixed help text positioning of ``contrib.admin`` fields that use the
  ``ModelAdmin.filter_horizontal`` and ``filter_vertical`` options
  (:ticket:`24676`).
  
  * Fixed ``AttributeError: function 'GDALAllRegister' not found`` error when
  initializing ``contrib.gis`` on Windows.
  
  Optimizations
  =============
  
  * Changed ``ModelState`` to deepcopy fields instead of deconstructing and
  reconstructing (:ticket:`24591`). This speeds up the rendering of model
  states and reduces memory usage when running :djadmin:`manage.py migrate
  <migrate>` (although other changes in this release may negate any performance
  benefits).
  
  
  ========================

1.8 not secure

========================
  
  *April 1, 2015*
  
  Welcome to Django 1.8!
  
  These release notes cover the :ref:`new features <whats-new-1.8>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.8>` you'll
  want to be aware of when upgrading from Django 1.7 or older versions. We've
  also :ref:`begun the deprecation process for some features
  <deprecated-features-1.8>`, and some features have reached the end of their
  deprecation process and :ref:`have been removed <removed-features-1.8>`.
  
  See the :doc:`/howto/upgrade-version` guide if you're updating an existing
  project.
  
  Django 1.8 has been designated as Django's second :term:`long-term support
  release <Long-term support release>`. It will receive security updates for at
  least three years after its release. Support for the previous LTS, Django 1.4,
  will end 6 months from the release date of Django 1.8.
  
  Python compatibility
  ====================
  
  Django 1.8 requires Python 2.7, 3.2, 3.3, 3.4, or 3.5. We **highly recommend**
  and only officially support the latest release of each series.
  
  Django 1.8 is the first release to support Python 3.5.
  
  Due to the end of upstream support for Python 3.2 in February 2016, we won't
  test Django 1.8.x on Python 3.2 after the end of 2016.
  
  .. _whats-new-1.8:
  
  What's new in Django 1.8
  ========================
  
  ``Model._meta`` API
  -------------------
  
  Django now has a formalized API for :doc:`Model._meta </ref/models/meta>`,
  providing an officially supported way to :ref:`retrieve fields
  <model-meta-field-api>` and filter fields based on their :ref:`attributes
  <model-field-attributes>`.
  
  The ``Model._meta`` object has been part of Django since the days of pre-0.96
  "Magic Removal" -- it just wasn't an official, stable API. In recognition of
  this, we've endeavored to maintain backwards-compatibility with the old
  API endpoint where possible. However, API endpoints that aren't part of the
  new official API have been deprecated and will eventually be removed.
  
  Multiple template engines
  -------------------------
  
  Django 1.8 defines a stable API for integrating template backends. It includes
  built-in support for the Django template language and for
  :class:`~django.template.backends.jinja2.Jinja2`. It supports rendering
  templates with multiple engines within the same project. Learn more about the
  new features in the :doc:`topic guide </topics/templates>` and check the
  upgrade instructions in older versions of the documentation.
  
  Security enhancements
  ---------------------
  
  Several features of the django-secure_ third-party library have been
  integrated into Django. :class:`django.middleware.security.SecurityMiddleware`
  provides several security enhancements to the request/response cycle. The new
  :option:`check --deploy` option allows you to check your production settings
  file for ways to increase the security of your site.
  
  .. _django-secure: https://pypi.org/project/django-secure/
  
  New PostgreSQL specific functionality
  -------------------------------------
  
  Django now has a module with extensions for PostgreSQL specific features, such
  as :class:`~django.contrib.postgres.fields.ArrayField`,
  :class:`~django.contrib.postgres.fields.HStoreField`, :ref:`range-fields`, and
  :lookup:`unaccent` lookup. A full breakdown of the features is available
  :doc:`in the documentation </ref/contrib/postgres/index>`.
  
  New data types
  --------------
  
  * Django now has a :class:`~django.db.models.UUIDField` for storing
  universally unique identifiers. It is stored as the native ``uuid`` data type
  on PostgreSQL and as a fixed length character field on other backends. There
  is a corresponding :class:`form field <django.forms.UUIDField>`.
  
  * Django now has a :class:`~django.db.models.DurationField` for storing periods
  of time - modeled in Python by :class:`~python:datetime.timedelta`. It is
  stored in the native ``interval`` data type on PostgreSQL, as a ``INTERVAL
  DAY(9) TO SECOND(6)`` on Oracle, and as a ``bigint`` of microseconds on other
  backends. Date and time related arithmetic has also been improved on all
  backends. There is a corresponding :class:`form field
  <django.forms.DurationField>`.
  
  Query Expressions, Conditional Expressions, and Database Functions
  ------------------------------------------------------------------
  
  :doc:`Query Expressions </ref/models/expressions>` allow you to create,
  customize, and compose complex SQL expressions. This has enabled annotate
  to accept expressions other than aggregates. Aggregates are now able to
  reference multiple fields, as well as perform arithmetic, similar to ``F()``
  objects. :meth:`~django.db.models.query.QuerySet.order_by` has also gained the
  ability to accept expressions.
  
  :doc:`Conditional Expressions </ref/models/conditional-expressions>` allow
  you to use :keyword:`if` ... :keyword:`elif` ... :keyword:`else` logic within
  queries.
  
  A collection of :doc:`database functions </ref/models/database-functions>` is
  also included with functionality such as
  :class:`~django.db.models.functions.Coalesce`,
  :class:`~django.db.models.functions.Concat`, and
  :class:`~django.db.models.functions.Substr`.
  
  ``TestCase`` data setup
  -----------------------
  
  :class:`~django.test.TestCase` has been refactored to allow for data
  initialization at the class level using transactions and savepoints. Database
  backends which do not support transactions, like MySQL with the MyISAM storage
  engine, will still be able to run these tests but won't benefit from the
  improvements. Tests are now run within two nested
  :func:`~django.db.transaction.atomic()` blocks: one for the whole class and one
  for each test.
  
  * The class method
  :meth:`TestCase.setUpTestData() <django.test.TestCase.setUpTestData>` adds
  the ability to setup test data at the class level. Using this technique can
  speed up the tests as compared to using ``setUp()``.
  
  * Fixture loading within ``TestCase`` is now performed once for the whole
  ``TestCase``.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :class:`~django.contrib.admin.ModelAdmin` now has a
  :meth:`~django.contrib.admin.ModelAdmin.has_module_permission`
  method to allow limiting access to the module on the admin index page.
  
  * :class:`~django.contrib.admin.InlineModelAdmin` now has an attribute
  :attr:`~django.contrib.admin.InlineModelAdmin.show_change_link` that
  supports showing a link to an inline object's change form.
  
  * Use the new ``django.contrib.admin.RelatedOnlyFieldListFilter`` in
  :attr:`ModelAdmin.list_filter <django.contrib.admin.ModelAdmin.list_filter>`
  to limit the ``list_filter`` choices to foreign objects which are attached to
  those from the ``ModelAdmin``.
  
  * The :meth:`ModelAdmin.delete_view()
  <django.contrib.admin.ModelAdmin.delete_view>` displays a summary of objects
  to be deleted on the deletion confirmation page.
  
  * The jQuery library embedded in the admin has been upgraded to version 1.11.2.
  
  * You can now specify :attr:`AdminSite.site_url
  <django.contrib.admin.AdminSite.site_url>` in order to display a link to the
  front-end site.
  
  * You can now specify :attr:`ModelAdmin.show_full_result_count
  <django.contrib.admin.ModelAdmin.show_full_result_count>` to control whether
  or not the full count of objects should be displayed on a filtered admin page.
  
  * The ``AdminSite.password_change()`` method now has an ``extra_context``
  parameter.
  
  * You can now control who may login to the admin site by overriding only
  :meth:`AdminSite.has_permission()
  <django.contrib.admin.AdminSite.has_permission>` and
  :attr:`AdminSite.login_form <django.contrib.admin.AdminSite.login_form>`.
  The ``base.html`` template has a new block ``usertools`` which contains the
  user-specific header. A new context variable ``has_permission``, which gets
  its value from :meth:`~django.contrib.admin.AdminSite.has_permission`,
  indicates whether the user may access the site.
  
  * Foreign key dropdowns now have buttons for changing or deleting related
  objects using a popup.
  
  :mod:`django.contrib.admindocs`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * reStructuredText is now parsed in model docstrings.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Authorization backends can now raise
  :class:`~django.core.exceptions.PermissionDenied` in
  :meth:`~django.contrib.auth.models.User.has_perm`
  and :meth:`~django.contrib.auth.models.User.has_module_perms`
  to short-circuit permission checking.
  * :class:`~django.contrib.auth.forms.PasswordResetForm` now
  has a method :meth:`~django.contrib.auth.forms.PasswordResetForm.send_mail`
  that can be overridden to customize the mail to be sent.
  
  * The ``max_length`` of :attr:`Permission.name
  <django.contrib.auth.models.Permission.name>` has been increased from 50 to
  255 characters. Please run the database migration.
  
  * :attr:`~django.contrib.auth.models.CustomUser.USERNAME_FIELD` and
  :attr:`~django.contrib.auth.models.CustomUser.REQUIRED_FIELDS` now supports
  :class:`~django.db.models.ForeignKey`\s.
  
  * The default iteration count for the PBKDF2 password hasher has been
  increased by 33%. This backwards compatible change will not affect users who
  have subclassed ``django.contrib.auth.hashers.PBKDF2PasswordHasher`` to
  change the default value.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * A new :doc:`GeoJSON serializer </ref/contrib/gis/serializers>` is now
  available.
  
  * It is now allowed to include a subquery as a geographic lookup argument, for
  example ``City.objects.filter(point__within=Country.objects.filter(continent='Africa').values('mpoly'))``.
  
  * The SpatiaLite backend now supports ``Collect`` and ``Extent`` aggregates
  when the database version is 3.0 or later.
  
  * The PostGIS 2 ``CREATE EXTENSION postgis`` and the SpatiaLite
  ``SELECT InitSpatialMetaData`` initialization commands are now automatically
  run by :djadmin:`migrate`.
  
  * The GDAL interface now supports retrieving properties of
  :ref:`raster (image) data file <raster-data-source-objects>`.
  
  * Compatibility shims for ``SpatialRefSys`` and ``GeometryColumns`` changed in
  Django 1.2 have been removed.
  
  * All GDAL-related exceptions are now raised with ``GDALException``. The former
  ``OGRException`` has been kept for backwards compatibility but should not be
  used any longer.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Session cookie is now deleted after
  :meth:`~django.contrib.sessions.backends.base.SessionBase.flush()` is called.
  
  :mod:`django.contrib.sitemaps`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :attr:`Sitemap.i18n <django.contrib.sitemaps.Sitemap.i18n>` attribute
  allows you to generate a sitemap based on the :setting:`LANGUAGES` setting.
  
  :mod:`django.contrib.sites`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :func:`~django.contrib.sites.shortcuts.get_current_site` will now lookup
  the current site based on :meth:`request.get_host()
  <django.http.HttpRequest.get_host>` if the :setting:`SITE_ID` setting is not
  defined.
  
  * The default :class:`~django.contrib.sites.models.Site` created when running
  ``migrate`` now respects the :setting:`SITE_ID` setting (instead of always
  using ``pk=1``).
  
  Cache
  ~~~~~
  
  * The ``incr()`` method of the
  ``django.core.cache.backends.locmem.LocMemCache`` backend is now thread-safe.
  
  Cryptography
  ~~~~~~~~~~~~
  
  * The ``max_age`` parameter of the
  :meth:`django.core.signing.TimestampSigner.unsign` method now also accepts a
  :py:class:`datetime.timedelta` object.
  
  Database backends
  ~~~~~~~~~~~~~~~~~
  
  * The MySQL backend no longer strips microseconds from ``datetime`` values as
  MySQL 5.6.4 and up supports fractional seconds depending on the declaration
  of the datetime field (when ``DATETIME`` includes fractional precision greater
  than 0). New datetime database columns created with Django 1.8 and MySQL 5.6.4
  and up will support microseconds. See the :ref:`MySQL database notes
  <mysql-fractional-seconds>` for more details.
  
  * The MySQL backend no longer creates explicit indexes for foreign keys when
  using the InnoDB storage engine, as MySQL already creates them automatically.
  
  * The Oracle backend no longer defines the ``connection_persists_old_columns``
  feature as ``True``. Instead, Oracle will now include a cache busting clause
  when getting the description of a table.
  
  Email
  ~~~~~
  
  * :ref:`Email backends <topic-email-backends>` now support the context manager
  protocol for opening and closing connections.
  
  * The SMTP email backend now supports ``keyfile`` and ``certfile``
  authentication with the :setting:`EMAIL_SSL_CERTFILE` and
  :setting:`EMAIL_SSL_KEYFILE` settings.
  
  * The SMTP :class:`~django.core.mail.backends.smtp.EmailBackend` now supports
  setting the ``timeout`` parameter with the :setting:`EMAIL_TIMEOUT` setting.
  
  * :class:`~django.core.mail.EmailMessage` and ``EmailMultiAlternatives`` now
  support the ``reply_to`` parameter.
  
  File Storage
  ~~~~~~~~~~~~
  
  * :meth:`Storage.get_available_name()
  <django.core.files.storage.Storage.get_available_name>` and
  :meth:`Storage.save() <django.core.files.storage.Storage.save>`
  now take a ``max_length`` argument to implement storage-level maximum
  filename length constraints. Filenames exceeding this argument will get
  truncated. This prevents a database error when appending a unique suffix to a
  long filename that already exists on the storage. See the :ref:`deprecation
  note <storage-max-length-update>` about adding this argument to your custom
  storage classes.
  
  Forms
  ~~~~~
  
  * Form widgets now render attributes with a value of ``True`` or ``False``
  as HTML5 boolean attributes.
  
  * The new :meth:`~django.forms.Form.has_error()` method allows checking
  if a specific error has happened.
  
  * If :attr:`~django.forms.Form.required_css_class` is defined on a form, then
  the ``<label>`` tags for required fields will have this class present in its
  attributes.
  
  * The rendering of non-field errors in unordered lists (``<ul>``) now includes
  ``nonfield`` in its list of classes to distinguish them from field-specific
  errors.
  
  * :class:`~django.forms.Field` now accepts a
  :attr:`~django.forms.Field.label_suffix` argument, which will override the
  form's :attr:`~django.forms.Form.label_suffix`. This enables customizing the
  suffix on a per-field basis — previously it wasn't possible to override
  a form's :attr:`~django.forms.Form.label_suffix` while using  shortcuts such
  as ``{{ form.as_p }}`` in templates.
  
  * :class:`~django.forms.SelectDateWidget` now accepts an
  :attr:`~django.forms.SelectDateWidget.empty_label` argument, which will
  override the top list choice label when :class:`~django.forms.DateField`
  is not required.
  
  * After an :class:`~django.forms.ImageField` has been cleaned and validated, the
  ``UploadedFile`` object will have an additional ``image`` attribute containing
  the Pillow ``Image`` instance used to check if the file was a valid image. It
  will also update ``UploadedFile.content_type`` with the image's content type
  as determined by Pillow.
  
  * You can now pass a callable that returns an iterable of choices when
  instantiating a :class:`~django.forms.ChoiceField`.
  
  Generic Views
  ~~~~~~~~~~~~~
  
  * Generic views that use :class:`~django.views.generic.list.MultipleObjectMixin`
  may now specify the ordering applied to the
  :attr:`~django.views.generic.list.MultipleObjectMixin.queryset` by setting
  :attr:`~django.views.generic.list.MultipleObjectMixin.ordering` or overriding
  :meth:`~django.views.generic.list.MultipleObjectMixin.get_ordering()`.
  
  * The new :attr:`SingleObjectMixin.query_pk_and_slug
  <django.views.generic.detail.SingleObjectMixin.query_pk_and_slug>`
  attribute allows changing the behavior of
  :meth:`~django.views.generic.detail.SingleObjectMixin.get_object()`
  so that it'll perform its lookup using both the primary key and the slug.
  
  * The :meth:`~django.views.generic.edit.FormMixin.get_form()` method doesn't
  require a ``form_class`` to be provided anymore. If not provided ``form_class``
  defaults to :meth:`~django.views.generic.edit.FormMixin.get_form_class()`.
  
  * Placeholders in :attr:`ModelFormMixin.success_url
  <django.views.generic.edit.ModelFormMixin.success_url>` now support the Python
  :py:meth:`str.format()` syntax. The legacy ``%(<foo>)s`` syntax is still
  supported but will be removed in Django 1.10.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * :setting:`FORMAT_MODULE_PATH` can now be a list of strings representing
  module paths. This allows importing several format modules from different
  reusable apps. It also allows overriding those custom formats in your main
  Django project.
  
  Logging
  ~~~~~~~
  
  * The :class:`django.utils.log.AdminEmailHandler` class now has a
  :meth:`~django.utils.log.AdminEmailHandler.send_mail` method to make it more
  subclass friendly.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * Database connections are now always closed after a management command called
  from the command line has finished doing its job.
  
  * Commands from alternate package formats like eggs are now also discovered.
  
  * The new :option:`dumpdata --output` option allows specifying a file to which
  the serialized data is written.
  
  * The new :option:`makemessages --exclude` and :option:`compilemessages
  --exclude` options allow excluding specific locales from processing.
  
  * :djadmin:`compilemessages` now has a ``--use-fuzzy`` or ``-f`` option which
  includes fuzzy translations into compiled files.
  
  * The :option:`loaddata --ignorenonexistent` option now ignores data for models
  that no longer exist.
  
  * :djadmin:`runserver` now uses daemon threads for faster reloading.
  
  * :djadmin:`inspectdb` now outputs ``Meta.unique_together``. It is also able to
  introspect :class:`~django.db.models.AutoField` for MySQL and PostgreSQL
  databases.
  
  * When calling management commands with options using
  :func:`~django.core.management.call_command`, the option name can match the
  command line option name (without the initial dashes) or the final option
  destination variable name, but in either case, the resulting option received
  by the command is now always the ``dest`` name specified in the command
  option definition (as long as the command uses the :mod:`argparse` module).
  
  * The :djadmin:`dbshell` command now supports MySQL's optional SSL certificate
  authority setting (``--ssl-ca``).
  
  * The new :option:`makemigrations --name` allows giving the migration(s) a
  custom name instead of a generated one.
  
  * The :djadmin:`loaddata` command now prevents repeated fixture loading. If
  :setting:`FIXTURE_DIRS` contains duplicates or a default fixture directory
  path (``app_name/fixtures``), an exception is raised.
  
  * The new ``makemigrations --exit`` option allows exiting with an error
  code if no migrations are created.
  
  * The new :djadmin:`showmigrations` command allows listing all migrations and
  their dependencies in a project.
  
  Middleware
  ~~~~~~~~~~
  
  * The :attr:`CommonMiddleware.response_redirect_class
  <django.middleware.common.CommonMiddleware.response_redirect_class>`
  attribute allows you to customize the redirects issued by the middleware.
  
  * A debug message will be logged to the ``django.request`` logger when a
  middleware raises a :exc:`~django.core.exceptions.MiddlewareNotUsed` exception
  in :setting:`DEBUG` mode.
  
  Migrations
  ~~~~~~~~~~
  
  * The :class:`~django.db.migrations.operations.RunSQL` operation can now handle
  parameters passed to the SQL statements.
  
  * It is now possible to have migrations (most probably :ref:`data migrations
  <data-migrations>`) for applications without models.
  
  * Migrations can now :ref:`serialize model managers
  <using-managers-in-migrations>` as part of the model state.
  
  * A :ref:`generic mechanism to handle the deprecation of model fields
  <migrations-removing-model-fields>` was added.
  
  * The :meth:`RunPython.noop() <django.db.migrations.operations.RunPython.noop>`
  and :attr:`RunSQL.noop <django.db.migrations.operations.RunSQL.noop>` class
  method/attribute were added to ease in making ``RunPython`` and ``RunSQL``
  operations reversible.
  
  * The migration operations :class:`~django.db.migrations.operations.RunPython`
  and :class:`~django.db.migrations.operations.RunSQL` now call the
  :meth:`allow_migrate` method of database routers. The router can use the
  newly introduced ``app_label`` and ``hints`` arguments to make a routing
  decision. To take advantage of this feature you need to update the router to
  the new ``allow_migrate`` signature, see the :ref:`deprecation section
  <deprecated-signature-of-allow-migrate>` for more details.
  
  Models
  ~~~~~~
  
  * Django now logs at most 9000 queries in ``connections.queries``, in order
  to prevent excessive memory usage in long-running processes in debug mode.
  
  * There is now a model ``Meta`` option to define a
  :attr:`default related name <django.db.models.Options.default_related_name>`
  for all relational fields of a model.
  
  * Pickling models and querysets across different versions of Django isn't
  officially supported (it may work, but there's no guarantee). An extra
  variable that specifies the current Django version is now added to the
  pickled state of models and querysets, and Django raises a ``RuntimeWarning``
  when these objects are unpickled in a different version than the one in
  which they were pickled.
  
  * Added :meth:`Model.from_db() <django.db.models.Model.from_db()>` which
  Django uses whenever objects are loaded using the ORM. The method allows
  customizing model loading behavior.
  
  * ``extra(select={...})`` now allows you to escape a literal ``%s`` sequence
  using ``%%s``.
  
  * :doc:`Custom Lookups</howto/custom-lookups>` can now be registered using
  a decorator pattern.
  
  * The new :attr:`Transform.bilateral <django.db.models.Transform.bilateral>`
  attribute allows creating bilateral transformations. These transformations
  are applied to both ``lhs`` and ``rhs`` when used in a lookup expression,
  providing opportunities for more sophisticated lookups.
  
  * SQL special characters (\, %, _) are now escaped properly when a pattern
  lookup (e.g. ``contains``, ``startswith``, etc.) is used with an ``F()``
  expression as the right-hand side. In those cases, the escaping is performed
  by the database, which can lead to somewhat complex queries involving nested
  ``REPLACE`` function calls.
  
  * You can now refresh model instances by using :meth:`Model.refresh_from_db()
  <django.db.models.Model.refresh_from_db>`.
  
  * You can now get the set of deferred fields for a model using
  :meth:`Model.get_deferred_fields() <django.db.models.Model.get_deferred_fields>`.
  
  * Model field ``default``’s are now used when primary key field's are set to
  ``None``.
  
  Signals
  ~~~~~~~
  
  * Exceptions from the ``(receiver, exception)`` tuples returned by
  :meth:`Signal.send_robust() <django.dispatch.Signal.send_robust>` now have
  their traceback attached as a ``__traceback__`` attribute.
  
  * The ``environ`` argument, which contains the WSGI environment structure from
  the request, was added to the :data:`~django.core.signals.request_started`
  signal.
  
  * You can now import the :func:`~django.test.signals.setting_changed` signal
  from ``django.core.signals`` to avoid loading ``django.test`` in non-test
  situations. Django no longer does so itself.
  
  System Check Framework
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * :attr:`~django.core.checks.register` can now be used as a function.
  
  Templates
  ~~~~~~~~~
  
  * :tfilter:`urlize` now supports domain-only links that include characters after
  the top-level domain (e.g. ``djangoproject.com/`` and
  ``djangoproject.com/download/``).
  
  * :tfilter:`urlize` doesn't treat exclamation marks at the end of a domain or
  its query string as part of the URL (the URL in e.g. ``'djangoproject.com!``
  is ``djangoproject.com``)
  
  * Added a :class:`locmem.Loader <django.template.loaders.locmem.Loader>`
  class that loads Django templates from a Python dictionary.
  
  * The :ttag:`now` tag can now store its output in a context variable with the
  usual syntax: ``{% now 'j n Y' as varname %}``.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * ``WSGIRequest`` now respects paths starting with ``//``.
  
  * The :meth:`HttpRequest.build_absolute_uri()
  <django.http.HttpRequest.build_absolute_uri>` method now handles paths
  starting with ``//`` correctly.
  
  * If :setting:`DEBUG` is ``True`` and a request raises a
  :exc:`~django.core.exceptions.SuspiciousOperation`, the response will be
  rendered with a detailed error page.
  
  * The ``query_string`` argument of :class:`~django.http.QueryDict` is now
  optional, defaulting to ``None``, so a blank ``QueryDict`` can now be
  instantiated with ``QueryDict()`` instead of ``QueryDict(None)`` or
  ``QueryDict('')``.
  
  * The ``GET`` and ``POST`` attributes of an :class:`~django.http.HttpRequest`
  object are now :class:`~django.http.QueryDict`\s rather than dictionaries,
  and the ``FILES`` attribute is now a ``MultiValueDict``.
  This brings this class into line with the documentation and with
  ``WSGIRequest``.
  
  * The :attr:`HttpResponse.charset <django.http.HttpResponse.charset>` attribute
  was added.
  
  * ``WSGIRequestHandler`` now follows RFC in converting URI to IRI, using
  ``uri_to_iri()``.
  
  * The :meth:`HttpRequest.get_full_path()
  <django.http.HttpRequest.get_full_path>` method now escapes unsafe characters
  from the path portion of a Uniform Resource Identifier (URI) properly.
  
  * :class:`~django.http.HttpResponse` now implements a few additional methods
  like :meth:`~django.http.HttpResponse.getvalue` so that instances can be used
  as stream objects.
  
  * The new :meth:`HttpResponse.setdefault()
  <django.http.HttpResponse.setdefault>` method allows setting a header unless
  it has already been set.
  
  * You can use the new :class:`~django.http.FileResponse` to stream files.
  
  * The :func:`~django.views.decorators.http.condition` decorator for
  conditional view processing now supports the ``If-unmodified-since`` header.
  
  Tests
  ~~~~~
  
  * The :class:`RequestFactory.trace() <django.test.RequestFactory>`
  and :class:`Client.trace() <django.test.Client.trace>` methods were
  implemented, allowing you to create ``TRACE`` requests in your tests.
  
  * The ``count`` argument was added to
  :meth:`~django.test.SimpleTestCase.assertTemplateUsed`. This allows you to
  assert that a template was rendered a specific number of times.
  
  * The new :meth:`~django.test.SimpleTestCase.assertJSONNotEqual` assertion
  allows you to test that two JSON fragments are not equal.
  
  * Added options to the :djadmin:`test` command to preserve the test database
  (:option:`--keepdb <test --keepdb>`), to run the test cases in reverse order
  (:option:`--reverse <test --reverse>`), and to enable SQL logging for failing
  tests (:option:`--debug-sql <test --debug-sql>`).
  
  * Added the :attr:`~django.test.Response.resolver_match` attribute to test
  client responses.
  
  * Added several settings that allow customization of test tablespace parameters
  for Oracle: :setting:`DATAFILE`, :setting:`DATAFILE_TMP`,
  :setting:`DATAFILE_MAXSIZE` and :setting:`DATAFILE_TMP_MAXSIZE`.
  
  * The :func:`~django.test.override_settings` decorator can now affect the
  master router in :setting:`DATABASE_ROUTERS`.
  
  * Added test client support for file uploads with file-like objects.
  
  * A shared cache is now used when testing with an SQLite in-memory database when
  using Python 3.4+ and SQLite 3.7.13+. This allows sharing the database
  between threads.
  
  Validators
  ~~~~~~~~~~
  
  * :class:`~django.core.validators.URLValidator` now supports IPv6 addresses,
  Unicode domains, and URLs containing authentication data.
  
  .. _backwards-incompatible-1.8:
  
  Backwards incompatible changes in 1.8
  =====================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`deprecation plan <deprecation-removed-in-1.8>` for any features that
  have been removed. If you haven't updated your code within the
  deprecation timeline for a given feature, its removal may appear as a
  backwards incompatible change.
  
  Related object operations are run in a transaction
  --------------------------------------------------
  
  Some operations on related objects such as
  :meth:`~django.db.models.fields.related.RelatedManager.add()` or direct
  assignment ran multiple data modifying queries without wrapping them in
  transactions. To reduce the risk of data corruption, all data modifying methods
  that affect multiple related objects (i.e. ``add()``, ``remove()``,
  ``clear()``, and direct assignment) now perform their data modifying queries
  from within a transaction, provided your database supports transactions.
  
  This has one backwards incompatible side effect, signal handlers triggered from
  these methods are now executed within the method's transaction and any
  exception in a signal handler will prevent the whole operation.
  
  .. _unsaved-model-instance-check-18:
  
  Assigning unsaved objects to relations raises an error
  ------------------------------------------------------
  
  .. note::
  
  To more easily allow in-memory usage of models, this change was reverted in
  Django 1.8.4 and replaced with a check during ``model.save()``. For example::
  
  >>> book = Book.objects.create(name="Django")
  >>> book.author = Author(name="John")
  >>> book.save()
  Traceback (most recent call last):
  ...
  ValueError: save() prohibited to prevent data loss due to unsaved related object 'author'.
  
  A similar check on assignment to reverse one-to-one relations was removed
  in Django 1.8.5.
  
  Assigning unsaved objects to a :class:`~django.db.models.ForeignKey`,
  :class:`~django.contrib.contenttypes.fields.GenericForeignKey`, and
  :class:`~django.db.models.OneToOneField` now raises a :exc:`ValueError`.
  
  Previously, the assignment of an unsaved object would be silently ignored.
  For example::
  
  >>> book = Book.objects.create(name="Django")
  >>> book.author = Author(name="John")
  >>> book.author.save()
  >>> book.save()
  
  >>> Book.objects.get(name="Django")
  >>> book.author
  >>>
  
  Now, an error will be raised to prevent data loss::
  
  >>> book.author = Author(name="john")
  Traceback (most recent call last):
  ...
  ValueError: Cannot assign "<Author: John>": "Author" instance isn't saved in the database.
  
  If you require allowing the assignment of unsaved instances (the old behavior)
  and aren't concerned about the data loss possibility (e.g. you never save the
  objects to the database), you can disable this check by using the
  ``ForeignKey.allow_unsaved_instance_assignment`` attribute. (This attribute was
  removed in 1.8.4 as it's no longer relevant.)
  
  Management commands that only accept positional arguments
  ---------------------------------------------------------
  
  If you have written a custom management command that only accepts positional
  arguments and you didn't specify the ``args`` command variable, you might get
  an error like ``Error: unrecognized arguments: ...``, as variable parsing is
  now based on :py:mod:`argparse` which doesn't implicitly accept positional
  arguments. You can make your command backwards compatible by simply setting the
  ``args`` class variable. However, if you don't have to keep compatibility with
  older Django versions, it's better to implement the new
  :meth:`~django.core.management.BaseCommand.add_arguments` method as described
  in :doc:`/howto/custom-management-commands`.
  
  Custom test management command arguments through test runner
  ------------------------------------------------------------
  
  The method to add custom arguments to the ``test`` management command through
  the test runner has changed. Previously, you could provide an ``option_list``
  class variable on the test runner to add more arguments (à la
  :py:mod:`optparse`). Now to implement the same behavior, you have to create an
  ``add_arguments(cls, parser)`` class method on the test runner and call
  ``parser.add_argument`` to add any custom arguments, as parser is now an
  :py:class:`argparse.ArgumentParser` instance.
  
  Model check ensures auto-generated column names are within limits specified by database
  ---------------------------------------------------------------------------------------
  
  A field name that's longer than the column name length supported by a database
  can create problems. For example, with MySQL you'll get an exception trying to
  create the column, and with PostgreSQL the column name is truncated by the
  database (you may see a warning in the PostgreSQL logs).
  
  A model check has been introduced to better alert users to this scenario before
  the actual creation of database tables.
  
  If you have an existing model where this check seems to be a false positive,
  for example on PostgreSQL where the name was already being truncated, simply
  use :attr:`~django.db.models.Field.db_column` to specify the name that's being
  used.
  
  The check also applies to the columns generated in an implicit
  ``ManyToManyField.through`` model. If you run into an issue there, use
  :attr:`~django.db.models.ManyToManyField.through` to create an explicit model
  and then specify :attr:`~django.db.models.Field.db_column` on its column(s)
  as needed.
  
  Query relation lookups now check object types
  ---------------------------------------------
  
  Querying for model lookups now checks if the object passed is of correct type
  and raises a :exc:`ValueError` if not. Previously, Django didn't care if the
  object was of correct type; it just used the object's related field attribute
  (e.g. ``id``) for the lookup. Now, an error is raised to prevent incorrect
  lookups::
  
  >>> book = Book.objects.create(name="Django")
  >>> book = Book.objects.filter(author=book)
  Traceback (most recent call last):
  ...
  ValueError: Cannot query "<Book: Django>": Must be "Author" instance.
  
  ``select_related()`` now checks given fields
  --------------------------------------------
  
  ``select_related()`` now validates that the given fields actually exist.
  Previously, nonexistent fields were silently ignored. Now, an error is raised::
  
  >>> book = Book.objects.select_related('nonexistent_field')
  Traceback (most recent call last):
  ...
  FieldError: Invalid field name(s) given in select_related: 'nonexistent_field'
  
  The validation also makes sure that the given field is relational::
  
  >>> book = Book.objects.select_related('name')
  Traceback (most recent call last):
  ...
  FieldError: Non-relational field given in select_related: 'name'
  
  Default ``EmailField.max_length`` increased to 254
  --------------------------------------------------
  
  The old default 75 character ``max_length`` was not capable of storing all
  possible RFC3696/5321-compliant email addresses. In order to store all
  possible valid email addresses, the ``max_length`` has been increased to 254
  characters. You will need to generate and apply database migrations for your
  affected models (or add ``max_length=75`` if you wish to keep the length on
  your current fields). A migration for
  :attr:`django.contrib.auth.models.User.email` is included.
  
  Support for PostgreSQL versions older than 9.0
  ----------------------------------------------
  
  The end of upstream support periods was reached in July 2014 for PostgreSQL 8.4.
  As a consequence, Django 1.8 sets 9.0 as the minimum PostgreSQL version it
  officially supports.
  
  This also includes dropping support for PostGIS 1.3 and 1.4 as these versions
  are not supported on versions of PostgreSQL later than 8.4.
  
  Django also now requires the use of Psycopg2 version 2.4.5 or higher (or 2.5+
  if you want to use :mod:`django.contrib.postgres`).
  
  Support for MySQL versions older than 5.5
  -----------------------------------------
  
  The end of upstream support periods was reached in January 2012 for MySQL 5.0
  and December 2013 for MySQL 5.1. As a consequence, Django 1.8 sets 5.5 as the
  minimum MySQL version it officially supports.
  
  Support for Oracle versions older than 11.1
  -------------------------------------------
  
  The end of upstream support periods was reached in July 2010 for Oracle 9.2,
  January 2012 for Oracle 10.1, and July 2013 for Oracle 10.2. As a consequence,
  Django 1.8 sets 11.1 as the minimum Oracle version it officially supports.
  
  Specific privileges used instead of roles for tests on Oracle
  -------------------------------------------------------------
  
  Earlier versions of Django granted the CONNECT and RESOURCE roles to the test
  user on Oracle. These roles have been deprecated, so Django 1.8 uses the
  specific underlying privileges instead. This changes the privileges required
  of the main user for running tests (unless the project is configured to avoid
  creating a test user). The exact privileges required now are detailed in
  :ref:`Oracle notes <oracle-notes>`.
  
  ``AbstractUser.last_login`` allows null values
  ----------------------------------------------
  
  The :attr:`AbstractUser.last_login <django.contrib.auth.models.User.last_login>`
  field now allows null values. Previously, it defaulted to the time when the user
  was created which was misleading if the user never logged in. If you are using
  the default user (:class:`django.contrib.auth.models.User`), run the database
  migration included in ``contrib.auth``.
  
  If you are using a custom user model that inherits from ``AbstractUser``,
  you'll need to run :djadmin:`makemigrations` and generate a migration for your
  app that contains that model. Also, if wish to set ``last_login`` to ``NULL``
  for users who haven't logged in, you can run this query::
  
  from django.db import models
  from django.contrib.auth import get_user_model
  from django.contrib.auth.models import AbstractBaseUser
  
  UserModel = get_user_model()
  if issubclass(UserModel, AbstractBaseUser):
  UserModel._default_manager.filter(
  last_login=models.F('date_joined')
  ).update(last_login=None)
  
  :mod:`django.contrib.gis`
  -------------------------
  
  * Support for GEOS 3.1 and GDAL 1.6 has been dropped.
  
  * Support for SpatiaLite < 2.4 has been dropped.
  
  * GIS-specific lookups have been refactored to use the
  :class:`django.db.models.Lookup` API.
  
  * The default ``str`` representation of
  :class:`~django.contrib.gis.geos.GEOSGeometry` objects has been changed from
  WKT to EWKT format (including the SRID). As this representation is used in
  the serialization framework, that means that ``dumpdata`` output will now
  contain the SRID value of geometry objects.
  
  Priority of context processors for ``TemplateResponse`` brought in line with ``render``
  ---------------------------------------------------------------------------------------
  
  The :class:`~django.template.response.TemplateResponse` constructor is designed to be a
  drop-in replacement for the :func:`~django.shortcuts.render` function. However,
  it had a slight incompatibility, in that for ``TemplateResponse``, context data
  from the passed in context dictionary could be shadowed by context data returned
  from context processors, whereas for ``render`` it was the other way
  around. This was a bug, and the behavior of ``render`` is more appropriate,
  since it allows the globally defined context processors to be overridden locally
  in the view. If you were relying on the fact context data in a
  ``TemplateResponse`` could be overridden using a context processor, you will
  need to change your code.
  
  Overriding ``setUpClass`` / ``tearDownClass`` in test cases
  -----------------------------------------------------------
  
  The decorators :func:`~django.test.override_settings` and
  :func:`~django.test.modify_settings` now act at the class level when used as
  class decorators. As a consequence, when overriding ``setUpClass()`` or
  ``tearDownClass()``, the ``super`` implementation should always be called.
  
  Removal of ``django.contrib.formtools``
  ---------------------------------------
  
  The formtools contrib app has been moved to a separate package and the
  relevant documentation pages have been updated or removed.
  
  The new package is available `on GitHub`_ and on PyPI.
  
  .. _on GitHub: https://github.com/django/django-formtools/
  
  Database connection reloading between tests
  -------------------------------------------
  
  Django previously closed database connections between each test within a
  ``TestCase``. This is no longer the case as Django now wraps the whole
  ``TestCase`` within a transaction. If some of your tests relied on the old
  behavior, you should have them inherit from ``TransactionTestCase`` instead.
  
  Cleanup of the ``django.template`` namespace
  --------------------------------------------
  
  If you've been relying on private APIs exposed in the ``django.template``
  module, you may have to import them from ``django.template.base`` instead.
  
  Also private APIs ``django.template.base.compile_string()``,
  ``django.template.loader.find_template()``, and
  ``django.template.loader.get_template_from_string()`` were removed.
  
  ``model`` attribute on private model relations
  ----------------------------------------------
  
  In earlier versions of Django, on a model with a reverse foreign key
  relationship (for example), ``model._meta.get_all_related_objects()`` returned
  the relationship as a ``django.db.models.related.RelatedObject`` with the
  ``model`` attribute set to the source of the relationship. Now, this method
  returns the relationship as ``django.db.models.fields.related.ManyToOneRel``
  (private API ``RelatedObject`` has been removed), and the ``model`` attribute
  is set to the target of the relationship instead of the source. The source
  model is accessible on the ``related_model`` attribute instead.
  
  Consider this example from the tutorial in Django 1.8::
  
  >>> p = Poll.objects.get(pk=1)
  >>> p._meta.get_all_related_objects()
  [<ManyToOneRel: polls.choice>]
  >>> p._meta.get_all_related_objects()[0].model
  <class 'polls.models.Poll'>
  >>> p._meta.get_all_related_objects()[0].related_model
  <class 'polls.models.Choice'>
  
  and compare it to the behavior on older versions::
  
  >>> p._meta.get_all_related_objects()
  [<RelatedObject: polls:choice related to poll>]
  >>> p._meta.get_all_related_objects()[0].model
  <class 'polls.models.Choice'>
  
  To access the source model, you can use a pattern like this to write code that
  will work with both Django 1.8 and older versions::
  
  for relation in opts.get_all_related_objects():
  to_model = getattr(relation, 'related_model', relation.model)
  
  Also note that ``get_all_related_objects()`` is deprecated in 1.8.
  
  Database backend API
  --------------------
  
  The following changes to the database backend API are documented to assist
  those writing third-party backends in updating their code:
  
  * ``BaseDatabaseXXX`` classes have been moved to ``django.db.backends.base``.
  Please import them from the new locations::
  
  from django.db.backends.base.base import BaseDatabaseWrapper
  from django.db.backends.base.client import BaseDatabaseClient
  from django.db.backends.base.creation import BaseDatabaseCreation
  from django.db.backends.base.features import BaseDatabaseFeatures
  from django.db.backends.base.introspection import BaseDatabaseIntrospection
  from django.db.backends.base.introspection import FieldInfo, TableInfo
  from django.db.backends.base.operations import BaseDatabaseOperations
  from django.db.backends.base.schema import BaseDatabaseSchemaEditor
  from django.db.backends.base.validation import BaseDatabaseValidation
  
  * The ``data_types``, ``data_types_suffix``, and
  ``data_type_check_constraints`` attributes have moved from the
  ``DatabaseCreation`` class to ``DatabaseWrapper``.
  
  * The ``SQLCompiler.as_sql()`` method now takes a ``subquery`` parameter
  (:ticket:`24164`).
  
  * The ``BaseDatabaseOperations.date_interval_sql()`` method now only takes a
  ``timedelta`` parameter.
  
  :mod:`django.contrib.admin`
  ---------------------------
  
  * ``AdminSite`` no longer takes an ``app_name`` argument and its ``app_name``
  attribute has been removed. The application name is always ``admin`` (as
  opposed to the instance name which you can still customize using
  ``AdminSite(name="...")``.
  
  * The ``ModelAdmin.get_object()`` method (private API) now takes a third
  argument named ``from_field`` in order to specify which field should match
  the provided ``object_id``.
  
  * The :meth:`ModelAdmin.response_delete()
  <django.contrib.admin.ModelAdmin.response_delete>` method
  now takes a second argument named ``obj_id`` which is the serialized
  identifier used to retrieve the object before deletion.
  
  Default autoescaping of functions in ``django.template.defaultfilters``
  -----------------------------------------------------------------------
  
  In order to make built-in template filters that output HTML "safe by default"
  when calling them in Python code, the following functions in
  ``django.template.defaultfilters`` have been changed to automatically escape
  their input value:
  
  * ``join``
  * ``linebreaksbr``
  * ``linebreaks_filter``
  * ``linenumbers``
  * ``unordered_list``
  * ``urlize``
  * ``urlizetrunc``
  
  You can revert to the old behavior by specifying ``autoescape=False`` if you
  are passing trusted content. This change doesn't have any effect when using
  the corresponding filters in templates.
  
  Miscellaneous
  -------------
  
  * ``connections.queries`` is now a read-only attribute.
  
  * Database connections are considered equal only if they're the same object.
  They aren't hashable any more.
  
  * :class:`~django.middleware.gzip.GZipMiddleware` used to disable compression
  for some content types when the request is from Internet Explorer, in order
  to work around a bug in IE6 and earlier. This behavior could affect
  performance on IE7 and later. It was removed.
  
  * ``URLField.to_python`` no longer adds a trailing slash to pathless URLs.
  
  * The :tfilter:`length` template filter now returns ``0`` for an undefined
  variable, rather than an empty string.
  
  * ``ForeignKey.default_error_message['invalid']`` has been changed from
  ``'%(model)s instance with pk %(pk)r does not exist.'`` to
  ``'%(model)s instance with %(field)s %(value)r does not exist.'`` If you are
  using this message in your own code, please update the list of interpolated
  parameters. Internally, Django will continue to provide the
  ``pk`` parameter in ``params`` for backwards compatibility.
  
  * ``UserCreationForm.error_messages['duplicate_username']`` is no longer used.
  If you wish to customize that error message, :ref:`override it on the form
  <modelforms-overriding-default-fields>` using the ``'unique'`` key in
  ``Meta.error_messages['username']`` or, if you have a custom form field for
  ``'username'``, using the ``'unique'`` key in its
  :attr:`~django.forms.Field.error_messages` argument.
  
  * The block ``usertools`` in the ``base.html`` template of
  :mod:`django.contrib.admin` now requires the ``has_permission`` context
  variable to be set. If you have any custom admin views that use this
  template, update them to pass :meth:`AdminSite.has_permission()
  <django.contrib.admin.AdminSite.has_permission>` as this new variable's
  value or simply include :meth:`AdminSite.each_context(request)
  <django.contrib.admin.AdminSite.each_context>` in the context.
  
  * Internal changes were made to the :class:`~django.forms.ClearableFileInput`
  widget to allow more customization. The undocumented ``url_markup_template``
  attribute was removed in favor of ``template_with_initial``.
  
  * For consistency with other major vendors, the ``en_GB`` locale now has Monday
  as the first day of the week.
  
  * Seconds have been removed from any locales that had them in ``TIME_FORMAT``,
  ``DATETIME_FORMAT``, or ``SHORT_DATETIME_FORMAT``.
  
  * The default max size of the Oracle test tablespace has increased from 300M
  (or 200M, before 1.7.2) to 500M.
  
  * ``reverse()`` and ``reverse_lazy()`` now return Unicode strings instead of
  bytestrings.
  
  * The ``CacheClass`` shim has been removed from all cache backends.
  These aliases were provided for backwards compatibility with Django 1.3.
  If you are still using them, please update your project to use the real
  class name found in the :setting:`BACKEND <CACHES-BACKEND>` key of the
  :setting:`CACHES` setting.
  
  * By default, :func:`~django.core.management.call_command` now always skips the
  check framework (unless you pass it ``skip_checks=False``).
  
  * When iterating over lines, :class:`~django.core.files.File` now uses
  :pep:`universal newlines <278>`. The following are recognized as ending a
  line: the Unix end-of-line convention ``'\n'``, the Windows convention
  ``'\r\n'``, and the old Macintosh convention ``'\r'``.
  
  * The Memcached cache backends ``MemcachedCache`` and ``PyLibMCCache`` will
  delete a key if ``set()`` fails. This is necessary to ensure the ``cache_db``
  session store always fetches the most current session data.
  
  * Private APIs ``override_template_loaders`` and ``override_with_test_loader``
  in ``django.test.utils`` were removed. Override ``TEMPLATES`` with
  ``override_settings`` instead.
  
  * Warnings from the MySQL database backend are no longer converted to
  exceptions when :setting:`DEBUG` is ``True``.
  
  * :class:`~django.http.HttpRequest` now has a simplified ``repr`` (e.g.
  ``<WSGIRequest: GET '/somepath/'>``). This won't change the behavior of
  the :class:`~django.views.debug.SafeExceptionReporterFilter` class.
  
  * Class-based views that use :class:`~django.views.generic.edit.ModelFormMixin`
  will raise an :exc:`~django.core.exceptions.ImproperlyConfigured` exception
  when both the ``fields`` and ``form_class`` attributes are specified.
  Previously, ``fields`` was silently ignored.
  
  * When following redirects, the test client now raises
  :exc:`~django.test.client.RedirectCycleError` if it detects a loop or hits a
  maximum redirect limit (rather than passing silently).
  
  * Translatable strings set as the ``default`` parameter of the field are cast
  to concrete strings later, so the return type of ``Field.get_default()`` is
  different in some cases. There is no change to default values which are the
  result of a callable.
  
  * ``GenericIPAddressField.empty_strings_allowed`` is now ``False``. Database
  backends that interpret empty strings as null (only Oracle among the backends
  that Django includes) will no longer convert null values back to an empty
  string. This is consistent with other backends.
  
  * When the ``BaseCommand.leave_locale_alone``
  attribute is ``False``, translations are now deactivated instead of forcing
  the "en-us" locale. In the case your models contained non-English strings and
  you counted on English translations to be activated in management commands,
  this will not happen any longer. It might be that new database migrations are
  generated (once) after migrating to 1.8.
  
  * :func:`django.utils.translation.get_language()` now returns ``None`` instead
  of :setting:`LANGUAGE_CODE` when translations are temporarily deactivated.
  
  * When a translation doesn't exist for a specific literal, the fallback is now
  taken from the :setting:`LANGUAGE_CODE` language (instead of from the
  untranslated ``msgid`` message).
  
  * The ``name`` field of :class:`django.contrib.contenttypes.models.ContentType`
  has been removed by a migration and replaced by a property. That means it's
  not possible to query or filter a ``ContentType`` by this field any longer.
  
  Be careful if you upgrade to Django 1.8 and skip Django 1.7. If you run
  ``manage.py migrate --fake``, this migration will be skipped and you'll see
  a ``RuntimeError: Error creating new content types.`` exception because the
  ``name`` column won't be dropped from the database. Use ``manage.py migrate
  --fake-initial`` to fake only the initial migration instead.
  
  * The new :option:`migrate --fake-initial` option allows faking initial
  migrations. In 1.7, initial migrations were always automatically faked if all
  tables created in an initial migration already existed.
  
  * An app *without* migrations with a ``ForeignKey`` to an app *with* migrations
  may now result in a foreign key constraint error when migrating the database
  or running tests. In Django 1.7, this could fail silently and result in a
  missing constraint. To resolve the error, add migrations to the app without
  them.
  
  .. _deprecated-features-1.8:
  
  Features deprecated in 1.8
  ==========================
  
  Selected methods in ``django.db.models.options.Options``
  --------------------------------------------------------
  
  As part of the formalization of the ``Model._meta`` API (from the
  :class:`django.db.models.options.Options` class), a number of methods have been
  deprecated and will be removed in Django 1.10:
  
  * ``get_all_field_names()``
  * ``get_all_related_objects()``
  * ``get_all_related_objects_with_model()``
  * ``get_all_related_many_to_many_objects()``
  * ``get_all_related_m2m_objects_with_model()``
  * ``get_concrete_fields_with_model()``
  * ``get_field_by_name()``
  * ``get_fields_with_model()``
  * ``get_m2m_with_model()``
  
  Loading ``cycle`` and ``firstof`` template tags from ``future`` library
  -----------------------------------------------------------------------
  
  Django 1.6 introduced ``{% load cycle from future %}`` and
  ``{% load firstof from future %}`` syntax for forward compatibility of the
  :ttag:`cycle` and :ttag:`firstof` template tags. This syntax is now deprecated
  and will be removed in Django 1.10. You can simply remove the
  ``{% load ... from future %}`` tags.
  
  ``django.conf.urls.patterns()``
  -------------------------------
  
  In the olden days of Django, it was encouraged to reference views as strings
  in ``urlpatterns``::
  
  urlpatterns = patterns('',
  url('^$', 'myapp.views.myview'),
  )
  
  and Django would magically import ``myapp.views.myview`` internally and turn
  the string into a real function reference. In order to reduce repetition when
  referencing many views from the same module, the ``patterns()`` function takes
  a required initial ``prefix`` argument which is prepended to all
  views-as-strings in that set of ``urlpatterns``::
  
  urlpatterns = patterns('myapp.views',
  url('^$', 'myview'),
  url('^other/$', 'otherview'),
  )
  
  In the modern era, we have updated the tutorial to instead recommend importing
  your views module and referencing your view functions (or classes) directly.
  This has a number of advantages, all deriving from the fact that we are using
  normal Python in place of "Django String Magic": the errors when you mistype a
  view name are less obscure, IDEs can help with autocompletion of view names,
  etc.
  
  So these days, the above use of the ``prefix`` arg is much more likely to be
  written (and is better written) as::
  
  from myapp import views
  
  urlpatterns = patterns('',
  url('^$', views.myview),
  url('^other/$', views.otherview),
  )
  
  Thus ``patterns()`` serves little purpose and is a burden when teaching new users
  (answering the newbie's question "why do I need this empty string as the first
  argument to ``patterns()``?"). For these reasons, we are deprecating it.
  Updating your code is as simple as ensuring that ``urlpatterns`` is a list of
  ``django.conf.urls.url()`` instances. For example::
  
  from django.conf.urls import url
  from myapp import views
  
  urlpatterns = [
  url('^$', views.myview),
  url('^other/$', views.otherview),
  ]
  
  Passing a string as ``view`` to ``django.conf.urls.url()``
  ----------------------------------------------------------
  
  Related to the previous item, referencing views as strings in the ``url()``
  function is deprecated. Pass the callable view as described in the previous
  section instead.
  
  Template-related settings
  -------------------------
  
  As a consequence of the multiple template engines refactor, several settings
  are deprecated in favor of :setting:`TEMPLATES`:
  
  * ``ALLOWED_INCLUDE_ROOTS``
  * ``TEMPLATE_CONTEXT_PROCESSORS``
  * ``TEMPLATE_DEBUG``
  * ``TEMPLATE_DIRS``
  * ``TEMPLATE_LOADERS``
  * ``TEMPLATE_STRING_IF_INVALID``
  
  ``django.core.context_processors``
  ----------------------------------
  
  Built-in template context processors have been moved to
  ``django.template.context_processors``.
  
  ``django.test.SimpleTestCase.urls``
  -----------------------------------
  
  The attribute ``SimpleTestCase.urls`` for specifying URLconf configuration in
  tests has been deprecated and will be removed in Django 1.10. Use
  :func:`override_settings(ROOT_URLCONF=...) <django.test.override_settings>`
  instead.
  
  ``prefix`` argument to :func:`~django.conf.urls.i18n.i18n_patterns`
  -------------------------------------------------------------------
  
  Related to the previous item, the ``prefix`` argument to
  :func:`django.conf.urls.i18n.i18n_patterns` has been deprecated. Simply pass a
  list of ``django.conf.urls.url()`` instances instead.
  
  Using an incorrect count of unpacked values in the :ttag:`for` template tag
  ---------------------------------------------------------------------------
  
  Using an incorrect count of unpacked values in :ttag:`for` tag will raise an
  exception rather than fail silently in Django 1.10.
  
  Passing a dotted path to ``reverse()`` and :ttag:`url`
  ------------------------------------------------------
  
  Reversing URLs by Python path is an expensive operation as it causes the
  path being reversed to be imported. This behavior has also resulted in a
  `security issue`_. Use :ref:`named URL patterns <naming-url-patterns>`
  for reversing instead.
  
  If you are using :mod:`django.contrib.sitemaps`, add the ``name`` argument to
  the ``url`` that references :func:`django.contrib.sitemaps.views.sitemap`::
  
  from django.contrib.sitemaps.views import sitemap
  
  url(r'^sitemap\.xml$', sitemap, {'sitemaps': sitemaps},
  name='django.contrib.sitemaps.views.sitemap')
  
  to ensure compatibility when reversing by Python path is removed in Django 1.10.
  
  Similarly for GIS sitemaps, add ``name='django.contrib.gis.sitemaps.views.kml'``
  or ``name='django.contrib.gis.sitemaps.views.kmz'``.
  
  If you are using a Python path for the :setting:`LOGIN_URL` or
  :setting:`LOGIN_REDIRECT_URL` setting, use the name of the ``url()`` instead.
  
  .. _security issue: https://www.djangoproject.com/weblog/2014/apr/21/security/s-issue-unexpected-code-execution-using-reverse
  
  Aggregate methods and modules
  -----------------------------
  
  The ``django.db.models.sql.aggregates`` and
  ``django.contrib.gis.db.models.sql.aggregates`` modules (both private API), have
  been deprecated as ``django.db.models.aggregates`` and
  ``django.contrib.gis.db.models.aggregates`` are now also responsible
  for SQL generation. The old modules will be removed in Django 1.10.
  
  If you were using the old modules, see :doc:`Query Expressions
  </ref/models/expressions>` for instructions on rewriting custom aggregates
  using the new stable API.
  
  The following methods and properties of ``django.db.models.sql.query.Query``
  have also been deprecated and the backwards compatibility shims will be removed
  in Django 1.10:
  
  * ``Query.aggregates``, replaced by ``annotations``.
  * ``Query.aggregate_select``, replaced by ``annotation_select``.
  * ``Query.add_aggregate()``, replaced by ``add_annotation()``.
  * ``Query.set_aggregate_mask()``, replaced by ``set_annotation_mask()``.
  * ``Query.append_aggregate_mask()``, replaced by ``append_annotation_mask()``.
  
  Extending management command arguments through ``Command.option_list``
  ----------------------------------------------------------------------
  
  Management commands now use :py:mod:`argparse` instead of :py:mod:`optparse` to
  parse command-line arguments passed to commands. This also means that the way
  to add custom arguments to commands has changed: instead of extending the
  ``option_list`` class list, you should now override the
  :meth:`~django.core.management.BaseCommand.add_arguments` method and add
  arguments through ``argparse.add_argument()``. See
  :ref:`this example <custom-commands-options>` for more details.
  
  ``django.core.management.NoArgsCommand``
  ----------------------------------------
  
  The class ``NoArgsCommand`` is now deprecated and will be removed in Django
  1.10. Use :class:`~django.core.management.BaseCommand` instead, which takes no
  arguments by default.
  
  Listing all migrations in a project
  -----------------------------------
  
  The ``--list`` option of the :djadmin:`migrate` management command is
  deprecated and will be removed in Django 1.10. Use :djadmin:`showmigrations`
  instead.
  
  ``cache_choices`` option of ``ModelChoiceField`` and ``ModelMultipleChoiceField``
  ---------------------------------------------------------------------------------
  
  :class:`~django.forms.ModelChoiceField` and
  :class:`~django.forms.ModelMultipleChoiceField` took an undocumented, untested
  option ``cache_choices``. This cached querysets between multiple renderings of
  the same ``Form`` object. This option is subject to an accelerated deprecation
  and will be removed in Django 1.9.
  
  ``django.template.resolve_variable()``
  --------------------------------------
  
  The function has been informally marked as "Deprecated" for some time. Replace
  ``resolve_variable(path, context)`` with
  ``django.template.Variable(path).resolve(context)``.
  
  ``django.contrib.webdesign``
  ----------------------------
  
  It provided the :ttag:`lorem` template tag which is now included in the
  built-in tags. Simply remove ``'django.contrib.webdesign'`` from
  :setting:`INSTALLED_APPS` and ``{% load webdesign %}`` from your templates.
  
  ``error_message`` argument to ``django.forms.RegexField``
  ---------------------------------------------------------
  
  It provided backwards compatibility for pre-1.0 code, but its functionality is
  redundant. Use ``Field.error_messages['invalid']`` instead.
  
  Old :tfilter:`unordered_list` syntax
  ------------------------------------
  
  An older (pre-1.0), more restrictive and verbose input format for the
  :tfilter:`unordered_list` template filter has been deprecated::
  
  ['States', [['Kansas', [['Lawrence', []], ['Topeka', []]]], ['Illinois', []]]]
  
  Using the new syntax, this becomes::
  
  ['States', ['Kansas', ['Lawrence', 'Topeka'], 'Illinois']]
  
  ``django.forms.Field._has_changed()``
  -------------------------------------
  
  Rename this method to :meth:`~django.forms.Field.has_changed` by removing the
  leading underscore. The old name will still work until Django 1.10.
  
  ``django.utils.html.remove_tags()`` and ``removetags`` template filter
  ----------------------------------------------------------------------
  
  ``django.utils.html.remove_tags()`` as well as the template filter
  ``removetags`` have been deprecated as they cannot guarantee safe output. Their
  existence is likely to lead to their use in security-sensitive contexts where
  they are not actually safe.
  
  The unused and undocumented ``django.utils.html.strip_entities()`` function has
  also been deprecated.
  
  ``is_admin_site`` argument to ``django.contrib.auth.views.password_reset()``
  ----------------------------------------------------------------------------
  
  It's a legacy option that should no longer be necessary.
  
  ``SubfieldBase``
  ----------------
  
  ``django.db.models.fields.subclassing.SubfieldBase`` has been deprecated and
  will be removed in Django 1.10. Historically, it was used to handle fields where
  type conversion was needed when loading from the database, but it was not used
  in ``.values()`` calls or in aggregates. It has been replaced with
  :meth:`~django.db.models.Field.from_db_value`.
  
  The new approach doesn't call the :meth:`~django.db.models.Field.to_python`
  method on assignment as was the case with ``SubfieldBase``. If you need that
  behavior, reimplement the ``Creator`` class `from Django's source code
  <https://github.com/django/django/blob/stable/1.8.x/django/db/models/fields/subclassing.pyL31-L44>`_
  in your project.
  
  ``django.utils.checksums``
  --------------------------
  
  The ``django.utils.checksums`` module has been deprecated and will be removed
  in Django 1.10. The functionality it provided (validating checksum using the
  Luhn algorithm) was undocumented and not used in Django. The module has been
  moved to the `django-localflavor`_ package (version 1.1+).
  
  .. _django-localflavor: https://pypi.org/project/django-localflavor/
  
  ``InlineAdminForm.original_content_type_id``
  --------------------------------------------
  
  The ``original_content_type_id`` attribute on ``InlineAdminForm`` has been
  deprecated and will be removed in Django 1.10. Historically, it was used
  to construct the "view on site" URL. This URL is now accessible using the
  ``absolute_url`` attribute of the form.
  
  ``django.views.generic.edit.FormMixin.get_form()``’s ``form_class`` argument
  ----------------------------------------------------------------------------
  
  ``FormMixin`` subclasses that override the ``get_form()`` method should make
  sure to provide a default value for the ``form_class`` argument since it's
  now optional.
  
  Rendering templates loaded by :func:`~django.template.loader.get_template()` with a :class:`~django.template.Context`
  ---------------------------------------------------------------------------------------------------------------------
  
  The return type of :func:`~django.template.loader.get_template()` has changed
  in Django 1.8: instead of a :class:`django.template.Template`, it returns a
  ``Template`` instance whose exact type depends on which backend loaded it.
  
  Both classes provide a ``render()`` method, however, the former takes a
  :class:`django.template.Context` as an argument while the latter expects a
  :class:`dict`. This change is enforced through a deprecation path for Django
  templates.
  
  All this also applies to :func:`~django.template.loader.select_template()`.
  
  :class:`~django.template.Template` and :class:`~django.template.Context` classes in template responses
  ------------------------------------------------------------------------------------------------------
  
  Some methods of :class:`~django.template.response.SimpleTemplateResponse` and
  :class:`~django.template.response.TemplateResponse` accepted
  :class:`django.template.Context` and :class:`django.template.Template` objects
  as arguments. They should now receive :class:`dict` and backend-dependent
  template objects respectively.
  
  This also applies to the return types if you have subclassed either template
  response class.
  
  Check the :doc:`template response API documentation </ref/template-response>`
  for details.
  
  ``current_app`` argument of template-related APIs
  -------------------------------------------------
  
  The following functions and classes will no longer accept a ``current_app``
  parameter to set an URL namespace in Django 1.10:
  
  * ``django.shortcuts.render()``
  * ``django.template.Context()``
  * ``django.template.RequestContext()``
  * ``django.template.response.TemplateResponse()``
  
  Set ``request.current_app`` instead, where ``request`` is the first argument
  to these functions or classes. If you're using a plain ``Context``, use a
  ``RequestContext`` instead.
  
  ``dictionary`` and ``context_instance`` arguments of rendering functions
  ------------------------------------------------------------------------
  
  The following functions will no longer accept the ``dictionary`` and
  ``context_instance`` parameters in Django 1.10:
  
  * ``django.shortcuts.render()``
  * ``django.shortcuts.render_to_response()``
  * ``django.template.loader.render_to_string()``
  
  Use the ``context`` parameter instead. When ``dictionary`` is passed as a
  positional argument, which is the most common idiom, no changes are needed.
  
  If you're passing a :class:`~django.template.Context` in ``context_instance``,
  pass a :class:`dict` in the ``context`` parameter instead. If you're passing a
  :class:`~django.template.RequestContext`, pass the request separately in the
  ``request`` parameter.
  
  ``dirs`` argument of template-finding functions
  -----------------------------------------------
  
  The following functions will no longer accept a ``dirs`` parameter to override
  ``TEMPLATE_DIRS`` in Django 1.10:
  
  * :func:`django.template.loader.get_template()`
  * :func:`django.template.loader.select_template()`
  * :func:`django.shortcuts.render()`
  * ``django.shortcuts.render_to_response()``
  
  The parameter didn't work consistently across different template loaders and
  didn't work for included templates.
  
  ``django.template.loader.BaseLoader``
  -------------------------------------
  
  ``django.template.loader.BaseLoader`` was renamed to
  ``django.template.loaders.base.Loader``. If you've written a custom template
  loader that inherits ``BaseLoader``, you must inherit ``Loader`` instead.
  
  ``django.test.utils.TestTemplateLoader``
  ----------------------------------------
  
  Private API ``django.test.utils.TestTemplateLoader`` is deprecated in favor of
  ``django.template.loaders.locmem.Loader`` and will be removed in Django 1.9.
  
  .. _storage-max-length-update:
  
  Support for the ``max_length`` argument on custom ``Storage`` classes
  ---------------------------------------------------------------------
  
  ``Storage`` subclasses should add ``max_length=None`` as a parameter to
  :meth:`~django.core.files.storage.Storage.get_available_name` and/or
  :meth:`~django.core.files.storage.Storage.save` if they override either method.
  Support for storages that do not accept this argument will be removed in
  Django 1.10.
  
  ``qn`` replaced by ``compiler``
  -------------------------------
  
  In previous Django versions, various internal ORM methods (mostly ``as_sql``
  methods) accepted a ``qn`` (for "quote name") argument, which was a reference
  to a function that quoted identifiers for sending to the database. In Django
  1.8, that argument has been renamed to ``compiler`` and is now a full
  ``SQLCompiler`` instance. For backwards-compatibility, calling a
  ``SQLCompiler`` instance performs the same name-quoting that the ``qn``
  function used to. However, this backwards-compatibility shim is immediately
  deprecated: you should rename your ``qn`` arguments to ``compiler``, and call
  ``compiler.quote_name_unless_alias(...)`` where you previously called
  ``qn(...)``.
  
  Default value of ``RedirectView.permanent``
  -------------------------------------------
  
  The default value of the
  :attr:`RedirectView.permanent <django.views.generic.base.RedirectView.permanent>`
  attribute will change from ``True`` to ``False`` in Django 1.9.
  
  Using ``AuthenticationMiddleware`` without ``SessionAuthenticationMiddleware``
  ------------------------------------------------------------------------------
  
  ``django.contrib.auth.middleware.SessionAuthenticationMiddleware`` was
  added in Django 1.7. In Django 1.7.2, its functionality was moved to
  ``auth.get_user()`` and, for backwards compatibility, enabled only if
  ``'django.contrib.auth.middleware.SessionAuthenticationMiddleware'`` appears in
  ``MIDDLEWARE_CLASSES``.
  
  In Django 1.10, session verification will be enabled regardless of whether or not
  ``SessionAuthenticationMiddleware`` is enabled (at which point
  ``SessionAuthenticationMiddleware`` will have no significance). You can add it
  to your ``MIDDLEWARE_CLASSES`` sometime before then to opt-in. Please read the
  :ref:`upgrade considerations <session-invalidation-on-password-change>` first.
  
  ``django.contrib.sitemaps.FlatPageSitemap``
  -------------------------------------------
  
  ``django.contrib.sitemaps.FlatPageSitemap`` has moved to
  ``django.contrib.flatpages.sitemaps.FlatPageSitemap``. The old import location
  is deprecated and will be removed in Django 1.9.
  
  Model ``Field.related``
  -----------------------
  
  Private attribute ``django.db.models.Field.related`` is deprecated in favor
  of ``Field.rel``.  The latter is an instance of
  ``django.db.models.fields.related.ForeignObjectRel`` which replaces
  ``django.db.models.related.RelatedObject``. The ``django.db.models.related``
  module has been removed and the ``Field.related`` attribute will be removed in
  Django 1.10.
  
  ``ssi`` template tag
  --------------------
  
  The ``ssi`` template tag allows files to be included in a template by
  absolute path. This is of limited use in most deployment situations, and
  the :ttag:`include` tag often makes more sense. This tag is now deprecated and
  will be removed in Django 1.10.
  
  ``=`` as comparison operator in ``if`` template tag
  ---------------------------------------------------
  
  Using a single equals sign with the ``{% if %}`` template tag for equality
  testing was undocumented and untested. It's now deprecated in favor of ``==``.
  
  ``%(<foo>)s`` syntax in ``ModelFormMixin.success_url``
  ------------------------------------------------------
  
  The legacy ``%(<foo>)s`` syntax in :attr:`ModelFormMixin.success_url
  <django.views.generic.edit.ModelFormMixin.success_url>` is deprecated and
  will be removed in Django 1.10.
  
  ``GeoQuerySet`` aggregate methods
  ---------------------------------
  
  The ``collect()``, ``extent()``, ``extent3d()``, ``make_line()``, and
  ``unionagg()`` aggregate methods are deprecated and should be replaced by their
  function-based aggregate equivalents (``Collect``, ``Extent``, ``Extent3D``,
  ``MakeLine``, and ``Union``).
  
  .. _deprecated-signature-of-allow-migrate:
  
  Signature of the ``allow_migrate`` router method
  ------------------------------------------------
  
  The signature of the :meth:`allow_migrate` method of database routers has
  changed from ``allow_migrate(db, model)`` to
  ``allow_migrate(db, app_label, model_name=None, **hints)``.
  
  When ``model_name`` is set, the value that was previously given through the
  ``model`` positional argument may now be found inside the ``hints`` dictionary
  under the key ``'model'``.
  
  After switching to the new signature the router will also be called by the
  :class:`~django.db.migrations.operations.RunPython` and
  :class:`~django.db.migrations.operations.RunSQL` operations.
  
  .. _removed-features-1.8:
  
  Features removed in 1.8
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 1.8. See :ref:`deprecated-features-1.6` for details, including how to
  remove usage of these features.
  
  * ``django.contrib.comments`` is removed.
  
  * The following transaction management APIs are removed:
  
  - ``TransactionMiddleware``
  - the decorators and context managers ``autocommit``, ``commit_on_success``,
  and ``commit_manually``, defined in ``django.db.transaction``
  - the functions ``commit_unless_managed`` and ``rollback_unless_managed``,
  also defined in ``django.db.transaction``
  - the ``TRANSACTIONS_MANAGED`` setting
  
  * The :ttag:`cycle` and :ttag:`firstof` template tags auto-escape their
  arguments.
  
  * The ``SEND_BROKEN_LINK_EMAILS`` setting is removed.
  
  * ``django.middleware.doc.XViewMiddleware`` is removed.
  
  * The ``Model._meta.module_name`` alias is removed.
  
  * The backward compatible shims introduced to rename ``get_query_set``
  and similar queryset methods are removed. This affects the following classes:
  ``BaseModelAdmin``, ``ChangeList``, ``BaseCommentNode``,
  ``GenericForeignKey``, ``Manager``, ``SingleRelatedObjectDescriptor`` and
  ``ReverseSingleRelatedObjectDescriptor``.
  
  * The backward compatible shims introduced to rename the attributes
  ``ChangeList.root_query_set`` and ``ChangeList.query_set`` are removed.
  
  * ``django.views.defaults.shortcut`` and ``django.conf.urls.shortcut`` are
  removed.
  
  * Support for the Python Imaging Library (PIL) module is removed.
  
  * The following private APIs are removed:
  
  - ``django.db.backend``
  - ``django.db.close_connection()``
  - ``django.db.backends.creation.BaseDatabaseCreation.set_autocommit()``
  - ``django.db.transaction.is_managed()``
  - ``django.db.transaction.managed()``
  
  * ``django.forms.widgets.RadioInput`` is removed.
  
  * The module ``django.test.simple`` and the class
  ``django.test.simple.DjangoTestSuiteRunner`` are removed.
  
  * The module ``django.test._doctest`` is removed.
  
  * The ``CACHE_MIDDLEWARE_ANONYMOUS_ONLY`` setting is removed. This change
  affects both ``django.middleware.cache.CacheMiddleware`` and
  ``django.middleware.cache.UpdateCacheMiddleware`` despite the lack of a
  deprecation warning in the latter class.
  
  * Usage of the hard-coded *Hold down "Control", or "Command" on a Mac, to select
  more than one.* string to override or append to user-provided ``help_text`` in
  forms for ``ManyToMany`` model fields is not performed by Django anymore
  either at the model or forms layer.
  
  * The ``Model._meta.get_(add|change|delete)_permission`` methods are removed.
  
  * The session key ``django_language`` is no longer read for backwards
  compatibility.
  
  * Geographic Sitemaps are removed
  (``django.contrib.gis.sitemaps.views.index`` and
  ``django.contrib.gis.sitemaps.views.sitemap``).
  
  * ``django.utils.html.fix_ampersands``, the ``fix_ampersands`` template filter,
  and ``django.utils.html.clean_html`` are removed.
  
  
  ===========================

1.7.11 not secure

===========================
  
  *November 24, 2015*
  
  Django 1.7.11 fixes a security issue and a data loss bug in 1.7.10.
  
  Fixed settings leak possibility in ``date`` template filter
  ===========================================================
  
  If an application allows users to specify an unvalidated format for dates and
  passes this format to the :tfilter:`date` filter, e.g.
  ``{{ last_updated|date:user_date_format }}``, then a malicious user could
  obtain any secret in the application's settings by specifying a settings key
  instead of a date format. e.g. ``"SECRET_KEY"`` instead of ``"j/m/Y"``.
  
  To remedy this, the underlying function used by the ``date`` template filter,
  ``django.utils.formats.get_format()``, now only allows accessing the date/time
  formatting settings.
  
  Bugfixes
  ========
  
  * Fixed a data loss possibility with :class:`~django.db.models.Prefetch` if
  ``to_attr`` is set to a ``ManyToManyField`` (:ticket:`25693`).
  
  
  ===========================

1.7.10 not secure

===========================
  
  *August 18, 2015*
  
  Django 1.7.10 fixes a security issue in 1.7.9.
  
  Denial-of-service possibility in ``logout()`` view by filling session store
  ===========================================================================
  
  Previously, a session could be created when anonymously accessing the
  ``django.contrib.auth.views.logout()`` view (provided it wasn't decorated
  with :func:`~django.contrib.auth.decorators.login_required` as done in the
  admin). This could allow an attacker to easily create many new session records
  by sending repeated requests, potentially filling up the session store or
  causing other users' session records to be evicted.
  
  The :class:`~django.contrib.sessions.middleware.SessionMiddleware` has been
  modified to no longer create empty session records, including when
  :setting:`SESSION_SAVE_EVERY_REQUEST` is active.
  
  Additionally, the ``contrib.sessions.backends.base.SessionBase.flush()`` and
  ``cache_db.SessionStore.flush()`` methods have been modified to avoid creating
  a new empty session. Maintainers of third-party session backends should check
  if the same vulnerability is present in their backend and correct it if so.
  
  
  ==========================

1.7.9 not secure

==========================
  
  *July 8, 2015*
  
  Django 1.7.9 fixes several security issues and bugs in 1.7.8.
  
  Denial-of-service possibility by filling session store
  ======================================================
  
  In previous versions of Django, the session backends created a new empty record
  in the session storage anytime ``request.session`` was accessed and there was a
  session key provided in the request cookies that didn't already have a session
  record. This could allow an attacker to easily create many new session records
  simply by sending repeated requests with unknown session keys, potentially
  filling up the session store or causing other users' session records to be
  evicted.
  
  The built-in session backends now create a session record only if the session
  is actually modified; empty session records are not created. Thus this
  potential DoS is now only possible if the site chooses to expose a
  session-modifying view to anonymous users.
  
  As each built-in session backend was fixed separately (rather than a fix in the
  core sessions framework), maintainers of third-party session backends should
  check whether the same vulnerability is present in their backend and correct
  it if so.
  
  Header injection possibility since validators accept newlines in input
  ======================================================================
  
  Some of Django's built-in validators
  (:class:`~django.core.validators.EmailValidator`, most seriously) didn't
  prohibit newline characters (due to the usage of ``$`` instead of ``\Z`` in the
  regular expressions). If you use values with newlines in HTTP response or email
  headers, you can suffer from header injection attacks. Django itself isn't
  vulnerable because :class:`~django.http.HttpResponse` and the mail sending
  utilities in :mod:`django.core.mail` prohibit newlines in HTTP and SMTP
  headers, respectively. While the validators have been fixed in Django, if
  you're creating HTTP responses or email messages in other ways, it's a good
  idea to ensure that those methods prohibit newlines as well. You might also
  want to validate that any existing data in your application doesn't contain
  unexpected newlines.
  
  :func:`~django.core.validators.validate_ipv4_address`,
  :func:`~django.core.validators.validate_slug`, and
  :class:`~django.core.validators.URLValidator` are also affected, however, as
  of Django 1.6 the ``GenericIPAddresseField``, ``IPAddressField``, ``SlugField``,
  and ``URLField`` form fields which use these validators all strip the input, so
  the possibility of newlines entering your data only exists if you are using
  these validators outside of the form fields.
  
  The undocumented, internally unused ``validate_integer()`` function is now
  stricter as it validates using a regular expression instead of simply casting
  the value using ``int()`` and checking if an exception was raised.
  
  Bugfixes
  ========
  
  * Prevented the loss of ``null``/``not null`` column properties during field
  renaming of MySQL databases (:ticket:`24817`).
  
  * Fixed ``SimpleTestCase.assertRaisesMessage()`` on Python 2.7.10
  (:ticket:`24903`).
  
  
  ==========================

1.7.8 not secure

==========================
  
  *May 1, 2015*
  
  Django 1.7.8 fixes:
  
  * Database introspection with SQLite 3.8.9 (released April 8, 2015)
  (:ticket:`24637`).
  
  * A database table name quoting regression in 1.7.2 (:ticket:`24605`).
  
  * The loss of ``null``/``not null`` column properties during field alteration
  of MySQL databases (:ticket:`24595`).
  
  
  ==========================

1.7.7 not secure

==========================
  
  *March 18, 2015*
  
  Django 1.7.7 fixes several bugs and security issues in 1.7.6.
  
  Denial-of-service possibility with ``strip_tags()``
  ===================================================
  
  Last year :func:`~django.utils.html.strip_tags`  was changed to work
  iteratively. The problem is that the size of the input it's processing can
  increase on each iteration which results in an infinite loop in
  ``strip_tags()``. This issue only affects versions of Python that haven't
  received  `a bugfix in HTMLParser <https://bugs.python.org/issue20288>`_; namely
  Python < 2.7.7 and 3.3.5. Some operating system vendors have also backported
  the fix for the Python bug into their packages of earlier versions.
  
  To remedy this issue, ``strip_tags()`` will now return the original input if
  it detects the length of the string it's processing increases. Remember that
  absolutely NO guarantee is provided about the results of ``strip_tags()`` being
  HTML safe. So NEVER mark safe the result of a ``strip_tags()`` call without
  escaping it first, for example with :func:`~django.utils.html.escape`.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) accepted URLs with
  leading control characters and so considered URLs like ``\x08javascript:...``
  safe. This issue doesn't affect Django currently, since we only put this URL
  into the ``Location`` response header and browsers seem to ignore JavaScript
  there. Browsers we tested also treat URLs prefixed with control characters such
  as ``%08//example.com`` as relative paths so redirection to an unsafe target
  isn't a problem either.
  
  However, if a developer relies on ``is_safe_url()`` to
  provide safe redirect targets and puts such a URL into a link, they could
  suffer from an XSS attack as some browsers such as Google Chrome ignore control
  characters at the start of a URL in an anchor ``href``.
  
  Bugfixes
  ========
  
  * Fixed renaming of classes in migrations where renaming a subclass would
  cause incorrect state to be recorded for objects that referenced the
  superclass (:ticket:`24354`).
  
  * Stopped writing migration files in dry run mode when merging migration
  conflicts. When ``makemigrations --merge`` is called with ``verbosity=3`` the
  migration file is written to ``stdout`` (:ticket:`24427`).
  
  
  ==========================

1.7.6 not secure

==========================
  
  *March 9, 2015*
  
  Django 1.7.6 fixes a security issue and several bugs in 1.7.5.
  
  Mitigated an XSS attack via properties in ``ModelAdmin.readonly_fields``
  ========================================================================
  
  The :attr:`ModelAdmin.readonly_fields
  <django.contrib.admin.ModelAdmin.readonly_fields>` attribute in the Django
  admin allows displaying model fields and model attributes. While the former
  were correctly escaped, the latter were not. Thus untrusted content could be
  injected into the admin, presenting an exploitation vector for XSS attacks.
  
  In this vulnerability, every model attribute used in ``readonly_fields`` that
  is not an actual model field (e.g. a :class:`property`) will **fail to be
  escaped** even if that attribute is not marked as safe. In this release,
  autoescaping is now correctly applied.
  
  Bugfixes
  ========
  
  * Fixed crash when coercing ``ManyRelatedManager`` to a string
  (:ticket:`24352`).
  
  * Fixed a bug that prevented migrations from adding a foreign key constraint
  when converting an existing field to a foreign key (:ticket:`24447`).
  
  
  ==========================

1.7.5 not secure

==========================
  
  *February 25, 2015*
  
  Django 1.7.5 fixes several bugs in 1.7.4.
  
  Bugfixes
  ========
  
  * Reverted a fix that prevented a migration crash when unapplying
  ``contrib.contenttypes``’s or ``contrib.auth``’s first migration
  (:ticket:`24075`) due to severe impact on the test performance
  (:ticket:`24251`) and problems in multi-database setups (:ticket:`24298`).
  
  * Fixed a regression that prevented custom fields inheriting from
  ``ManyToManyField`` from being recognized in migrations (:ticket:`24236`).
  
  * Fixed crash in ``contrib.sites`` migrations when a default database isn't
  used (:ticket:`24332`).
  
  * Added the ability to set the isolation level on PostgreSQL with psycopg2 ≥
  2.4.2 (:ticket:`24318`). It was advertised as a new feature in Django 1.6
  but it didn't work in practice.
  
  * Formats for the Azerbaijani locale (``az``) have been added.
  
  
  ==========================

1.7.4 not secure

==========================
  
  *January 27, 2015*
  
  Django 1.7.4 fixes several bugs in 1.7.3.
  
  Bugfixes
  ========
  
  * Fixed a migration crash when unapplying ``contrib.contenttypes``’s or
  ``contrib.auth``’s first migration (:ticket:`24075`).
  
  * Made the migration's ``RenameModel`` operation rename ``ManyToManyField``
  tables (:ticket:`24135`).
  
  * Fixed a migration crash on MySQL when migrating from a ``OneToOneField`` to a
  ``ForeignKey`` (:ticket:`24163`).
  
  * Prevented the ``static.serve`` view from producing ``ResourceWarning``\s in
  certain circumstances (security fix regression, :ticket:`24193`).
  
  * Fixed schema check for ManyToManyField to look for internal type instead
  of checking class instance, so you can write custom m2m-like fields with the
  same behavior. (:ticket:`24104`).
  
  
  ==========================

1.7.3 not secure

==========================
  
  *January 13, 2015*
  
  Django 1.7.3 fixes several security issues and bugs in 1.7.2.
  
  WSGI header spoofing via underscore/dash conflation
  ===================================================
  
  When HTTP headers are placed into the WSGI environ, they are normalized by
  converting to uppercase, converting all dashes to underscores, and prepending
  ``HTTP_``. For instance, a header ``X-Auth-User`` would become
  ``HTTP_X_AUTH_USER`` in the WSGI environ (and thus also in Django's
  ``request.META`` dictionary).
  
  Unfortunately, this means that the WSGI environ cannot distinguish between
  headers containing dashes and headers containing underscores: ``X-Auth-User``
  and ``X-Auth_User`` both become ``HTTP_X_AUTH_USER``. This means that if a
  header is used in a security-sensitive way (for instance, passing
  authentication information along from a front-end proxy), even if the proxy
  carefully strips any incoming value for ``X-Auth-User``, an attacker may be
  able to provide an ``X-Auth_User`` header (with underscore) and bypass this
  protection.
  
  In order to prevent such attacks, both Nginx and Apache 2.4+ strip all headers
  containing underscores from incoming requests by default. Django's built-in
  development server now does the same. Django's development server is not
  recommended for production use, but matching the behavior of common production
  servers reduces the surface area for behavior changes during deployment.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) didn't strip leading
  whitespace on the tested URL and as such considered URLs like
  ``\njavascript:...`` safe. If a developer relied on ``is_safe_url()`` to
  provide safe redirect targets and put such a URL into a link, they could suffer
  from a XSS attack. This bug doesn't affect Django currently, since we only put
  this URL into the ``Location`` response header and browsers seem to ignore
  JavaScript there.
  
  Denial-of-service attack against ``django.views.static.serve``
  ==============================================================
  
  In older versions of Django, the :func:`django.views.static.serve` view read
  the files it served one line at a time. Therefore, a big file with no newlines
  would result in memory usage equal to the size of that file. An attacker could
  exploit this and launch a denial-of-service attack by simultaneously requesting
  many large files. This view now reads the file in chunks to prevent large
  memory usage.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid. Now
  may be a good time to audit your project and serve your files in production
  using a real front-end web server if you are not doing so.
  
  Database denial-of-service with ``ModelMultipleChoiceField``
  ============================================================
  
  Given a form that uses ``ModelMultipleChoiceField`` and
  ``show_hidden_initial=True`` (not a documented API), it was possible for a user
  to cause an unreasonable number of SQL queries by submitting duplicate values
  for the field's data. The validation logic in ``ModelMultipleChoiceField`` now
  deduplicates submitted values to address this issue.
  
  Bugfixes
  ========
  
  * The default iteration count for the PBKDF2 password hasher has been
  increased by 25%. This part of the normal major release process was
  inadvertently omitted in 1.7. This backwards compatible change will not
  affect users who have subclassed
  ``django.contrib.auth.hashers.PBKDF2PasswordHasher`` to change the
  default value.
  
  * Fixed a crash in the CSRF middleware when handling non-ASCII referer header
  (:ticket:`23815`).
  
  * Fixed a crash in the ``django.contrib.auth.redirect_to_login`` view when
  passing a ``reverse_lazy()`` result on Python 3 (:ticket:`24097`).
  
  * Added correct formats for Greek (``el``) (:ticket:`23967`).
  
  * Fixed a migration crash when unapplying a migration where multiple operations
  interact with the same model (:ticket:`24110`).
  
  
  ==========================

1.7.2 not secure

==========================
  
  *January 2, 2015*
  
  Django 1.7.2 fixes several bugs in 1.7.1.
  
  Additionally, Django's vendored version of six, ``django.utils.six``, has
  been upgraded to the latest release (1.9.0).
  
  Bugfixes
  ========
  
  * Fixed migration's renaming of auto-created many-to-many tables when changing
  :attr:`Meta.db_table <django.db.models.Options.db_table>` (:ticket:`23630`).
  
  * Fixed a migration crash when adding an explicit ``id`` field to a model on
  SQLite (:ticket:`23702`).
  
  * Added a warning for duplicate models when a module is reloaded. Previously a
  ``RuntimeError`` was raised every time two models clashed in the app registry.
  (:ticket:`23621`).
  
  * Prevented :djadmin:`flush` from loading initial data for migrated apps
  (:ticket:`23699`).
  
  * Fixed a :djadmin:`makemessages` regression in 1.7.1 when
  :setting:`STATIC_ROOT` has the default ``None`` value (:ticket:`23717`).
  
  * Added GeoDjango compatibility with mysqlclient database driver.
  
  * Fixed MySQL 5.6+ crash with ``GeometryField``\s in migrations
  (:ticket:`23719`).
  
  * Fixed a migration crash when removing a field that is referenced in
  ``AlterIndexTogether`` or ``AlterUniqueTogether`` (:ticket:`23614`).
  
  * Updated the first day of the week in the Ukrainian locale to Monday.
  
  * Added support for transactional spatial metadata initialization on
  SpatiaLite 4.1+ (:ticket:`23152`).
  
  * Fixed a migration crash that prevented changing a nullable field with a
  default to non-nullable with the same default (:ticket:`23738`).
  
  * Fixed a migration crash when adding ``GeometryField``\s with ``blank=True``
  on PostGIS (:ticket:`23731`).
  
  * Allowed usage of ``DateTimeField()`` as ``Transform.output_field``
  (:ticket:`23420`).
  
  * Fixed a migration serializing bug involving ``float("nan")`` and
  ``float("inf")`` (:ticket:`23770`).
  
  * Fixed a regression where custom form fields having a ``queryset`` attribute
  but no ``limit_choices_to`` could not be used in a
  :class:`~django.forms.ModelForm` (:ticket:`23795`).
  
  * Fixed a custom field type validation error with MySQL backend when
  ``db_type`` returned ``None`` (:ticket:`23761`).
  
  * Fixed a migration crash when a field is renamed that is part of an
  ``index_together`` (:ticket:`23859`).
  
  * Fixed :djadmin:`squashmigrations` to respect the ``--no-optimize`` parameter
  (:ticket:`23799`).
  
  * Made :class:`~django.db.migrations.operations.RenameModel` reversible
  (:ticket:`22248`)
  
  * Avoided unnecessary rollbacks of migrations from other apps when migrating
  backwards (:ticket:`23410`).
  
  * Fixed a rare query error when using deeply nested subqueries
  (:ticket:`23605`).
  
  * Fixed a crash in migrations when deleting a field that is part of a
  ``index/unique_together`` constraint (:ticket:`23794`).
  
  * Fixed ``django.core.files.File.__repr__()`` when the file's ``name`` contains
  Unicode characters (:ticket:`23888`).
  
  * Added missing context to the admin's ``delete_selected`` view that prevented
  custom site header, etc. from appearing (:ticket:`23898`).
  
  * Fixed a regression with dynamically generated inlines and allowed field
  references in the admin (:ticket:`23754`).
  
  * Fixed an infinite loop bug for certain cyclic migration dependencies, and made
  the error message for cyclic dependencies much more helpful.
  
  * Added missing ``index_together`` handling for SQLite (:ticket:`23880`).
  
  * Fixed a crash when ``RunSQL`` SQL content was collected by the schema editor,
  typically when using ``sqlmigrate`` (:ticket:`23909`).
  
  * Fixed a regression in ``contrib.admin`` add/change views which caused some
  ``ModelAdmin`` methods to receive the incorrect ``obj`` value
  (:ticket:`23934`).
  
  * Fixed ``runserver`` crash when socket error message contained Unicode
  characters (:ticket:`23946`).
  
  * Fixed serialization of ``type`` when adding a ``deconstruct()`` method
  (:ticket:`23950`).
  
  * Prevented the
  ``django.contrib.auth.middleware.SessionAuthenticationMiddleware`` from
  setting a ``"Vary: Cookie"`` header on all responses (:ticket:`23939`).
  
  * Fixed a crash when adding ``blank=True`` to ``TextField()`` on MySQL
  (:ticket:`23920`).
  
  * Fixed index creation by the migration infrastructure, particularly when
  dealing with PostgreSQL specific ``{text|varchar}_pattern_ops`` indexes
  (:ticket:`23954`).
  
  * Fixed bug in ``makemigrations`` that created broken migration files when
  dealing with multiple table inheritance and inheriting from more than one
  model (:ticket:`23956`).
  
  * Fixed a crash when a ``MultiValueField`` has invalid data (:ticket:`23674`).
  
  * Fixed a crash in the admin when using "Save as new" and also deleting a
  related inline (:ticket:`23857`).
  
  * Always converted ``related_name`` to text (Unicode), since that is required
  on Python 3 for interpolation. Removed conversion of ``related_name`` to text
  in migration deconstruction (:ticket:`23455` and :ticket:`23982`).
  
  * Enlarged the sizes of tablespaces which are created by default for testing
  on Oracle (the main tablespace was increased from 200M to 300M and the
  temporary tablespace from 100M to 150M). This was required to accommodate
  growth in Django's own test suite (:ticket:`23969`).
  
  * Fixed ``timesince`` filter translations in Korean (:ticket:`23989`).
  
  * Fixed the SQLite ``SchemaEditor`` to properly add defaults in the absence of
  a user specified ``default``. For example, a ``CharField`` with ``blank=True``
  didn't set existing rows to an empty string which resulted in a crash when
  adding the ``NOT NULL`` constraint (:ticket:`23987`).
  
  * ``makemigrations`` no longer prompts for a default value when adding
  ``TextField()`` or ``CharField()`` without a ``default`` (:ticket:`23405`).
  
  * Fixed a migration crash when adding ``order_with_respect_to`` to a table
  with existing rows (:ticket:`23983`).
  
  * Restored the ``pre_migrate`` signal if all apps have migrations
  (:ticket:`23975`).
  
  * Made admin system checks run for custom ``AdminSite``\s (:ticket:`23497`).
  
  * Ensured the app registry is fully populated when unpickling models. When an
  external script (like a queueing infrastructure) reloads pickled models, it
  could crash with an ``AppRegistryNotReady`` exception (:ticket:`24007`).
  
  * Added quoting to field indexes in the SQL generated by migrations to prevent
  a crash when the index name requires it (:ticket:`24015`).
  
  * Added ``datetime.time`` support to migrations questioner (:ticket:`23998`).
  
  * Fixed admindocs crash on apps installed as eggs (:ticket:`23525`).
  
  * Changed migrations autodetector to generate an ``AlterModelOptions`` operation
  instead of ``DeleteModel`` and ``CreateModel`` operations when changing
  ``Meta.managed``. This prevents data loss when changing ``managed`` from
  ``False`` to ``True`` and vice versa (:ticket:`24037`).
  
  * Enabled the ``sqlsequencereset`` command on apps with migrations
  (:ticket:`24054`).
  
  * Added tablespace SQL to apps with migrations (:ticket:`24051`).
  
  * Corrected ``contrib.sites`` default site creation in a multiple database
  setup (:ticket:`24000`).
  
  * Restored support for objects that aren't :class:`str` or :class:`bytes` in
  ``django.utils.safestring.mark_for_escaping()`` on Python 3.
  
  * Supported strings escaped by third-party libraries with the ``__html__``
  convention in the template engine (:ticket:`23831`).
  
  * Prevented extraneous ``DROP DEFAULT`` SQL in migrations (:ticket:`23581`).
  
  * Restored the ability to use more than five levels of subqueries
  (:ticket:`23758`).
  
  * Fixed crash when ``ValidationError`` is initialized with a ``ValidationError``
  that is initialized with a dictionary (:ticket:`24008`).
  
  * Prevented a crash on apps without migrations when running ``migrate --list``
  (:ticket:`23366`).
  
  
  ==========================

1.7.1 not secure

==========================
  
  *October 22, 2014*
  
  Django 1.7.1 fixes several bugs in 1.7.
  
  Bugfixes
  ========
  
  * Allowed related many-to-many fields to be referenced in the admin
  (:ticket:`23604`).
  
  * Added a more helpful error message if you try to migrate an app without first
  creating the ``contenttypes`` table (:ticket:`22411`).
  
  * Modified migrations dependency algorithm to avoid possible infinite recursion.
  
  * Fixed a ``UnicodeDecodeError`` when the ``flush`` error message contained
  Unicode characters (:ticket:`22882`).
  
  * Reinstated missing ``CHECK`` SQL clauses which were omitted on some backends
  when not using migrations (:ticket:`23416`).
  
  * Fixed serialization of ``type`` objects in migrations (:ticket:`22951`).
  
  * Allowed inline and hidden references to admin fields (:ticket:`23431`).
  
  * The ``deconstructible`` decorator now fails with a ``ValueError`` if the
  decorated object cannot automatically be imported (:ticket:`23418`).
  
  * Fixed a typo in an ``inlineformset_factory()`` error message that caused a
  crash (:ticket:`23451`).
  
  * Restored the ability to use :setting:`ABSOLUTE_URL_OVERRIDES` with the
  ``'auth.User'`` model (:ticket:`11775`). As a side effect, the setting now
  adds a ``get_absolute_url()`` method to any model that appears in
  ``ABSOLUTE_URL_OVERRIDES`` but doesn't define ``get_absolute_url()``.
  
  * Avoided masking some ``ImportError`` exceptions during application loading
  (:ticket:`22920`).
  
  * Empty ``index_together`` or ``unique_together`` model options no longer
  results in infinite migrations (:ticket:`23452`).
  
  * Fixed crash in ``contrib.sitemaps`` if ``lastmod`` returned a ``date`` rather
  than a ``datetime`` (:ticket:`23403`).
  
  * Allowed migrations to work with ``app_label``\s that have the same last
  part (e.g. ``django.contrib.auth`` and ``vendor.auth``) (:ticket:`23483`).
  
  * Restored the ability to deepcopy ``F`` objects (:ticket:`23492`).
  
  * Formats for Welsh (``cy``) and several Chinese locales (``zh_CN``,
  ``zh_Hans``, ``zh_Hant`` and ``zh_TW``) have been added. Formats for
  Macedonian have been fixed (trailing dot removed, :ticket:`23532`).
  
  * Added quoting of constraint names in the SQL generated by migrations to
  prevent crash with uppercase characters in the name (:ticket:`23065`).
  
  * Fixed renaming of models with a self-referential many-to-many field
  (``ManyToManyField('self')``) (:ticket:`23503`).
  
  * Added the :meth:`~django.contrib.admin.InlineModelAdmin.get_extra()`,
  :meth:`~django.contrib.admin.InlineModelAdmin.get_max_num()`, and
  :meth:`~django.contrib.admin.InlineModelAdmin.get_min_num()` hooks to
  :class:`~django.contrib.contenttypes.admin.GenericInlineModelAdmin`
  (:ticket:`23539`).
  
  * Made ``migrations.RunSQL`` no longer require percent sign escaping. This is
  now consistent with ``cursor.execute()`` (:ticket:`23426`).
  
  * Made the :setting:`SERIALIZE <TEST_SERIALIZE>` entry in the
  :setting:`TEST <DATABASE-TEST>` dictionary usable (:ticket:`23421`).
  
  * Fixed bug in migrations that prevented foreign key constraints to unmanaged
  models with a custom primary key (:ticket:`23415`).
  
  * Added ``SchemaEditor`` for MySQL GIS backend so that spatial indexes will be
  created for apps with migrations (:ticket:`23538`).
  
  * Added ``SchemaEditor`` for Oracle GIS backend so that spatial metadata and
  indexes will be created for apps with migrations (:ticket:`23537`).
  
  * Coerced the ``related_name`` model field option to Unicode during migration
  generation to generate migrations that work with both Python 2 and 3
  (:ticket:`23455`).
  
  * Fixed ``MigrationWriter`` to handle builtin types without imports
  (:ticket:`23560`).
  
  * Fixed ``deepcopy`` on ``ErrorList`` (:ticket:`23594`).
  
  * Made the :mod:`~django.contrib.admindocs` view to browse view details check
  if the view specified in the URL exists in the URLconf. Previously it was
  possible to import arbitrary packages from the Python path. This was not
  considered a security issue because ``admindocs`` is only accessible to staff
  users (:ticket:`23601`).
  
  * Fixed ``UnicodeDecodeError`` crash in ``AdminEmailHandler`` with non-ASCII
  characters in the request (:ticket:`23593`).
  
  * Fixed missing ``get_or_create`` and ``update_or_create`` on related managers
  causing ``IntegrityError`` (:ticket:`23611`).
  
  * Made :func:`~django.utils.http.urlsafe_base64_decode` return the proper
  type (bytestring) on Python 3 (:ticket:`23333`).
  
  * :djadmin:`makemigrations` can now serialize timezone-aware values
  (:ticket:`23365`).
  
  * Added a prompt to the migrations questioner when removing the null constraint
  from a field to prevent an IntegrityError on existing NULL rows
  (:ticket:`23609`).
  
  * Fixed generic relations in ``ModelAdmin.list_filter`` (:ticket:`23616`).
  
  * Restored RFC compliance for the SMTP backend on Python 3 (:ticket:`23063`).
  
  * Fixed a crash while parsing cookies containing invalid content
  (:ticket:`23638`).
  
  * The system check framework now raises error **models.E020** when the
  class method ``Model.check()`` is unreachable (:ticket:`23615`).
  
  * Made the Oracle test database creation drop the test user in the event of an
  unclean exit of a previous test run (:ticket:`23649`).
  
  * Fixed :djadmin:`makemigrations` to detect changes to
  :attr:`Meta.db_table <django.db.models.Options.db_table>` (:ticket:`23629`).
  
  * Fixed a regression when feeding the Django test client with an empty data
  string (:ticket:`21740`).
  
  * Fixed a regression in :djadmin:`makemessages` where static files were
  unexpectedly ignored (:ticket:`23583`).
  
  
  ========================

1.7 not secure

========================
  
  *September 2, 2014*
  
  Welcome to Django 1.7!
  
  These release notes cover the :ref:`new features <whats-new-1.7>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.7>` you'll
  want to be aware of when upgrading from Django 1.6 or older versions. We've
  :ref:`begun the deprecation process for some features
  <deprecated-features-1.7>`, and some features have reached the end of their
  deprecation process and :ref:`have been removed <removed-features-1.7>`.
  
  Python compatibility
  ====================
  
  Django 1.7 requires Python 2.7, 3.2, 3.3, or 3.4. We **highly recommend** and
  only officially support the latest release of each series.
  
  The Django 1.6 series is the last to support Python 2.6. Django 1.7 is the
  first release to support Python 3.4.
  
  This change should affect only a small number of Django users, as most
  operating-system vendors today are shipping Python 2.7 or newer as their default
  version. If you're still using Python 2.6, however, you'll need to stick to
  Django 1.6 until you can upgrade your Python version. Per :doc:`our support
  policy </internals/release-process>`, Django 1.6 will continue to receive
  security support until the release of Django 1.8.
  
  .. _whats-new-1.7:
  
  What's new in Django 1.7
  ========================
  
  Schema migrations
  -----------------
  
  Django now has built-in support for schema migrations. It allows models
  to be updated, changed, and deleted by creating migration files that represent
  the model changes and which can be run on any development, staging or production
  database.
  
  Migrations are covered in :doc:`their own documentation</topics/migrations>`,
  but a few of the key features are:
  
  * ``syncdb`` has been deprecated and replaced by ``migrate``. Don't worry -
  calls to ``syncdb`` will still work as before.
  
  * A new ``makemigrations`` command provides an easy way to autodetect changes
  to your models and make migrations for them.
  
  ``django.db.models.signals.pre_syncdb`` and
  ``django.db.models.signals.post_syncdb`` have been deprecated,
  to be replaced by :data:`~django.db.models.signals.pre_migrate` and
  :data:`~django.db.models.signals.post_migrate` respectively. These
  new signals have slightly different arguments. Check the
  documentation for details.
  
  * The ``allow_syncdb`` method on database routers is now called ``allow_migrate``,
  but still performs the same function. Routers with ``allow_syncdb`` methods
  will still work, but that method name is deprecated and you should change
  it as soon as possible (nothing more than renaming is required).
  
  * ``initial_data`` fixtures are no longer loaded for apps with migrations; if
  you want to load initial data for an app, we suggest you create a migration for
  your application and define a :class:`~django.db.migrations.operations.RunPython`
  or :class:`~django.db.migrations.operations.RunSQL` operation in the ``operations`` section of the migration.
  
  * Test rollback behavior is different for apps with migrations; in particular,
  Django will no longer emulate rollbacks on non-transactional databases or
  inside ``TransactionTestCase`` :ref:`unless specifically requested
  <test-case-serialized-rollback>`.
  
  * It is not advised to have apps without migrations depend on (have a
  :class:`~django.db.models.ForeignKey` or
  :class:`~django.db.models.ManyToManyField` to) apps with migrations.
  
  .. _app-loading-refactor-17-release-note:
  
  App-loading refactor
  --------------------
  
  Historically, Django applications were tightly linked to models. A singleton
  known as the "app cache" dealt with both installed applications and models.
  The models module was used as an identifier for applications in many APIs.
  
  As the concept of :doc:`Django applications </ref/applications>` matured, this
  code showed some shortcomings. It has been refactored into an "app registry"
  where models modules no longer have a central role and where it's possible to
  attach configuration data to applications.
  
  Improvements thus far include:
  
  * Applications can run code at startup, before Django does anything else, with
  the :meth:`~django.apps.AppConfig.ready` method of their configuration.
  
  * Application labels are assigned correctly to models even when they're
  defined outside of ``models.py``. You don't have to set
  :attr:`~django.db.models.Options.app_label` explicitly any more.
  
  * It is possible to omit ``models.py`` entirely if an application doesn't
  have any models.
  
  * Applications can be relabeled with the :attr:`~django.apps.AppConfig.label`
  attribute of application configurations, to work around label conflicts.
  
  * The name of applications can be customized in the admin with the
  :attr:`~django.apps.AppConfig.verbose_name` of application configurations.
  
  * The admin automatically calls :func:`~django.contrib.admin.autodiscover()`
  when Django starts. You can consequently remove this line from your
  URLconf.
  
  * Django imports all application configurations and models as soon as it
  starts, through a deterministic and straightforward process. This should
  make it easier to diagnose import issues such as import loops.
  
  New method on Field subclasses
  ------------------------------
  
  To help power both schema migrations and to enable easier addition of
  composite keys in future releases of Django, the
  :class:`~django.db.models.Field` API now has a new required method:
  ``deconstruct()``.
  
  This method takes no arguments, and returns a tuple of four items:
  
  * ``name``: The field's attribute name on its parent model, or None if it is not part of a model
  * ``path``: A dotted, Python path to the class of this field, including the class name.
  * ``args``: Positional arguments, as a list
  * ``kwargs``: Keyword arguments, as a dict
  
  These four values allow any field to be serialized into a file, as well as
  allowing the field to be copied safely, both essential parts of these new features.
  
  This change should not affect you unless you write custom Field subclasses;
  if you do, you may need to reimplement the ``deconstruct()`` method if your
  subclass changes the method signature of ``__init__`` in any way. If your
  field just inherits from a built-in Django field and doesn't override ``__init__``,
  no changes are necessary.
  
  If you do need to override ``deconstruct()``, a good place to start is the
  built-in Django fields (``django/db/models/fields/__init__.py``) as several
  fields, including ``DecimalField`` and ``DateField``, override it and show how
  to call the method on the superclass and simply add or remove extra arguments.
  
  This also means that all arguments to fields must themselves be serializable;
  to see what we consider serializable, and to find out how to make your own
  classes serializable, read the
  :ref:`migration serialization documentation <migration-serializing>`.
  
  Calling custom ``QuerySet`` methods from the ``Manager``
  --------------------------------------------------------
  
  Historically, the recommended way to make reusable model queries was to create
  methods on a custom ``Manager`` class. The problem with this approach was that
  after the first method call, you'd get back a ``QuerySet`` instance and
  couldn't call additional custom manager methods.
  
  Though not documented, it was common to work around this issue by creating a
  custom ``QuerySet`` so that custom methods could be chained; but the solution
  had a number of drawbacks:
  
  * The custom ``QuerySet`` and its custom methods were lost after the first
  call to ``values()`` or ``values_list()``.
  
  * Writing a custom ``Manager`` was still necessary to return the custom
  ``QuerySet`` class and all methods that were desired on the ``Manager``
  had to be proxied to the ``QuerySet``. The whole process went against
  the DRY principle.
  
  The :meth:`QuerySet.as_manager() <django.db.models.query.QuerySet.as_manager>`
  class method can now directly :ref:`create Manager with QuerySet methods
  <create-manager-with-queryset-methods>`::
  
  class FoodQuerySet(models.QuerySet):
  def pizzas(self):
  return self.filter(kind='pizza')
  
  def vegetarian(self):
  return self.filter(vegetarian=True)
  
  class Food(models.Model):
  kind = models.CharField(max_length=50)
  vegetarian = models.BooleanField(default=False)
  objects = FoodQuerySet.as_manager()
  
  Food.objects.pizzas().vegetarian()
  
  Using a custom manager when traversing reverse relations
  --------------------------------------------------------
  
  It is now possible to :ref:`specify a custom manager
  <using-custom-reverse-manager>` when traversing a reverse relationship::
  
  class Blog(models.Model):
  pass
  
  class Entry(models.Model):
  blog = models.ForeignKey(Blog)
  
  objects = models.Manager()   Default Manager
  entries = EntryManager()     Custom Manager
  
  b = Blog.objects.get(id=1)
  b.entry_set(manager='entries').all()
  
  New system check framework
  --------------------------
  
  We've added a new :doc:`System check framework </ref/checks>` for
  detecting common problems (like invalid models) and providing hints for
  resolving those problems. The framework is extensible so you can add your
  own checks for your own apps and libraries.
  
  To perform system checks, you use the :djadmin:`check` management command.
  This command replaces the older ``validate`` management command.
  
  New ``Prefetch`` object for advanced ``prefetch_related`` operations.
  ---------------------------------------------------------------------
  
  The new :class:`~django.db.models.Prefetch` object allows customizing
  prefetch operations.
  
  You can specify the ``QuerySet`` used to traverse a given relation
  or customize the storage location of prefetch results.
  
  This enables things like filtering prefetched relations, calling
  :meth:`~django.db.models.query.QuerySet.select_related()` from a prefetched
  relation, or prefetching the same relation multiple times with different
  querysets. See :meth:`~django.db.models.query.QuerySet.prefetch_related()`
  for more details.
  
  Admin shortcuts support time zones
  ----------------------------------
  
  The "today" and "now" shortcuts next to date and time input widgets in the
  admin are now operating in the :ref:`current time zone
  <default-current-time-zone>`. Previously, they used the browser time zone,
  which could result in saving the wrong value when it didn't match the current
  time zone on the server.
  
  In addition, the widgets now display a help message when the browser and
  server time zone are different, to clarify how the value inserted in the field
  will be interpreted.
  
  Using database cursors as context managers
  ------------------------------------------
  
  Prior to Python 2.7, database cursors could be used as a context manager. The
  specific backend's cursor defined the behavior of the context manager. The
  behavior of magic method lookups was changed with Python 2.7 and cursors were
  no longer usable as context managers.
  
  Django 1.7 allows a cursor to be used as a context manager. That is,
  the following can be used::
  
  with connection.cursor() as c:
  c.execute(...)
  
  instead of::
  
  c = connection.cursor()
  try:
  c.execute(...)
  finally:
  c.close()
  
  Custom lookups
  --------------
  
  It is now possible to write custom lookups and transforms for the ORM.
  Custom lookups work just like Django's built-in lookups (e.g. ``lte``,
  ``icontains``) while transforms are a new concept.
  
  The :class:`django.db.models.Lookup` class provides a way to add lookup
  operators for model fields. As an example it is possible to add ``day_lte``
  operator for ``DateFields``.
  
  The :class:`django.db.models.Transform` class allows transformations of
  database values prior to the final lookup. For example it is possible to
  write a ``year`` transform that extracts year from the field's value.
  Transforms allow for chaining. After the ``year`` transform has been added
  to ``DateField`` it is possible to filter on the transformed value, for
  example ``qs.filter(author__birthdate__year__lte=1981)``.
  
  For more information about both custom lookups and transforms refer to
  the :doc:`custom lookups </howto/custom-lookups>` documentation.
  
  Improvements to ``Form`` error handling
  ---------------------------------------
  
  ``Form.add_error()``
  ~~~~~~~~~~~~~~~~~~~~
  
  Previously there were two main patterns for handling errors in forms:
  
  * Raising a :exc:`~django.core.exceptions.ValidationError` from within certain
  functions (e.g. ``Field.clean()``, ``Form.clean_<fieldname>()``, or
  ``Form.clean()`` for non-field errors.)
  
  * Fiddling with ``Form._errors`` when targeting a specific field in
  ``Form.clean()`` or adding errors from outside of a "clean" method
  (e.g. directly from a view).
  
  Using the former pattern was straightforward since the form can guess from the
  context (i.e. which method raised the exception) where the errors belong and
  automatically process them. This remains the canonical way of adding errors
  when possible. However the latter was fiddly and error-prone, since the burden
  of handling edge cases fell on the user.
  
  The new :meth:`~django.forms.Form.add_error()` method allows adding errors
  to specific form fields from anywhere without having to worry about the details
  such as creating instances of ``django.forms.utils.ErrorList`` or dealing with
  ``Form.cleaned_data``. This new API replaces manipulating ``Form._errors``
  which now becomes a private API.
  
  See :ref:`validating-fields-with-clean` for an example using
  ``Form.add_error()``.
  
  Error metadata
  ~~~~~~~~~~~~~~
  
  The :exc:`~django.core.exceptions.ValidationError` constructor accepts metadata
  such as error ``code`` or ``params`` which are then available for interpolating
  into the error message (see :ref:`raising-validation-error` for more details);
  however, before Django 1.7 those metadata were discarded as soon as the errors
  were added to :attr:`Form.errors <django.forms.Form.errors>`.
  
  :attr:`Form.errors <django.forms.Form.errors>` and
  ``django.forms.utils.ErrorList`` now store the ``ValidationError`` instances
  so these metadata can be retrieved at any time through the new
  :meth:`Form.errors.as_data <django.forms.Form.errors.as_data()>` method.
  
  The retrieved ``ValidationError`` instances can then be identified thanks to
  their error ``code`` which enables things like rewriting the error's message
  or writing custom logic in a view when a given error is present. It can also
  be used to serialize the errors in a custom format such as XML.
  
  The new :meth:`Form.errors.as_json() <django.forms.Form.errors.as_json()>`
  method is a convenience method which returns error messages along with error
  codes serialized as JSON. ``as_json()`` uses ``as_data()`` and gives an idea
  of how the new system could be extended.
  
  Error containers and backward compatibility
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  Heavy changes to the various error containers were necessary in order
  to support the features above, specifically
  :attr:`Form.errors <django.forms.Form.errors>`,
  ``django.forms.utils.ErrorList``, and the internal storages of
  :exc:`~django.core.exceptions.ValidationError`. These containers which used
  to store error strings now store ``ValidationError`` instances and public APIs
  have been adapted to make this as transparent as possible, but if you've been
  using private APIs, some of the changes are backwards incompatible; see
  :ref:`validation-error-constructor-and-internal-storage` for more details.
  
  Minor features
  --------------
  
  :mod:`django.contrib.admin`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * You can now implement :attr:`~django.contrib.admin.AdminSite.site_header`,
  :attr:`~django.contrib.admin.AdminSite.site_title`, and
  :attr:`~django.contrib.admin.AdminSite.index_title` attributes on a custom
  :class:`~django.contrib.admin.AdminSite` in order to easily change the admin
  site's page title and header text. No more needing to override templates!
  
  * Buttons in :mod:`django.contrib.admin` now use the ``border-radius`` CSS
  property for rounded corners rather than GIF background images.
  
  * Some admin templates now have ``app-<app_name>`` and ``model-<model_name>``
  classes in their ``<body>`` tag to allow customizing the CSS per app or per
  model.
  
  * The admin changelist cells now have a ``field-<field_name>`` class in the
  HTML to enable style customizations.
  
  * The admin's search fields can now be customized per-request thanks to the new
  :meth:`django.contrib.admin.ModelAdmin.get_search_fields` method.
  
  * The :meth:`ModelAdmin.get_fields()
  <django.contrib.admin.ModelAdmin.get_fields>` method may be overridden to
  customize the value of :attr:`ModelAdmin.fields
  <django.contrib.admin.ModelAdmin.fields>`.
  
  * In addition to the existing ``admin.site.register`` syntax, you can use the
  new :func:`~django.contrib.admin.register` decorator to register a
  :class:`~django.contrib.admin.ModelAdmin`.
  
  * You may specify :meth:`ModelAdmin.list_display_links
  <django.contrib.admin.ModelAdmin.list_display_links>` ``= None`` to disable
  links on the change list page grid.
  
  * You may now specify :attr:`ModelAdmin.view_on_site
  <django.contrib.admin.ModelAdmin.view_on_site>` to control whether or not to
  display the "View on site" link.
  
  * You can specify a descending ordering for a :attr:`ModelAdmin.list_display
  <django.contrib.admin.ModelAdmin.list_display>` value by prefixing the
  ``admin_order_field`` value with a hyphen.
  
  * The :meth:`ModelAdmin.get_changeform_initial_data()
  <django.contrib.admin.ModelAdmin.get_changeform_initial_data>` method may be
  overridden to define custom behavior for setting initial change form data.
  
  :mod:`django.contrib.auth`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Any ``**kwargs`` passed to
  :meth:`~django.contrib.auth.models.User.email_user()` are passed to the
  underlying :meth:`~django.core.mail.send_mail()` call.
  
  * The :func:`~django.contrib.auth.decorators.permission_required` decorator can
  take a list of permissions as well as a single permission.
  
  * You can override the new :meth:`AuthenticationForm.confirm_login_allowed()
  <django.contrib.auth.forms.AuthenticationForm.confirm_login_allowed>` method
  to more easily customize the login policy.
  
  * ``django.contrib.auth.views.password_reset()`` takes an optional
  ``html_email_template_name`` parameter used to send a multipart HTML email
  for password resets.
  
  * The :meth:`AbstractBaseUser.get_session_auth_hash()
  <django.contrib.auth.models.AbstractBaseUser.get_session_auth_hash>`
  method was added and if your :setting:`AUTH_USER_MODEL` inherits from
  :class:`~django.contrib.auth.models.AbstractBaseUser`, changing a user's
  password now invalidates old sessions if the
  ``django.contrib.auth.middleware.SessionAuthenticationMiddleware`` is
  enabled. See :ref:`session-invalidation-on-password-change` for more details.
  
  ``django.contrib.formtools``
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * Calls to ``WizardView.done()`` now include a ``form_dict`` to allow easier
  access to forms by their step name.
  
  :mod:`django.contrib.gis`
  ~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The default OpenLayers library version included in widgets has been updated
  from 2.11 to 2.13.
  
  * Prepared geometries now also support the ``crosses``, ``disjoint``,
  ``overlaps``, ``touches`` and ``within`` predicates, if GEOS 3.3 or later is
  installed.
  
  :mod:`django.contrib.messages`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The backends for :mod:`django.contrib.messages` that use cookies, will now
  follow the :setting:`SESSION_COOKIE_SECURE` and
  :setting:`SESSION_COOKIE_HTTPONLY` settings.
  
  * The :ref:`messages context processor <message-displaying>` now adds a
  dictionary of default levels under the name ``DEFAULT_MESSAGE_LEVELS``.
  
  * :class:`~django.contrib.messages.storage.base.Message` objects now have a
  ``level_tag`` attribute that contains the string representation of the
  message level.
  
  :mod:`django.contrib.redirects`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * :class:`~django.contrib.redirects.middleware.RedirectFallbackMiddleware`
  has two new attributes
  (:attr:`~django.contrib.redirects.middleware.RedirectFallbackMiddleware.response_gone_class`
  and
  :attr:`~django.contrib.redirects.middleware.RedirectFallbackMiddleware.response_redirect_class`)
  that specify the types of :class:`~django.http.HttpResponse` instances the
  middleware returns.
  
  :mod:`django.contrib.sessions`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The ``"django.contrib.sessions.backends.cached_db"`` session backend now
  respects :setting:`SESSION_CACHE_ALIAS`. In previous versions, it always used
  the ``default`` cache.
  
  :mod:`django.contrib.sitemaps`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :mod:`sitemap framework<django.contrib.sitemaps>` now makes use of
  :attr:`~django.contrib.sitemaps.Sitemap.lastmod` to set a ``Last-Modified``
  header in the response. This makes it possible for the
  :class:`~django.middleware.http.ConditionalGetMiddleware` to handle
  conditional ``GET`` requests for sitemaps which set ``lastmod``.
  
  :mod:`django.contrib.sites`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :class:`django.contrib.sites.middleware.CurrentSiteMiddleware` allows
  setting the current site on each request.
  
  :mod:`django.contrib.staticfiles`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :ref:`static files storage classes <staticfiles-storages>` may be
  subclassed to override the permissions that collected static files and
  directories receive by setting the
  :attr:`~django.core.files.storage.FileSystemStorage.file_permissions_mode`
  and :attr:`~django.core.files.storage.FileSystemStorage.directory_permissions_mode`
  parameters. See :djadmin:`collectstatic` for example usage.
  
  * The ``CachedStaticFilesStorage`` backend gets a sibling class called
  :class:`~django.contrib.staticfiles.storage.ManifestStaticFilesStorage`
  that doesn't use the cache system at all but instead a JSON file called
  ``staticfiles.json`` for storing the mapping between the original file name
  (e.g. ``css/styles.css``) and the hashed file name (e.g.
  ``css/styles.55e7cbb9ba48.css``). The ``staticfiles.json`` file is created
  when running the :djadmin:`collectstatic` management command and should
  be a less expensive alternative for remote storages such as Amazon S3.
  
  See the :class:`~django.contrib.staticfiles.storage.ManifestStaticFilesStorage`
  docs for more information.
  
  * :djadmin:`findstatic` now accepts verbosity flag level 2, meaning it will
  show the relative paths of the directories it searched. See
  :djadmin:`findstatic` for example output.
  
  :mod:`django.contrib.syndication`
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :class:`~django.utils.feedgenerator.Atom1Feed` syndication feed's
  ``updated`` element now utilizes ``updateddate`` instead of ``pubdate``,
  allowing the ``published`` element to be included in the feed (which
  relies on ``pubdate``).
  
  Cache
  ~~~~~
  
  * Access to caches configured in :setting:`CACHES` is now available via
  :data:`django.core.cache.caches`. This dict-like object provides a different
  instance per thread. It supersedes ``django.core.cache.get_cache()`` which
  is now deprecated.
  
  * If you instantiate cache backends directly, be aware that they aren't
  thread-safe any more, as :data:`django.core.cache.caches` now yields
  different instances per thread.
  
  * Defining the :setting:`TIMEOUT <CACHES-TIMEOUT>` argument of the
  :setting:`CACHES` setting as ``None`` will set the cache keys as
  "non-expiring" by default. Previously, it was only possible to pass
  ``timeout=None`` to the cache backend's ``set()`` method.
  
  Cross Site Request Forgery
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  * The :setting:`CSRF_COOKIE_AGE` setting facilitates the use of session-based
  CSRF cookies.
  
  Email
  ~~~~~
  
  * :func:`~django.core.mail.send_mail` now accepts an ``html_message``
  parameter for sending a multipart :mimetype:`text/plain` and
  :mimetype:`text/html` email.
  
  * The SMTP :class:`~django.core.mail.backends.smtp.EmailBackend` now accepts a
  ``timeout`` parameter.
  
  File Storage
  ~~~~~~~~~~~~
  
  * File locking on Windows previously depended on the PyWin32 package; if it
  wasn't installed, file locking failed silently. That dependency has been
  removed, and file locking is now implemented natively on both Windows
  and Unix.
  
  File Uploads
  ~~~~~~~~~~~~
  
  * The new :attr:`UploadedFile.content_type_extra
  <django.core.files.uploadedfile.UploadedFile.content_type_extra>` attribute
  contains extra parameters passed to the ``content-type`` header on a file
  upload.
  
  * The new :setting:`FILE_UPLOAD_DIRECTORY_PERMISSIONS` setting controls
  the file system permissions of directories created during file upload, like
  :setting:`FILE_UPLOAD_PERMISSIONS` does for the files themselves.
  
  * The :attr:`FileField.upload_to <django.db.models.FileField.upload_to>`
  attribute is now optional. If it is omitted or given ``None`` or an empty
  string, a subdirectory won't be used for storing the uploaded files.
  
  * Uploaded files are now explicitly closed before the response is delivered to
  the client. Partially uploaded files are also closed as long as they are
  named ``file`` in the upload handler.
  
  * :meth:`Storage.get_available_name()
  <django.core.files.storage.Storage.get_available_name>` now appends an
  underscore plus a random 7 character alphanumeric string (e.g.
  ``"_x3a1gho"``), rather than iterating through an underscore followed by a
  number (e.g. ``"_1"``, ``"_2"``, etc.) to prevent a denial-of-service attack.
  This change was also made in the 1.6.6, 1.5.9, and 1.4.14 security releases.
  
  Forms
  ~~~~~
  
  * The ``<label>`` and ``<input>`` tags rendered by
  :class:`~django.forms.RadioSelect` and
  :class:`~django.forms.CheckboxSelectMultiple` when looping over the radio
  buttons or checkboxes now include ``for`` and ``id`` attributes, respectively.
  Each radio button or checkbox includes an ``id_for_label`` attribute to
  output the element's ID.
  
  * The ``<textarea>`` tags rendered by :class:`~django.forms.Textarea` now
  include a ``maxlength`` attribute if the :class:`~django.db.models.TextField`
  model field has a ``max_length``.
  
  * :attr:`Field.choices<django.db.models.Field.choices>` now allows you to
  customize the "empty choice" label by including a tuple with an empty string
  or ``None`` for the key and the custom label as the value. The default blank
  option ``"----------"`` will be omitted in this case.
  
  * :class:`~django.forms.MultiValueField` allows optional subfields by setting
  the ``require_all_fields`` argument to ``False``. The ``required`` attribute
  for each individual field will be respected, and a new ``incomplete``
  validation error will be raised when any required fields are empty.
  
  * The :meth:`~django.forms.Form.clean` method on a form no longer needs to
  return ``self.cleaned_data``. If it does return a changed dictionary then
  that will still be used.
  
  * After a temporary regression in Django 1.6, it's now possible again to make
  :class:`~django.forms.TypedChoiceField` ``coerce`` method return an arbitrary
  value.
  
  * :attr:`SelectDateWidget.months
  <django.forms.SelectDateWidget.months>` can be used to
  customize the wording of the months displayed in the select widget.
  
  * The ``min_num`` and ``validate_min`` parameters were added to
  :func:`~django.forms.formsets.formset_factory` to allow validating
  a minimum number of submitted forms.
  
  * The metaclasses used by ``Form`` and ``ModelForm`` have been reworked to
  support more inheritance scenarios. The previous limitation that prevented
  inheriting from both ``Form`` and ``ModelForm`` simultaneously have been
  removed as long as ``ModelForm`` appears first in the MRO.
  
  * It's now possible to remove a field from a ``Form`` when subclassing by
  setting the name to ``None``.
  
  * It's now possible to customize the error messages for ``ModelForm``’s
  ``unique``, ``unique_for_date``, and ``unique_together`` constraints.
  In order to support ``unique_together`` or any other ``NON_FIELD_ERROR``,
  ``ModelForm`` now looks for the ``NON_FIELD_ERROR`` key in the
  ``error_messages`` dictionary of the ``ModelForm``’s inner ``Meta`` class.
  See :ref:`considerations regarding model's error_messages
  <considerations-regarding-model-errormessages>` for more details.
  
  Internationalization
  ~~~~~~~~~~~~~~~~~~~~
  
  * The :attr:`django.middleware.locale.LocaleMiddleware.response_redirect_class`
  attribute allows you to customize the redirects issued by the middleware.
  
  * The :class:`~django.middleware.locale.LocaleMiddleware` now stores the user's
  selected language with the session key ``_language``. This should only be
  accessed using the :data:`~django.utils.translation.LANGUAGE_SESSION_KEY`
  constant. Previously it was stored with the key ``django_language`` and the
  ``LANGUAGE_SESSION_KEY`` constant did not exist, but keys reserved for Django
  should start with an underscore. For backwards compatibility ``django_language``
  is still read from in 1.7. Sessions will be migrated to the new key
  as they are written.
  
  * The :ttag:`blocktrans` tag now supports a ``trimmed`` option. This
  option will remove newline characters from the beginning and the end of the
  content of the ``{% blocktrans %}`` tag, replace any whitespace at the
  beginning and end of a line and merge all lines into one using a space
  character to separate them. This is quite useful for indenting the content of
  a ``{% blocktrans %}`` tag without having the indentation characters end up
  in the corresponding entry in the PO file, which makes the translation
  process easier.
  
  * When you run :djadmin:`makemessages` from the root directory of your project,
  any extracted strings will now be automatically distributed to the proper
  app or project message file. See :ref:`how-to-create-language-files` for
  details.
  
  * The :djadmin:`makemessages` command now always adds the ``--previous``
  command line flag to the ``msgmerge`` command, keeping previously translated
  strings in po files for fuzzy strings.
  
  * The following settings to adjust the language cookie options were introduced:
  :setting:`LANGUAGE_COOKIE_AGE`, :setting:`LANGUAGE_COOKIE_DOMAIN`
  and :setting:`LANGUAGE_COOKIE_PATH`.
  
  * Added :doc:`/topics/i18n/formatting` for Esperanto.
  
  Management Commands
  ~~~~~~~~~~~~~~~~~~~
  
  * The new :option:`--no-color` option for ``django-admin`` disables the
  colorization of management command output.
  
  * The new :option:`dumpdata --natural-foreign` and :option:`dumpdata
  --natural-primary` options, and the new ``use_natural_foreign_keys`` and
  ``use_natural_primary_keys`` arguments for ``serializers.serialize()``, allow
  the use of natural primary keys when serializing.
  
  * It is no longer necessary to provide the cache table name or the
  ``--database`` option for the :djadmin:`createcachetable` command.
  Django takes this information from your settings file. If you have configured
  multiple caches or multiple databases, all cache tables are created.
  
  * The :djadmin:`runserver` command received several improvements:
  
  * On Linux systems, if pyinotify_ is installed, the development server will
  reload immediately when a file is changed. Previously, it polled the
  filesystem for changes every second. That caused a small delay before
  reloads and reduced battery life on laptops.
  
  .. _pyinotify: https://pypi.org/project/pyinotify/
  
  * In addition, the development server automatically reloads when a
  translation file is updated, i.e. after running
  :djadmin:`compilemessages`.
  
  * All HTTP requests are logged to the console, including requests for static
  files or ``favicon.ico`` that used to be filtered out.
  
  * Management commands can now produce syntax colored output under Windows if
  the ANSICON third-party tool is installed and active.
  
  * :djadmin:`collectstatic` command with symlink option is now supported on
  Windows NT 6 (Windows Vista and newer).
  
  * Initial SQL data now works better if the sqlparse_ Python library is
  installed.
  
  Note that it's deprecated in favor of the
  :class:`~django.db.migrations.operations.RunSQL` operation of migrations,
  which benefits from the improved behavior.
  
  .. _sqlparse: https://pypi.org/project/sqlparse/
  
  Models
  ~~~~~~
  
  * The :meth:`QuerySet.update_or_create()
  <django.db.models.query.QuerySet.update_or_create>` method was added.
  
  * The new :attr:`~django.db.models.Options.default_permissions` model
  ``Meta`` option allows you to customize (or disable) creation of the default
  add, change, and delete permissions.
  
  * Explicit :class:`~django.db.models.OneToOneField` for
  :ref:`multi-table-inheritance` are now discovered in abstract classes.
  
  * It is now possible to avoid creating a backward relation for
  :class:`~django.db.models.OneToOneField` by setting its
  :attr:`~django.db.models.ForeignKey.related_name` to
  ``'+'`` or ending it with ``'+'``.
  
  * :class:`F expressions <django.db.models.F>` support the power operator
  (``**``).
  
  * The ``remove()`` and ``clear()`` methods of the related managers created by
  ``ForeignKey`` and ``GenericForeignKey`` now accept the ``bulk`` keyword
  argument to control whether or not to perform operations in bulk
  (i.e. using ``QuerySet.update()``). Defaults to ``True``.
  
  * It is now possible to use ``None`` as a query value for the :lookup:`iexact`
  lookup.
  
  * It is now possible to pass a callable as value for the attribute
  :attr:`~django.db.models.ForeignKey.limit_choices_to` when defining a
  ``ForeignKey`` or ``ManyToManyField``.
  
  * Calling :meth:`only() <django.db.models.query.QuerySet.only>` and
  :meth:`defer() <django.db.models.query.QuerySet.defer>` on the result of
  :meth:`QuerySet.values() <django.db.models.query.QuerySet.values>` now raises
  an error (before that, it would either result in a database error or
  incorrect data).
  
  * You can use a single list for :attr:`~django.db.models.Options.index_together`
  (rather than a list of lists) when specifying a single set of fields.
  
  * Custom intermediate models having more than one foreign key to any of the
  models participating in a many-to-many relationship are now permitted,
  provided you explicitly specify which foreign keys should be used by setting
  the new :attr:`ManyToManyField.through_fields <django.db.models.ManyToManyField.through_fields>`
  argument.
  
  * Assigning a model instance to a non-relation field will now throw an error.
  Previously this used to work if the field accepted integers as input as it
  took the primary key.
  
  * Integer fields are now validated against database backend specific min and
  max values based on their :meth:`internal_type <django.db.models.Field.get_internal_type>`.
  Previously model field validation didn't prevent values out of their associated
  column data type range from being saved resulting in an integrity error.
  
  * It is now possible to explicitly :meth:`~django.db.models.query.QuerySet.order_by`
  a relation ``_id`` field by using its attribute name.
  
  Signals
  ~~~~~~~
  
  * The ``enter`` argument was added to the
  :data:`~django.test.signals.setting_changed` signal.
  
  * The model signals can be now be connected to using a ``str`` of the
  ``'app_label.ModelName'`` form – just like related fields – to lazily
  reference their senders.
  
  Templates
  ~~~~~~~~~
  
  * The :meth:`Context.push() <django.template.Context.push>` method now returns
  a context manager which automatically calls :meth:`pop()
  <django.template.Context.pop>` upon exiting the ``with`` statement.
  Additionally, :meth:`push() <django.template.Context.push>` now accepts
  parameters that are passed to the ``dict`` constructor used to build the new
  context level.
  
  * The new :meth:`Context.flatten() <django.template.Context.flatten>` method
  returns a ``Context``'s stack as one flat dictionary.
  
  * ``Context`` objects can now be compared for equality (internally, this
  uses :meth:`Context.flatten() <django.template.Context.flatten>` so the
  internal structure of each ``Context``'s stack doesn't matter as long as their
  flattened version is identical).
  
  * The :ttag:`widthratio` template tag now accepts an ``"as"`` parameter to
  capture the result in a variable.
  
  * The :ttag:`include` template tag will now also accept anything with a
  ``render()`` method (such as a ``Template``) as an argument. String
  arguments will be looked up using
  :func:`~django.template.loader.get_template` as always.
  
  * It is now possible to :ttag:`include` templates recursively.
  
  * Template objects now have an origin attribute set when
  ``TEMPLATE_DEBUG`` is ``True``. This allows template origins to be
  inspected and logged outside of the ``django.template`` infrastructure.
  
  * ``TypeError`` exceptions are no longer silenced when raised during the
  rendering of a template.
  
  * The following functions now accept a ``dirs`` parameter which is a list or
  tuple to override ``TEMPLATE_DIRS``:
  
  * :func:`django.template.loader.get_template()`
  * :func:`django.template.loader.select_template()`
  * :func:`django.shortcuts.render()`
  * ``django.shortcuts.render_to_response()``
  
  * The :tfilter:`time` filter now accepts timezone-related :ref:`format
  specifiers <date-and-time-formatting-specifiers>` ``'e'``, ``'O'`` , ``'T'``
  and ``'Z'`` and is able to digest :ref:`time-zone-aware
  <naive_vs_aware_datetimes>` ``datetime`` instances performing the expected
  rendering.
  
  * The :ttag:`cache` tag will now try to use the cache called
  "template_fragments" if it exists and fall back to using the default cache
  otherwise. It also now accepts an optional ``using`` keyword argument to
  control which cache it uses.
  
  * The new :tfilter:`truncatechars_html` filter truncates a string to be no
  longer than the specified number of characters, taking HTML into account.
  
  Requests and Responses
  ~~~~~~~~~~~~~~~~~~~~~~
  
  * The new :attr:`HttpRequest.scheme <django.http.HttpRequest.scheme>` attribute
  specifies the scheme of the request (``http`` or ``https`` normally).
  
  
  * The shortcut :func:`redirect() <django.shortcuts.redirect>` now supports
  relative URLs.
  
  * The new :class:`~django.http.JsonResponse` subclass of
  :class:`~django.http.HttpResponse` helps easily create JSON-encoded responses.
  
  Tests
  ~~~~~
  
  * :class:`~django.test.runner.DiscoverRunner` has two new attributes,
  :attr:`~django.test.runner.DiscoverRunner.test_suite` and
  :attr:`~django.test.runner.DiscoverRunner.test_runner`, which facilitate
  overriding the way tests are collected and run.
  
  * The ``fetch_redirect_response`` argument was added to
  :meth:`~django.test.SimpleTestCase.assertRedirects`. Since the test
  client can't fetch externals URLs, this allows you to use ``assertRedirects``
  with redirects that aren't part of your Django app.
  
  * Correct handling of scheme when making comparisons in
  :meth:`~django.test.SimpleTestCase.assertRedirects`.
  
  * The ``secure`` argument was added to all the request methods of
  :class:`~django.test.Client`. If ``True``, the request will be made
  through HTTPS.
  
  * :meth:`~django.test.TransactionTestCase.assertNumQueries` now prints
  out the list of executed queries if the assertion fails.
  
  * The ``WSGIRequest`` instance generated by the test handler is now attached to
  the :attr:`django.test.Response.wsgi_request` attribute.
  
  * The database settings for testing have been collected into a dictionary
  named :setting:`TEST <DATABASE-TEST>`.
  
  Utilities
  ~~~~~~~~~
  
  * Improved :func:`~django.utils.html.strip_tags` accuracy (but it still cannot
  guarantee an HTML-safe result, as stated in the documentation).
  
  Validators
  ~~~~~~~~~~
  
  * :class:`~django.core.validators.RegexValidator` now accepts the optional
  :attr:`~django.core.validators.RegexValidator.flags` and
  Boolean :attr:`~django.core.validators.RegexValidator.inverse_match` arguments.
  The :attr:`~django.core.validators.RegexValidator.inverse_match` attribute
  determines if the :exc:`~django.core.exceptions.ValidationError` should
  be raised when the regular expression pattern matches (``True``) or does not
  match (``False``, by default) the provided ``value``. The
  :attr:`~django.core.validators.RegexValidator.flags` attribute sets the flags
  used when compiling a regular expression string.
  
  * :class:`~django.core.validators.URLValidator` now accepts an optional
  ``schemes`` argument which allows customization of the accepted URI schemes
  (instead of the defaults ``http(s)`` and ``ftp(s)``).
  
  * :func:`~django.core.validators.validate_email` now accepts addresses with
  IPv6 literals, like ``example[2001:db8::1]``, as specified in RFC 5321.
  
  .. _backwards-incompatible-1.7:
  
  Backwards incompatible changes in 1.7
  =====================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`deprecation plan <deprecation-removed-in-1.7>` for any features that
  have been removed. If you haven't updated your code within the
  deprecation timeline for a given feature, its removal may appear as a
  backwards incompatible change.
  
  ``allow_syncdb`` / ``allow_migrate``
  ------------------------------------
  
  While Django will still look at ``allow_syncdb`` methods even though they
  should be renamed to ``allow_migrate``, there is a subtle difference in which
  models get passed to these methods.
  
  For apps with migrations, ``allow_migrate`` will now get passed
  :ref:`historical models <historical-models>`, which are special versioned models
  without custom attributes, methods or managers. Make sure your ``allow_migrate``
  methods are only referring to fields or other items in ``model._meta``.
  
  initial_data
  ------------
  
  Apps with migrations will not load ``initial_data`` fixtures when they have
  finished migrating. Apps without migrations will continue to load these fixtures
  during the phase of ``migrate`` which emulates the old ``syncdb`` behavior,
  but any new apps will not have this support.
  
  Instead, you are encouraged to load initial data in migrations if you need it
  (using the ``RunPython`` operation and your model classes);
  this has the added advantage that your initial data will not need updating
  every time you change the schema.
  
  Additionally, like the rest of Django's old ``syncdb`` code, ``initial_data``
  has been started down the deprecation path and will be removed in Django 1.9.
  
  deconstruct() and serializability
  ---------------------------------
  
  Django now requires all Field classes and all of their constructor arguments
  to be serializable. If you modify the constructor signature in your custom
  Field in any way, you'll need to implement a deconstruct() method;
  we've expanded the custom field documentation with :ref:`instructions
  on implementing this method <custom-field-deconstruct-method>`.
  
  The requirement for all field arguments to be
  :ref:`serializable <migration-serializing>` means that any custom class
  instances being passed into Field constructors - things like custom Storage
  subclasses, for instance - need to have a :ref:`deconstruct method defined on
  them as well <custom-deconstruct-method>`, though Django provides a handy
  class decorator that will work for most applications.
  
  App-loading changes
  -------------------
  
  Start-up sequence
  ~~~~~~~~~~~~~~~~~
  
  Django 1.7 loads application configurations and models as soon as it starts.
  While this behavior is more straightforward and is believed to be more robust,
  regressions cannot be ruled out. See :ref:`applications-troubleshooting` for
  solutions to some problems you may encounter.
  
  Standalone scripts
  ~~~~~~~~~~~~~~~~~~
  
  If you're using Django in a plain Python script — rather than a management
  command — and you rely on the :envvar:`DJANGO_SETTINGS_MODULE` environment
  variable, you must now explicitly initialize Django at the beginning of your
  script with::
  
  >>> import django
  >>> django.setup()
  
  Otherwise, you will hit an ``AppRegistryNotReady`` exception.
  
  WSGI scripts
  ~~~~~~~~~~~~
  
  Until Django 1.3, the recommended way to create a WSGI application was::
  
  import django.core.handlers.wsgi
  application = django.core.handlers.wsgi.WSGIHandler()
  
  In Django 1.4, support for WSGI was improved and the API changed to::
  
  from django.core.wsgi import get_wsgi_application
  application = get_wsgi_application()
  
  If you're still using the former style in your WSGI script, you need to
  upgrade to the latter, or you will hit an ``AppRegistryNotReady`` exception.
  
  App registry consistency
  ~~~~~~~~~~~~~~~~~~~~~~~~
  
  It is no longer possible to have multiple installed applications with the same
  label. In previous versions of Django, this didn't always work correctly, but
  didn't crash outright either.
  
  If you have two apps with the same label, you should create an
  :class:`~django.apps.AppConfig` for one of them and override its
  :class:`~django.apps.AppConfig.label` there. You should then adjust your code
  wherever it references this application or its models with the old label.
  
  It isn't possible to import the same model twice through different paths any
  more. As of Django 1.6, this may happen only if you're manually putting a
  directory and a subdirectory on :envvar:`PYTHONPATH`. Refer to the section on
  the new project layout in the :doc:`1.4 release notes </releases/1.4>` for
  migration instructions.
  
  You should make sure that:
  
  * All models are defined in applications that are listed in
  :setting:`INSTALLED_APPS` or have an explicit
  :attr:`~django.db.models.Options.app_label`.
  
  * Models aren't imported as a side-effect of loading their application.
  Specifically, you shouldn't import models in the root module of an
  application nor in the module that define its configuration class.
  
  Django will enforce these requirements as of version 1.9, after a deprecation
  period.
  
  Subclassing AppCommand
  ~~~~~~~~~~~~~~~~~~~~~~
  
  Subclasses of :class:`~django.core.management.AppCommand` must now implement a
  :meth:`~django.core.management.AppCommand.handle_app_config` method instead of
  ``handle_app()``. This method receives an :class:`~django.apps.AppConfig`
  instance instead of a models module.
  
  Introspecting applications
  ~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  Since :setting:`INSTALLED_APPS` now supports application configuration classes
  in addition to application modules, you should review code that accesses this
  setting directly and use the app registry (:attr:`django.apps.apps`) instead.
  
  The app registry has preserved some features of the old app cache. Even though
  the app cache was a private API, obsolete methods and arguments will be
  removed through a standard deprecation path, with the exception of the
  following changes that take effect immediately:
  
  * ``get_model`` raises :exc:`LookupError` instead of returning ``None`` when no
  model is found.
  
  * The ``only_installed`` argument of ``get_model`` and ``get_models`` no
  longer exists, nor does the ``seed_cache`` argument of ``get_model``.
  
  Management commands and order of :setting:`INSTALLED_APPS`
  ----------------------------------------------------------
  
  When several applications provide management commands with the same name,
  Django loads the command from the application that comes first in
  :setting:`INSTALLED_APPS`. Previous versions loaded the command from the
  application that came last.
  
  This brings discovery of management commands in line with other parts of
  Django that rely on the order of :setting:`INSTALLED_APPS`, such as static
  files, templates, and translations.
  
  .. _validation-error-constructor-and-internal-storage:
  
  ``ValidationError`` constructor and internal storage
  ----------------------------------------------------
  
  The behavior of the ``ValidationError`` constructor has changed when it
  receives a container of errors as an argument (e.g. a ``list`` or an
  ``ErrorList``):
  
  * It converts any strings it finds to instances of ``ValidationError``
  before adding them to its internal storage.
  
  * It doesn't store the given container but rather copies its content to its
  own internal storage; previously the container itself was added to the
  ``ValidationError`` instance and used as internal storage.
  
  This means that if you access the ``ValidationError`` internal storages, such
  as ``error_list``; ``error_dict``; or the return value of
  ``update_error_dict()`` you may find instances of ``ValidationError`` where you
  would have previously found strings.
  
  Also if you directly assigned the return value of ``update_error_dict()``
  to ``Form._errors`` you may inadvertently add ``list`` instances where
  ``ErrorList`` instances are expected. This is a problem because unlike a
  simple ``list``, an ``ErrorList`` knows how to handle instances of
  ``ValidationError``.
  
  Most use-cases that warranted using these private APIs are now covered by
  the newly introduced :meth:`Form.add_error() <django.forms.Form.add_error()>`
  method::
  
  Old pattern:
  try:
  ...
  except ValidationError as e:
  self._errors = e.update_error_dict(self._errors)
  
  New pattern:
  try:
  ...
  except ValidationError as e:
  self.add_error(None, e)
  
  If you need both Django <= 1.6 and 1.7 compatibility you can't use
  :meth:`Form.add_error() <django.forms.Form.add_error()>` since it
  wasn't available before Django 1.7, but you can use the following
  workaround to convert any ``list`` into ``ErrorList``::
  
  try:
  ...
  except ValidationError as e:
  self._errors = e.update_error_dict(self._errors)
  
  Additional code to ensure ``ErrorDict`` is exclusively
  composed of ``ErrorList`` instances.
  for field, error_list in self._errors.items():
  if not isinstance(error_list, self.error_class):
  self._errors[field] = self.error_class(error_list)
  
  Behavior of ``LocMemCache`` regarding pickle errors
  ---------------------------------------------------
  
  An inconsistency existed in previous versions of Django regarding how pickle
  errors are handled by different cache backends.
  ``django.core.cache.backends.locmem.LocMemCache`` used to fail silently when
  such an error occurs, which is inconsistent with other backends and leads to
  cache-specific errors. This has been fixed in Django 1.7, see
  :ticket:`21200` for more details.
  
  Cache keys are now generated from the request's absolute URL
  ------------------------------------------------------------
  
  Previous versions of Django generated cache keys using a request's path and
  query string but not the scheme or host. If a Django application was serving
  multiple subdomains or domains, cache keys could collide. In Django 1.7, cache
  keys vary by the absolute URL of the request including scheme, host, path, and
  query string. For example, the URL portion of a cache key is now generated from
  ``https://www.example.com/path/to/?key=val`` rather than ``/path/to/?key=val``.
  The cache keys generated by Django 1.7 will be different from the keys
  generated by older versions of Django. After upgrading to Django 1.7, the first
  request to any previously cached URL will be a cache miss.
  
  Passing ``None`` to ``Manager.db_manager()``
  --------------------------------------------
  
  In previous versions of Django, it was possible to use
  ``db_manager(using=None)`` on a model manager instance to obtain a manager
  instance using default routing behavior, overriding any manually specified
  database routing. In Django 1.7, a value of ``None`` passed to db_manager will
  produce a router that *retains* any manually assigned database routing -- the
  manager will *not* be reset. This was necessary to resolve an inconsistency in
  the way routing information cascaded over joins. See :ticket:`13724` for more
  details.
  
  pytz may be required
  --------------------
  
  If your project handles datetimes before 1970 or after 2037 and Django raises
  a :exc:`ValueError` when encountering them, you will have to install pytz_. You
  may be affected by this problem if you use Django's time zone-related date
  formats or :mod:`django.contrib.syndication`.
  
  .. _pytz: https://pypi.org/project/pytz/
  
  ``remove()`` and ``clear()`` methods of related managers
  --------------------------------------------------------
  
  The ``remove()`` and ``clear()`` methods of the related managers created by
  ``ForeignKey``, ``GenericForeignKey``, and ``ManyToManyField`` suffered from a
  number of issues. Some operations ran multiple data modifying queries without
  wrapping them in a transaction, and some operations didn't respect default
  filtering when it was present (i.e. when the default manager on the related
  model implemented a custom ``get_queryset()``).
  
  Fixing the issues introduced some backward incompatible changes:
  
  - The default implementation of ``remove()`` for ``ForeignKey`` related managers
  changed from a series of ``Model.save()`` calls to a single
  ``QuerySet.update()`` call. The change means that ``pre_save`` and
  ``post_save`` signals aren't sent anymore. You can use the ``bulk=False``
  keyword argument to revert to the previous behavior.
  
  - The ``remove()`` and ``clear()`` methods for ``GenericForeignKey`` related
  managers now perform bulk delete. The ``Model.delete()`` method isn't called
  on each instance anymore. You can use the ``bulk=False`` keyword argument to
  revert to the previous behavior.
  
  - The ``remove()`` and ``clear()`` methods for ``ManyToManyField`` related
  managers perform nested queries when filtering is involved, which may or
  may not be an issue depending on your database and your data itself.
  See :ref:`this note <nested-queries-performance>` for more details.
  
  Admin login redirection strategy
  --------------------------------
  
  Historically, the Django admin site passed the request from an unauthorized or
  unauthenticated user directly to the login view, without HTTP redirection. In
  Django 1.7, this behavior changed to conform to a more traditional workflow
  where any unauthorized request to an admin page will be redirected (by HTTP
  status code 302) to the login page, with the ``next`` parameter set to the
  referring path. The user will be redirected there after a successful login.
  
  Note also that the admin login form has been updated to not contain the
  ``this_is_the_login_form`` field (now unused) and the ``ValidationError`` code
  has been set to the more regular ``invalid_login`` key.
  
  ``select_for_update()`` requires a transaction
  ----------------------------------------------
  
  Historically, queries that use
  :meth:`~django.db.models.query.QuerySet.select_for_update()` could be
  executed in autocommit mode, outside of a transaction. Before Django
  1.6, Django's automatic transactions mode allowed this to be used to
  lock records until the next write operation. Django 1.6 introduced
  database-level autocommit; since then, execution in such a context
  voids the effect of ``select_for_update()``. It is, therefore, assumed
  now to be an error and raises an exception.
  
  This change was made because such errors can be caused by including an
  app which expects global transactions (e.g. :setting:`ATOMIC_REQUESTS
  <DATABASE-ATOMIC_REQUESTS>` set to ``True``), or Django's old autocommit
  behavior, in a project which runs without them; and further, such
  errors may manifest as data-corruption bugs. It was also made in
  Django 1.6.3.
  
  This change may cause test failures if you use ``select_for_update()``
  in a test class which is a subclass of
  :class:`~django.test.TransactionTestCase` rather than
  :class:`~django.test.TestCase`.
  
  Contrib middleware removed from default ``MIDDLEWARE_CLASSES``
  --------------------------------------------------------------
  
  The :ref:`app-loading refactor <app-loading-refactor-17-release-note>`
  deprecated using models from apps which are not part of the
  :setting:`INSTALLED_APPS` setting. This exposed an incompatibility between
  the default :setting:`INSTALLED_APPS` and ``MIDDLEWARE_CLASSES`` in the
  global defaults (``django.conf.global_settings``). To bring these settings in
  sync and prevent deprecation warnings when doing things like testing reusable
  apps with minimal settings,
  :class:`~django.contrib.sessions.middleware.SessionMiddleware`,
  :class:`~django.contrib.auth.middleware.AuthenticationMiddleware`, and
  :class:`~django.contrib.messages.middleware.MessageMiddleware` were removed
  from the defaults. These classes will still be included in the default settings
  generated by :djadmin:`startproject`. Most projects will not be affected by
  this change but if you were not previously declaring the
  ``MIDDLEWARE_CLASSES`` in your project settings and relying on the
  global default you should ensure that the new defaults are in line with your
  project's needs. You should also check for any code that accesses
  ``django.conf.global_settings.MIDDLEWARE_CLASSES`` directly.
  
  Miscellaneous
  -------------
  
  * The :meth:`django.core.files.uploadhandler.FileUploadHandler.new_file()`
  method is now passed an additional ``content_type_extra`` parameter. If you
  have a custom :class:`~django.core.files.uploadhandler.FileUploadHandler`
  that implements ``new_file()``, be sure it accepts this new parameter.
  
  * :class:`ModelFormSet<django.forms.models.BaseModelFormSet>`\s no longer
  delete instances when ``save(commit=False)`` is called. See
  :attr:`~django.forms.formsets.BaseFormSet.can_delete` for instructions on how
  to manually delete objects from deleted forms.
  
  * Loading empty fixtures emits a ``RuntimeWarning`` rather than raising
  :exc:`~django.core.management.CommandError`.
  
  * :func:`django.contrib.staticfiles.views.serve` will now raise an
  :exc:`~django.http.Http404` exception instead of
  :exc:`~django.core.exceptions.ImproperlyConfigured` when :setting:`DEBUG`
  is ``False``. This change removes the need to conditionally add the view to
  your root URLconf, which in turn makes it safe to reverse by name. It also
  removes the ability for visitors to generate spurious HTTP 500 errors by
  requesting static files that don't exist or haven't been collected yet.
  
  * The :meth:`django.db.models.Model.__eq__` method is now defined in a
  way where instances of a proxy model and its base model are considered
  equal when primary keys match. Previously only instances of exact same
  class were considered equal on primary key match.
  
  * The :meth:`django.db.models.Model.__eq__` method has changed such that
  two ``Model`` instances without primary key values won't be considered
  equal (unless they are the same instance).
  
  * The :meth:`django.db.models.Model.__hash__` method will now raise ``TypeError``
  when called on an instance without a primary key value. This is done to
  avoid mutable ``__hash__`` values in containers.
  
  * :class:`~django.db.models.AutoField` columns in SQLite databases will now be
  created using the ``AUTOINCREMENT`` option, which guarantees monotonic
  increments. This will cause primary key numbering behavior to change on
  SQLite, becoming consistent with most other SQL databases. This will only
  apply to newly created tables. If you have a database created with an older
  version of Django, you will need to migrate it to take advantage of this
  feature. For example, you could do the following:
  
  ) Use :djadmin:`dumpdata` to save your data.
  ) Rename the existing database file (keep it as a backup).
  ) Run :djadmin:`migrate` to create the updated schema.
  ) Use :djadmin:`loaddata` to import the fixtures you exported in (1).
  
  * ``django.contrib.auth.models.AbstractUser`` no longer defines a
  :meth:`~django.db.models.Model.get_absolute_url()` method. The old definition
  returned  ``"/users/%s/" % urlquote(self.username)`` which was arbitrary
  since applications may or may not define such a url in ``urlpatterns``.
  Define a ``get_absolute_url()`` method on your own custom user object or use
  :setting:`ABSOLUTE_URL_OVERRIDES` if you want a URL for your user.
  
  * The static asset-serving functionality of the
  :class:`django.test.LiveServerTestCase` class has been simplified: Now it's
  only able to serve content already present in :setting:`STATIC_ROOT` when
  tests are run. The ability to transparently serve all the static assets
  (similarly to what one gets with :setting:`DEBUG = True <DEBUG>` at
  development-time) has been moved to a new class that lives in the
  ``staticfiles`` application (the one actually in charge of such feature):
  :class:`django.contrib.staticfiles.testing.StaticLiveServerTestCase`. In other
  words, ``LiveServerTestCase`` itself is less powerful but at the same time
  has less magic.
  
  Rationale behind this is removal of dependency of non-contrib code on
  contrib applications.
  
  * The old cache URI syntax (e.g. ``"locmem://"``) is no longer supported. It
  still worked, even though it was not documented or officially supported. If
  you're still using it, please update to the current :setting:`CACHES` syntax.
  
  * The default ordering of ``Form`` fields in case of inheritance has changed to
  follow normal Python MRO. Fields are now discovered by iterating through the
  MRO in reverse with the topmost class coming last. This only affects you if
  you relied on the default field ordering while having fields defined on both
  the current class *and* on a parent ``Form``.
  
  * The ``required`` argument of
  :class:`~django.forms.SelectDateWidget` has been removed.
  This widget now respects the form field's ``is_required`` attribute like
  other widgets.
  
  * ``Widget.is_hidden`` is now a read-only property, getting its value by
  introspecting the presence of ``input_type == 'hidden'``.
  
  * :meth:`~django.db.models.query.QuerySet.select_related` now chains in the
  same way as other similar calls like ``prefetch_related``. That is,
  ``select_related('foo', 'bar')`` is equivalent to
  ``select_related('foo').select_related('bar')``. Previously the latter would
  have been equivalent to ``select_related('bar')``.
  
  * GeoDjango dropped support for GEOS < 3.1.
  
  * The ``init_connection_state`` method of database backends now executes in
  autocommit mode (unless you set :setting:`AUTOCOMMIT <DATABASE-AUTOCOMMIT>`
  to ``False``). If you maintain a custom database backend, you should check
  that method.
  
  * The ``django.db.backends.BaseDatabaseFeatures.allows_primary_key_0``
  attribute has been renamed to ``allows_auto_pk_0`` to better describe it.
  It's ``True`` for all database backends included with Django except MySQL
  which does allow primary keys with value 0. It only forbids *autoincrement*
  primary keys with value 0.
  
  * Shadowing model fields defined in a parent model has been forbidden as this
  creates ambiguity in the expected model behavior. In addition, clashing
  fields in the model inheritance hierarchy result in a system check error.
  For example, if you use multi-inheritance, you need to define custom primary
  key fields on parent models, otherwise the default ``id`` fields will clash.
  See :ref:`model-multiple-inheritance-topic` for details.
  
  * ``django.utils.translation.parse_accept_lang_header()`` now returns
  lowercase locales, instead of the case as it was provided. As locales should
  be treated case-insensitive this allows us to speed up locale detection.
  
  * ``django.utils.translation.get_language_from_path()`` and
  ``django.utils.translation.trans_real.get_supported_language_variant()``
  now no longer have a ``supported`` argument.
  
  * The ``shortcut`` view in ``django.contrib.contenttypes.views`` now supports
  protocol-relative URLs (e.g. ``//example.com``).
  
  * :class:`~django.contrib.contenttypes.fields.GenericRelation` now supports an
  optional ``related_query_name`` argument. Setting ``related_query_name`` adds
  a relation from the related object back to the content type for filtering,
  ordering and other query operations.
  
  * When running tests on PostgreSQL, the :setting:`USER` will need read access
  to the built-in ``postgres`` database. This is in lieu of the previous
  behavior of connecting to the actual non-test database.
  
  * As part of the :doc:`System check framework </ref/checks>`, :ref:`fields,
  models, and model managers <field-checking>` all implement a ``check()``
  method that is registered with the check framework. If you have an existing
  method called ``check()`` on one of these objects, you will need to rename it.
  
  * As noted above in the "Cache" section of "Minor Features", defining the
  :setting:`TIMEOUT <CACHES-TIMEOUT>` argument of the
  :setting:`CACHES` setting as ``None`` will set the cache keys as
  "non-expiring". Previously, with the memcache backend, a
  :setting:`TIMEOUT <CACHES-TIMEOUT>` of ``0`` would set non-expiring keys,
  but this was inconsistent with the set-and-expire (i.e. no caching) behavior
  of ``set("key", "value", timeout=0)``. If you want non-expiring keys,
  please update your settings to use ``None`` instead of ``0`` as the latter
  now designates set-and-expire in the settings as well.
  
  * The ``sql*`` management commands now respect the ``allow_migrate()`` method
  of :setting:`DATABASE_ROUTERS`. If you have models synced to non-default
  databases, use the ``--database`` flag to get SQL for those models
  (previously they would always be included in the output).
  
  * Decoding the query string from URLs now falls back to the ISO-8859-1 encoding
  when the input is not valid UTF-8.
  
  * With the addition of the
  ``django.contrib.auth.middleware.SessionAuthenticationMiddleware`` to
  the default project template (pre-1.7.2 only), a database must be created
  before accessing a page using :djadmin:`runserver`.
  
  * The addition of the ``schemes`` argument to ``URLValidator`` will appear
  as a backwards-incompatible change if you were previously using a custom
  regular expression to validate schemes. Any scheme not listed in ``schemes``
  will fail validation, even if the regular expression matches the given URL.
  
  .. _deprecated-features-1.7:
  
  Features deprecated in 1.7
  ==========================
  
  ``django.core.cache.get_cache``
  -------------------------------
  
  ``django.core.cache.get_cache`` has been supplanted by
  :data:`django.core.cache.caches`.
  
  ``django.utils.dictconfig``/``django.utils.importlib``
  ------------------------------------------------------
  
  ``django.utils.dictconfig`` and ``django.utils.importlib`` were copies of
  respectively :mod:`logging.config` and :mod:`importlib` provided for Python
  versions prior to 2.7. They have been deprecated.
  
  ``django.utils.module_loading.import_by_path``
  ----------------------------------------------
  
  The current ``django.utils.module_loading.import_by_path`` function
  catches ``AttributeError``, ``ImportError``, and ``ValueError`` exceptions,
  and re-raises :exc:`~django.core.exceptions.ImproperlyConfigured`. Such
  exception masking makes it needlessly hard to diagnose circular import
  problems, because it makes it look like the problem comes from inside Django.
  It has been deprecated in favor of
  :meth:`~django.utils.module_loading.import_string`.
  
  ``django.utils.tzinfo``
  -----------------------
  
  ``django.utils.tzinfo`` provided two :class:`~datetime.tzinfo` subclasses,
  ``LocalTimezone`` and ``FixedOffset``. They've been deprecated in favor of
  more correct alternatives provided by :mod:`django.utils.timezone`,
  :func:`django.utils.timezone.get_default_timezone` and
  :func:`django.utils.timezone.get_fixed_timezone`.
  
  ``django.utils.unittest``
  -------------------------
  
  ``django.utils.unittest`` provided uniform access to the ``unittest2`` library
  on all Python versions. Since ``unittest2`` became the standard library's
  :mod:`unittest` module in Python 2.7, and Django 1.7 drops support for older
  Python versions, this module isn't useful anymore. It has been deprecated. Use
  :mod:`unittest` instead.
  
  ``django.utils.datastructures.SortedDict``
  ------------------------------------------
  
  As :class:`~collections.OrderedDict` was added to the standard library in
  Python 2.7, ``SortedDict`` is no longer needed and has been deprecated.
  
  The two additional, deprecated methods provided by ``SortedDict`` (``insert()``
  and ``value_for_index()``) have been removed. If you relied on these methods to
  alter structures like form fields, you should now treat these ``OrderedDict``\s
  as immutable objects and override them to change their content.
  
  For example, you might want to override ``MyFormClass.base_fields`` (although
  this attribute isn't considered a public API) to change the ordering of fields
  for all ``MyFormClass`` instances; or similarly, you could override
  ``self.fields`` from inside ``MyFormClass.__init__()``, to change the fields
  for a particular form instance. For example (from Django itself)::
  
  PasswordChangeForm.base_fields = OrderedDict(
  (k, PasswordChangeForm.base_fields[k])
  for k in ['old_password', 'new_password1', 'new_password2']
  )
  
  Custom SQL location for models package
  --------------------------------------
  
  Previously, if models were organized in a package (``myapp/models/``) rather
  than simply ``myapp/models.py``, Django would look for initial SQL data in
  ``myapp/models/sql/``. This bug has been fixed so that Django
  will search ``myapp/sql/`` as documented. After this issue was fixed, migrations
  were added which deprecates initial SQL data. Thus, while this change still
  exists, the deprecation is irrelevant as the entire feature will be removed in
  Django 1.9.
  
  Reorganization of ``django.contrib.sites``
  ------------------------------------------
  
  ``django.contrib.sites`` provides reduced functionality when it isn't in
  :setting:`INSTALLED_APPS`. The app-loading refactor adds some constraints in
  that situation. As a consequence, two objects were moved, and the old
  locations are deprecated:
  
  * :class:`~django.contrib.sites.requests.RequestSite` now lives in
  ``django.contrib.sites.requests``.
  * :func:`~django.contrib.sites.shortcuts.get_current_site` now lives in
  ``django.contrib.sites.shortcuts``.
  
  ``declared_fieldsets`` attribute on ``ModelAdmin``
  --------------------------------------------------
  
  ``ModelAdmin.declared_fieldsets`` has been deprecated. Despite being a private
  API, it will go through a regular deprecation path. This attribute was mostly
  used by methods that bypassed ``ModelAdmin.get_fieldsets()`` but this was
  considered a bug and has been addressed.
  
  Reorganization of ``django.contrib.contenttypes``
  -------------------------------------------------
  
  Since ``django.contrib.contenttypes.generic`` defined both admin and model
  related objects, an import of this module could trigger unexpected side effects.
  As a consequence, its contents were split into :mod:`~django.contrib.contenttypes`
  submodules and the ``django.contrib.contenttypes.generic`` module is deprecated:
  
  * :class:`~django.contrib.contenttypes.fields.GenericForeignKey` and
  :class:`~django.contrib.contenttypes.fields.GenericRelation` now live in
  :mod:`~django.contrib.contenttypes.fields`.
  * :class:`~django.contrib.contenttypes.forms.BaseGenericInlineFormSet` and
  :func:`~django.contrib.contenttypes.forms.generic_inlineformset_factory` now
  live in :mod:`~django.contrib.contenttypes.forms`.
  * :class:`~django.contrib.contenttypes.admin.GenericInlineModelAdmin`,
  :class:`~django.contrib.contenttypes.admin.GenericStackedInline` and
  :class:`~django.contrib.contenttypes.admin.GenericTabularInline` now live in
  :mod:`~django.contrib.contenttypes.admin`.
  
  ``syncdb``
  ----------
  
  The ``syncdb`` command has been deprecated in favor of the new :djadmin:`migrate`
  command. ``migrate`` takes the same arguments as ``syncdb`` used to plus a few
  more, so it's safe to just change the name you're calling and nothing else.
  
  ``util`` modules renamed to ``utils``
  -------------------------------------
  
  The following instances of ``util.py`` in the Django codebase have been renamed
  to ``utils.py`` in an effort to unify all util and utils references:
  
  * ``django.contrib.admin.util``
  * ``django.contrib.gis.db.backends.util``
  * ``django.db.backends.util``
  * ``django.forms.util``
  
  ``get_formsets`` method on ``ModelAdmin``
  -----------------------------------------
  
  ``ModelAdmin.get_formsets`` has been deprecated in favor of the new
  :meth:`~django.contrib.admin.ModelAdmin.get_formsets_with_inlines`, in order to
  better handle the case of selectively showing inlines on a ``ModelAdmin``.
  
  ``IPAddressField``
  ------------------
  
  The ``django.db.models.IPAddressField`` and ``django.forms.IPAddressField``
  fields have been deprecated in favor of
  :class:`django.db.models.GenericIPAddressField` and
  :class:`django.forms.GenericIPAddressField`.
  
  ``BaseMemcachedCache._get_memcache_timeout`` method
  ---------------------------------------------------
  
  The ``BaseMemcachedCache._get_memcache_timeout()`` method has been renamed to
  ``get_backend_timeout()``. Despite being a private API, it will go through the
  normal deprecation.
  
  Natural key serialization options
  ---------------------------------
  
  The ``--natural`` and ``-n`` options for :djadmin:`dumpdata` have been
  deprecated. Use :option:`dumpdata --natural-foreign` instead.
  
  Similarly, the ``use_natural_keys`` argument for ``serializers.serialize()``
  has been deprecated. Use ``use_natural_foreign_keys`` instead.
  
  Merging of ``POST`` and ``GET`` arguments into ``WSGIRequest.REQUEST``
  ----------------------------------------------------------------------
  
  It was already strongly suggested that you use ``GET`` and ``POST`` instead of
  ``REQUEST``, because the former are more explicit. The property ``REQUEST`` is
  deprecated and will be removed in Django 1.9.
  
  ``django.utils.datastructures.MergeDict`` class
  -----------------------------------------------
  
  ``MergeDict`` exists primarily to support merging ``POST`` and ``GET``
  arguments into a ``REQUEST`` property on ``WSGIRequest``. To merge
  dictionaries, use ``dict.update()`` instead. The class ``MergeDict`` is
  deprecated and will be removed in Django 1.9.
  
  Language codes ``zh-cn``, ``zh-tw`` and ``fy-nl``
  -------------------------------------------------
  
  The currently used language codes for Simplified Chinese ``zh-cn``,
  Traditional Chinese ``zh-tw`` and (Western) Frysian ``fy-nl`` are deprecated
  and should be replaced by the language codes ``zh-hans``, ``zh-hant`` and
  ``fy`` respectively. If you use these language codes, you should rename the
  locale directories and update your settings to reflect these changes. The
  deprecated language codes will be removed in Django 1.9.
  
  ``django.utils.functional.memoize`` function
  --------------------------------------------
  
  The function ``memoize`` is deprecated and should be replaced by the
  ``functools.lru_cache`` decorator (available from Python 3.2 onwards).
  
  Django ships a backport of this decorator for older Python versions and it's
  available at ``django.utils.lru_cache.lru_cache``. The deprecated function will
  be removed in Django 1.9.
  
  Geo Sitemaps
  ------------
  
  Google has retired support for the Geo Sitemaps format. Hence Django support
  for Geo Sitemaps is deprecated and will be removed in Django 1.8.
  
  Passing callable arguments to queryset methods
  ----------------------------------------------
  
  Callable arguments for querysets were an undocumented feature that was
  unreliable. It's been deprecated and will be removed in Django 1.9.
  
  Callable arguments were evaluated when a queryset was constructed rather than
  when it was evaluated, thus this feature didn't offer any benefit compared to
  evaluating arguments before passing them to queryset and created confusion that
  the arguments may have been evaluated at query time.
  
  ``ADMIN_FOR`` setting
  ---------------------
  
  The ``ADMIN_FOR`` feature, part of the admindocs, has been removed. You can
  remove the setting from your configuration at your convenience.
  
  ``SplitDateTimeWidget`` with ``DateTimeField``
  ----------------------------------------------
  
  ``SplitDateTimeWidget`` support in :class:`~django.forms.DateTimeField` is
  deprecated, use ``SplitDateTimeWidget`` with
  :class:`~django.forms.SplitDateTimeField` instead.
  
  ``validate``
  ------------
  
  The ``validate`` management command is deprecated in favor of the
  :djadmin:`check` command.
  
  ``django.core.management.BaseCommand``
  --------------------------------------
  
  ``requires_model_validation`` is deprecated in favor of a new
  ``requires_system_checks`` flag. If the latter flag is missing, then the
  value of the former flag is used. Defining both ``requires_system_checks`` and
  ``requires_model_validation`` results in an error.
  
  The ``check()`` method has replaced the old ``validate()`` method.
  
  ``ModelAdmin`` validators
  -------------------------
  
  The ``ModelAdmin.validator_class`` and ``default_validator_class`` attributes
  are deprecated in favor of the new ``checks_class`` attribute.
  
  The ``ModelAdmin.validate()`` method is deprecated in favor of
  ``ModelAdmin.check()``.
  
  The ``django.contrib.admin.validation`` module is deprecated.
  
  ``django.db.backends.DatabaseValidation.validate_field``
  --------------------------------------------------------
  
  This method is deprecated in favor of a new ``check_field`` method.
  The functionality required by ``check_field()`` is the same as that provided
  by ``validate_field()``, but the output format is different. Third-party database
  backends needing this functionality should provide an implementation of
  ``check_field()``.
  
  Loading ``ssi`` and ``url`` template tags from ``future`` library
  -----------------------------------------------------------------
  
  Django 1.3 introduced ``{% load ssi from future %}`` and
  ``{% load url from future %}`` syntax for forward compatibility of the
  ``ssi`` and :ttag:`url` template tags. This syntax is now deprecated and
  will be removed in Django 1.9. You can simply remove the
  ``{% load ... from future %}`` tags.
  
  ``django.utils.text.javascript_quote``
  --------------------------------------
  
  ``javascript_quote()`` was an undocumented function present in ``django.utils.text``.
  It was used internally in the ``javascript_catalog()`` view
  whose implementation was changed to make use of ``json.dumps()`` instead.
  If you were relying on this function to provide safe output from untrusted
  strings, you should use ``django.utils.html.escapejs`` or the
  :tfilter:`escapejs` template filter.
  If all you need is to generate valid JavaScript strings, you can simply use
  ``json.dumps()``.
  
  ``fix_ampersands`` utils method and template filter
  ---------------------------------------------------
  
  The ``django.utils.html.fix_ampersands`` method and the ``fix_ampersands``
  template filter are deprecated, as the escaping of ampersands is already taken care
  of by Django's standard HTML escaping features. Combining this with ``fix_ampersands``
  would either result in double escaping, or, if the output is assumed to be safe,
  a risk of introducing XSS vulnerabilities. Along with ``fix_ampersands``,
  ``django.utils.html.clean_html`` is deprecated, an undocumented function that calls
  ``fix_ampersands``.
  As this is an accelerated deprecation, ``fix_ampersands`` and ``clean_html``
  will be removed in Django 1.8.
  
  Reorganization of database test settings
  ----------------------------------------
  
  All database settings with a ``TEST_`` prefix have been deprecated in favor of
  entries in a :setting:`TEST <DATABASE-TEST>` dictionary in the database
  settings. The old settings will be supported until Django 1.9. For backwards
  compatibility with older versions of Django, you can define both versions of
  the settings as long as they match.
  
  FastCGI support
  ---------------
  
  FastCGI support via the ``runfcgi`` management command will be removed in
  Django 1.9. Please deploy your project using WSGI.
  
  Moved objects in ``contrib.sites``
  ----------------------------------
  
  Following the app-loading refactor, two objects in
  ``django.contrib.sites.models`` needed to be moved because they must be
  available without importing ``django.contrib.sites.models`` when
  ``django.contrib.sites`` isn't installed. Import ``RequestSite`` from
  ``django.contrib.sites.requests`` and ``get_current_site()`` from
  ``django.contrib.sites.shortcuts``. The old import locations will work until
  Django 1.9.
  
  ``django.forms.forms.get_declared_fields()``
  --------------------------------------------
  
  Django no longer uses this functional internally. Even though it's a private
  API, it'll go through the normal deprecation cycle.
  
  Private Query Lookup APIs
  -------------------------
  
  Private APIs ``django.db.models.sql.where.WhereNode.make_atom()`` and
  ``django.db.models.sql.where.Constraint`` are deprecated in favor of the new
  :doc:`custom lookups API </ref/models/lookups>`.
  
  .. _removed-features-1.7:
  
  Features removed in 1.7
  =======================
  
  These features have reached the end of their deprecation cycle and are removed
  in Django 1.7. See :ref:`deprecated-features-1.5` for details, including how to
  remove usage of these features.
  
  * ``django.utils.simplejson`` is removed.
  
  * ``django.utils.itercompat.product`` is removed.
  
  * INSTALLED_APPS and TEMPLATE_DIRS are no longer corrected from a plain
  string into a tuple.
  
  * :class:`~django.http.HttpResponse`,
  :class:`~django.template.response.SimpleTemplateResponse`,
  :class:`~django.template.response.TemplateResponse`,
  ``render_to_response()``, :func:`~django.contrib.sitemaps.views.index`, and
  :func:`~django.contrib.sitemaps.views.sitemap` no longer take a ``mimetype``
  argument
  
  * :class:`~django.http.HttpResponse` immediately consumes its content if it's
  an iterator.
  
  * The ``AUTH_PROFILE_MODULE`` setting, and the ``get_profile()`` method on
  the User model are removed.
  
  * The ``cleanup`` management command is removed.
  
  * The ``daily_cleanup.py`` script is removed.
  
  * :meth:`~django.db.models.query.QuerySet.select_related` no longer has a
  ``depth`` keyword argument.
  
  * The ``get_warnings_state()``/``restore_warnings_state()``
  functions from :mod:`django.test.utils` and the ``save_warnings_state()``/
  ``restore_warnings_state()``
  :ref:`django.test.*TestCase <django-testcase-subclasses>` are removed.
  
  * The ``check_for_test_cookie`` method in
  :class:`~django.contrib.auth.forms.AuthenticationForm` is removed.
  
  * The version of ``django.contrib.auth.views.password_reset_confirm()`` that
  supports base36 encoded user IDs
  (``django.contrib.auth.views.password_reset_confirm_uidb36``) is removed.
  
  * The ``django.utils.encoding.StrAndUnicode`` mix-in is removed.
  
  
  ===========================

1.6.11 not secure

===========================
  
  *March 18, 2015*
  
  Django 1.6.11 fixes two security issues in 1.6.10.
  
  Denial-of-service possibility with ``strip_tags()``
  ===================================================
  
  Last year :func:`~django.utils.html.strip_tags`  was changed to work
  iteratively. The problem is that the size of the input it's processing can
  increase on each iteration which results in an infinite loop in
  ``strip_tags()``. This issue only affects versions of Python that haven't
  received  `a bugfix in HTMLParser <https://bugs.python.org/issue20288>`_; namely
  Python < 2.7.7 and 3.3.5. Some operating system vendors have also backported
  the fix for the Python bug into their packages of earlier versions.
  
  To remedy this issue, ``strip_tags()`` will now return the original input if
  it detects the length of the string it's processing increases. Remember that
  absolutely NO guarantee is provided about the results of ``strip_tags()`` being
  HTML safe. So NEVER mark safe the result of a ``strip_tags()`` call without
  escaping it first, for example with :func:`~django.utils.html.escape`.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) accepted URLs with
  leading control characters and so considered URLs like ``\x08javascript:...``
  safe. This issue doesn't affect Django currently, since we only put this URL
  into the ``Location`` response header and browsers seem to ignore JavaScript
  there. Browsers we tested also treat URLs prefixed with control characters such
  as ``%08//example.com`` as relative paths so redirection to an unsafe target
  isn't a problem either.
  
  However, if a developer relies on ``is_safe_url()`` to
  provide safe redirect targets and puts such a URL into a link, they could
  suffer from an XSS attack as some browsers such as Google Chrome ignore control
  characters at the start of a URL in an anchor ``href``.
  
  
  ===========================

1.6.10 not secure

===========================
  
  *January 13, 2015*
  
  Django 1.6.10 fixes several security issues in 1.6.9.
  
  WSGI header spoofing via underscore/dash conflation
  ===================================================
  
  When HTTP headers are placed into the WSGI environ, they are normalized by
  converting to uppercase, converting all dashes to underscores, and prepending
  ``HTTP_``. For instance, a header ``X-Auth-User`` would become
  ``HTTP_X_AUTH_USER`` in the WSGI environ (and thus also in Django's
  ``request.META`` dictionary).
  
  Unfortunately, this means that the WSGI environ cannot distinguish between
  headers containing dashes and headers containing underscores: ``X-Auth-User``
  and ``X-Auth_User`` both become ``HTTP_X_AUTH_USER``. This means that if a
  header is used in a security-sensitive way (for instance, passing
  authentication information along from a front-end proxy), even if the proxy
  carefully strips any incoming value for ``X-Auth-User``, an attacker may be
  able to provide an ``X-Auth_User`` header (with underscore) and bypass this
  protection.
  
  In order to prevent such attacks, both Nginx and Apache 2.4+ strip all headers
  containing underscores from incoming requests by default. Django's built-in
  development server now does the same. Django's development server is not
  recommended for production use, but matching the behavior of common production
  servers reduces the surface area for behavior changes during deployment.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) didn't strip leading
  whitespace on the tested URL and as such considered URLs like
  ``\njavascript:...`` safe. If a developer relied on ``is_safe_url()`` to
  provide safe redirect targets and put such a URL into a link, they could suffer
  from a XSS attack. This bug doesn't affect Django currently, since we only put
  this URL into the ``Location`` response header and browsers seem to ignore
  JavaScript there.
  
  Denial-of-service attack against ``django.views.static.serve``
  ==============================================================
  
  In older versions of Django, the :func:`django.views.static.serve` view read
  the files it served one line at a time. Therefore, a big file with no newlines
  would result in memory usage equal to the size of that file. An attacker could
  exploit this and launch a denial-of-service attack by simultaneously requesting
  many large files. This view now reads the file in chunks to prevent large
  memory usage.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid. Now
  may be a good time to audit your project and serve your files in production
  using a real front-end web server if you are not doing so.
  
  Database denial-of-service with ``ModelMultipleChoiceField``
  ============================================================
  
  Given a form that uses ``ModelMultipleChoiceField`` and
  ``show_hidden_initial=True`` (not a documented API), it was possible for a user
  to cause an unreasonable number of SQL queries by submitting duplicate values
  for the field's data. The validation logic in ``ModelMultipleChoiceField`` now
  deduplicates submitted values to address this issue.
  
  
  ==========================

1.6.9 not secure

==========================
  
  *January 2, 2015*
  
  Django 1.6.9 fixes a regression in the 1.6.6 security release.
  
  Additionally, Django's vendored version of six, ``django.utils.six``, has
  been upgraded to the latest release (1.9.0).
  
  Bugfixes
  ========
  
  * Fixed a regression with dynamically generated inlines and allowed field
  references in the admin (:ticket:`23754`).
  
  
  ==========================

1.6.8 not secure

==========================
  
  *October 22, 2014*
  
  Django 1.6.8 fixes a couple regressions in the 1.6.6 security release.
  
  Bugfixes
  ========
  
  * Allowed related many-to-many fields to be referenced in the admin
  (:ticket:`23604`).
  
  * Allowed inline and hidden references to admin fields (:ticket:`23431`).
  
  
  ==========================

1.6.7 not secure

==========================
  
  *September 2, 2014*
  
  Django 1.6.7 fixes several bugs in 1.6.6, including a regression related to
  a security fix in that release.
  
  Bugfixes
  ========
  
  * Allowed inherited and m2m fields to be referenced in the admin
  (:ticket:`23329`).
  * Fixed a crash when using ``QuerySet.defer()`` with ``select_related()``
  (:ticket:`23370`).
  
  
  ==========================

1.6.6 not secure

==========================
  
  *August 20, 2014*
  
  Django 1.6.6 fixes several security issues and bugs in 1.6.5.
  
  ``reverse()`` could generate URLs pointing to other hosts
  =========================================================
  
  In certain situations, URL reversing could generate scheme-relative URLs  (URLs
  starting with two slashes), which could unexpectedly redirect a user  to a
  different host. An attacker could exploit this, for example, by redirecting
  users to a phishing site designed to ask for user's passwords.
  
  To remedy this, URL reversing now ensures that no URL starts with two slashes
  (//), replacing the second slash with its URL encoded counterpart (%2F). This
  approach ensures that semantics stay the same, while making the URL relative to
  the domain and not to the scheme.
  
  File upload denial-of-service
  =============================
  
  Before this release, Django's file upload handing in its default configuration
  may degrade to producing a huge number of ``os.stat()`` system calls when a
  duplicate filename is uploaded. Since ``stat()`` may invoke IO, this may produce
  a huge data-dependent slowdown that slowly worsens over time. The net result is
  that given enough time, a user with the ability to upload files can cause poor
  performance in the upload handler, eventually causing it to become very slow
  simply by uploading 0-byte files. At this point, even a slow network connection
  and few HTTP requests would be all that is necessary to make a site unavailable.
  
  We've remedied the issue by changing the algorithm for generating file names
  if a file with the uploaded name already exists.
  :meth:`Storage.get_available_name()
  <django.core.files.storage.Storage.get_available_name>` now appends an
  underscore plus a random 7 character alphanumeric string (e.g. ``"_x3a1gho"``),
  rather than iterating through an underscore followed by a number (e.g. ``"_1"``,
  ``"_2"``, etc.).
  
  ``RemoteUserMiddleware`` session hijacking
  ==========================================
  
  When using the :class:`~django.contrib.auth.middleware.RemoteUserMiddleware`
  and the ``RemoteUserBackend``, a change to the ``REMOTE_USER`` header between
  requests without an intervening logout could result in the prior user's session
  being co-opted by the subsequent user. The middleware now logs the user out on
  a failed login attempt.
  
  Data leakage via query string manipulation in ``contrib.admin``
  ===============================================================
  
  In older versions of Django it was possible to reveal any field's data by
  modifying the "popup" and "to_field" parameters of the query string on an admin
  change form page. For example, requesting a URL like
  ``/admin/auth/user/?_popup=1&t=password`` and viewing the page's HTML allowed
  viewing the password hash of each user. While the admin requires users to have
  permissions to view the change form pages in the first place, this could leak
  data if you rely on users having access to view only certain fields on a model.
  
  To address the issue, an exception will now be raised if a ``to_field`` value
  that isn't a related field to a model that has been registered with the admin
  is specified.
  
  Bugfixes
  ========
  
  * Corrected email and URL validation to reject a trailing dash
  (:ticket:`22579`).
  
  * Prevented indexes on PostgreSQL virtual fields (:ticket:`22514`).
  
  * Prevented edge case where values of FK fields could be initialized with a
  wrong value when an inline model formset is created for a relationship
  defined to point to a field other than the PK (:ticket:`13794`).
  
  * Restored ``pre_delete``  signals for ``GenericRelation`` cascade deletion
  (:ticket:`22998`).
  
  * Fixed transaction handling when specifying non-default database in
  ``createcachetable`` and ``flush`` (:ticket:`23089`).
  
  * Fixed the "ORA-01843: not a valid month" errors when using Unicode
  with older versions of Oracle server (:ticket:`20292`).
  
  * Restored bug fix for sending Unicode email with Python 2.6.5 and below
  (:ticket:`19107`).
  
  * Prevented ``UnicodeDecodeError`` in ``runserver`` with non-UTF-8 and
  non-English locale (:ticket:`23265`).
  
  * Fixed JavaScript errors while editing multi-geometry objects in the OpenLayers
  widget (:ticket:`23137`, :ticket:`23293`).
  
  * Prevented a crash on Python 3 with query strings containing unencoded
  non-ASCII characters (:ticket:`22996`).
  
  
  ==========================

1.6.5 not secure

==========================
  
  *May 14, 2014*
  
  Django 1.6.5 fixes two security issues and several bugs in 1.6.4.
  
  Issue: Caches may incorrectly be allowed to store and serve private data
  ========================================================================
  
  In certain situations, Django may allow caches to store private data
  related to a particular session and then serve that data to requests
  with a different session, or no session at all. This can lead to
  information disclosure and can be a vector for cache poisoning.
  
  When using Django sessions, Django will set a ``Vary: Cookie`` header to
  ensure caches do not serve cached data to requests from other sessions.
  However, older versions of Internet Explorer (most likely only Internet
  Explorer 6, and Internet Explorer 7 if run on Windows XP or Windows Server
  2003) are unable to handle the ``Vary`` header in combination with many content
  types. Therefore, Django would remove the header if the request was made by
  Internet Explorer.
  
  To remedy this, the special behavior for these older Internet Explorer versions
  has been removed, and the ``Vary`` header is no longer stripped from the response.
  In addition, modifications to the ``Cache-Control`` header for all Internet Explorer
  requests with a ``Content-Disposition`` header have also been removed as they
  were found to have similar issues.
  
  Issue: Malformed redirect URLs from user input not correctly validated
  ======================================================================
  
  The validation for redirects did not correctly validate some malformed URLs,
  which are accepted by some browsers. This allows a user to be redirected to
  an unsafe URL unexpectedly.
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()``, ``django.contrib.comments``, and
  :doc:`i18n </topics/i18n/index>`) to redirect the user to an "on success" URL.
  The security checks for these redirects (namely
  ``django.utils.http.is_safe_url()``) did not correctly validate some malformed
  URLs, such as ``http:\\\\\\djangoproject.com``, which are accepted by some
  browsers with more liberal URL parsing.
  
  To remedy this, the validation in ``is_safe_url()`` has been tightened to be able
  to handle and correctly validate these malformed URLs.
  
  Bugfixes
  ========
  
  * Made the ``year_lookup_bounds_for_datetime_field`` Oracle backend method
  Python 3 compatible (:ticket:`22551`).
  
  * Fixed ``pgettext_lazy`` crash when receiving bytestring content on Python 2
  (:ticket:`22565`).
  
  * Fixed the SQL generated when filtering by a negated ``Q`` object that contains
  a ``F`` object. (:ticket:`22429`).
  
  * Avoided overwriting data fetched by ``select_related()`` in certain cases
  which could cause minor performance regressions
  (:ticket:`22508`).
  
  
  ==========================

1.6.4 not secure

==========================
  
  *April 28, 2014*
  
  Django 1.6.4 fixes several bugs in 1.6.3.
  
  Bugfixes
  ========
  
  * Added backwards compatibility support for the :mod:`django.contrib.messages`
  cookie format of Django 1.4 and earlier to facilitate upgrading to 1.6 from
  1.4 (:ticket:`22426`).
  
  * Restored the ability to ``reverse()`` views created using
  :func:`functools.partial()` (:ticket:`22486`).
  
  * Fixed the ``object_id`` of the ``LogEntry`` that's created after a user
  password change in the admin (:ticket:`22515`).
  
  
  ==========================

1.6.3 not secure

==========================
  
  *April 21, 2014*
  
  Django 1.6.3 fixes several bugs in 1.6.2, including three security issues,
  and makes one backwards-incompatible change:
  
  Unexpected code execution using ``reverse()``
  =============================================
  
  Django's URL handling is based on a mapping of regex patterns
  (representing the URLs) to callable views, and Django's own processing
  consists of matching a requested URL against those patterns to
  determine the appropriate view to invoke.
  
  Django also provides a convenience function -- ``reverse()`` -- which performs
  this process in the opposite direction. The ``reverse()`` function takes
  information about a view and returns a URL which would invoke that view. Use
  of ``reverse()`` is encouraged for application developers, as the output of
  ``reverse()`` is always based on the current URL patterns, meaning developers
  do not need to change other code when making changes to URLs.
  
  One argument signature for ``reverse()`` is to pass a dotted Python
  path to the desired view. In this situation, Django will import the
  module indicated by that dotted path as part of generating the
  resulting URL. If such a module has import-time side effects, those
  side effects will occur.
  
  Thus it is possible for an attacker to cause unexpected code
  execution, given the following conditions:
  
  1. One or more views are present which construct a URL based on user
  input (commonly, a "next" parameter in a querystring indicating
  where to redirect upon successful completion of an action).
  
  2. One or more modules are known to an attacker to exist on the
  server's Python import path, which perform code execution with side
  effects on importing.
  
  To remedy this, ``reverse()`` will now only accept and import dotted
  paths based on the view-containing modules listed in the project's :doc:`URL
  pattern configuration </topics/http/urls>`, so as to ensure that only modules
  the developer intended to be imported in this fashion can or will be imported.
  
  Caching of anonymous pages could reveal CSRF token
  ==================================================
  
  Django includes both a :doc:`caching framework </topics/cache>` and a system
  for :doc:`preventing cross-site request forgery (CSRF) attacks
  </ref/csrf/>`. The CSRF-protection system is based on a random nonce
  sent to the client in a cookie which must be sent by the client on future
  requests and, in forms, a hidden value which must be submitted back with the
  form.
  
  The caching framework includes an option to cache responses to
  anonymous (i.e., unauthenticated) clients.
  
  When the first anonymous request to a given page is by a client which
  did not have a CSRF cookie, the cache framework will also cache the
  CSRF cookie and serve the same nonce to other anonymous clients who
  do not have a CSRF cookie. This can allow an attacker to obtain a
  valid CSRF cookie value and perform attacks which bypass the check for
  the cookie.
  
  To remedy this, the caching framework will no longer cache such
  responses. The heuristic for this will be:
  
  1. If the incoming request did not submit any cookies, and
  
  2. If the response did send one or more cookies, and
  
  3. If the ``Vary: Cookie`` header is set on the response, then the
  response will not be cached.
  
  MySQL typecasting
  =================
  
  The MySQL database is known to "typecast" on certain queries; for
  example, when querying a table which contains string values, but using
  a query which filters based on an integer value, MySQL will first
  silently coerce the strings to integers and return a result based on that.
  
  If a query is performed without first converting values to the
  appropriate type, this can produce unexpected results, similar to what
  would occur if the query itself had been manipulated.
  
  Django's model field classes are aware of their own types and most
  such classes perform explicit conversion of query arguments to the
  correct database-level type before querying. However, three model
  field classes did not correctly convert their arguments:
  
  * :class:`~django.db.models.FilePathField`
  * :class:`~django.db.models.GenericIPAddressField`
  * ``IPAddressField``
  
  These three fields have been updated to convert their arguments to the
  correct types before querying.
  
  Additionally, developers of custom model fields are now warned via
  documentation to ensure their custom field classes will perform
  appropriate type conversions, and users of the :meth:`raw()
  <django.db.models.query.QuerySet.raw>` and :meth:`extra()
  <django.db.models.query.QuerySet.extra>` query methods -- which allow the
  developer to supply raw SQL or SQL fragments -- will be advised to ensure they
  perform appropriate manual type conversions prior to executing queries.
  
  ``select_for_update()`` requires a transaction
  ==============================================
  
  Historically, queries that use
  :meth:`~django.db.models.query.QuerySet.select_for_update()` could be
  executed in autocommit mode, outside of a transaction. Before Django
  1.6, Django's automatic transactions mode allowed this to be used to
  lock records until the next write operation. Django 1.6 introduced
  database-level autocommit; since then, execution in such a context
  voids the effect of ``select_for_update()``. It is, therefore, assumed
  now to be an error and raises an exception.
  
  This change was made because such errors can be caused by including an
  app which expects global transactions (e.g. :setting:`ATOMIC_REQUESTS
  <DATABASE-ATOMIC_REQUESTS>` set to ``True``), or Django's old autocommit
  behavior, in a project which runs without them; and further, such
  errors may manifest as data-corruption bugs.
  
  This change may cause test failures if you use ``select_for_update()``
  in a test class which is a subclass of
  :class:`~django.test.TransactionTestCase` rather than
  :class:`~django.test.TestCase`.
  
  Other bugfixes and changes
  ==========================
  
  * Content retrieved from the GeoIP library is now properly decoded from its
  default ``iso-8859-1`` encoding
  (:ticket:`21996`).
  
  * Fixed ``AttributeError`` when using
  :meth:`~django.db.models.query.QuerySet.bulk_create` with ``ForeignObject``
  (:ticket:`21566`).
  
  * Fixed crash of ``QuerySet``\s that use ``F() + timedelta()`` when their query
  was compiled more once
  (:ticket:`21643`).
  
  * Prevented custom ``widget`` class attribute of
  :class:`~django.forms.IntegerField` subclasses from being overwritten by the
  code in their ``__init__`` method
  (:ticket:`22245`).
  
  * Improved :func:`~django.utils.html.strip_tags` accuracy (but it still cannot
  guarantee an HTML-safe result, as stated in the documentation).
  
  * Fixed a regression in the :mod:`django.contrib.gis` SQL compiler for
  non-concrete fields (:ticket:`22250`).
  
  * Fixed :attr:`ModelAdmin.preserve_filters
  <django.contrib.admin.ModelAdmin.preserve_filters>` when running a site with
  a URL prefix (:ticket:`21795`).
  
  * Fixed a crash in the ``find_command`` management utility when the ``PATH``
  environment variable wasn't set
  (:ticket:`22256`).
  
  * Fixed :djadmin:`changepassword` on Windows
  (:ticket:`22364`).
  
  * Avoided shadowing deadlock exceptions on MySQL
  (:ticket:`22291`).
  
  * Wrapped database exceptions in ``_set_autocommit``
  (:ticket:`22321`).
  
  * Fixed atomicity when closing a database connection or when the database server
  disconnects (:ticket:`21239` and :ticket:`21202`)
  
  * Fixed regression in ``prefetch_related`` that caused the related objects
  query to include an unnecessary join
  (:ticket:`21760`).
  
  Additionally, Django's vendored version of six, ``django.utils.six`` has been
  upgraded to the latest release (1.6.1).
  
  
  ==========================

1.6.2 not secure

==========================
  
  *February 6, 2014*
  
  This is Django 1.6.2, a bugfix release for Django 1.6. Django 1.6.2 fixes
  several bugs in 1.6.1:
  
  * Prevented the base geometry object of a prepared geometry to be garbage
  collected, which could lead to crash Django
  (:ticket:`21662`).
  
  * Fixed a crash when executing the :djadmin:`changepassword` command when the
  user object representation contained non-ASCII characters
  (:ticket:`21627`).
  
  * The :djadmin:`collectstatic` command will raise an error rather than
  default to using the current working directory if :setting:`STATIC_ROOT` is
  not set. Combined with the ``--clear`` option, the previous behavior could
  wipe anything below the current working directory
  (:ticket:`21581`).
  
  * Fixed mail encoding on Python 3.3.3+
  (:ticket:`21093`).
  
  * Fixed an issue where when
  ``settings.DATABASES['default']['AUTOCOMMIT'] = False``, the connection
  wasn't in autocommit mode but Django pretended it was.
  
  * Fixed a regression in multiple-table inheritance ``exclude()`` queries
  (:ticket:`21787`).
  
  * Added missing items to ``django.utils.timezone.__all__``
  (:ticket:`21880`).
  
  * Fixed a field misalignment issue with ``select_related()`` and model
  inheritance
  (:ticket:`21413`).
  
  * Fixed join promotion for negated ``AND`` conditions
  (:ticket:`21748`).
  
  * Oracle database introspection now works with boolean and float fields
  (:ticket:`19884`).
  
  * Fixed an issue where lazy objects weren't actually marked as safe when passed
  through :func:`~django.utils.safestring.mark_safe` and could end up being
  double-escaped (:ticket:`21882`).
  
  Additionally, Django's vendored version of six, ``django.utils.six`` has been
  upgraded to the latest release (1.5.2).
  
  
  ==========================

1.6.1 not secure

==========================
  
  *December 12, 2013*
  
  This is Django 1.6.1, a bugfix release for Django 1.6. In addition to the bug
  fixes listed below, translations submitted since the 1.6 release are also
  included.
  
  Bug fixes
  =========
  
  * Fixed ``BCryptSHA256PasswordHasher`` with py-bcrypt and Python 3 (21398).
  * Fixed a regression that prevented a ``ForeignKey`` with a hidden reverse
  manager (``related_name`` ending with '+') from being used as a lookup for
  ``prefetch_related`` (21410).
  * Fixed :meth:`Queryset.datetimes<django.db.models.query.QuerySet.datetimes>`
  raising ``AttributeError`` in some situations (21432).
  * Fixed :class:`~django.contrib.auth.backends.ModelBackend` raising
  ``UnboundLocalError`` if :func:`~django.contrib.auth.get_user_model`
  raised an error (21439).
  * Fixed a regression that prevented editable ``GenericRelation`` subclasses
  from working in ``ModelForms`` (21428).
  * Added missing ``to_python`` method for ``ModelMultipleChoiceField`` which
  is required in Django 1.6 to properly detect changes from initial values
  (21568).
  * Fixed ``django.contrib.humanize`` translations where the Unicode sequence
  for the non-breaking space was returned verbatim (21415).
  * Fixed :djadmin:`loaddata` error when fixture file name contained any dots
  not related to file extensions (21457) or when fixture path was relative
  but located in a subdirectory (21551).
  * Fixed display of inline instances in formsets when parent has 0 for primary
  key (21472).
  * Fixed a regression where custom querysets for foreign keys were overwritten
  if ``ModelAdmin`` had ordering set (21405).
  * Removed mention of a feature in the ``--locale``/``-l`` option of the
  ``makemessages`` and ``compilemessages`` commands that never worked as
  promised: Support of multiple locale names separated by commas. It's still
  possible to specify multiple locales in one run by using the option
  multiple times (21488, 17181).
  * Fixed a regression that unnecessarily triggered settings configuration when
  importing ``get_wsgi_application`` (21486).
  * Fixed test client ``logout()`` method when using the cookie-based session
  backend (21448).
  * Fixed a crash when a ``GeometryField`` uses a non-geometric widget (21496).
  * Fixed password hash upgrade when changing the iteration count (21535).
  * Fixed a bug in the debug view when the URLconf only contains one element
  (21530).
  * Re-added missing search result count and reset link in changelist admin view
  (21510).
  * The current language is no longer saved to the session by ``LocaleMiddleware``
  on every response, but rather only after a logout (21473).
  * Fixed a crash when executing ``runserver`` on non-English systems and when the
  formatted date in its output contained non-ASCII characters (21358).
  * Fixed a crash in the debug view after an exception occurred on Python ≥ 3.3
  (21443).
  * Fixed a crash in :class:`~django.db.models.ImageField` on some platforms
  (Homebrew and RHEL6 reported) (21355).
  * Fixed a regression when using generic relations in ``ModelAdmin.list_filter``
  (21431).
  
  
  =========================

1.6 not secure

=========================
  
  .. note::
  
  Dedicated to Malcolm Tredinnick
  
  On March 17, 2013, the Django project and the free software community lost
  a very dear friend and developer.
  
  Malcolm was a long-time contributor to Django, a model community member, a
  brilliant mind, and a friend. His contributions to Django — and to many other
  open source projects — are nearly impossible to enumerate. Many on the core
  Django team had their first patches reviewed by him; his mentorship enriched
  us. His consideration, patience, and dedication will always be an inspiration
  to us.
  
  This release of Django is for Malcolm.
  
  -- The Django Developers
  
  *November 6, 2013*
  
  Welcome to Django 1.6!
  
  These release notes cover the :ref:`new features <whats-new-1.6>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.6>` you'll
  want to be aware of when upgrading from Django 1.5 or older versions. We've
  also dropped some features, which are detailed in :ref:`our deprecation plan
  <deprecation-removed-in-1.6>`, and we've :ref:`begun the deprecation process
  for some features <deprecated-features-1.6>`.
  
  Python compatibility
  ====================
  
  Django 1.6, like Django 1.5, requires Python 2.6.5 or above. Python 3 is also
  officially supported. We **highly recommend** the latest minor release for each
  supported Python series (2.6.X, 2.7.X, 3.2.X, and 3.3.X).
  
  Django 1.6 will be the final release series to support Python 2.6; beginning
  with Django 1.7, the minimum supported Python version will be 2.7.
  
  Python 3.4 is not supported, but support will be added in Django 1.7.
  
  .. _whats-new-1.6:
  
  What's new in Django 1.6
  ========================
  
  Simplified default project and app templates
  --------------------------------------------
  
  The default templates used by :djadmin:`startproject` and :djadmin:`startapp`
  have been simplified and modernized. The :doc:`admin
  </ref/contrib/admin/index>` is now enabled by default in new projects; the
  :doc:`sites </ref/contrib/sites>` framework no longer is. :ref:`clickjacking
  prevention <clickjacking-prevention>` is now on and the database defaults to
  SQLite.
  
  If the default templates don't suit your tastes, you can use :ref:`custom
  project and app templates <custom-app-and-project-templates>`.
  
  Improved transaction management
  -------------------------------
  
  Django's transaction management was overhauled. Database-level autocommit is
  now turned on by default. This makes transaction handling more explicit and
  should improve performance. The existing APIs were deprecated, and new APIs
  were introduced, as described in the :doc:`transaction management docs
  </topics/db/transactions>`.
  
  Persistent database connections
  -------------------------------
  
  Django now supports reusing the same database connection for several requests.
  This avoids the overhead of re-establishing a connection at the beginning of
  each request. For backwards compatibility, this feature is disabled by
  default. See :ref:`persistent-database-connections` for details.
  
  Discovery of tests in any test module
  -------------------------------------
  
  Django 1.6 ships with a new test runner that allows more flexibility in the
  location of tests. The previous runner
  (``django.test.simple.DjangoTestSuiteRunner``) found tests only in the
  ``models.py`` and ``tests.py`` modules of a Python package in
  :setting:`INSTALLED_APPS`.
  
  The new runner (``django.test.runner.DiscoverRunner``) uses the test discovery
  features built into ``unittest2`` (the version of ``unittest`` in the
  Python 2.7+ standard library, and bundled with Django). With test discovery,
  tests can be located in any module whose name matches the pattern ``test*.py``.
  
  In addition, the test labels provided to ``./manage.py test`` to nominate
  specific tests to run must now be full Python dotted paths (or directory
  paths), rather than ``applabel.TestCase.test_method_name`` pseudo-paths. This
  allows running tests located anywhere in your codebase, rather than only in
  :setting:`INSTALLED_APPS`. For more details, see :doc:`/topics/testing/index`.
  
  This change is backwards-incompatible; see the :ref:`backwards-incompatibility
  notes<new-test-runner>`.
  
  Time zone aware aggregation
  ---------------------------
  
  The support for :doc:`time zones </topics/i18n/timezones>` introduced in
  Django 1.4 didn't work well with :meth:`QuerySet.dates()
  <django.db.models.query.QuerySet.dates>`: aggregation was always performed in
  UTC. This limitation was lifted in Django 1.6. Use :meth:`QuerySet.datetimes()
  <django.db.models.query.QuerySet.datetimes>` to perform time zone aware
  aggregation on a :class:`~django.db.models.DateTimeField`.
  
  Support for savepoints in SQLite
  --------------------------------
  
  Django 1.6 adds support for savepoints in SQLite, with some :ref:`limitations
  <savepoints-in-sqlite>`.
  
  ``BinaryField`` model field
  ---------------------------
  
  A new :class:`django.db.models.BinaryField` model field allows storage of raw
  binary data in the database.
  
  GeoDjango form widgets
  ----------------------
  
  GeoDjango now provides :doc:`form fields and widgets </ref/contrib/gis/forms-api>`
  for its geo-specialized fields. They are OpenLayers-based by default, but they
  can be customized to use any other JS framework.
  
  ``check`` management command added for verifying compatibility
  --------------------------------------------------------------
  
  A :djadmin:`check` management command was added, enabling you to verify if your
  current configuration (currently oriented at settings) is compatible with the
  current version of Django.
  
  :meth:`Model.save() <django.db.models.Model.save()>` algorithm changed
  ----------------------------------------------------------------------
  
  The :meth:`Model.save() <django.db.models.Model.save()>` method now
  tries to directly ``UPDATE`` the database if the instance has a primary
  key value. Previously ``SELECT`` was performed to determine if ``UPDATE``
  or ``INSERT`` were needed. The new algorithm needs only one query for
  updating an existing row while the old algorithm needed two. See
  :meth:`Model.save() <django.db.models.Model.save()>` for more details.
  
  In some rare cases the database doesn't report that a matching row was
  found when doing an ``UPDATE``. An example is the PostgreSQL ``ON UPDATE``
  trigger which returns ``NULL``. In such cases it is possible to set
  :attr:`django.db.models.Options.select_on_save` flag to force saving to
  use the old algorithm.
  
  Minor features
  --------------
  
  * Authentication backends can raise ``PermissionDenied`` to immediately fail
  the authentication chain.
  
  * The ``HttpOnly`` flag can be set on the CSRF cookie with
  :setting:`CSRF_COOKIE_HTTPONLY`.
  
  * The :meth:`~django.test.TransactionTestCase.assertQuerysetEqual` now checks
  for undefined order and raises :exc:`ValueError` if undefined
  order is spotted. The order is seen as undefined if the given ``QuerySet``
  isn't ordered and there are more than one ordered values to compare against.
  
  * Added :meth:`~django.db.models.query.QuerySet.earliest` for symmetry with
  :meth:`~django.db.models.query.QuerySet.latest`.
  
  * In addition to :lookup:`year`, :lookup:`month` and :lookup:`day`, the ORM
  now supports :lookup:`hour`, :lookup:`minute` and :lookup:`second` lookups.
  
  * Django now wraps all :pep:`249` exceptions.
  
  * The default widgets for :class:`~django.forms.EmailField`,
  :class:`~django.forms.URLField`, :class:`~django.forms.IntegerField`,
  :class:`~django.forms.FloatField` and :class:`~django.forms.DecimalField` use
  the new type attributes available in HTML5 (``type='email'``, ``type='url'``,
  ``type='number'``). Note that due to erratic support of the ``number``
  input type with localized numbers in current browsers, Django only uses it
  when numeric fields are not localized.
  
  * The ``number`` argument for :ref:`lazy plural translations
  <lazy-plural-translations>` can be provided at translation time rather than
  at definition time.
  
  * For custom management commands: Verification of the presence of valid
  settings in commands that ask for it by using the
  ``BaseCommand.can_import_settings`` internal
  option is now performed independently from handling of the locale that
  should be active during the execution of the command. The latter can now be
  influenced by the new
  ``BaseCommand.leave_locale_alone`` internal
  option. See :ref:`management-commands-and-locales` for more details.
  
  * The :attr:`~django.views.generic.edit.DeletionMixin.success_url` of
  :class:`~django.views.generic.edit.DeletionMixin` is now interpolated with
  its ``object``’s ``__dict__``.
  
  * :class:`~django.http.HttpResponseRedirect` and
  :class:`~django.http.HttpResponsePermanentRedirect` now provide an ``url``
  attribute (equivalent to the URL the response will redirect to).
  
  * The ``MemcachedCache`` cache backend now uses the latest :mod:`pickle`
  protocol available.
  
  * Added :class:`~django.contrib.messages.views.SuccessMessageMixin` which
  provides a ``success_message`` attribute for
  :class:`~django.views.generic.edit.FormView` based classes.
  
  * Added the :attr:`django.db.models.ForeignKey.db_constraint` and
  :attr:`django.db.models.ManyToManyField.db_constraint` options.
  
  * The jQuery library embedded in the admin has been upgraded to version 1.9.1.
  
  * Syndication feeds (:mod:`django.contrib.syndication`) can now pass extra
  context through to feed templates using a new
  :meth:`Feed.get_context_data()
  <django.contrib.syndication.Feed.get_context_data>` callback.
  
  * The admin list columns have a ``column-<field_name>`` class in the HTML
  so the columns header can be styled with CSS, e.g. to set a column width.
  
  * The :ref:`isolation level<database-isolation-level>` can be customized under
  PostgreSQL.
  
  * The :ttag:`blocktrans` template tag now respects
  ``TEMPLATE_STRING_IF_INVALID`` for variables not present in the
  context, just like other template constructs.
  
  * ``SimpleLazyObject``\s will now present more helpful representations in shell
  debugging situations.
  
  * Generic :class:`~django.contrib.gis.db.models.GeometryField` is now editable
  with the OpenLayers widget in the admin.
  
  * The documentation contains a :doc:`deployment checklist
  </howto/deployment/checklist>`.
  
  * The :djadmin:`diffsettings` command gained a ``--all`` option.
  
  * ``django.forms.fields.Field.__init__`` now calls ``super()``, allowing
  field mixins to implement ``__init__()`` methods that will reliably be
  called.
  
  * The ``validate_max`` parameter was added to ``BaseFormSet`` and
  :func:`~django.forms.formsets.formset_factory`, and ``ModelForm`` and inline
  versions of the same.  The behavior of validation for formsets with
  ``max_num`` was clarified.  The previously undocumented behavior that
  hardened formsets against memory exhaustion attacks was documented,
  and the undocumented limit of the higher of 1000 or ``max_num`` forms
  was changed so it is always 1000 more than ``max_num``.
  
  * Added ``BCryptSHA256PasswordHasher`` to resolve the password truncation issue
  with bcrypt.
  
  * `Pillow`_ is now the preferred image manipulation library to use with Django.
  `PIL`_ is pending deprecation (support to be removed in Django 1.8).
  To upgrade, you should **first** uninstall PIL, **then** install Pillow.
  
  .. _`Pillow`: https://pypi.org/project/Pillow/
  .. _`PIL`: https://pypi.org/project/PIL/
  
  * :class:`~django.forms.ModelForm` accepts several new ``Meta``
  options.
  
  * Fields included in the ``localized_fields`` list will be localized
  (by setting ``localize`` on the form field).
  * The  ``labels``, ``help_texts`` and ``error_messages`` options may be used
  to customize the default fields, see
  :ref:`modelforms-overriding-default-fields` for details.
  
  * The ``choices`` argument to model fields now accepts an iterable of iterables
  instead of requiring an iterable of lists or tuples.
  
  * The reason phrase can be customized in HTTP responses using
  :attr:`~django.http.HttpResponse.reason_phrase`.
  
  * When giving the URL of the next page for
  ``django.contrib.auth.views.logout()``,
  ``django.contrib.auth.views.password_reset()``,
  ``django.contrib.auth.views.password_reset_confirm()``,
  and ``django.contrib.auth.views.password_change()``, you can now pass
  URL names and they will be resolved.
  
  * The new :option:`dumpdata --pks` option specifies the primary keys of objects
  to dump. This option can only be used with one model.
  
  * Added ``QuerySet`` methods :meth:`~django.db.models.query.QuerySet.first`
  and :meth:`~django.db.models.query.QuerySet.last` which are convenience
  methods returning the first or last object matching the filters. Returns
  ``None`` if there are no objects matching.
  
  * :class:`~django.views.generic.base.View` and
  :class:`~django.views.generic.base.RedirectView` now support HTTP ``PATCH``
  method.
  
  * ``GenericForeignKey`` now takes an optional ``for_concrete_model`` argument,
  which when set to ``False`` allows the field to reference proxy models. The
  default is ``True`` to retain the old behavior.
  
  * The :class:`~django.middleware.locale.LocaleMiddleware` now stores the active
  language in session if it is not present there. This prevents loss of
  language settings after session flush, e.g. logout.
  
  * :exc:`~django.core.exceptions.SuspiciousOperation` has been differentiated
  into a number of subclasses, and each will log to a matching named logger
  under the ``django.security`` logging hierarchy. Along with this change,
  a ``handler400`` mechanism and default view are used whenever
  a ``SuspiciousOperation`` reaches the WSGI handler to return an
  ``HttpResponseBadRequest``.
  
  * The :exc:`~django.db.models.Model.DoesNotExist` exception now includes a
  message indicating the name of the attribute used for the lookup.
  
  * The :meth:`~django.db.models.query.QuerySet.get_or_create` method no longer
  requires at least one keyword argument.
  
  * The :class:`~django.test.SimpleTestCase` class includes a new assertion
  helper for testing formset errors:
  :meth:`~django.test.SimpleTestCase.assertFormsetError`.
  
  * The list of related fields added to a
  :class:`~django.db.models.query.QuerySet` by
  :meth:`~django.db.models.query.QuerySet.select_related` can be cleared using
  ``select_related(None)``.
  
  * The :meth:`~django.contrib.admin.InlineModelAdmin.get_extra` and
  :meth:`~django.contrib.admin.InlineModelAdmin.get_max_num` methods on
  :class:`~django.contrib.admin.InlineModelAdmin` may be overridden to
  customize the extra and maximum number of inline forms.
  
  * Formsets now have a
  :meth:`~django.forms.formsets.BaseFormSet.total_error_count` method.
  
  * :class:`~django.forms.ModelForm` fields can now override error messages
  defined in model fields by using the
  :attr:`~django.forms.Field.error_messages` argument of a ``Field``’s
  constructor. To take advantage of this new feature with your custom fields,
  :ref:`see the updated recommendation <raising-validation-error>` for raising
  a ``ValidationError``.
  
  * :class:`~django.contrib.admin.ModelAdmin` now preserves filters on the list view
  after creating, editing or deleting an object. It's possible to restore the previous
  behavior of clearing filters by setting the
  :attr:`~django.contrib.admin.ModelAdmin.preserve_filters` attribute to ``False``.
  
  * Added
  :meth:`FormMixin.get_prefix<django.views.generic.edit.FormMixin.get_prefix>`
  (which returns
  :attr:`FormMixin.prefix<django.views.generic.edit.FormMixin.prefix>` by
  default) to allow customizing the :attr:`~django.forms.Form.prefix` of the
  form.
  
  * Raw queries (``Manager.raw()`` or ``cursor.execute()``) can now use the
  "pyformat" parameter style, where placeholders in the query are given as
  ``'%(name)s'`` and the parameters are passed as a dictionary rather than
  a list (except on SQLite). This has long been possible (but not officially
  supported) on MySQL and PostgreSQL, and is now also available on Oracle.
  
  * The default iteration count for the PBKDF2 password hasher has been
  increased by 20%. This backwards compatible change will not affect
  existing passwords or users who have subclassed
  ``django.contrib.auth.hashers.PBKDF2PasswordHasher`` to change the
  default value. Passwords :ref:`will be upgraded <password-upgrades>` to use
  the new iteration count as necessary.
  
  .. _backwards-incompatible-1.6:
  
  Backwards incompatible changes in 1.6
  =====================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`deprecation plan <deprecation-removed-in-1.6>` for any features that
  have been removed. If you haven't updated your code within the
  deprecation timeline for a given feature, its removal may appear as a
  backwards incompatible change.
  
  New transaction management model
  --------------------------------
  
  Behavior changes
  ~~~~~~~~~~~~~~~~
  
  Database-level autocommit is enabled by default in Django 1.6. While this
  doesn't change the general spirit of Django's transaction management, there
  are a few backwards-incompatibilities.
  
  Savepoints and ``assertNumQueries``
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  The changes in transaction management may result in additional statements to
  create, release or rollback savepoints. This is more likely to happen with
  SQLite, since it didn't support savepoints until this release.
  
  If tests using :meth:`~django.test.TransactionTestCase.assertNumQueries` fail
  because of a higher number of queries than expected, check that the extra
  queries are related to savepoints, and adjust the expected number of queries
  accordingly.
  
  Autocommit option for PostgreSQL
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  In previous versions, database-level autocommit was only an option for
  PostgreSQL, and it was disabled by default. This option is now ignored and can
  be removed.
  
  .. _new-test-runner:
  
  New test runner
  ---------------
  
  In order to maintain greater consistency with Python's ``unittest`` module, the
  new test runner (``django.test.runner.DiscoverRunner``) does not automatically
  support some types of tests that were supported by the previous runner:
  
  * Tests in ``models.py`` and ``tests/__init__.py`` files will no longer be
  found and run. Move them to a file whose name begins with ``test``.
  
  * Doctests will no longer be automatically discovered. To integrate doctests in
  your test suite, follow the :ref:`recommendations in the Python documentation
  <doctest-unittest-api>`.
  
  Django bundles a modified version of the :mod:`doctest` module from the Python
  standard library (in ``django.test._doctest``) and includes some additional
  doctest utilities. These utilities are deprecated and will be removed in Django
  1.8; doctest suites should be updated to work with the standard library's
  doctest module (or converted to ``unittest``-compatible tests).
  
  If you wish to delay updates to your test suite, you can set your
  :setting:`TEST_RUNNER` setting to ``django.test.simple.DjangoTestSuiteRunner``
  to fully restore the old test behavior. ``DjangoTestSuiteRunner`` is deprecated
  but will not be removed from Django until version 1.8.
  
  Removal of ``django.contrib.gis.tests.GeoDjangoTestSuiteRunner`` GeoDjango custom test runner
  ---------------------------------------------------------------------------------------------
  
  This is for developers working on the GeoDjango application itself and related
  to the item above about changes in the test runners:
  
  The ``django.contrib.gis.tests.GeoDjangoTestSuiteRunner`` test runner has been
  removed and the standalone GeoDjango tests execution setup it implemented isn't
  supported anymore. To run the GeoDjango tests simply use the new
  ``DiscoverRunner`` and specify the ``django.contrib.gis`` app.
  
  Custom user models in tests
  ---------------------------
  
  The introduction of the new test runner has also slightly changed the way that
  test models are imported. As a result, any test that overrides ``AUTH_USER_MODEL``
  to test behavior with one of Django's test user models (
  ``django.contrib.auth.tests.custom_user.CustomUser`` and
  ``django.contrib.auth.tests.custom_user.ExtensionUser``) must now
  explicitly import the User model in your test module::
  
  from django.contrib.auth.tests.custom_user import CustomUser
  
  override_settings(AUTH_USER_MODEL='auth.CustomUser')
  class CustomUserFeatureTests(TestCase):
  def test_something(self):
  Test code here ...
  
  This import forces the custom user model to be registered. Without this import,
  the test will be unable to swap in the custom user model, and you will get an
  error reporting::
  
  ImproperlyConfigured: AUTH_USER_MODEL refers to model 'auth.CustomUser' that has not been installed
  
  Time zone-aware ``day``, ``month``, and ``week_day`` lookups
  ------------------------------------------------------------
  
  Django 1.6 introduces time zone support for :lookup:`day`, :lookup:`month`,
  and :lookup:`week_day` lookups when :setting:`USE_TZ` is ``True``. These
  lookups were previously performed in UTC regardless of the current time zone.
  
  This requires :ref:`time zone definitions in the database
  <database-time-zone-definitions>`. If you're using SQLite, you must install
  pytz_. If you're using MySQL, you must install pytz_ and load the time zone
  tables with `mysql_tzinfo_to_sql`_.
  
  .. _pytz: http://pytz.sourceforge.net/
  .. _mysql_tzinfo_to_sql: https://dev.mysql.com/doc/refman/en/mysql-tzinfo-to-sql.html
  
  Addition of ``QuerySet.datetimes()``
  ------------------------------------
  
  When the :doc:`time zone support </topics/i18n/timezones>` added in Django 1.4
  was active, :meth:`QuerySet.dates() <django.db.models.query.QuerySet.dates>`
  lookups returned unexpected results, because the aggregation was performed in
  UTC. To fix this, Django 1.6 introduces a new API, :meth:`QuerySet.datetimes()
  <django.db.models.query.QuerySet.datetimes>`. This requires a few changes in
  your code.
  
  ``QuerySet.dates()`` returns ``date`` objects
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  :meth:`QuerySet.dates() <django.db.models.query.QuerySet.dates>` now returns a
  list of :class:`~datetime.date`. It used to return a list of
  :class:`~datetime.datetime`.
  
  :meth:`QuerySet.datetimes() <django.db.models.query.QuerySet.datetimes>`
  returns a list of :class:`~datetime.datetime`.
  
  ``QuerySet.dates()`` no longer usable on ``DateTimeField``
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  :meth:`QuerySet.dates() <django.db.models.query.QuerySet.dates>` raises an
  error if it's used on :class:`~django.db.models.DateTimeField` when time
  zone support is active. Use :meth:`QuerySet.datetimes()
  <django.db.models.query.QuerySet.datetimes>` instead.
  
  ``date_hierarchy`` requires time zone definitions
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  The :attr:`~django.contrib.admin.ModelAdmin.date_hierarchy` feature of the
  admin now relies on :meth:`QuerySet.datetimes()
  <django.db.models.query.QuerySet.datetimes>` when it's used on a
  :class:`~django.db.models.DateTimeField`.
  
  This requires time zone definitions in the database when :setting:`USE_TZ` is
  ``True``. :ref:`Learn more <database-time-zone-definitions>`.
  
  ``date_list`` in generic views requires time zone definitions
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  For the same reason, accessing ``date_list`` in the context of a date-based
  generic view requires time zone definitions in the database when the view is
  based on a :class:`~django.db.models.DateTimeField` and :setting:`USE_TZ` is
  ``True``. :ref:`Learn more <database-time-zone-definitions>`.
  
  New lookups may clash with model fields
  ---------------------------------------
  
  Django 1.6 introduces ``hour``, ``minute``, and ``second`` lookups on
  :class:`~django.db.models.DateTimeField`. If you had model fields called
  ``hour``, ``minute``, or ``second``, the new lookups will clash with you field
  names. Append an explicit :lookup:`exact` lookup if this is an issue.
  
  ``BooleanField`` no longer defaults to ``False``
  ------------------------------------------------
  
  When a :class:`~django.db.models.BooleanField` doesn't have an explicit
  :attr:`~django.db.models.Field.default`, the implicit default value is
  ``None``. In previous version of Django, it was ``False``, but that didn't
  represent accurately the lack of a value.
  
  Code that relies on the default value being ``False`` may raise an exception
  when saving new model instances to the database, because ``None`` isn't an
  acceptable value for a :class:`~django.db.models.BooleanField`. You should
  either specify ``default=False`` in the field definition, or ensure the field
  is set to ``True`` or ``False`` before saving the object.
  
  Translations and comments in templates
  --------------------------------------
  
  Extraction of translations after comments
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  Extraction of translatable literals from templates with the
  :djadmin:`makemessages` command now correctly detects i18n constructs when
  they are located after a ``{`` / ``}``-type comment on the same line. E.g.:
  
  .. code-block:: html+django
  
  { A comment }{% trans "This literal was incorrectly ignored. Not anymore" %}
  
  Location of translator comments
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  :ref:`translator-comments-in-templates` specified using ``{`` / ``}`` need to
  be at the end of a line. If they are not, the comments are ignored and
  :djadmin:`makemessages` will generate a warning. For example:
  
  .. code-block:: html+django
  
  { Translators: This is ignored }{% trans "Translate me" %}
  {{ title }}{ Translators: Extracted and associated with 'Welcome' below }
  <h1>{% trans "Welcome" %}</h1>
  
  Quoting in ``reverse()``
  ------------------------
  
  When reversing URLs, Django didn't apply ``django.utils.http.urlquote``
  to arguments before interpolating them in URL patterns. This bug is fixed in
  Django 1.6. If you worked around this bug by applying URL quoting before
  passing arguments to ``reverse()``, this may result in double-quoting. If this
  happens, simply remove the URL quoting from your code. You will also have to
  replace special characters in URLs used in
  :func:`~django.test.SimpleTestCase.assertRedirects` with their encoded
  versions.
  
  Storage of IP addresses in the comments app
  -------------------------------------------
  
  The comments app now uses a
  ``GenericIPAddressField`` for storing commenters' IP addresses, to support
  comments submitted from IPv6 addresses. Until now, it stored them in an
  ``IPAddressField``, which is only meant to support IPv4. When saving a comment
  made from an IPv6 address, the address would be silently truncated on MySQL
  databases, and raise an exception on Oracle. You will need to change the
  column type in your database to benefit from this change.
  
  For MySQL, execute this query on your project's database:
  
  .. code-block:: sql
  
  ALTER TABLE django_comments MODIFY ip_address VARCHAR(39);
  
  For Oracle, execute this query:
  
  .. code-block:: sql
  
  ALTER TABLE DJANGO_COMMENTS MODIFY (ip_address VARCHAR2(39));
  
  If you do not apply this change, the behavior is unchanged: on MySQL, IPv6
  addresses are silently truncated; on Oracle, an exception is generated. No
  database change is needed for SQLite or PostgreSQL databases.
  
  Percent literals in ``cursor.execute`` queries
  ----------------------------------------------
  
  When you are running raw SQL queries through the
  :ref:`cursor.execute <executing-custom-sql>` method, the rule about doubling
  percent literals (``%``) inside the query has been unified. Past behavior
  depended on the database backend. Now, across all backends, you only need to
  double literal percent characters if you are also providing replacement
  parameters. For example::
  
  No parameters, no percent doubling
  cursor.execute("SELECT foo FROM bar WHERE baz = '30%'")
  
  Parameters passed, non-placeholders have to be doubled
  cursor.execute("SELECT foo FROM bar WHERE baz = '30%%' and id = %s", [self.id])
  
  ``SQLite`` users need to check and update such queries.
  
  .. _m2m-help_text:
  
  Help text of model form fields for ManyToManyField fields
  ---------------------------------------------------------
  
  HTML rendering of model form fields corresponding to
  :class:`~django.db.models.ManyToManyField` model fields used to get the
  hard-coded sentence:
  
  *Hold down "Control", or "Command" on a Mac, to select more than one.*
  
  (or its translation to the active locale) imposed as the help legend shown along
  them if neither :attr:`model <django.db.models.Field.help_text>` nor :attr:`form
  <django.forms.Field.help_text>` ``help_text`` attributes were specified by the
  user (or this string was appended to any ``help_text`` that was provided).
  
  Since this happened at the model layer, there was no way to prevent the text
  from appearing in cases where it wasn't applicable such as form fields that
  implement user interactions that don't involve a keyboard and/or a mouse.
  
  Starting with Django 1.6, as an ad-hoc temporary backward-compatibility
  provision, the logic to add the "Hold down..." sentence has been moved to the
  model form field layer and modified to add the text only when the associated
  widget is :class:`~django.forms.SelectMultiple` or selected subclasses.
  
  The change can affect you in a backward incompatible way if you employ custom
  model form fields and/or widgets for ``ManyToManyField`` model fields whose UIs
  do rely on the automatic provision of the mentioned hard-coded sentence. These
  form field implementations need to adapt to the new scenario by providing their
  own handling of the ``help_text`` attribute.
  
  Applications that use Django :doc:`model form </topics/forms/modelforms>`
  facilities together with Django built-in form :doc:`fields </ref/forms/fields>`
  and :doc:`widgets </ref/forms/widgets>` aren't affected but need to be aware of
  what's described in :ref:`m2m-help_text-deprecation` below.
  
  QuerySet iteration
  ------------------
  
  The ``QuerySet`` iteration was changed to immediately convert all fetched
  rows to ``Model`` objects. In Django 1.5 and earlier the fetched rows were
  converted to ``Model`` objects in chunks of 100.
  
  Existing code will work, but the amount of rows converted to objects
  might change in certain use cases. Such usages include partially looping
  over a queryset or any usage which ends up doing ``__bool__`` or
  ``__contains__``.
  
  Notably most database backends did fetch all the rows in one go already in
  1.5.
  
  It is still possible to convert the fetched rows to ``Model`` objects
  lazily by using the :meth:`~django.db.models.query.QuerySet.iterator()`
  method.
  
  :meth:`BoundField.label_tag<django.forms.BoundField.label_tag>` now includes the form's :attr:`~django.forms.Form.label_suffix`
  -------------------------------------------------------------------------------------------------------------------------------
  
  This is consistent with how methods like
  :meth:`Form.as_p<django.forms.Form.as_p>` and
  :meth:`Form.as_ul<django.forms.Form.as_ul>` render labels.
  
  If you manually render ``label_tag`` in your templates:
  
  .. code-block:: html+django
  
  {{ form.my_field.label_tag }}: {{ form.my_field }}
  
  you'll want to remove the colon (or whatever other separator you may be
  using) to avoid duplicating it when upgrading to Django 1.6. The following
  template in Django 1.6 will render identically to the above template in Django
  1.5, except that the colon will appear inside the ``<label>`` element.
  
  .. code-block:: html+django
  
  {{ form.my_field.label_tag }} {{ form.my_field }}
  
  will render something like:
  
  .. code-block:: html
  
  <label for="id_my_field">My Field:</label> <input id="id_my_field" type="text" name="my_field" />
  
  If you want to keep the current behavior of rendering ``label_tag`` without
  the ``label_suffix``, instantiate the form ``label_suffix=''``. You can also
  customize the ``label_suffix`` on a per-field basis using the new
  ``label_suffix`` parameter on :meth:`~django.forms.BoundField.label_tag`.
  
  Admin views ``_changelist_filters`` GET parameter
  -------------------------------------------------
  
  To achieve preserving and restoring list view filters, admin views now
  pass around the ``_changelist_filters`` GET parameter. It's important that you
  account for that change if you have custom admin templates or if your tests
  rely on the previous URLs. If you want to revert to the original behavior you
  can set the
  :attr:`~django.contrib.admin.ModelAdmin.preserve_filters` attribute to ``False``.
  
  ``django.contrib.auth`` password reset uses base 64 encoding of ``User`` PK
  ---------------------------------------------------------------------------
  
  Past versions of Django used base 36 encoding of the ``User`` primary key in
  the password reset views and URLs
  (``django.contrib.auth.views.password_reset_confirm()``). Base 36 encoding is
  sufficient if the user primary key is an integer, however, with the
  introduction of custom user models in Django 1.5, that assumption may no longer
  be true.
  
  ``django.contrib.auth.views.password_reset_confirm()`` has been modified to
  take a ``uidb64`` parameter instead of ``uidb36``. If you are reversing this
  view, for example in a custom ``password_reset_email.html`` template, be sure
  to update your code.
  
  A temporary shim for ``django.contrib.auth.views.password_reset_confirm()``
  that will allow password reset links generated prior to Django 1.6 to continue
  to work has been added to provide backwards compatibility; this will be removed
  in Django 1.7. Thus, as long as your site has been running Django 1.6 for more
  than :setting:`PASSWORD_RESET_TIMEOUT_DAYS`, this change will have no effect.
  If not (for example, if you upgrade directly from Django 1.5 to Django 1.7),
  then any password reset links generated before you upgrade to Django 1.7 or
  later won't work after the upgrade.
  
  In addition, if you have any custom password reset URLs, you will need to
  update them by replacing ``uidb36`` with ``uidb64`` and the dash that follows
  that pattern with a slash. Also add ``_\-`` to the list of characters that may
  match the ``uidb64`` pattern.
  
  For example::
  
  url(r'^reset/(?P<uidb36>[0-9A-Za-z]+)-(?P<token>.+)/$',
  'django.contrib.auth.views.password_reset_confirm',
  name='password_reset_confirm'),
  
  becomes::
  
  url(r'^reset/(?P<uidb64>[0-9A-Za-z_\-]+)/(?P<token>.+)/$',
  'django.contrib.auth.views.password_reset_confirm',
  name='password_reset_confirm'),
  
  You may also want to add the shim to support the old style reset links. Using
  the example above, you would modify the existing url by replacing
  ``django.contrib.auth.views.password_reset_confirm`` with
  ``django.contrib.auth.views.password_reset_confirm_uidb36`` and also remove
  the ``name`` argument so it doesn't conflict with the new url::
  
  url(r'^reset/(?P<uidb36>[0-9A-Za-z]+)-(?P<token>.+)/$',
  'django.contrib.auth.views.password_reset_confirm_uidb36'),
  
  You can remove this URL pattern after your app has been deployed with Django
  1.6 for :setting:`PASSWORD_RESET_TIMEOUT_DAYS`.
  
  Default session serialization switched to JSON
  ----------------------------------------------
  
  Historically, :mod:`django.contrib.sessions` used :mod:`pickle` to serialize
  session data before storing it in the backend. If you're using the :ref:`signed
  cookie session backend<cookie-session-backend>` and :setting:`SECRET_KEY` is
  known by an attacker (there isn't an inherent vulnerability in Django that
  would cause it to leak), the attacker could insert a string into his session
  which, when unpickled, executes arbitrary code on the server. The technique for
  doing so is simple and easily available on the internet. Although the cookie
  session storage signs the cookie-stored data to prevent tampering, a
  :setting:`SECRET_KEY` leak immediately escalates to a remote code execution
  vulnerability.
  
  This attack can be mitigated by serializing session data using JSON rather
  than :mod:`pickle`. To facilitate this, Django 1.5.3 introduced a new setting,
  :setting:`SESSION_SERIALIZER`, to customize the session serialization format.
  For backwards compatibility, this setting defaulted to using :mod:`pickle`
  in Django 1.5.3, but we've changed the default to JSON in 1.6. If you upgrade
  and switch from pickle to JSON, sessions created before the upgrade will be
  lost. While JSON serialization does not support all Python objects like
  :mod:`pickle` does, we highly recommend using JSON-serialized sessions. Be
  aware of the following when checking your code to determine if JSON
  serialization will work for your application:
  
  * JSON requires string keys, so you will likely run into problems if you are
  using non-string keys in ``request.session``.
  * Setting session expiration by passing ``datetime`` values to
  :meth:`~django.contrib.sessions.backends.base.SessionBase.set_expiry` will
  not work as ``datetime`` values are not serializable in JSON. You can use
  integer values instead.
  
  See the :ref:`session_serialization` documentation for more details.
  
  Object Relational Mapper changes
  --------------------------------
  
  Django 1.6 contains many changes to the ORM. These changes fall mostly in
  three categories:
  
  1. Bug fixes (e.g. proper join clauses for generic relations, query combining,
  join promotion, and join trimming fixes)
  2. Preparation for new features. For example the ORM is now internally ready
  for multicolumn foreign keys.
  3. General cleanup.
  
  These changes can result in some compatibility problems. For example, some
  queries will now generate different table aliases. This can affect
  :meth:`QuerySet.extra() <django.db.models.query.QuerySet.extra>`. In addition
  some queries will now produce different results. An example is
  :meth:`exclude(condition) <django.db.models.query.QuerySet.exclude>`
  where the condition is a complex one (referencing multijoins inside
  :class:`Q objects <django.db.models.Q>`). In many cases the affected
  queries didn't produce correct results in Django 1.5 but do now.
  Unfortunately there are also cases that produce different results, but
  neither Django 1.5 nor 1.6 produce correct results.
  
  Finally, there have been many changes to the ORM internal APIs.
  
  Miscellaneous
  -------------
  
  * The ``django.db.models.query.EmptyQuerySet`` can't be instantiated any more -
  it is only usable as a marker class for checking if
  :meth:`~django.db.models.query.QuerySet.none` has been called:
  ``isinstance(qs.none(), EmptyQuerySet)``
  
  * If your CSS/JavaScript code used to access HTML input widgets by type, you
  should review it as ``type='text'`` widgets might be now output as
  ``type='email'``, ``type='url'`` or ``type='number'`` depending on their
  corresponding field type.
  
  * Form field's :attr:`~django.forms.Field.error_messages` that contain a
  placeholder should now always use a named placeholder (``"Value '%(value)s' is
  too big"`` instead of ``"Value '%s' is too big"``). See the corresponding
  field documentation for details about the names of the placeholders. The
  changes in 1.6 particularly affect :class:`~django.forms.DecimalField` and
  :class:`~django.forms.ModelMultipleChoiceField`.
  
  * Some :attr:`~django.forms.Field.error_messages` for
  :class:`~django.forms.IntegerField`, :class:`~django.forms.EmailField`,
  ``IPAddressField``, :class:`~django.forms.GenericIPAddressField`, and
  :class:`~django.forms.SlugField` have been suppressed because they
  duplicated error messages already provided by validators tied to the fields.
  
  * Due to a change in the form validation workflow,
  :class:`~django.forms.TypedChoiceField` ``coerce`` method should always
  return a value present in the ``choices`` field attribute. That limitation
  should be lift again in Django 1.7.
  
  * There have been changes in the way timeouts are handled in cache backends.
  Explicitly passing in ``timeout=None`` no longer results in using the
  default timeout. It will now set a non-expiring timeout. Passing 0 into the
  memcache backend no longer uses the default timeout, and now will
  set-and-expire-immediately the value.
  
  * The ``django.contrib.flatpages`` app used to set custom HTTP headers for
  debugging purposes. This functionality was not documented and made caching
  ineffective so it has been removed, along with its generic implementation,
  previously available in ``django.core.xheaders``.
  
  * The ``XViewMiddleware`` has been moved from ``django.middleware.doc`` to
  ``django.contrib.admindocs.middleware`` because it is an implementation
  detail of admindocs, proven not to be reusable in general.
  
  * :class:`~django.db.models.GenericIPAddressField` will now only allow
  ``blank`` values if ``null`` values are also allowed. Creating a
  ``GenericIPAddressField`` where ``blank`` is allowed but ``null`` is not
  will trigger a model validation error because ``blank`` values are always
  stored as ``null``. Previously, storing a ``blank`` value in a field which
  did not allow ``null`` would cause a database exception at runtime.
  
  * If a ``NoReverseMatch`` exception is raised from a method when rendering a
  template, it is not silenced. For example, ``{{ obj.view_href }}`` will
  cause template rendering to fail if ``view_href()`` raises
  ``NoReverseMatch``. There is no change to the :ttag:`{% url %}<url>` tag, it
  causes template rendering to fail like always when ``NoReverseMatch`` is
  raised.
  
  * :meth:`django.test.Client.logout` now calls
  :meth:`django.contrib.auth.logout` which will send the
  :func:`~django.contrib.auth.signals.user_logged_out` signal.
  
  * :ref:`Authentication views <built-in-auth-views>` are now reversed by name,
  not their locations in ``django.contrib.auth.views``. If you are using the
  views without a ``name``, you should update your ``urlpatterns`` to use
  ``django.conf.urls.url()`` with the ``name`` parameter. For example::
  
  (r'^reset/done/$', 'django.contrib.auth.views.password_reset_complete')
  
  becomes::
  
  url(r'^reset/done/$', 'django.contrib.auth.views.password_reset_complete', name='password_reset_complete')
  
  * :class:`~django.views.generic.base.RedirectView` now has a ``pattern_name``
  attribute which allows it to choose the target by reversing the URL.
  
  * In Django 1.4 and 1.5, a blank string was unintentionally not considered to
  be a valid password. This meant
  :meth:`~django.contrib.auth.models.User.set_password()` would save a blank
  password as an unusable password like
  :meth:`~django.contrib.auth.models.User.set_unusable_password()` does, and
  thus :meth:`~django.contrib.auth.models.User.check_password()` always
  returned ``False`` for blank passwords. This has been corrected in this
  release: blank passwords are now valid.
  
  * The admin :attr:`~django.contrib.admin.ModelAdmin.changelist_view` previously
  accepted a ``pop`` GET parameter to signify it was to be displayed in a popup.
  This parameter has been renamed to ``_popup`` to be consistent with the rest
  of the admin views. You should update your custom templates if they use the
  previous parameter name.
  
  * :meth:`~django.core.validators.validate_email` now accepts email addresses
  with ``localhost`` as the domain.
  
  * The new :option:`makemessages --keep-pot` option prevents deleting the
  temporary .pot file generated before creating the .po file.
  
  * The undocumented ``django.core.servers.basehttp.WSGIServerException`` has
  been removed. Use ``socket.error`` provided by the standard library instead.
  This change was also released in Django 1.5.5.
  
  * The signature of :meth:`django.views.generic.base.RedirectView.get_redirect_url`
  has changed and now accepts positional arguments as well (``*args, **kwargs``).
  Any unnamed captured group will now be passed to ``get_redirect_url()``
  which may result in a ``TypeError`` if you don't update the signature of your
  custom method.
  
  .. _deprecated-features-1.6:
  
  Features deprecated in 1.6
  ==========================
  
  Transaction management APIs
  ---------------------------
  
  Transaction management was completely overhauled in Django 1.6, and the
  current APIs are deprecated:
  
  - ``django.middleware.transaction.TransactionMiddleware``
  - ``django.db.transaction.autocommit``
  - ``django.db.transaction.commit_on_success``
  - ``django.db.transaction.commit_manually``
  - the ``TRANSACTIONS_MANAGED`` setting
  
  ``django.contrib.comments``
  ---------------------------
  
  Django's comment framework has been deprecated and is no longer supported. It
  will be available in Django 1.6 and 1.7, and removed in Django 1.8. Most users
  will be better served with a custom solution, or a hosted product like Disqus__.
  
  The code formerly known as ``django.contrib.comments`` is `still available
  in an external repository`__.
  
  __ https://disqus.com/
  __ https://github.com/django/django-contrib-comments
  
  Support for PostgreSQL versions older than 8.4
  ----------------------------------------------
  
  The end of upstream support periods was reached in December 2011 for
  PostgreSQL 8.2 and in February 2013 for 8.3. As a consequence, Django 1.6 sets
  8.4 as the minimum PostgreSQL version it officially supports.
  
  You're strongly encouraged to use the most recent version of PostgreSQL
  available, because of performance improvements and to take advantage of the
  native streaming replication available in PostgreSQL 9.x.
  
  Changes to :ttag:`cycle` and :ttag:`firstof`
  --------------------------------------------
  
  The template system generally escapes all variables to avoid XSS attacks.
  However, due to an accident of history, the :ttag:`cycle` and :ttag:`firstof`
  tags render their arguments as-is.
  
  Django 1.6 starts a process to correct this inconsistency. The ``future``
  template library provides alternate implementations of :ttag:`cycle` and
  :ttag:`firstof` that autoescape their inputs. If you're using these tags,
  you're encouraged to include the following line at the top of your templates to
  enable the new behavior::
  
  {% load cycle from future %}
  
  or::
  
  {% load firstof from future %}
  
  The tags implementing the old behavior have been deprecated, and in Django
  1.8, the old behavior will be replaced with the new behavior. To ensure
  compatibility with future versions of Django, existing templates should be
  modified to use the ``future`` versions.
  
  If necessary, you can temporarily disable auto-escaping with
  :func:`~django.utils.safestring.mark_safe` or :ttag:`{% autoescape off %}
  <autoescape>`.
  
  ``CACHE_MIDDLEWARE_ANONYMOUS_ONLY`` setting
  -------------------------------------------
  
  ``CacheMiddleware`` and ``UpdateCacheMiddleware`` used to provide a way to
  cache requests only if they weren't made by a logged-in user. This mechanism
  was largely ineffective because the middleware correctly takes into account the
  ``Vary: Cookie`` HTTP header, and this header is being set on a variety of
  occasions, such as:
  
  * accessing the session, or
  * using CSRF protection, which is turned on by default, or
  * using a client-side library which sets cookies, like `Google Analytics`__.
  
  This makes the cache effectively work on a per-session basis regardless of the
  ``CACHE_MIDDLEWARE_ANONYMOUS_ONLY`` setting.
  
  __ https://www.google.com/analytics/
  
  ``SEND_BROKEN_LINK_EMAILS`` setting
  -----------------------------------
  
  :class:`~django.middleware.common.CommonMiddleware` used to provide basic
  reporting of broken links by email when ``SEND_BROKEN_LINK_EMAILS`` is set to
  ``True``.
  
  Because of intractable ordering problems between
  :class:`~django.middleware.common.CommonMiddleware` and
  :class:`~django.middleware.locale.LocaleMiddleware`, this feature was split
  out into a new middleware:
  :class:`~django.middleware.common.BrokenLinkEmailsMiddleware`.
  
  If you're relying on this feature, you should add
  ``'django.middleware.common.BrokenLinkEmailsMiddleware'`` to your
  ``MIDDLEWARE_CLASSES`` setting and remove ``SEND_BROKEN_LINK_EMAILS``
  from your settings.
  
  ``_has_changed`` method on widgets
  ----------------------------------
  
  If you defined your own form widgets and defined the ``_has_changed`` method
  on a widget, you should now define this method on the form field itself.
  
  ``module_name`` model _meta attribute
  -------------------------------------
  
  ``Model._meta.module_name`` was renamed to ``model_name``. Despite being a
  private API, it will go through a regular deprecation path.
  
  ``get_(add|change|delete)_permission`` model _meta methods
  ----------------------------------------------------------
  
  ``Model._meta.get_(add|change|delete)_permission`` methods were deprecated.
  Even if they were not part of the public API they'll also go through
  a regular deprecation path. You can replace them with
  ``django.contrib.auth.get_permission_codename('action', Model._meta)`` where
  ``'action'`` is ``'add'``, ``'change'``, or ``'delete'``.
  
  ``get_query_set`` and similar methods renamed to ``get_queryset``
  -----------------------------------------------------------------
  
  Methods that return a ``QuerySet`` such as ``Manager.get_query_set`` or
  ``ModelAdmin.queryset`` have been renamed to ``get_queryset``.
  
  If you are writing a library that implements, for example, a
  ``Manager.get_query_set`` method, and you need to support old Django versions,
  you should rename the method and conditionally add an alias with the old name::
  
  class CustomManager(models.Manager):
  def get_queryset(self):
  pass  ...
  
  if django.VERSION < (1, 6):
  get_query_set = get_queryset
  
  For Django >= 1.6, models.Manager provides a get_query_set fallback
  that emits a warning when used.
  
  If you are writing a library that needs to call the ``get_queryset`` method and
  must support old Django versions, you should write::
  
  get_queryset = (some_manager.get_query_set
  if hasattr(some_manager, 'get_query_set')
  else some_manager.get_queryset)
  return get_queryset()  etc
  
  In the general case of a custom manager that both implements its own
  ``get_queryset`` method and calls that method, and needs to work with older Django
  versions, and libraries that have not been updated yet, it is useful to define
  a ``get_queryset_compat`` method as below and use it internally to your manager::
  
  class YourCustomManager(models.Manager):
  def get_queryset(self):
  return YourCustomQuerySet()  for example
  
  if django.VERSION < (1, 6):
  get_query_set = get_queryset
  
  def active(self):  for example
  return self.get_queryset_compat().filter(active=True)
  
  def get_queryset_compat(self):
  get_queryset = (self.get_query_set
  if hasattr(self, 'get_query_set')
  else self.get_queryset)
  return get_queryset()
  
  This helps to minimize the changes that are needed, but also works correctly in
  the case of subclasses (such as ``RelatedManagers`` from Django 1.5) which might
  override either ``get_query_set`` or ``get_queryset``.
  
  
  ``shortcut`` view and URLconf
  -----------------------------
  
  The ``shortcut`` view was moved from ``django.views.defaults`` to
  ``django.contrib.contenttypes.views`` shortly after the 1.0 release, but the
  old location was never deprecated. This oversight was corrected in Django 1.6
  and you should now use the new location.
  
  The URLconf ``django.conf.urls.shortcut`` was also deprecated. If you're
  including it in an URLconf, simply replace::
  
  (r'^prefix/', include('django.conf.urls.shortcut')),
  
  with::
  
  (r'^prefix/(?P<content_type_id>\d+)/(?P<object_id>.*)/$', 'django.contrib.contenttypes.views.shortcut'),
  
  ``ModelForm`` without ``fields`` or ``exclude``
  -----------------------------------------------
  
  Previously, if you wanted a :class:`~django.forms.ModelForm` to use all fields on
  the model, you could simply omit the ``Meta.fields`` attribute, and all fields
  would be used.
  
  This can lead to security problems where fields are added to the model and,
  unintentionally, automatically become editable by end users. In some cases,
  particular with boolean fields, it is possible for this problem to be completely
  invisible. This is a form of `Mass assignment vulnerability
  <https://en.wikipedia.org/wiki/Mass_assignment_vulnerability>`_.
  
  For this reason, this behavior is deprecated, and using the ``Meta.exclude``
  option is strongly discouraged. Instead, all fields that are intended for
  inclusion in the form should be listed explicitly in the ``fields`` attribute.
  
  If this security concern really does not apply in your case, there is a shortcut
  to explicitly indicate that all fields should be used - use the special value
  ``"__all__"`` for the fields attribute::
  
  class MyModelForm(ModelForm):
  class Meta:
  fields = "__all__"
  model = MyModel
  
  If you have custom ``ModelForms`` that only need to be used in the admin, there
  is another option. The admin has its own methods for defining fields
  (``fieldsets`` etc.), and so adding a list of fields to the ``ModelForm`` is
  redundant. Instead, simply omit the ``Meta`` inner class of the ``ModelForm``,
  or omit the ``Meta.model`` attribute. Since the ``ModelAdmin`` subclass knows
  which model it is for, it can add the necessary attributes to derive a
  functioning ``ModelForm``. This behavior also works for earlier Django
  versions.
  
  ``UpdateView`` and ``CreateView`` without explicit fields
  ---------------------------------------------------------
  
  The generic views :class:`~django.views.generic.edit.CreateView` and
  :class:`~django.views.generic.edit.UpdateView`, and anything else derived from
  :class:`~django.views.generic.edit.ModelFormMixin`, are vulnerable to the
  security problem described in the section above, because they can automatically
  create a ``ModelForm`` that uses all fields for a model.
  
  For this reason, if you use these views for editing models, you must also supply
  the ``fields`` attribute (new in Django 1.6), which is a list of model fields
  and works in the same way as the :class:`~django.forms.ModelForm`
  ``Meta.fields`` attribute. Alternatively, you can set the ``form_class``
  attribute to a ``ModelForm`` that explicitly defines the fields to be used.
  Defining an ``UpdateView`` or ``CreateView`` subclass to be used with a model
  but without an explicit list of fields is deprecated.
  
  .. _m2m-help_text-deprecation:
  
  Munging of help text of model form fields for ``ManyToManyField`` fields
  ------------------------------------------------------------------------
  
  All special handling of the ``help_text`` attribute of ``ManyToManyField`` model
  fields performed by standard model or model form fields as described in
  :ref:`m2m-help_text` above is deprecated and will be removed in Django 1.8.
  
  Help text of these fields will need to be handled either by applications, custom
  form fields or widgets, just like happens with the rest of the model field
  types.
  
  
  ===========================

1.5.12 not secure

===========================
  
  *January 2, 2015*
  
  Django 1.5.12 fixes a regression in the 1.5.9 security release.
  
  Bugfixes
  ========
  
  * Fixed a regression with dynamically generated inlines and allowed field
  references in the admin
  (:ticket:`23754`).
  
  
  ===========================

1.5.11 not secure

===========================
  
  *October 22, 2014*
  
  Django 1.5.11 fixes a couple regressions in the 1.5.9 security release.
  
  Bugfixes
  ========
  
  * Allowed related many-to-many fields to be referenced in the admin
  (:ticket:`23604`).
  
  * Allowed inline and hidden references to admin fields
  (:ticket:`23431`).
  
  
  ===========================

1.5.10 not secure

===========================
  
  *September 2, 2014*
  
  Django 1.5.10 fixes a regression in the 1.5.9 security release.
  
  Bugfixes
  ========
  
  * Allowed inherited and m2m fields to be referenced in the admin
  (:ticket:`22486`)
  
  
  ==========================

1.5.9 not secure

==========================
  
  *August 20, 2014*
  
  Django 1.5.9 fixes several security issues in 1.5.8.
  
  ``reverse()`` could generate URLs pointing to other hosts
  =========================================================
  
  In certain situations, URL reversing could generate scheme-relative URLs  (URLs
  starting with two slashes), which could unexpectedly redirect a user  to a
  different host. An attacker could exploit this, for example, by redirecting
  users to a phishing site designed to ask for user's passwords.
  
  To remedy this, URL reversing now ensures that no URL starts with two slashes
  (//), replacing the second slash with its URL encoded counterpart (%2F). This
  approach ensures that semantics stay the same, while making the URL relative to
  the domain and not to the scheme.
  
  File upload denial-of-service
  =============================
  
  Before this release, Django's file upload handing in its default configuration
  may degrade to producing a huge number of ``os.stat()`` system calls when a
  duplicate filename is uploaded. Since ``stat()`` may invoke IO, this may produce
  a huge data-dependent slowdown that slowly worsens over time. The net result is
  that given enough time, a user with the ability to upload files can cause poor
  performance in the upload handler, eventually causing it to become very slow
  simply by uploading 0-byte files. At this point, even a slow network connection
  and few HTTP requests would be all that is necessary to make a site unavailable.
  
  We've remedied the issue by changing the algorithm for generating file names
  if a file with the uploaded name already exists.
  :meth:`Storage.get_available_name()
  <django.core.files.storage.Storage.get_available_name>` now appends an
  underscore plus a random 7 character alphanumeric string (e.g. ``"_x3a1gho"``),
  rather than iterating through an underscore followed by a number (e.g. ``"_1"``,
  ``"_2"``, etc.).
  
  ``RemoteUserMiddleware`` session hijacking
  ==========================================
  
  When using the :class:`~django.contrib.auth.middleware.RemoteUserMiddleware`
  and the ``RemoteUserBackend``, a change to the ``REMOTE_USER`` header between
  requests without an intervening logout could result in the prior user's session
  being co-opted by the subsequent user. The middleware now logs the user out on
  a failed login attempt.
  
  Data leakage via query string manipulation in ``contrib.admin``
  ===============================================================
  
  In older versions of Django it was possible to reveal any field's data by
  modifying the "popup" and "to_field" parameters of the query string on an admin
  change form page. For example, requesting a URL like
  ``/admin/auth/user/?pop=1&t=password`` and viewing the page's HTML allowed
  viewing the password hash of each user. While the admin requires users to have
  permissions to view the change form pages in the first place, this could leak
  data if you rely on users having access to view only certain fields on a model.
  
  To address the issue, an exception will now be raised if a ``to_field`` value
  that isn't a related field to a model that has been registered with the admin
  is specified.
  
  
  ==========================

1.5.8 not secure

==========================
  
  *May 14, 2014*
  
  Django 1.5.8 fixes two security issues in 1.5.8.
  
  Caches may incorrectly be allowed to store and serve private data
  =================================================================
  
  In certain situations, Django may allow caches to store private data
  related to a particular session and then serve that data to requests
  with a different session, or no session at all. This can lead to
  information disclosure and can be a vector for cache poisoning.
  
  When using Django sessions, Django will set a ``Vary: Cookie`` header to
  ensure caches do not serve cached data to requests from other sessions.
  However, older versions of Internet Explorer (most likely only Internet
  Explorer 6, and Internet Explorer 7 if run on Windows XP or Windows Server
  2003) are unable to handle the ``Vary`` header in combination with many content
  types. Therefore, Django would remove the header if the request was made by
  Internet Explorer.
  
  To remedy this, the special behavior for these older Internet Explorer versions
  has been removed, and the ``Vary`` header is no longer stripped from the response.
  In addition, modifications to the ``Cache-Control`` header for all Internet Explorer
  requests with a ``Content-Disposition`` header have also been removed as they
  were found to have similar issues.
  
  Malformed redirect URLs from user input not correctly validated
  ===============================================================
  
  The validation for redirects did not correctly validate some malformed URLs,
  which are accepted by some browsers. This allows a user to be redirected to
  an unsafe URL unexpectedly.
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()``, ``django.contrib.comments``, and
  :doc:`i18n </topics/i18n/index>`) to redirect the user to an "on success" URL.
  The security checks for these redirects (namely
  ``django.utils.http.is_safe_url()``) did not correctly validate some malformed
  URLs, such as ``http:\\\\\\djangoproject.com``, which are accepted by some
  browsers with more liberal URL parsing.
  
  To remedy this, the validation in ``is_safe_url()`` has been tightened to be able
  to handle and correctly validate these malformed URLs.
  
  
  ==========================

1.5.7 not secure

==========================
  
  *April 28, 2014*
  
  Django 1.5.7 fixes a regression in the 1.5.6 security release.
  
  Bugfixes
  ========
  
  * Restored the ability to ``reverse()`` views created using
  :func:`functools.partial()` (:ticket:`22486`).
  
  
  ==========================

1.5.6 not secure

==========================
  
  *April 21, 2014*
  
  Django 1.5.6 fixes several bugs in 1.5.5, including three security
  issues.
  
  Unexpected code execution using ``reverse()``
  =============================================
  
  Django's URL handling is based on a mapping of regex patterns
  (representing the URLs) to callable views, and Django's own processing
  consists of matching a requested URL against those patterns to
  determine the appropriate view to invoke.
  
  Django also provides a convenience function -- ``reverse()`` -- which performs
  this process in the opposite direction. The ``reverse()`` function takes
  information about a view and returns a URL which would invoke that view. Use
  of ``reverse()`` is encouraged for application developers, as the output of
  ``reverse()`` is always based on the current URL patterns, meaning developers
  do not need to change other code when making changes to URLs.
  
  One argument signature for ``reverse()`` is to pass a dotted Python
  path to the desired view. In this situation, Django will import the
  module indicated by that dotted path as part of generating the
  resulting URL. If such a module has import-time side effects, those
  side effects will occur.
  
  Thus it is possible for an attacker to cause unexpected code
  execution, given the following conditions:
  
  1. One or more views are present which construct a URL based on user
  input (commonly, a "next" parameter in a querystring indicating
  where to redirect upon successful completion of an action).
  
  2. One or more modules are known to an attacker to exist on the
  server's Python import path, which perform code execution with side
  effects on importing.
  
  To remedy this, ``reverse()`` will now only accept and import dotted
  paths based on the view-containing modules listed in the project's :doc:`URL
  pattern configuration </topics/http/urls>`, so as to ensure that only modules
  the developer intended to be imported in this fashion can or will be imported.
  
  Caching of anonymous pages could reveal CSRF token
  ==================================================
  
  Django includes both a :doc:`caching framework </topics/cache>` and a system
  for :doc:`preventing cross-site request forgery (CSRF) attacks
  </ref/csrf/>`. The CSRF-protection system is based on a random nonce
  sent to the client in a cookie which must be sent by the client on future
  requests and, in forms, a hidden value which must be submitted back with the
  form.
  
  The caching framework includes an option to cache responses to
  anonymous (i.e., unauthenticated) clients.
  
  When the first anonymous request to a given page is by a client which
  did not have a CSRF cookie, the cache framework will also cache the
  CSRF cookie and serve the same nonce to other anonymous clients who
  do not have a CSRF cookie. This can allow an attacker to obtain a
  valid CSRF cookie value and perform attacks which bypass the check for
  the cookie.
  
  To remedy this, the caching framework will no longer cache such
  responses. The heuristic for this will be:
  
  1. If the incoming request did not submit any cookies, and
  
  2. If the response did send one or more cookies, and
  
  3. If the ``Vary: Cookie`` header is set on the response, then the
  response will not be cached.
  
  MySQL typecasting
  =================
  
  The MySQL database is known to "typecast" on certain queries; for
  example, when querying a table which contains string values, but using
  a query which filters based on an integer value, MySQL will first
  silently coerce the strings to integers and return a result based on that.
  
  If a query is performed without first converting values to the
  appropriate type, this can produce unexpected results, similar to what
  would occur if the query itself had been manipulated.
  
  Django's model field classes are aware of their own types and most
  such classes perform explicit conversion of query arguments to the
  correct database-level type before querying. However, three model
  field classes did not correctly convert their arguments:
  
  * :class:`~django.db.models.FilePathField`
  * :class:`~django.db.models.GenericIPAddressField`
  * ``IPAddressField``
  
  These three fields have been updated to convert their arguments to the
  correct types before querying.
  
  Additionally, developers of custom model fields are now warned via
  documentation to ensure their custom field classes will perform
  appropriate type conversions, and users of the :meth:`raw()
  <django.db.models.query.QuerySet.raw>` and :meth:`extra()
  <django.db.models.query.QuerySet.extra>` query methods -- which allow the
  developer to supply raw SQL or SQL fragments -- will be advised to ensure they
  perform appropriate manual type conversions prior to executing queries.
  
  Bugfixes
  ========
  
  * Fixed :class:`~django.contrib.auth.backends.ModelBackend` raising
  ``UnboundLocalError`` if :func:`~django.contrib.auth.get_user_model`
  raised an error (21439).
  
  Additionally, Django's vendored version of six, ``django.utils.six``,
  has been upgraded to the latest release (1.6.1).
  
  
  ==========================

1.5.5 not secure

==========================
  
  *October 23, 2013*
  
  Django 1.5.5 fixes a couple security-related bugs and several other bugs in the
  1.5 series.
  
  Readdressed denial-of-service via password hashers
  ==================================================
  
  Django 1.5.4 imposes a 4096-byte limit on passwords in order to mitigate a
  denial-of-service attack through submission of bogus but extremely large
  passwords. In Django 1.5.5, we've reverted this change and instead improved
  the speed of our PBKDF2 algorithm by not rehashing the key on every iteration.
  
  Properly rotate CSRF token on login
  ===================================
  
  This behavior introduced as a security hardening measure in Django 1.5.2 did
  not work properly and is now fixed.
  
  Bugfixes
  ========
  
  * Fixed a data corruption bug with ``datetime_safe.datetime.combine`` (21256).
  * Fixed a Python 3 incompatibility in ``django.utils.text.unescape_entities()``
  (21185).
  * Fixed a couple data corruption issues with ``QuerySet`` edge cases under
  Oracle and MySQL (21203, 21126).
  * Fixed crashes when using combinations of ``annotate()``,
  ``select_related()``, and ``only()`` (16436).
  
  Backwards incompatible changes
  ==============================
  
  * The undocumented ``django.core.servers.basehttp.WSGIServerException`` has
  been removed. Use ``socket.error`` provided by the standard library instead.
  
  
  ==========================

1.5.4 not secure

==========================
  
  *September 14, 2013*
  
  This is Django 1.5.4, the fourth release in the Django 1.5 series. It addresses
  two security issues and one bug.
  
  Denial-of-service via password hashers
  ======================================
  
  In previous versions of Django, no limit was imposed on the plaintext
  length of a password. This allowed a denial-of-service attack through
  submission of bogus but extremely large passwords, tying up server
  resources performing the (expensive, and increasingly expensive with
  the length of the password) calculation of the corresponding hash.
  
  As of 1.5.4, Django's authentication framework imposes a 4096-byte
  limit on passwords, and will fail authentication with any submitted
  password of greater length.
  
  Corrected usage of :func:`~django.views.decorators.debug.sensitive_post_parameters` in :mod:`django.contrib.auth`’s admin
  =========================================================================================================================
  
  The decoration of the ``add_view`` and ``user_change_password`` user admin
  views with :func:`~django.views.decorators.debug.sensitive_post_parameters`
  did not include :func:`~django.utils.decorators.method_decorator` (required
  since the views are methods) resulting in the decorator not being properly
  applied. This usage has been fixed and
  :func:`~django.views.decorators.debug.sensitive_post_parameters` will now
  throw an exception if it's improperly used.
  
  Bugfixes
  ========
  
  * Fixed a bug that prevented a ``QuerySet`` that uses
  :meth:`~django.db.models.query.QuerySet.prefetch_related` from being pickled
  and unpickled more than once (the second pickling attempt raised an
  exception) (21102).
  
  
  ==========================

1.5.3 not secure

==========================
  
  *September 10, 2013*
  
  This is Django 1.5.3, the third release in the Django 1.5 series. It addresses
  one security issue and also contains an opt-in feature to enhance the security
  of :mod:`django.contrib.sessions`.
  
  Directory traversal vulnerability in ``ssi`` template tag
  =========================================================
  
  In previous versions of Django it was possible to bypass the
  ``ALLOWED_INCLUDE_ROOTS`` setting used for security with the ``ssi``
  template tag by specifying a relative path that starts with one of the allowed
  roots. For example, if ``ALLOWED_INCLUDE_ROOTS = ("/var/www",)`` the following
  would be possible:
  
  .. code-block:: html+django
  
  {% ssi "/var/www/../../etc/passwd" %}
  
  In practice this is not a very common problem, as it would require the template
  author to put the ``ssi`` file in a user-controlled variable, but it's possible
  in principle.
  
  Mitigating a remote-code execution vulnerability in :mod:`django.contrib.sessions`
  ==================================================================================
  
  :mod:`django.contrib.sessions` currently uses :mod:`pickle` to serialize
  session data before storing it in the backend. If you're using the :ref:`signed
  cookie session backend<cookie-session-backend>` and :setting:`SECRET_KEY` is
  known by an attacker (there isn't an inherent vulnerability in Django that
  would cause it to leak), the attacker could insert a string into his session
  which, when unpickled, executes arbitrary code on the server. The technique for
  doing so is simple and easily available on the internet. Although the cookie
  session storage signs the cookie-stored data to prevent tampering, a
  :setting:`SECRET_KEY` leak immediately escalates to a remote code execution
  vulnerability.
  
  This attack can be mitigated by serializing session data using JSON rather
  than :mod:`pickle`. To facilitate this, Django 1.5.3 introduces a new setting,
  :setting:`SESSION_SERIALIZER`, to customize the session serialization format.
  For backwards compatibility, this setting defaults to using :mod:`pickle`.
  While JSON serialization does not support all Python objects like :mod:`pickle`
  does, we highly recommend switching to JSON-serialized values. Also,
  as JSON requires string keys, you will likely run into problems if you are
  using non-string keys in ``request.session``. See the
  :ref:`session_serialization` documentation for more details.
  
  
  ==========================

1.5.2 not secure

==========================
  
  *August 13, 2013*
  
  This is Django 1.5.2, a bugfix and security release for Django 1.5.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()``, ``django.contrib.comments``, and
  :doc:`i18n </topics/i18n/index>`) to redirect the user to an "on success" URL.
  The security checks for these redirects (namely
  ``django.utils.http.is_safe_url()``) didn't check if the scheme is ``http(s)``
  and as such allowed ``javascript:...`` URLs to be entered. If a developer
  relied on ``is_safe_url()`` to provide safe redirect targets and put such a
  URL into a link, they could suffer from a XSS attack. This bug doesn't affect
  Django currently, since we only put this URL into the ``Location`` response
  header and browsers seem to ignore JavaScript there.
  
  XSS vulnerability in :mod:`django.contrib.admin`
  ================================================
  
  If a :class:`~django.db.models.URLField` is used in Django 1.5, it displays the
  current value of the field and a link to the target on the admin change page.
  The display routine of this widget was flawed and allowed for XSS.
  
  Bugfixes
  ========
  
  * Fixed a crash with :meth:`~django.db.models.query.QuerySet.prefetch_related`
  (19607) as well as some ``pickle`` regressions with ``prefetch_related``
  (20157 and 20257).
  * Fixed a regression in :mod:`django.contrib.gis` in the Google Map output on
  Python 3 (20773).
  * Made ``DjangoTestSuiteRunner.setup_databases`` properly handle aliases for
  the default database (19940) and prevented ``teardown_databases`` from
  attempting to tear down aliases (20681).
  * Fixed the ``django.core.cache.backends.memcached.MemcachedCache`` backend's
  ``get_many()`` method on Python 3 (20722).
  * Fixed :mod:`django.contrib.humanize` translation syntax errors. Affected
  languages: Mexican Spanish, Mongolian, Romanian, Turkish (20695).
  * Added support for wheel packages (19252).
  * The CSRF token now rotates when a user logs in.
  * Some Python 3 compatibility fixes including 20212 and 20025.
  * Fixed some rare cases where :meth:`~django.db.models.query.QuerySet.get`
  exceptions recursed infinitely (20278).
  * :djadmin:`makemessages` no longer crashes with ``UnicodeDecodeError``
  (20354).
  * Fixed ``geojson`` detection with SpatiaLite.
  * :meth:`~django.test.SimpleTestCase.assertContains` once again works with
  binary content (20237).
  * Fixed :class:`~django.db.models.ManyToManyField` if it has a Unicode ``name``
  parameter (20207).
  * Ensured that the WSGI request's path is correctly based on the
  ``SCRIPT_NAME`` environment variable or the :setting:`FORCE_SCRIPT_NAME`
  setting, regardless of whether or not either has a trailing slash (20169).
  * Fixed an obscure bug with the :func:`~django.test.override_settings`
  decorator. If you hit an ``AttributeError: 'Settings' object has no attribute
  '_original_allowed_hosts'`` exception, it's probably fixed (20636).
  
  
  ==========================

1.5.1 not secure

==========================
  
  *March 28, 2013*
  
  This is Django 1.5.1, a bugfix release for Django 1.5. It's completely backwards
  compatible with Django 1.5, but includes a handful of fixes.
  
  The biggest fix is for a memory leak introduced in Django 1.5. Under certain
  circumstances, repeated iteration over querysets could leak memory - sometimes
  quite a bit of it. If you'd like more information, the details are in
  :ticket:`our ticket tracker <19895>` (and in `a related issue`__ in Python
  itself).
  
  __ https://bugs.python.org/issue17468
  
  If you've noticed memory problems under Django 1.5, upgrading to 1.5.1 should
  fix those issues.
  
  Django 1.5.1 also includes a couple smaller fixes:
  
  * Module-level warnings emitted during tests are no longer silently hidden
  (:ticket:`18985`).
  * Prevented filtering on password hashes in the user admin (:ticket:`20078`).
  
  
  ========================

1.5 not secure

========================
  
  *February 26, 2013*
  
  Welcome to Django 1.5!
  
  These release notes cover the :ref:`new features <whats-new-1.5>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.5>` you'll
  want to be aware of when upgrading from Django 1.4 or older versions. We've
  also dropped some features, which are detailed in :ref:`our deprecation plan
  <deprecation-removed-in-1.5>`, and we've :ref:`begun the deprecation process
  for some features <deprecated-features-1.5>`.
  
  Overview
  ========
  
  The biggest new feature in Django 1.5 is the `configurable User model`_. Before
  Django 1.5, applications that wanted to use Django's auth framework
  (:mod:`django.contrib.auth`) were forced to use Django's definition of a "user".
  In Django 1.5, you can now swap out the ``User`` model for one that you write
  yourself. This could be a simple extension to the existing ``User`` model -- for
  example, you could add a Twitter or Facebook ID field -- or you could completely
  replace the ``User`` with one totally customized for your site.
  
  Django 1.5 is also the first release with `Python 3 support`_! We're labeling
  this support "experimental" because we don't yet consider it production-ready,
  but everything's in place for you to start porting your apps to Python 3.
  Our next release, Django 1.6, will support Python 3 without reservations.
  
  Other notable new features in Django 1.5 include:
  
  * `Support for saving a subset of model's fields`_ -
  :meth:`Model.save() <django.db.models.Model.save()>` now accepts an
  ``update_fields`` argument, letting you specify which fields are
  written back to the database when you call ``save()``. This can help
  in high-concurrency operations, and can improve performance.
  
  * Better `support for streaming responses <explicit-streaming-responses>`_ via
  the new  :class:`~django.http.StreamingHttpResponse` response class.
  
  * `GeoDjango`_ now supports PostGIS 2.0.
  
  * ... and more; `see below <what-s-new-in-django-1-5>`_.
  
  Wherever possible we try to introduce new features in a backwards-compatible
  manner per :doc:`our API stability policy </misc/api-stability>`.
  However, as with previous releases, Django 1.5 ships with some minor
  :ref:`backwards incompatible changes <backwards-incompatible-1.5>`; people
  upgrading from previous versions of Django should read that list carefully.
  
  One deprecated feature worth noting is the shift to "new-style" :ttag:`url` tag.
  Prior to Django 1.3, syntax like ``{% url myview %}`` was interpreted
  incorrectly (Django considered ``"myview"`` to be a literal name of a view, not
  a template variable named ``myview``). Django 1.3 and above introduced the
  ``{% load url from future %}`` syntax to bring in the corrected behavior where
  ``myview`` was seen as a variable.
  
  The upshot of this is that if you are not using ``{% load url from future %}``
  in your templates, you'll need to change tags like ``{% url myview %}`` to
  ``{% url "myview" %}``. If you *were* using ``{% load url from future %}`` you
  can simply remove that line under Django 1.5
  
  Python compatibility
  ====================
  
  Django 1.5 requires Python 2.6.5 or above, though we **highly recommend**
  Python 2.7.3 or above. Support for Python 2.5 and below has been dropped.
  
  This change should affect only a small number of Django users, as most
  operating-system vendors today are shipping Python 2.6 or newer as their default
  version. If you're still using Python 2.5, however, you'll need to stick to
  Django 1.4 until you can upgrade your Python version. Per :doc:`our support
  policy </internals/release-process>`, Django 1.4 will continue to receive
  security support until the release of Django 1.6.
  
  Django 1.5 does not run on a Jython final release, because Jython's latest
  release doesn't currently support Python 2.6. However, Jython currently does
  offer an alpha release featuring 2.7 support, and Django 1.5 supports that alpha
  release.
  
  Python 3 support
  ----------------
  
  Django 1.5 introduces support for Python 3 - specifically, Python
  3.2 and above. This comes in the form of a **single** codebase; you don't
  need to install a different version of Django on Python 3. This means that
  you can write applications targeted for just Python 2, just Python 3, or single
  applications that support both platforms.
  
  However, we're labeling this support "experimental" for now: although it's
  received extensive testing via our automated test suite, it's received very
  little real-world testing. We've done our best to eliminate bugs, but we can't
  be sure we covered all possible uses of Django.
  
  Some features of Django aren't available because they depend on third-party
  software that hasn't been ported to Python 3 yet, including:
  
  - the MySQL database backend (depends on MySQLdb)
  - :class:`~django.db.models.ImageField` (depends on PIL)
  - :class:`~django.test.LiveServerTestCase` (depends on Selenium WebDriver)
  
  Further, Django's more than a web framework; it's an ecosystem of pluggable
  components. At this point, very few third-party applications have been ported
  to Python 3, so it's unlikely that a real-world application will have all its
  dependencies satisfied under Python 3.
  
  Thus, we're recommending that Django 1.5 not be used in production under Python
  3. Instead, use this opportunity to begin porting applications to Python 3. If
  you're an author of a pluggable component, we encourage you to start porting
  now.
  
  We plan to offer first-class, production-ready support for Python 3 in our next
  release, Django 1.6.
  
  .. _whats-new-1.5:
  
  What's new in Django 1.5
  ========================
  
  Configurable User model
  -----------------------
  
  In Django 1.5, you can now use your own model as the store for user-related
  data. If your project needs a username with more than 30 characters, or if
  you want to store user's names in a format other than first name/last name,
  or you want to put custom profile information onto your User object, you can
  now do so.
  
  If you have a third-party reusable application that references the User model,
  you may need to make some changes to the way you reference User instances. You
  should also document any specific features of the User model that your
  application relies upon.
  
  See the :ref:`documentation on custom user models <auth-custom-user>` for
  more details.
  
  Support for saving a subset of model's fields
  ---------------------------------------------
  
  The method :meth:`Model.save() <django.db.models.Model.save()>` has a new
  keyword argument ``update_fields``. By using this argument it is possible to
  save only a select list of model's fields. This can be useful for performance
  reasons or when trying to avoid overwriting concurrent changes.
  
  Deferred instances (those loaded by ``.only()`` or ``.defer()``) will
  automatically save just the loaded fields. If any field is set manually after
  load, that field will also get updated on save.
  
  See the :meth:`Model.save() <django.db.models.Model.save()>` documentation for
  more details.
  
  Caching of related model instances
  ----------------------------------
  
  When traversing relations, the ORM will avoid re-fetching objects that were
  previously loaded. For example, with the tutorial's models::
  
  >>> first_poll = Poll.objects.all()[0]
  >>> first_choice = first_poll.choice_set.all()[0]
  >>> first_choice.poll is first_poll
  True
  
  In Django 1.5, the third line no longer triggers a new SQL query to fetch
  ``first_choice.poll``; it was set by the second line.
  
  For one-to-one relationships, both sides can be cached. For many-to-one
  relationships, only the single side of the relationship can be cached. This
  is particularly helpful in combination with ``prefetch_related``.
  
  .. _explicit-streaming-responses:
  
  Explicit support for streaming responses
  ----------------------------------------
  
  Before Django 1.5, it was possible to create a streaming response by passing
  an iterator to :class:`~django.http.HttpResponse`. But this was unreliable:
  any middleware that accessed the :attr:`~django.http.HttpResponse.content`
  attribute would consume the iterator prematurely.
  
  You can now explicitly generate a streaming response with the new
  :class:`~django.http.StreamingHttpResponse` class. This class exposes a
  :class:`~django.http.StreamingHttpResponse.streaming_content` attribute which
  is an iterator.
  
  Since :class:`~django.http.StreamingHttpResponse` does not have a ``content``
  attribute, middleware that needs access to the response content must test for
  streaming responses and behave accordingly.
  
  ``{% verbatim %}`` template tag
  -------------------------------
  
  To make it easier to deal with JavaScript templates which collide with Django's
  syntax, you can now use the :ttag:`verbatim` block tag to avoid parsing the
  tag's content.
  
  Retrieval of ``ContentType`` instances associated with proxy models
  -------------------------------------------------------------------
  
  The methods :meth:`ContentTypeManager.get_for_model() <django.contrib.contenttypes.models.ContentTypeManager.get_for_model()>`
  and :meth:`ContentTypeManager.get_for_models() <django.contrib.contenttypes.models.ContentTypeManager.get_for_models()>`
  have a new keyword argument – respectively ``for_concrete_model`` and ``for_concrete_models``.
  By passing ``False`` using this argument it is now possible to retrieve the
  :class:`ContentType <django.contrib.contenttypes.models.ContentType>`
  associated with proxy models.
  
  New ``view`` variable in class-based views context
  --------------------------------------------------
  
  In all :doc:`generic class-based views </topics/class-based-views/index>`
  (or any class-based view inheriting from ``ContextMixin``), the context dictionary
  contains a ``view`` variable that points to the ``View`` instance.
  
  GeoDjango
  ---------
  
  * :class:`~django.contrib.gis.geos.LineString` and
  :class:`~django.contrib.gis.geos.MultiLineString` GEOS objects now support the
  :meth:`~django.contrib.gis.geos.GEOSGeometry.interpolate()` and
  :meth:`~django.contrib.gis.geos.GEOSGeometry.project()` methods
  (so-called linear referencing).
  
  * The ``wkb`` and ``hex`` properties of
  :class:`~django.contrib.gis.geos.GEOSGeometry` objects preserve the Z
  dimension.
  
  * Support for PostGIS 2.0 has been added and support for GDAL < 1.5 has been
  dropped.
  
  New tutorials
  -------------
  
  Additions to the docs include a revamped :doc:`Tutorial 3</intro/tutorial03>`
  and a new :doc:`tutorial on testing</intro/tutorial05>`. A new section,
  "Advanced Tutorials", offers :doc:`How to write reusable apps
  </intro/reusable-apps>` as well as a step-by-step guide for new contributors in
  :doc:`Writing your first patch for Django </intro/contributing>`.
  
  Minor features
  --------------
  
  Django 1.5 also includes several smaller improvements worth noting:
  
  * The template engine now interprets ``True``, ``False`` and ``None`` as the
  corresponding Python objects.
  
  * :mod:`django.utils.timezone` provides a helper for converting aware
  datetimes between time zones. See :func:`~django.utils.timezone.localtime`.
  
  * The generic views support OPTIONS requests.
  
  * Management commands do not raise ``SystemExit`` any more when called by code
  from :func:`~django.core.management.call_command`. Any exception raised by
  the command (mostly :exc:`~django.core.management.CommandError`) is
  propagated.
  
  Moreover, when you output errors or messages in your custom commands, you
  should now use ``self.stdout.write('message')`` and
  ``self.stderr.write('error')`` (see the note on
  :ref:`management commands output <management-commands-output>`).
  
  * The :djadmin:`dumpdata` management command outputs one row at a time,
  preventing out-of-memory errors when dumping large datasets.
  
  * In the localflavor for Canada, "pq" was added to the acceptable codes for
  Quebec. It's an old abbreviation.
  
  * The :ref:`receiver <connecting-receiver-functions>` decorator is now able to
  connect to more than one signal by supplying a list of signals.
  
  * In the admin, you can now filter users by groups which they are members of.
  
  * :meth:`QuerySet.bulk_create()
  <django.db.models.query.QuerySet.bulk_create>` now has a batch_size
  argument. By default the batch_size is unlimited except for SQLite where
  single batch is limited so that 999 parameters per query isn't exceeded.
  
  * The :setting:`LOGIN_URL` and :setting:`LOGIN_REDIRECT_URL` settings now also
  accept view function names and
  :ref:`named URL patterns <naming-url-patterns>`. This allows you to reduce
  configuration duplication. More information can be found in the
  :func:`~django.contrib.auth.decorators.login_required` documentation.
  
  * Django now provides a mod_wsgi :doc:`auth handler
  </howto/deployment/wsgi/apache-auth>`.
  
  * The :meth:`QuerySet.delete() <django.db.models.query.QuerySet.delete>`
  and :meth:`Model.delete() <django.db.models.Model.delete()>` can now take
  fast-path in some cases. The fast-path allows for less queries and less
  objects fetched into memory. See :meth:`QuerySet.delete()
  <django.db.models.query.QuerySet.delete>` for details.
  
  * An instance of ``ResolverMatch`` is stored on the request as
  ``resolver_match``.
  
  * By default, all logging messages reaching the ``django`` logger when
  :setting:`DEBUG` is ``True`` are sent to the console (unless you redefine the
  logger in your :setting:`LOGGING` setting).
  
  * When using :class:`~django.template.RequestContext`, it is now possible to
  look up permissions by using ``{% if 'someapp.someperm' in perms %}``
  in templates.
  
  * It's not required any more to have ``404.html`` and ``500.html`` templates in
  the root templates directory. Django will output some basic error messages for
  both situations when those templates are not found. It's still recommended as
  good practice to provide those templates in order to present pretty error
  pages to the user.
  
  * :mod:`django.contrib.auth` provides a new signal that is emitted
  whenever a user fails to login successfully. See
  :data:`~django.contrib.auth.signals.user_login_failed`
  
  * The new :option:`loaddata --ignorenonexistent` option ignore data for fields
  that no longer exist.
  
  * :meth:`~django.test.SimpleTestCase.assertXMLEqual` and
  :meth:`~django.test.SimpleTestCase.assertXMLNotEqual` new assertions allow
  you to test equality for XML content at a semantic level, without caring for
  syntax differences (spaces, attribute order, etc.).
  
  * RemoteUserMiddleware now forces logout when the REMOTE_USER header
  disappears during the same browser session.
  
  * The :ref:`cache-based session backend <cached-sessions-backend>` can store
  session data in a non-default cache.
  
  * Multi-column indexes can now be created on models. Read the
  :attr:`~django.db.models.Options.index_together` documentation for more
  information.
  
  * During Django's logging configuration verbose Deprecation warnings are
  enabled and warnings are captured into the logging system. Logged warnings
  are routed through the ``console`` logging handler, which by default requires
  :setting:`DEBUG` to be True for output to be generated. The result is that
  DeprecationWarnings should be printed to the console in development
  environments the way they have been in Python versions < 2.7.
  
  * The API for :meth:`django.contrib.admin.ModelAdmin.message_user` method has
  been modified to accept additional arguments adding capabilities similar to
  :func:`django.contrib.messages.add_message`. This is useful for generating
  error messages from admin actions.
  
  * The admin's list filters can now be customized per-request thanks to the new
  :meth:`django.contrib.admin.ModelAdmin.get_list_filter` method.
  
  .. _backwards-incompatible-1.5:
  
  Backwards incompatible changes in 1.5
  =====================================
  
  .. warning::
  
  In addition to the changes outlined in this section, be sure to review the
  :ref:`deprecation plan <deprecation-removed-in-1.5>` for any features that
  have been removed. If you haven't updated your code within the
  deprecation timeline for a given feature, its removal may appear as a
  backwards incompatible change.
  
  ``ALLOWED_HOSTS`` required in production
  ----------------------------------------
  
  The new :setting:`ALLOWED_HOSTS` setting validates the request's ``Host``
  header and protects against host-poisoning attacks. This setting is now
  required whenever :setting:`DEBUG` is ``False``, or else
  :meth:`django.http.HttpRequest.get_host()` will raise
  :exc:`~django.core.exceptions.SuspiciousOperation`. For more details see the
  :setting:`full documentation<ALLOWED_HOSTS>` for the new setting.
  
  Managers on abstract models
  ---------------------------
  
  Abstract models are able to define a custom manager, and that manager
  :ref:`will be inherited by any concrete models extending the abstract model
  <custom-managers-and-inheritance>`. However, if you try to use the abstract
  model to call a method on the manager, an exception will now be raised.
  Previously, the call would have been permitted, but would have failed as soon
  as any database operation was attempted (usually with a "table does not exist"
  error from the database).
  
  If you have functionality on a manager that you have been invoking using
  the abstract class, you should migrate that logic to a Python
  ``staticmethod`` or ``classmethod`` on the abstract class.
  
  Context in year archive class-based views
  -----------------------------------------
  
  For consistency with the other date-based generic views,
  :class:`~django.views.generic.dates.YearArchiveView` now passes ``year`` in
  the context as a :class:`datetime.date` rather than a string.  If you are
  using ``{{ year }}`` in your templates, you must replace it with ``{{
  year|date:"Y" }}``.
  
  ``next_year`` and ``previous_year`` were also added in the context. They are
  calculated according to ``allow_empty`` and ``allow_future``.
  
  Context in year and month archive class-based views
  ---------------------------------------------------
  
  :class:`~django.views.generic.dates.YearArchiveView` and
  :class:`~django.views.generic.dates.MonthArchiveView` were documented to
  provide a ``date_list`` sorted in ascending order in the context, like their
  function-based predecessors, but it actually was in descending order. In 1.5,
  the documented order was restored. You may want to add (or remove) the
  ``reversed`` keyword when you're iterating on ``date_list`` in a template::
  
  {% for date in date_list reversed %}
  
  :class:`~django.views.generic.dates.ArchiveIndexView` still provides a
  ``date_list`` in descending order.
  
  Context in TemplateView
  -----------------------
  
  For consistency with the design of the other generic views,
  :class:`~django.views.generic.base.TemplateView` no longer passes a ``params``
  dictionary into the context, instead passing the variables from the URLconf
  directly into the context.
  
  Non-form data in HTTP requests
  ------------------------------
  
  :attr:`request.POST <django.http.HttpRequest.POST>` will no longer include data
  posted via HTTP requests with non form-specific content-types in the header.
  In prior versions, data posted with content-types other than
  :mimetype:`multipart/form-data` or
  :mimetype:`application/x-www-form-urlencoded` would still end up represented in
  the :attr:`request.POST <django.http.HttpRequest.POST>` attribute. Developers
  wishing to access the raw POST data for these cases, should use the
  :attr:`request.body <django.http.HttpRequest.body>` attribute instead.
  
  :data:`~django.core.signals.request_finished` signal
  ----------------------------------------------------
  
  Django used to send the :data:`~django.core.signals.request_finished` signal
  as soon as the view function returned a response. This interacted badly with
  :ref:`streaming responses <httpresponse-streaming>` that delay content
  generation.
  
  This signal is now sent after the content is fully consumed by the WSGI
  gateway. This might be backwards incompatible if you rely on the signal being
  fired before sending the response content to the client. If you do, you should
  consider using :doc:`middleware </topics/http/middleware>` instead.
  
  .. note::
  
  Some WSGI servers and middleware do not always call ``close`` on the
  response object after handling a request, most notably uWSGI prior to 1.2.6
  and Sentry's error reporting middleware up to 2.0.7. In those cases the
  ``request_finished`` signal isn't sent at all. This can result in idle
  connections to database and memcache servers.
  
  OPTIONS, PUT and DELETE requests in the test client
  ---------------------------------------------------
  
  Unlike GET and POST, these HTTP methods aren't implemented by web browsers.
  Rather, they're used in APIs, which transfer data in various formats such as
  JSON or XML. Since such requests may contain arbitrary data, Django doesn't
  attempt to decode their body.
  
  However, the test client used to build a query string for OPTIONS and DELETE
  requests like for GET, and a request body for PUT requests like for POST. This
  encoding was arbitrary and inconsistent with Django's behavior when it
  receives the requests, so it was removed in Django 1.5.
  
  If you were using the ``data`` parameter in an OPTIONS or a DELETE request,
  you must convert it to a query string and append it to the ``path`` parameter.
  
  If you were using the ``data`` parameter in a PUT request without a
  ``content_type``, you must encode your data before passing it to the test
  client and set the ``content_type`` argument.
  
  .. _simplejson-incompatibilities:
  
  System version of ``simplejson`` no longer used
  -----------------------------------------------
  
  :ref:`As explained below <simplejson-deprecation>`, Django 1.5 deprecates
  ``django.utils.simplejson`` in favor of Python 2.6's built-in :mod:`json`
  module. In theory, this change is harmless. Unfortunately, because of
  incompatibilities between versions of ``simplejson``, it may trigger errors
  in some circumstances.
  
  JSON-related features in Django 1.4 always used ``django.utils.simplejson``.
  This module was actually:
  
  - A system version of ``simplejson``, if one was available (ie. ``import
  simplejson`` works), if it was more recent than Django's built-in copy or it
  had the C speedups, or
  - The :mod:`json` module from the standard library, if it was available (ie.
  Python 2.6 or greater), or
  - A built-in copy of version 2.0.7 of ``simplejson``.
  
  In Django 1.5, those features use Python's :mod:`json` module, which is based
  on version 2.0.9 of ``simplejson``.
  
  There are no known incompatibilities between Django's copy of version 2.0.7 and
  Python's copy of version 2.0.9. However, there are some incompatibilities
  between other versions of ``simplejson``:
  
  - While the ``simplejson`` API is documented as always returning Unicode
  strings, the optional C implementation can return a bytestring. This was
  fixed in Python 2.7.
  - ``simplejson.JSONEncoder`` gained a ``namedtuple_as_object`` keyword
  argument in version 2.2.
  
  More information on these incompatibilities is available in
  :ticket:`ticket 18023 <18023comment:10>`.
  
  The net result is that, if you have installed ``simplejson`` and your code
  uses Django's serialization internals directly -- for instance
  ``django.core.serializers.json.DjangoJSONEncoder``, the switch from
  ``simplejson`` to :mod:`json` could break your code. (In general, changes to
  internals aren't documented; we're making an exception here.)
  
  At this point, the maintainers of Django believe that using :mod:`json` from
  the standard library offers the strongest guarantee of backwards-compatibility.
  They recommend to use it from now on.
  
  String types of hasher method parameters
  ----------------------------------------
  
  If you have written a :ref:`custom password hasher <auth_password_storage>`,
  your ``encode()``, ``verify()`` or ``safe_summary()`` methods should accept
  Unicode parameters (``password``, ``salt`` or ``encoded``). If any of the
  hashing methods need bytestrings, you can use the
  :func:`~django.utils.encoding.force_bytes` utility to encode the strings.
  
  Validation of previous_page_number and next_page_number
  -------------------------------------------------------
  
  When using :doc:`object pagination </topics/pagination>`,
  the ``previous_page_number()`` and ``next_page_number()`` methods of the
  :class:`~django.core.paginator.Page` object did not check if the returned
  number was inside the existing page range.
  It does check it now and raises an :exc:`~django.core.paginator.InvalidPage`
  exception when the number is either too low or too high.
  
  Behavior of autocommit database option on PostgreSQL changed
  ------------------------------------------------------------
  
  PostgreSQL's autocommit option didn't work as advertised previously. It did
  work for single transaction block, but after the first block was left the
  autocommit behavior was never restored. This bug is now fixed in 1.5. While
  this is only a bug fix, it is worth checking your applications behavior if
  you are using PostgreSQL together with the autocommit option.
  
  Session not saved on 500 responses
  ----------------------------------
  
  Django's session middleware will skip saving the session data if the
  response's status code is 500.
  
  Email checks on failed admin login
  ----------------------------------
  
  Prior to Django 1.5, if you attempted to log into the admin interface and
  mistakenly used your email address instead of your username, the admin
  interface would provide a warning advising that your email address was
  not your username. In Django 1.5, the introduction of
  :ref:`custom user models <auth-custom-user>` has required the removal of this
  warning. This doesn't change the login behavior of the admin site; it only
  affects the warning message that is displayed under one particular mode of
  login failure.
  
  Changes in tests execution
  --------------------------
  
  Some changes have been introduced in the execution of tests that might be
  backward-incompatible for some testing setups:
  
  Database flushing in ``django.test.TransactionTestCase``
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  Previously, the test database was truncated *before* each test run in a
  :class:`~django.test.TransactionTestCase`.
  
  In order to be able to run unit tests in any order and to make sure they are
  always isolated from each other, :class:`~django.test.TransactionTestCase` will
  now reset the database *after* each test run instead.
  
  No more implicit DB sequences reset
  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  
  :class:`~django.test.TransactionTestCase` tests used to reset primary key
  sequences automatically together with the database flushing actions described
  above.
  
  This has been changed so no sequences are implicitly reset. This can cause
  :class:`~django.test.TransactionTestCase` tests that depend on hard-coded
  primary key values to break.
  
  The new :attr:`~django.test.TransactionTestCase.reset_sequences` attribute can
  be used to force the old behavior for :class:`~django.test.TransactionTestCase`
  that might need it.
  
  Ordering of tests
  ~~~~~~~~~~~~~~~~~
  
  In order to make sure all ``TestCase`` code starts with a clean database,
  tests are now executed in the following order:
  
  * First, all unit tests (including :class:`unittest.TestCase`,
  :class:`~django.test.SimpleTestCase`, :class:`~django.test.TestCase` and
  :class:`~django.test.TransactionTestCase`) are run with no particular ordering
  guaranteed nor enforced among them.
  
  * Then any other tests (e.g. doctests) that may alter the database without
  restoring it to its original state are run.
  
  This should not cause any problems unless you have existing doctests which
  assume a :class:`~django.test.TransactionTestCase` executed earlier left some
  database state behind or unit tests that rely on some form of state being
  preserved after the execution of other tests. Such tests are already very
  fragile, and must now be changed to be able to run independently.
  
  ``cleaned_data`` dictionary kept for invalid forms
  --------------------------------------------------
  
  The :attr:`~django.forms.Form.cleaned_data` dictionary is now always present
  after form validation. When the form doesn't validate, it contains only the
  fields that passed validation. You should test the success of the validation
  with the :meth:`~django.forms.Form.is_valid()` method and not with the
  presence or absence of the :attr:`~django.forms.Form.cleaned_data` attribute
  on the form.
  
  Behavior of ``syncdb`` with multiple databases
  ----------------------------------------------
  
  ``syncdb`` now queries the database routers to determine if content
  types (when :mod:`~django.contrib.contenttypes` is enabled) and permissions
  (when :mod:`~django.contrib.auth` is enabled) should be created in the target
  database. Previously, it created them in the default database, even when
  another database was specified with the ``--database`` option.
  
  If you use ``syncdb`` on multiple databases, you should ensure that
  your routers allow synchronizing content types and permissions to only one of
  them. See the docs on the :ref:`behavior of contrib apps with multiple
  databases <contrib_app_multiple_databases>` for more information.
  
  XML deserializer will not parse documents with a DTD
  ----------------------------------------------------
  
  In order to prevent exposure to denial-of-service attacks related to external
  entity references and entity expansion, the XML model deserializer now refuses
  to parse XML documents containing a DTD (DOCTYPE definition). Since the XML
  serializer does not output a DTD, this will not impact typical usage, only
  cases where custom-created XML documents are passed to Django's model
  deserializer.
  
  Formsets default ``max_num``
  ----------------------------
  
  A (default) value of ``None`` for the ``max_num`` argument to a formset factory
  no longer defaults to allowing any number of forms in the formset. Instead, in
  order to prevent memory-exhaustion attacks, it now defaults to a limit of 1000
  forms. This limit can be raised by explicitly setting a higher value for
  ``max_num``.
  
  Miscellaneous
  -------------
  
  * :class:`django.forms.ModelMultipleChoiceField` now returns an empty
  ``QuerySet`` as the empty value instead of an empty list.
  
  * :func:`~django.utils.http.int_to_base36` properly raises a
  :exc:`TypeError` instead of :exc:`ValueError` for non-integer inputs.
  
  * The ``slugify`` template filter is now available as a standard Python
  function at :func:`django.utils.text.slugify`. Similarly, ``remove_tags`` is
  available at ``django.utils.html.remove_tags()``.
  
  * Uploaded files are no longer created as executable by default. If you need
  them to be executable change :setting:`FILE_UPLOAD_PERMISSIONS` to your
  needs. The new default value is ``0o666`` (octal) and the current umask value
  is first masked out.
  
  * The :class:`F expressions <django.db.models.F>` supported bitwise operators by
  ``&`` and ``|``. These operators are now available using ``.bitand()`` and
  ``.bitor()`` instead. The removal of ``&`` and ``|`` was done to be
  consistent with :ref:`Q() expressions <complex-lookups-with-q>` and
  ``QuerySet`` combining where the operators are used as boolean AND and OR
  operators.
  
  * In a ``filter()`` call, when :class:`F expressions <django.db.models.F>`
  contained lookups spanning multi-valued relations, they didn't always reuse
  the same relations as other lookups along the same chain. This was changed,
  and now F() expressions will always use the same relations as other lookups
  within the same ``filter()`` call.
  
  * The :ttag:`csrf_token` template tag is no longer enclosed in a div. If you need
  HTML validation against pre-HTML5 Strict DTDs, you should add a div around it
  in your pages.
  
  * The template tags library ``adminmedia``, which only contained the
  deprecated template tag ``{% admin_media_prefix %}``, was removed.
  Attempting to load it with ``{% load adminmedia %}`` will fail. If your
  templates still contain that line you must remove it.
  
  * Because of an implementation oversight, it was possible to use
  :doc:`django.contrib.redirects </ref/contrib/redirects>` without enabling
  :doc:`django.contrib.sites </ref/contrib/sites>`. This isn't allowed any
  longer. If you're using ``django.contrib.redirects``, make sure
  :setting:`INSTALLED_APPS` contains ``django.contrib.sites``.
  
  * :meth:`BoundField.label_tag <django.forms.BoundField.label_tag>` now
  escapes its ``contents`` argument. To avoid the HTML escaping, use
  :func:`django.utils.safestring.mark_safe` on the argument before passing it.
  
  * Accessing reverse one-to-one relations fetched via
  :meth:`~django.db.models.query.QuerySet.select_related` now raises
  :exc:`~django.db.models.Model.DoesNotExist` instead of returning ``None``.
  
  .. _deprecated-features-1.5:
  
  Features deprecated in 1.5
  ==========================
  
  ``django.contrib.localflavor``
  ------------------------------
  
  The localflavor contrib app has been split into separate packages.
  ``django.contrib.localflavor`` itself will be removed in Django 1.6,
  after an accelerated deprecation.
  
  The new packages are available on GitHub. The core team cannot
  efficiently maintain these packages in the long term — it spans just a
  dozen countries at this time; similar to translations, maintenance
  will be handed over to interested members of the community.
  
  ``django.contrib.markup``
  -------------------------
  
  The markup contrib module has been deprecated and will follow an accelerated
  deprecation schedule. Direct use of Python markup libraries or 3rd party tag
  libraries is preferred to Django maintaining this functionality in the
  framework.
  
  ``AUTH_PROFILE_MODULE``
  -----------------------
  
  With the introduction of :ref:`custom user models <auth-custom-user>`, there is
  no longer any need for a built-in mechanism to store user profile data.
  
  You can still define user profiles models that have a one-to-one relation with
  the User model - in fact, for many applications needing to associate data with
  a User account, this will be an appropriate design pattern to follow. However,
  the ``AUTH_PROFILE_MODULE`` setting, and the
  ``django.contrib.auth.models.User.get_profile()`` method for accessing
  the user profile model, should not be used any longer.
  
  Streaming behavior of :class:`~django.http.HttpResponse`
  --------------------------------------------------------
  
  Django 1.5 deprecates the ability to stream a response by passing an iterator
  to :class:`~django.http.HttpResponse`. If you rely on this behavior, switch to
  :class:`~django.http.StreamingHttpResponse`. See
  :ref:`explicit-streaming-responses` above.
  
  In Django 1.7 and above, the iterator will be consumed immediately by
  :class:`~django.http.HttpResponse`.
  
  .. _simplejson-deprecation:
  
  ``django.utils.simplejson``
  ---------------------------
  
  Since Django 1.5 drops support for Python 2.5, we can now rely on the
  :mod:`json` module being available in Python's standard library, so we've
  removed our own copy of ``simplejson``. You should now import :mod:`json`
  instead of ``django.utils.simplejson``.
  
  Unfortunately, this change might have unwanted side-effects, because of
  incompatibilities between versions of ``simplejson`` -- see the
  :ref:`backwards-incompatible changes <simplejson-incompatibilities>` section.
  If you rely on features added to ``simplejson`` after it became Python's
  :mod:`json`, you should import ``simplejson`` explicitly.
  
  ``django.utils.encoding.StrAndUnicode``
  ---------------------------------------
  
  The ``django.utils.encoding.StrAndUnicode`` mix-in has been deprecated.
  Define a ``__str__`` method and apply the
  ``django.utils.encoding.python_2_unicode_compatible`` decorator instead.
  
  ``django.utils.itercompat.product``
  -----------------------------------
  
  The ``django.utils.itercompat.product`` function has been deprecated. Use
  the built-in :func:`itertools.product` instead.
  
  ``cleanup`` management command
  ------------------------------
  
  The ``cleanup`` management command has been deprecated and replaced by
  :djadmin:`clearsessions`.
  
  ``daily_cleanup.py`` script
  ---------------------------
  
  The undocumented ``daily_cleanup.py`` script has been deprecated. Use the
  :djadmin:`clearsessions` management command instead.
  
  ``depth`` keyword argument in ``select_related``
  ------------------------------------------------
  
  The ``depth`` keyword argument in
  :meth:`~django.db.models.query.QuerySet.select_related` has been deprecated.
  You should use field names instead.
  
  
  ===========================

1.4.22 not secure

===========================
  
  *August 18, 2015*
  
  Django 1.4.22 fixes a security issue in 1.4.21.
  
  It also fixes support with pip 7+ by disabling wheel support. Older versions
  of 1.4 would silently build a broken wheel when installed with those versions
  of pip.
  
  Denial-of-service possibility in ``logout()`` view by filling session store
  ===========================================================================
  
  Previously, a session could be created when anonymously accessing the
  ``django.contrib.auth.views.logout()`` view (provided it wasn't decorated
  with :func:`~django.contrib.auth.decorators.login_required` as done in the
  admin). This could allow an attacker to easily create many new session records
  by sending repeated requests, potentially filling up the session store or
  causing other users' session records to be evicted.
  
  The :class:`~django.contrib.sessions.middleware.SessionMiddleware` has been
  modified to no longer create empty session records, including when
  :setting:`SESSION_SAVE_EVERY_REQUEST` is active.
  
  Additionally, the ``contrib.sessions.backends.base.SessionBase.flush()`` and
  ``cache_db.SessionStore.flush()`` methods have been modified to avoid creating
  a new empty session. Maintainers of third-party session backends should check
  if the same vulnerability is present in their backend and correct it if so.
  
  
  ===========================

1.4.21 not secure

===========================
  
  *July 8, 2015*
  
  Django 1.4.21 fixes several security issues in 1.4.20.
  
  Denial-of-service possibility by filling session store
  ======================================================
  
  In previous versions of Django, the session backends created a new empty record
  in the session storage anytime ``request.session`` was accessed and there was a
  session key provided in the request cookies that didn't already have a session
  record. This could allow an attacker to easily create many new session records
  simply by sending repeated requests with unknown session keys, potentially
  filling up the session store or causing other users' session records to be
  evicted.
  
  The built-in session backends now create a session record only if the session
  is actually modified; empty session records are not created. Thus this
  potential DoS is now only possible if the site chooses to expose a
  session-modifying view to anonymous users.
  
  As each built-in session backend was fixed separately (rather than a fix in the
  core sessions framework), maintainers of third-party session backends should
  check whether the same vulnerability is present in their backend and correct
  it if so.
  
  Header injection possibility since validators accept newlines in input
  ======================================================================
  
  Some of Django's built-in validators
  (:class:`~django.core.validators.EmailValidator`, most seriously) didn't
  prohibit newline characters (due to the usage of ``$`` instead of ``\Z`` in the
  regular expressions). If you use values with newlines in HTTP response or email
  headers, you can suffer from header injection attacks. Django itself isn't
  vulnerable because :class:`~django.http.HttpResponse` and the mail sending
  utilities in :mod:`django.core.mail` prohibit newlines in HTTP and SMTP
  headers, respectively. While the validators have been fixed in Django, if
  you're creating HTTP responses or email messages in other ways, it's a good
  idea to ensure that those methods prohibit newlines as well. You might also
  want to validate that any existing data in your application doesn't contain
  unexpected newlines.
  
  :func:`~django.core.validators.validate_ipv4_address`,
  :func:`~django.core.validators.validate_slug`, and
  :class:`~django.core.validators.URLValidator` and their usage in the
  corresponding form fields ``GenericIPAddresseField``, ``IPAddressField``,
  ``SlugField``, and ``URLField`` are also affected.
  
  The undocumented, internally unused ``validate_integer()`` function is now
  stricter as it validates using a regular expression instead of simply casting
  the value using ``int()`` and checking if an exception was raised.
  
  
  ===========================

1.4.20 not secure

===========================
  
  *March 18, 2015*
  
  Django 1.4.20 fixes one security issue in 1.4.19.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) accepted URLs with
  leading control characters and so considered URLs like ``\x08javascript:...``
  safe. This issue doesn't affect Django currently, since we only put this URL
  into the ``Location`` response header and browsers seem to ignore JavaScript
  there. Browsers we tested also treat URLs prefixed with control characters such
  as ``%08//example.com`` as relative paths so redirection to an unsafe target
  isn't a problem either.
  
  However, if a developer relies on ``is_safe_url()`` to
  provide safe redirect targets and puts such a URL into a link, they could
  suffer from an XSS attack as some browsers such as Google Chrome ignore control
  characters at the start of a URL in an anchor ``href``.
  
  
  ===========================

1.4.19 not secure

===========================
  
  *January 27, 2015*
  
  Django 1.4.19 fixes a regression in the 1.4.18 security release.
  
  Bugfixes
  ========
  
  * ``GZipMiddleware`` now supports streaming responses. As part of the 1.4.18
  security release, the ``django.views.static.serve()`` function was altered
  to stream the files it serves. Unfortunately, the ``GZipMiddleware`` consumed
  the stream prematurely and prevented files from being served properly
  (:ticket:`24158`).
  
  
  ===========================

1.4.18 not secure

===========================
  
  *January 13, 2015*
  
  Django 1.4.18 fixes several security issues in 1.4.17 as well as a regression
  on Python 2.5 in the 1.4.17 release.
  
  WSGI header spoofing via underscore/dash conflation
  ===================================================
  
  When HTTP headers are placed into the WSGI environ, they are normalized by
  converting to uppercase, converting all dashes to underscores, and prepending
  ``HTTP_``. For instance, a header ``X-Auth-User`` would become
  ``HTTP_X_AUTH_USER`` in the WSGI environ (and thus also in Django's
  ``request.META`` dictionary).
  
  Unfortunately, this means that the WSGI environ cannot distinguish between
  headers containing dashes and headers containing underscores: ``X-Auth-User``
  and ``X-Auth_User`` both become ``HTTP_X_AUTH_USER``. This means that if a
  header is used in a security-sensitive way (for instance, passing
  authentication information along from a front-end proxy), even if the proxy
  carefully strips any incoming value for ``X-Auth-User``, an attacker may be
  able to provide an ``X-Auth_User`` header (with underscore) and bypass this
  protection.
  
  In order to prevent such attacks, both Nginx and Apache 2.4+ strip all headers
  containing underscores from incoming requests by default. Django's built-in
  development server now does the same. Django's development server is not
  recommended for production use, but matching the behavior of common production
  servers reduces the surface area for behavior changes during deployment.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()`` and :doc:`i18n </topics/i18n/index>`)
  to redirect the user to an "on success" URL. The security checks for these
  redirects (namely ``django.utils.http.is_safe_url()``) didn't strip leading
  whitespace on the tested URL and as such considered URLs like
  ``\njavascript:...`` safe. If a developer relied on ``is_safe_url()`` to
  provide safe redirect targets and put such a URL into a link, they could suffer
  from a XSS attack. This bug doesn't affect Django currently, since we only put
  this URL into the ``Location`` response header and browsers seem to ignore
  JavaScript there.
  
  Denial-of-service attack against ``django.views.static.serve``
  ==============================================================
  
  In older versions of Django, the :func:`django.views.static.serve` view read
  the files it served one line at a time. Therefore, a big file with no newlines
  would result in memory usage equal to the size of that file. An attacker could
  exploit this and launch a denial-of-service attack by simultaneously requesting
  many large files. This view now reads the file in chunks to prevent large
  memory usage.
  
  Note, however, that this view has always carried a warning that it is not
  hardened for production use and should be used only as a development aid. Now
  may be a good time to audit your project and serve your files in production
  using a real front-end web server if you are not doing so.
  
  Bugfixes
  ========
  
  * To maintain compatibility with Python 2.5, Django's vendored version of six,
  ``django.utils.six``, has been downgraded to 1.8.0 which is the last
  version to support Python 2.5.
  
  
  ===========================

1.4.17 not secure

===========================
  
  *January 2, 2015*
  
  Django 1.4.17 fixes a regression in the 1.4.14 security release.
  
  Additionally, Django's vendored version of six, ``django.utils.six``, has
  been upgraded to the latest release (1.9.0).
  
  Bugfixes
  ========
  
  * Fixed a regression with dynamically generated inlines and allowed field
  references in the admin (:ticket:`23754`).
  
  
  ===========================

1.4.16 not secure

===========================
  
  *October 22, 2014*
  
  Django 1.4.16 fixes a couple regressions in the 1.4.14 security release and a
  bug preventing the use of some GEOS versions with GeoDjango.
  
  Bugfixes
  ========
  
  * Allowed related many-to-many fields to be referenced in the admin
  (:ticket:`23604`).
  
  * Allowed inline and hidden references to admin fields
  (:ticket:`23431`).
  
  * Fixed parsing of the GEOS version string
  (:ticket:`20036`).
  
  
  ===========================

1.4.15 not secure

===========================
  
  *September 2, 2014*
  
  Django 1.4.15 fixes a regression in the 1.4.14 security release.
  
  Bugfixes
  ========
  
  * Allowed inherited and m2m fields to be referenced in the admin
  (:ticket:`22486`)
  
  
  ===========================

1.4.14 not secure

===========================
  
  *August 20, 2014*
  
  Django 1.4.14 fixes several security issues in 1.4.13.
  
  ``reverse()`` could generate URLs pointing to other hosts
  =========================================================
  
  In certain situations, URL reversing could generate scheme-relative URLs  (URLs
  starting with two slashes), which could unexpectedly redirect a user  to a
  different host. An attacker could exploit this, for example, by redirecting
  users to a phishing site designed to ask for user's passwords.
  
  To remedy this, URL reversing now ensures that no URL starts with two slashes
  (//), replacing the second slash with its URL encoded counterpart (%2F). This
  approach ensures that semantics stay the same, while making the URL relative to
  the domain and not to the scheme.
  
  File upload denial-of-service
  =============================
  
  Before this release, Django's file upload handing in its default configuration
  may degrade to producing a huge number of ``os.stat()`` system calls when a
  duplicate filename is uploaded. Since ``stat()`` may invoke IO, this may produce
  a huge data-dependent slowdown that slowly worsens over time. The net result is
  that given enough time, a user with the ability to upload files can cause poor
  performance in the upload handler, eventually causing it to become very slow
  simply by uploading 0-byte files. At this point, even a slow network connection
  and few HTTP requests would be all that is necessary to make a site unavailable.
  
  We've remedied the issue by changing the algorithm for generating file names
  if a file with the uploaded name already exists.
  :meth:`Storage.get_available_name()
  <django.core.files.storage.Storage.get_available_name>` now appends an
  underscore plus a random 7 character alphanumeric string (e.g. ``"_x3a1gho"``),
  rather than iterating through an underscore followed by a number (e.g. ``"_1"``,
  ``"_2"``, etc.).
  
  ``RemoteUserMiddleware`` session hijacking
  ==========================================
  
  When using the :class:`~django.contrib.auth.middleware.RemoteUserMiddleware`
  and the ``RemoteUserBackend``, a change to the ``REMOTE_USER`` header between
  requests without an intervening logout could result in the prior user's session
  being co-opted by the subsequent user. The middleware now logs the user out on
  a failed login attempt.
  
  Data leakage via query string manipulation in ``contrib.admin``
  ===============================================================
  
  In older versions of Django it was possible to reveal any field's data by
  modifying the "popup" and "to_field" parameters of the query string on an admin
  change form page. For example, requesting a URL like
  ``/admin/auth/user/?pop=1&t=password`` and viewing the page's HTML allowed
  viewing the password hash of each user. While the admin requires users to have
  permissions to view the change form pages in the first place, this could leak
  data if you rely on users having access to view only certain fields on a model.
  
  To address the issue, an exception will now be raised if a ``to_field`` value
  that isn't a related field to a model that has been registered with the admin
  is specified.
  
  
  ===========================

1.4.13 not secure

===========================
  
  *May 14, 2014*
  
  Django 1.4.13 fixes two security issues in 1.4.12.
  
  Caches may incorrectly be allowed to store and serve private data
  =================================================================
  
  In certain situations, Django may allow caches to store private data
  related to a particular session and then serve that data to requests
  with a different session, or no session at all. This can lead to
  information disclosure and can be a vector for cache poisoning.
  
  When using Django sessions, Django will set a ``Vary: Cookie`` header to
  ensure caches do not serve cached data to requests from other sessions.
  However, older versions of Internet Explorer (most likely only Internet
  Explorer 6, and Internet Explorer 7 if run on Windows XP or Windows Server
  2003) are unable to handle the ``Vary`` header in combination with many content
  types. Therefore, Django would remove the header if the request was made by
  Internet Explorer.
  
  To remedy this, the special behavior for these older Internet Explorer versions
  has been removed, and the ``Vary`` header is no longer stripped from the response.
  In addition, modifications to the ``Cache-Control`` header for all Internet Explorer
  requests with a ``Content-Disposition`` header have also been removed as they
  were found to have similar issues.
  
  Malformed redirect URLs from user input not correctly validated
  ===============================================================
  
  The validation for redirects did not correctly validate some malformed URLs,
  which are accepted by some browsers. This allows a user to be redirected to
  an unsafe URL unexpectedly.
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()``, ``django.contrib.comments``, and
  :doc:`i18n </topics/i18n/index>`) to redirect the user to an "on success" URL.
  The security checks for these redirects (namely
  ``django.utils.http.is_safe_url()``) did not correctly validate some malformed
  URLs, such as ``http:\\\\\\djangoproject.com``, which are accepted by some
  browsers with more liberal URL parsing.
  
  To remedy this, the validation in ``is_safe_url()`` has been tightened to be able
  to handle and correctly validate these malformed URLs.
  
  
  ===========================

1.4.12 not secure

===========================
  
  *April 28, 2014*
  
  Django 1.4.12 fixes a regression in the 1.4.11 security release.
  
  Bugfixes
  ========
  
  * Restored the ability to ``reverse()`` views created using
  :func:`functools.partial()` (:ticket:`22486`).
  
  
  ===========================

1.4.11 not secure

===========================
  
  *April 21, 2014*
  
  Django 1.4.11 fixes three security issues in 1.4.10. Additionally,
  Django's vendored version of six, ``django.utils.six``, has been
  upgraded to the latest release (1.6.1).
  
  Unexpected code execution using ``reverse()``
  =============================================
  
  Django's URL handling is based on a mapping of regex patterns
  (representing the URLs) to callable views, and Django's own processing
  consists of matching a requested URL against those patterns to
  determine the appropriate view to invoke.
  
  Django also provides a convenience function -- ``reverse()`` -- which performs
  this process in the opposite direction. The ``reverse()`` function takes
  information about a view and returns a URL which would invoke that view. Use
  of ``reverse()`` is encouraged for application developers, as the output of
  ``reverse()`` is always based on the current URL patterns, meaning developers
  do not need to change other code when making changes to URLs.
  
  One argument signature for ``reverse()`` is to pass a dotted Python
  path to the desired view. In this situation, Django will import the
  module indicated by that dotted path as part of generating the
  resulting URL. If such a module has import-time side effects, those
  side effects will occur.
  
  Thus it is possible for an attacker to cause unexpected code
  execution, given the following conditions:
  
  1. One or more views are present which construct a URL based on user
  input (commonly, a "next" parameter in a querystring indicating
  where to redirect upon successful completion of an action).
  
  2. One or more modules are known to an attacker to exist on the
  server's Python import path, which perform code execution with side
  effects on importing.
  
  To remedy this, ``reverse()`` will now only accept and import dotted
  paths based on the view-containing modules listed in the project's :doc:`URL
  pattern configuration </topics/http/urls>`, so as to ensure that only modules
  the developer intended to be imported in this fashion can or will be imported.
  
  Caching of anonymous pages could reveal CSRF token
  ==================================================
  
  Django includes both a :doc:`caching framework </topics/cache>` and a system
  for :doc:`preventing cross-site request forgery (CSRF) attacks
  </ref/csrf/>`. The CSRF-protection system is based on a random nonce
  sent to the client in a cookie which must be sent by the client on future
  requests and, in forms, a hidden value which must be submitted back with the
  form.
  
  The caching framework includes an option to cache responses to
  anonymous (i.e., unauthenticated) clients.
  
  When the first anonymous request to a given page is by a client which
  did not have a CSRF cookie, the cache framework will also cache the
  CSRF cookie and serve the same nonce to other anonymous clients who
  do not have a CSRF cookie. This can allow an attacker to obtain a
  valid CSRF cookie value and perform attacks which bypass the check for
  the cookie.
  
  To remedy this, the caching framework will no longer cache such
  responses. The heuristic for this will be:
  
  1. If the incoming request did not submit any cookies, and
  
  2. If the response did send one or more cookies, and
  
  3. If the ``Vary: Cookie`` header is set on the response, then the
  response will not be cached.
  
  MySQL typecasting
  =================
  
  The MySQL database is known to "typecast" on certain queries; for
  example, when querying a table which contains string values, but using
  a query which filters based on an integer value, MySQL will first
  silently coerce the strings to integers and return a result based on that.
  
  If a query is performed without first converting values to the
  appropriate type, this can produce unexpected results, similar to what
  would occur if the query itself had been manipulated.
  
  Django's model field classes are aware of their own types and most
  such classes perform explicit conversion of query arguments to the
  correct database-level type before querying. However, three model
  field classes did not correctly convert their arguments:
  
  * :class:`~django.db.models.FilePathField`
  * :class:`~django.db.models.GenericIPAddressField`
  * ``IPAddressField``
  
  These three fields have been updated to convert their arguments to the
  correct types before querying.
  
  Additionally, developers of custom model fields are now warned via
  documentation to ensure their custom field classes will perform
  appropriate type conversions, and users of the :meth:`raw()
  <django.db.models.query.QuerySet.raw>` and :meth:`extra()
  <django.db.models.query.QuerySet.extra>` query methods -- which allow the
  developer to supply raw SQL or SQL fragments -- will be advised to ensure they
  perform appropriate manual type conversions prior to executing queries.
  
  
  ===========================

1.4.10 not secure

===========================
  
  *November 6, 2013*
  
  Django 1.4.10 fixes a Python-compatibility bug in the 1.4 series.
  
  Python compatibility
  ====================
  
  Django 1.4.9 inadvertently introduced issues with Python 2.5 compatibility.
  Django 1.4.10 restores Python 2.5 compatibility. This was issue 21362 in
  Django's Trac.
  
  
  ==========================

1.4.9 not secure

==========================
  
  *October 23, 2013*
  
  Django 1.4.9 fixes a security-related bug in the 1.4 series and one other
  data corruption bug.
  
  Readdressed denial-of-service via password hashers
  ==================================================
  
  Django 1.4.8 imposes a 4096-byte limit on passwords in order to mitigate a
  denial-of-service attack through submission of bogus but extremely large
  passwords. In Django 1.4.9, we've reverted this change and instead improved
  the speed of our PBKDF2 algorithm by not rehashing the key on every iteration.
  
  Bugfixes
  ========
  
  * Fixed a data corruption bug with ``datetime_safe.datetime.combine`` (21256).
  
  
  ==========================

1.4.8 not secure

==========================
  
  *September 14, 2013*
  
  Django 1.4.8 fixes two security issues present in previous Django releases in
  the 1.4 series.
  
  Denial-of-service via password hashers
  ======================================
  
  In previous versions of Django, no limit was imposed on the plaintext
  length of a password. This allowed a denial-of-service attack through
  submission of bogus but extremely large passwords, tying up server
  resources performing the (expensive, and increasingly expensive with
  the length of the password) calculation of the corresponding hash.
  
  As of 1.4.8, Django's authentication framework imposes a 4096-byte
  limit on passwords and will fail authentication with any submitted
  password of greater length.
  
  Corrected usage of :func:`~django.views.decorators.debug.sensitive_post_parameters` in :mod:`django.contrib.auth`’s admin
  =========================================================================================================================
  
  The decoration of the ``add_view`` and ``user_change_password`` user admin
  views with :func:`~django.views.decorators.debug.sensitive_post_parameters`
  did not include :func:`~django.utils.decorators.method_decorator` (required
  since the views are methods) resulting in the decorator not being properly
  applied. This usage has been fixed and
  :func:`~django.views.decorators.debug.sensitive_post_parameters` will now
  throw an exception if it's improperly used.
  
  
  ==========================

1.4.7 not secure

==========================
  
  *September 10, 2013*
  
  Django 1.4.7 fixes one security issue present in previous Django releases in
  the 1.4 series.
  
  Directory traversal vulnerability in ``ssi`` template tag
  =========================================================
  
  In previous versions of Django it was possible to bypass the
  ``ALLOWED_INCLUDE_ROOTS`` setting used for security with the ``ssi``
  template tag by specifying a relative path that starts with one of the allowed
  roots. For example, if ``ALLOWED_INCLUDE_ROOTS = ("/var/www",)`` the following
  would be possible:
  
  .. code-block:: html+django
  
  {% ssi "/var/www/../../etc/passwd" %}
  
  In practice this is not a very common problem, as it would require the template
  author to put the ``ssi`` file in a user-controlled variable, but it's
  possible in principle.
  
  
  ==========================

1.4.6 not secure

==========================
  
  *August 13, 2013*
  
  Django 1.4.6 fixes one security issue present in previous Django releases in
  the 1.4 series, as well as one other bug.
  
  This is the sixth bugfix/security release in the Django 1.4 series.
  
  Mitigated possible XSS attack via user-supplied redirect URLs
  =============================================================
  
  Django relies on user input in some cases (e.g.
  ``django.contrib.auth.views.login()``, ``django.contrib.comments``, and
  :doc:`i18n </topics/i18n/index>`) to redirect the user to an "on success" URL.
  The security checks for these redirects (namely
  ``django.utils.http.is_safe_url()``) didn't check if the scheme is ``http(s)``
  and as such allowed ``javascript:...`` URLs to be entered. If a developer
  relied on ``is_safe_url()`` to provide safe redirect targets and put such a
  URL into a link, they could suffer from a XSS attack. This bug doesn't affect
  Django currently, since we only put this URL into the ``Location`` response
  header and browsers seem to ignore JavaScript there.
  
  Bugfixes
  ========
  
  * Fixed an obscure bug with the :func:`~django.test.override_settings`
  decorator. If you hit an ``AttributeError: 'Settings' object has no attribute
  '_original_allowed_hosts'`` exception, it's probably fixed (20636).
  
  
  ==========================

1.4.5 not secure

==========================
  
  *February 20, 2013*
  
  Django 1.4.5 corrects a packaging problem with yesterday's :doc:`1.4.4 release
  </releases/1.4.4>`.
  
  The release contained stray ``.pyc`` files that caused "bad magic number"
  errors when running with some versions of Python. This releases corrects this,
  and also fixes a bad documentation link in the project template ``settings.py``
  file generated by ``manage.py startproject``.
  
  
  ==========================

1.4.4 not secure

==========================
  
  *February 19, 2013*
  
  Django 1.4.4 fixes four security issues present in previous Django releases in
  the 1.4 series, as well as several other bugs and numerous documentation
  improvements.
  
  This is the fourth bugfix/security release in the Django 1.4 series.
  
  
  Host header poisoning
  =====================
  
  Some parts of Django -- independent of end-user-written applications -- make
  use of full URLs, including domain name, which are generated from the HTTP Host
  header. Django's documentation has for some time contained notes advising users
  on how to configure Web servers to ensure that only valid Host headers can reach
  the Django application. However, it has been reported to us that even with the
  recommended Web server configurations there are still techniques available for
  tricking many common Web servers into supplying the application with an
  incorrect and possibly malicious Host header.
  
  For this reason, Django 1.4.4 adds a new setting, ``ALLOWED_HOSTS``, containing
  an explicit list of valid host/domain names for this site. A request with a
  Host header not matching an entry in this list will raise
  ``SuspiciousOperation`` if ``request.get_host()`` is called. For full details
  see the documentation for the :setting:`ALLOWED_HOSTS` setting.
  
  The default value for this setting in Django 1.4.4 is ``['*']`` (matching any
  host), for backwards-compatibility, but we strongly encourage all sites to set
  a more restrictive value.
  
  This host validation is disabled when ``DEBUG`` is ``True`` or when running tests.
  
  
  XML deserialization
  ===================
  
  The XML parser in the Python standard library is vulnerable to a number of
  attacks via external entities and entity expansion. Django uses this parser for
  deserializing XML-formatted database fixtures. This deserializer is not
  intended for use with untrusted data, but in order to err on the side of safety
  in Django 1.4.4 the XML deserializer refuses to parse an XML document with a
  DTD (DOCTYPE definition), which closes off these attack avenues.
  
  These issues in the Python standard library are CVE-2013-1664 and
  CVE-2013-1665. More information available `from the Python security team`_.
  
  Django's XML serializer does not create documents with a DTD, so this should
  not cause any issues with the typical round-trip from ``dumpdata`` to
  ``loaddata``, but if you feed your own XML documents to the ``loaddata``
  management command, you will need to ensure they do not contain a DTD.
  
  .. _from the Python security team: https://blog.python.org/2013/02/announcing-defusedxml-fixes-for-xml.html
  
  
  Formset memory exhaustion
  =========================
  
  Previous versions of Django did not validate or limit the form-count data
  provided by the client in a formset's management form, making it possible to
  exhaust a server's available memory by forcing it to create very large numbers
  of forms.
  
  In Django 1.4.4, all formsets have a strictly-enforced maximum number of forms
  (1000 by default, though it can be set higher via the ``max_num`` formset
  factory argument).
  
  
  Admin history view information leakage
  ======================================
  
  In previous versions of Django, an admin user without change permission on a
  model could still view the Unicode representation of instances via their admin
  history log. Django 1.4.4 now limits the admin history log view for an object
  to users with change permission for that model.
  
  
  Other bugfixes and changes
  ==========================
  
  * Prevented transaction state from leaking from one request to the next (19707).
  * Changed an SQL command syntax to be MySQL 4 compatible (19702).
  * Added backwards-compatibility with old unsalted MD5 passwords (18144).
  * Numerous documentation improvements and fixes.
  
  
  ==========================

1.4.3 not secure

==========================
  
  *December 10, 2012*
  
  Django 1.4.3 addresses two security issues present in previous Django releases
  in the 1.4 series.
  
  Please be aware that this security release is slightly different from previous
  ones. Both issues addressed here have been dealt with in prior security updates
  to Django. In one case, we have received ongoing reports of problems, and in
  the other we've chosen to take further steps to tighten up Django's code in
  response to independent discovery of potential problems from multiple sources.
  
  Host header poisoning
  =====================
  
  Several earlier Django security releases focused on the issue of poisoning the
  HTTP Host header, causing Django to generate URLs pointing to arbitrary,
  potentially-malicious domains.
  
  In response to further input received and reports of continuing issues
  following the previous release, we're taking additional steps to tighten Host
  header validation. Rather than attempt to accommodate all features HTTP
  supports here, Django's Host header validation attempts to support a smaller,
  but far more common, subset:
  
  * Hostnames must consist of characters ``[A-Za-z0-9]`` plus hyphen ('-') or dot
  ('.').
  * IP addresses -- both IPv4 and IPv6 -- are permitted.
  * Port, if specified, is numeric.
  
  Any deviation from this will now be rejected, raising the exception
  :exc:`django.core.exceptions.SuspiciousOperation`.
  
  Redirect poisoning
  ==================
  
  Also following up on a previous issue: in July of this year, we made changes to
  Django's HTTP redirect classes, performing additional validation of the scheme
  of the URL to redirect to (since, both within Django's own supplied
  applications and many third-party applications, accepting a user-supplied
  redirect target is a common pattern).
  
  Since then, two independent audits of the code turned up further potential
  problems. So, similar to the Host-header issue, we are taking steps to provide
  tighter validation in response to reported problems (primarily with third-party
  applications, but to a certain extent also within Django itself). This comes in
  two parts:
  
  1. A new utility function, ``django.utils.http.is_safe_url``, is added; this
  function takes a URL and a hostname, and checks that the URL is either
  relative, or if absolute matches the supplied hostname. This function is
  intended for use whenever user-supplied redirect targets are accepted, to
  ensure that such redirects cannot lead to arbitrary third-party sites.
  
  2. All of Django's own built-in views -- primarily in the authentication system
  -- which allow user-supplied redirect targets now use ``is_safe_url`` to
  validate the supplied URL.
  
  
  ==========================

1.4.2 not secure

==========================
  
  *October 17, 2012*
  
  This is the second security release in the Django 1.4 series.
  
  Host header poisoning
  =====================
  
  Some parts of Django -- independent of end-user-written applications -- make
  use of full URLs, including domain name, which are generated from the HTTP Host
  header. Some attacks against this are beyond Django's ability to control, and
  require the web server to be properly configured; Django's documentation has
  for some time contained notes advising users on such configuration.
  
  Django's own built-in parsing of the Host header is, however, still vulnerable,
  as was reported to us recently. The Host header parsing in Django 1.3.3 and
  Django 1.4.1 -- specifically, ``django.http.HttpRequest.get_host()`` -- was
  incorrectly handling username/password information in the header. Thus, for
  example, the following Host header would be accepted by Django when running on
  "validsite.com"::
  
  Host: validsite.com:randomevilsite.com
  
  Using this, an attacker can cause parts of Django -- particularly the
  password-reset mechanism -- to generate and display arbitrary URLs to users.
  
  To remedy this, the parsing in ``HttpRequest.get_host()`` is being modified;
  Host headers which contain potentially dangerous content (such as
  username/password pairs) now raise the exception
  :exc:`django.core.exceptions.SuspiciousOperation`.
  
  Details of this issue were initially posted online as a `security advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2012/oct/17/security/
  
  Backwards incompatible changes
  ==============================
  
  * The newly introduced :class:`~django.db.models.GenericIPAddressField`
  constructor arguments have been adapted to match those of all other model
  fields. The first two keyword arguments are now verbose_name and name.
  
  Other bugfixes and changes
  ==========================
  
  * Subclass HTMLParser only for appropriate Python versions (18239).
  * Added batch_size argument to qs.bulk_create() (17788).
  * Fixed a small regression in the admin filters where wrongly formatted dates passed as url parameters caused an unhandled ValidationError (18530).
  * Fixed an endless loop bug when accessing permissions in templates (18979)
  * Fixed some Python 2.5 compatibility issues
  * Fixed an issue with quoted filenames in Content-Disposition header (19006)
  * Made the context option in ``trans`` and ``blocktrans`` tags accept literals wrapped in single quotes (18881).
  * Numerous documentation improvements and fixes.
  
  
  ==========================

1.4.1 not secure

==========================
  
  *July 30, 2012*
  
  This is the first security release in the Django 1.4 series, fixing several
  security issues in Django 1.4. Django 1.4.1 is a recommended upgrade for
  all users of Django 1.4.
  
  For a full list of issues addressed in this release, see the `security
  advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2012/jul/30/security-releases-issued/
  
  
  ========================

1.4 not secure

========================
  
  *March 23, 2012*
  
  Welcome to Django 1.4!
  
  These release notes cover the :ref:`new features <whats-new-1.4>`, as well as
  some :ref:`backwards incompatible changes <backwards-incompatible-1.4>` you'll
  want to be aware of when upgrading from Django 1.3 or older versions. We've
  also dropped some features, which are detailed in :ref:`our deprecation plan
  <deprecation-removed-in-1.4>`, and we've :ref:`begun the deprecation process
  for some features <deprecated-features-1.4>`.
  
  Overview
  ========
  
  The biggest new feature in Django 1.4 is `support for time zones`_ when
  handling date/times. When enabled, this Django will store date/times in UTC,
  use timezone-aware objects internally, and translate them to users' local
  timezones for display.
  
  If you're upgrading an existing project to Django 1.4, switching to the timezone
  aware mode may take some care: the new mode disallows some rather sloppy
  behavior that used to be accepted. We encourage anyone who's upgrading to check
  out the :ref:`timezone migration guide <time-zones-migration-guide>` and the
  :ref:`timezone FAQ <time-zones-faq>` for useful pointers.
  
  Other notable new features in Django 1.4 include:
  
  * A number of ORM improvements, including `SELECT FOR UPDATE support`_,
  the ability to `bulk insert <model-objects-bulk-create-in-the-orm>`_
  large datasets for improved performance, and
  `QuerySet.prefetch_related`_, a method to batch-load related objects
  in areas where :meth:`~django.db.models.query.QuerySet.select_related`
  doesn't work.
  
  * Some nice security additions, including `improved password hashing`_
  (featuring PBKDF2_ and bcrypt_ support), new `tools for cryptographic
  signing`_, several `CSRF improvements`_, and `simple clickjacking
  protection`_.
  
  * An `updated default project layout and manage.py`_ that removes the "magic"
  from prior versions. And for those who don't like the new layout, you can
  use `custom project and app templates`_ instead!
  
  * `Support for in-browser testing frameworks`_ (like Selenium_).
  
  * ... and a whole lot more; `see below <what-s-new-in-django-1-4>`_!
  
  Wherever possible we try to introduce new features in a backwards-compatible
  manner per :doc:`our API stability policy </misc/api-stability>` policy.
  However, as with previous releases, Django 1.4 ships with some minor
  :ref:`backwards incompatible changes <backwards-incompatible-1.4>`; people
  upgrading from previous versions of Django should read that list carefully.
  
  Python compatibility
  ====================
  
  Django 1.4 has dropped support for Python 2.4. Python 2.5 is now the minimum
  required Python version. Django is tested and supported on Python 2.5, 2.6 and
  2.7.
  
  This change should affect only a small number of Django users, as most
  operating-system vendors today are shipping Python 2.5 or newer as their default
  version. If you're still using Python 2.4, however, you'll need to stick to
  Django 1.3 until you can upgrade. Per :doc:`our support policy
  </internals/release-process>`, Django 1.3 will continue to receive security
  support until the release of Django 1.5.
  
  Django does not support Python 3.x at this time. At some point before the
  release of Django 1.4, we plan to publish a document outlining our full
  timeline for deprecating Python 2.x and moving to Python 3.x.
  
  .. _whats-new-1.4:
  
  What's new in Django 1.4
  ========================
  
  Support for time zones
  ----------------------
  
  In previous versions, Django used "naive" date/times (that is, date/times
  without an associated time zone), leaving it up to each developer to interpret
  what a given date/time "really means". This can cause all sorts of subtle
  timezone-related bugs.
  
  In Django 1.4, you can now switch Django into a more correct, time-zone aware
  mode. In this mode, Django stores date and  time information in UTC in the
  database, uses time-zone-aware datetime objects internally and translates them
  to the end user's time zone in templates and forms. Reasons for using this
  feature include:
  
  - Customizing date and time display for users around the world.
  
  - Storing datetimes in UTC for database portability and interoperability.
  (This argument doesn't apply to PostgreSQL, because it already stores
  timestamps with time zone information in Django 1.3.)
  
  - Avoiding data corruption problems around DST transitions.
  
  Time zone support is enabled by default in new projects created with
  :djadmin:`startproject`. If you want to use this feature in an existing
  project, read the :ref:`migration guide <time-zones-migration-guide>`. If you
  encounter problems, there's a helpful :ref:`FAQ <time-zones-faq>`.
  
  Support for in-browser testing frameworks
  -----------------------------------------
  
  Django 1.4 supports integration with in-browser testing frameworks like
  Selenium_. The new :class:`django.test.LiveServerTestCase` base class lets you
  test the interactions between your site's front and back ends more
  comprehensively. See the
  :class:`documentation<django.test.LiveServerTestCase>` for more details and
  concrete examples.
  
  .. _Selenium: https://selenium.dev/
  
  Updated default project layout and ``manage.py``
  ------------------------------------------------
  
  Django 1.4 ships with an updated default project layout and ``manage.py`` file
  for the :djadmin:`startproject` management command. These fix some issues with
  the previous ``manage.py`` handling of Python import paths that caused double
  imports, trouble moving from development to deployment, and other
  difficult-to-debug path issues.
  
  The previous ``manage.py`` called functions that are now deprecated, and thus
  projects upgrading to Django 1.4 should update their ``manage.py``. (The
  old-style ``manage.py`` will continue to work as before until Django 1.6. In
  1.5 it will raise ``DeprecationWarning``).
  
  The new recommended ``manage.py`` file should look like this::
  
  !/usr/bin/env python
  import os, sys
  
  if __name__ == "__main__":
  os.environ.setdefault("DJANGO_SETTINGS_MODULE", "{{ project_name }}.settings")
  
  from django.core.management import execute_from_command_line
  
  execute_from_command_line(sys.argv)
  
  ``{{ project_name }}`` should be replaced with the Python package name of the
  actual project.
  
  If settings, URLconfs and apps within the project are imported or referenced
  using the project name prefix (e.g. ``myproject.settings``, ``ROOT_URLCONF =
  "myproject.urls"``, etc.), the new ``manage.py`` will need to be moved one
  directory up, so it is outside the project package rather than adjacent to
  ``settings.py`` and ``urls.py``.
  
  For instance, with the following layout::
  
  manage.py
  mysite/
  __init__.py
  settings.py
  urls.py
  myapp/
  __init__.py
  models.py
  
  You could import ``mysite.settings``, ``mysite.urls``, and ``mysite.myapp``,
  but not ``settings``, ``urls``, or ``myapp`` as top-level modules.
  
  Anything imported as a top-level module can be placed adjacent to the new
  ``manage.py``. For instance, to decouple "myapp" from the project module and
  import it as just ``myapp``, place it outside the ``mysite/`` directory::
  
  manage.py
  myapp/
  __init__.py
  models.py
  mysite/
  __init__.py
  settings.py
  urls.py
  
  If the same code is imported inconsistently (some places with the project
  prefix, some places without it), the imports will need to be cleaned up when
  switching to the new ``manage.py``.
  
  Custom project and app templates
  --------------------------------
  
  The :djadmin:`startapp` and :djadmin:`startproject` management commands
  now have a ``--template`` option for specifying a path or URL to a custom app
  or project template.
  
  For example, Django will use the ``/path/to/my_project_template`` directory
  when you run the following command::
  
  django-admin.py startproject --template=/path/to/my_project_template myproject
  
  You can also now provide a destination directory as the second
  argument to both :djadmin:`startapp` and :djadmin:`startproject`::
  
  django-admin.py startapp myapp /path/to/new/app
  django-admin.py startproject myproject /path/to/new/project
  
  For more information, see the :djadmin:`startapp` and :djadmin:`startproject`
  documentation.
  
  Improved WSGI support
  ---------------------
  
  The :djadmin:`startproject` management command now adds a :file:`wsgi.py`
  module to the initial project layout, containing a simple WSGI application that
  can be used for :doc:`deploying with WSGI app
  servers</howto/deployment/wsgi/index>`.
  
  The :djadmin:`built-in development server<runserver>` now supports using an
  externally-defined WSGI callable, which makes it possible to run ``runserver``
  with the same WSGI configuration that is used for deployment. The new
  :setting:`WSGI_APPLICATION` setting lets you configure which WSGI callable
  :djadmin:`runserver` uses.
  
  (The ``runfcgi`` management command also internally wraps the WSGI
  callable configured via :setting:`WSGI_APPLICATION`.)
  
  ``SELECT FOR UPDATE`` support
  -----------------------------
  
  Django 1.4 includes a :meth:`QuerySet.select_for_update()
  <django.db.models.query.QuerySet.select_for_update>` method, which generates a
  ``SELECT ... FOR UPDATE`` SQL query. This will lock rows until the end of the
  transaction, meaning other transactions cannot modify or delete rows matched by
  a ``FOR UPDATE`` query.
  
  For more details, see the documentation for
  :meth:`~django.db.models.query.QuerySet.select_for_update`.
  
  ``Model.objects.bulk_create`` in the ORM
  ----------------------------------------
  
  This method lets you create multiple objects more efficiently. It can result in
  significant performance increases if you have many objects.
  
  Django makes use of this internally, meaning some operations (such as database
  setup for test suites) have seen a performance benefit as a result.
  
  See the :meth:`~django.db.models.query.QuerySet.bulk_create` docs for more
  information.
  
  ``QuerySet.prefetch_related``
  -----------------------------
  
  Similar to :meth:`~django.db.models.query.QuerySet.select_related` but with a
  different strategy and broader scope,
  :meth:`~django.db.models.query.QuerySet.prefetch_related` has been added to
  :class:`~django.db.models.query.QuerySet`. This method returns a new
  ``QuerySet`` that will prefetch each of the specified related lookups in a
  single batch as soon as the query begins to be evaluated. Unlike
  ``select_related``, it does the joins in Python, not in the database, and
  supports many-to-many relationships, ``GenericForeignKey`` and more. This
  allows you to fix a very common performance problem in which your code ends up
  doing O(n) database queries (or worse) if objects on your primary ``QuerySet``
  each have many related objects that you also need to fetch.
  
  Improved password hashing
  -------------------------
  
  Django's auth system (``django.contrib.auth``) stores passwords using a one-way
  algorithm. Django 1.3 uses the SHA1_ algorithm, but increasing processor speeds
  and theoretical attacks have revealed that SHA1 isn't as secure as we'd like.
  Thus, Django 1.4 introduces a new password storage system: by default Django now
  uses the PBKDF2_ algorithm (as recommended by NIST_). You can also easily choose
  a different algorithm (including the popular bcrypt_ algorithm). For more
  details, see :ref:`auth_password_storage`.
  
  .. _sha1: https://en.wikipedia.org/wiki/SHA1
  .. _pbkdf2: https://en.wikipedia.org/wiki/PBKDF2
  .. _nist: https://csrc.nist.gov/publications/detail/sp/800-132/final
  .. _bcrypt: https://en.wikipedia.org/wiki/Bcrypt
  
  HTML5 doctype
  -------------
  
  We've switched the admin and other bundled templates to use the HTML5
  doctype. While Django will be careful to maintain compatibility with older
  browsers, this change means that you can use any HTML5 features you need in
  admin pages without having to lose HTML validity or override the provided
  templates to change the doctype.
  
  List filters in admin interface
  -------------------------------
  
  Prior to Django 1.4, the :mod:`~django.contrib.admin` app let you specify
  change list filters by specifying a field lookup, but it didn't allow you to
  create custom filters. This has been rectified with a simple API (previously
  used internally and known as "FilterSpec"). For more details, see the
  documentation for :attr:`~django.contrib.admin.ModelAdmin.list_filter`.
  
  Multiple sort in admin interface
  --------------------------------
  
  The admin change list now supports sorting on multiple columns. It respects all
  elements of the :attr:`~django.contrib.admin.ModelAdmin.ordering` attribute, and
  sorting on multiple columns by clicking on headers is designed to mimic the
  behavior of desktop GUIs. We also added a
  :meth:`~django.contrib.admin.ModelAdmin.get_ordering` method for specifying the
  ordering dynamically (i.e., depending on the request).
  
  New ``ModelAdmin`` methods
  --------------------------
  
  We added a :meth:`~django.contrib.admin.ModelAdmin.save_related` method to
  :mod:`~django.contrib.admin.ModelAdmin` to ease customization of how
  related objects are saved in the admin.
  
  Two other new :class:`~django.contrib.admin.ModelAdmin` methods,
  :meth:`~django.contrib.admin.ModelAdmin.get_list_display` and
  :meth:`~django.contrib.admin.ModelAdmin.get_list_display_links`
  enable dynamic customization of fields and links displayed on the admin
  change list.
  
  Admin inlines respect user permissions
  --------------------------------------
  
  Admin inlines now only allow those actions for which the user has
  permission. For ``ManyToMany`` relationships with an auto-created intermediate
  model (which does not have its own permissions), the change permission for the
  related model determines if the user has the permission to add, change or
  delete relationships.
  
  Tools for cryptographic signing
  -------------------------------
  
  Django 1.4 adds both a low-level API for signing values and a high-level API
  for setting and reading signed cookies, one of the most common uses of
  signing in Web applications.
  
  See the :doc:`cryptographic signing </topics/signing>` docs for more
  information.
  
  Cookie-based session backend
  ----------------------------
  
  Django 1.4 introduces a cookie-based session backend that uses the tools for
  :doc:`cryptographic signing </topics/signing>` to store the session data in
  the client's browser.
  
  .. warning::
  
  Session data is signed and validated by the server, but it's not
  encrypted. This means a user can view any data stored in the
  session but cannot change it. Please read the documentation for
  further clarification before using this backend.
  
  See the :ref:`cookie-based session backend <cookie-session-backend>` docs for
  more information.
  
  New form wizard
  ---------------
  
  The previous ``FormWizard`` from ``django.contrib.formtools`` has been
  replaced with a new implementation based on the class-based views
  introduced in Django 1.3. It features a pluggable storage API and doesn't
  require the wizard to pass around hidden fields for every previous step.
  
  Django 1.4 ships with a session-based storage backend and a cookie-based
  storage backend. The latter uses the tools for
  :doc:`cryptographic signing </topics/signing>` also introduced in
  Django 1.4 to store the wizard's state in the user's cookies.
  
  ``reverse_lazy``
  ----------------
  
  A lazily evaluated version of ``reverse()`` was added to allow using URL
  reversals before the project's URLconf gets loaded.
  
  Translating URL patterns
  ------------------------
  
  Django can now look for a language prefix in the URLpattern when using the new
  :func:`~django.conf.urls.i18n.i18n_patterns` helper function.
  It's also now possible to define translatable URL patterns using
  ``django.utils.translation.ugettext_lazy()``. See
  :ref:`url-internationalization` for more information about the language prefix
  and how to internationalize URL patterns.
  
  Contextual translation support for ``{% trans %}`` and ``{% blocktrans %}``
  ---------------------------------------------------------------------------
  
  The :ref:`contextual translation<contextual-markers>` support introduced in
  Django 1.3 via the ``pgettext`` function has been extended to the
  :ttag:`trans` and :ttag:`blocktrans` template tags using the new ``context``
  keyword.
  
  Customizable ``SingleObjectMixin`` URLConf kwargs
  -------------------------------------------------
  
  Two new attributes,
  :attr:`pk_url_kwarg<django.views.generic.detail.SingleObjectMixin.pk_url_kwarg>`
  and
  :attr:`slug_url_kwarg<django.views.generic.detail.SingleObjectMixin.slug_url_kwarg>`,
  have been added to :class:`~django.views.generic.detail.SingleObjectMixin` to
  enable the customization of URLconf keyword arguments used for single
  object generic views.
  
  Assignment template tags
  ------------------------
  
  A new ``assignment_tag`` helper function was added to ``template.Library`` to
  ease the creation of template tags that store data in a specified context
  variable.
  
  ``*args`` and ``**kwargs`` support for template tag helper functions
  --------------------------------------------------------------------
  
  The :ref:`simple_tag<howto-custom-template-tags-simple-tags>`,
  :ref:`inclusion_tag <howto-custom-template-tags-inclusion-tags>` and newly
  introduced ``assignment_tag`` template helper functions may now accept any
  number of positional or keyword arguments. For example::
  
  register.simple_tag
  def my_tag(a, b, *args, **kwargs):
  warning = kwargs['warning']
  profile = kwargs['profile']
  ...
  return ...
  
  Then, in the template, any number of arguments may be passed to the template tag.
  For example:
  
  .. code-block:: html+django
  
  {% my_tag 123 "abcd" book.title warning=message|lower profile=user.profile %}
  
  No wrapping of exceptions in ``TEMPLATE_DEBUG`` mode
  ----------------------------------------------------
  
  In previous versions of Django, whenever the ``TEMPLATE_DEBUG`` setting
  was ``True``, any exception raised during template rendering (even exceptions
  unrelated to template syntax) were wrapped in ``TemplateSyntaxError`` and
  re-raised. This was done in order to provide detailed template source location
  information in the debug 500 page.
  
  In Django 1.4, exceptions are no longer wrapped. Instead, the original
  exception is annotated with the source information. This means that catching
  exceptions from template rendering is now consistent regardless of the value of
  ``TEMPLATE_DEBUG``, and there's no need to catch and unwrap
  ``TemplateSyntaxError`` in order to catch other errors.
  
  ``truncatechars`` template filter
  ---------------------------------
  
  This new filter truncates a string to be no longer than the specified
  number of characters. Truncated strings end with a translatable ellipsis
  sequence ("..."). See the documentation for :tfilter:`truncatechars` for
  more details.
  
  ``static`` template tag
  -----------------------
  
  The :mod:`staticfiles<django.contrib.staticfiles>` contrib app has a new
  ``static`` template tag to refer to files saved with the
  :setting:`STATICFILES_STORAGE` storage backend. It uses the storage backend's
  ``url`` method and therefore supports advanced features such as :ref:`serving
  files from a cloud service<staticfiles-from-cdn>`.
  
  ``CachedStaticFilesStorage`` storage backend
  --------------------------------------------
  
  The :mod:`staticfiles<django.contrib.staticfiles>` contrib app now has a
  ``django.contrib.staticfiles.storage.CachedStaticFilesStorage`` backend
  that caches the files it saves (when running the :djadmin:`collectstatic`
  management command) by appending the MD5 hash of the file's content to the
  filename. For example, the file ``css/styles.css`` would also be saved as
  ``css/styles.55e7cbb9ba48.css``
  
  Simple clickjacking protection
  ------------------------------
  
  We've added a middleware to provide easy protection against `clickjacking
  <https://en.wikipedia.org/wiki/Clickjacking>`_ using the ``X-Frame-Options``
  header. It's not enabled by default for backwards compatibility reasons, but
  you'll almost certainly want to :doc:`enable it </ref/clickjacking/>` to help
  plug that security hole for browsers that support the header.
  
  CSRF improvements
  -----------------
  
  We've made various improvements to our CSRF features, including the
  :func:`~django.views.decorators.csrf.ensure_csrf_cookie` decorator, which can
  help with AJAX-heavy sites; protection for PUT and DELETE requests; and the
  :setting:`CSRF_COOKIE_SECURE` and :setting:`CSRF_COOKIE_PATH` settings, which can
  improve the security and usefulness of CSRF protection. See the :doc:`CSRF
  docs </ref/csrf>` for more information.
  
  Error report filtering
  ----------------------
  
  We added two function decorators,
  :func:`~django.views.decorators.debug.sensitive_variables` and
  :func:`~django.views.decorators.debug.sensitive_post_parameters`, to allow
  designating the local variables and POST parameters that may contain sensitive
  information and should be filtered out of error reports.
  
  All POST parameters are now systematically filtered out of error reports for
  certain views (``login``, ``password_reset_confirm``, ``password_change`` and
  ``add_view`` in :mod:`django.contrib.auth.views`, as well as
  ``user_change_password`` in the admin app) to prevent the leaking of sensitive
  information such as user passwords.
  
  You can override or customize the default filtering by writing a :ref:`custom
  filter<custom-error-reports>`. For more information see the docs on
  :ref:`Filtering error reports<filtering-error-reports>`.
  
  Extended IPv6 support
  ---------------------
  
  Django 1.4 can now better handle IPv6 addresses with the new
  :class:`~django.db.models.GenericIPAddressField` model field,
  :class:`~django.forms.GenericIPAddressField` form field and
  the validators :data:`~django.core.validators.validate_ipv46_address` and
  :data:`~django.core.validators.validate_ipv6_address`.
  
  HTML comparisons in tests
  -------------------------
  
  The base classes in :mod:`django.test` now have some helpers to
  compare HTML without tripping over irrelevant differences in whitespace,
  argument quoting/ordering and closing of self-closing tags. You can either
  compare HTML directly with the new
  :meth:`~django.test.SimpleTestCase.assertHTMLEqual` and
  :meth:`~django.test.SimpleTestCase.assertHTMLNotEqual` assertions, or use
  the ``html=True`` flag with
  :meth:`~django.test.SimpleTestCase.assertContains` and
  :meth:`~django.test.SimpleTestCase.assertNotContains` to test whether the
  client's response contains a given HTML fragment. See the :ref:`assertions
  documentation <assertions>` for more.
  
  Two new date format strings
  ---------------------------
  
  Two new :tfilter:`date` formats were added for use in template filters,
  template tags and :doc:`/topics/i18n/formatting`:
  
  - ``e`` -- the name of the timezone of the given datetime object
  - ``o`` -- the ISO 8601 year number
  
  Please make sure to update your :ref:`custom format files
  <custom-format-files>` if they contain either ``e`` or ``o`` in a format
  string. For example a Spanish localization format previously only escaped the
  ``d`` format character::
  
  DATE_FORMAT = r'j \de F \de Y'
  
  But now it needs to also escape ``e`` and ``o``::
  
  DATE_FORMAT = r'j \d\e F \d\e Y'
  
  For more information, see the :tfilter:`date` documentation.
  
  Minor features
  --------------
  
  Django 1.4 also includes several smaller improvements worth noting:
  
  * A more usable stacktrace in the technical 500 page. Frames in the
  stack trace that reference Django's framework code are dimmed out,
  while frames in application code are slightly emphasized. This change
  makes it easier to scan a stacktrace for issues in application code.
  
  * :doc:`Tablespace support </topics/db/tablespaces>` in PostgreSQL.
  
  * Customizable names for :meth:`~django.template.Library.simple_tag`.
  
  * In the documentation, a helpful :doc:`security overview </topics/security>`
  page.
  
  * The ``django.contrib.auth.models.check_password`` function has been moved
  to the :mod:`django.contrib.auth.hashers` module. Importing it from the old
  location will still work, but you should update your imports.
  
  * The :djadmin:`collectstatic` management command now has a ``--clear`` option
  to delete all files at the destination before copying or linking the static
  files.
  
  * It's now possible to load fixtures containing forward references when using
  MySQL with the InnoDB database engine.
  
  * A new 403 response handler has been added as
  ``'django.views.defaults.permission_denied'``. You can set your own handler by
  setting the value of :data:`django.conf.urls.handler403`. See the
  documentation about :ref:`the 403 (HTTP Forbidden) view<http_forbidden_view>`
  for more information.
  
  * The :djadmin:`makemessages` command uses a new and more accurate lexer,
  `JsLex`_, for extracting translatable strings from JavaScript files.
  
  .. _JsLex: https://bitbucket.org/ned/jslex
  
  * The :ttag:`trans` template tag now takes an optional ``as`` argument to
  be able to retrieve a translation string without displaying it but setting
  a template context variable instead.
  
  * The :ttag:`if` template tag now supports ``{% elif %}`` clauses.
  
  * If your Django app is behind a proxy, you might find the new
  :setting:`SECURE_PROXY_SSL_HEADER` setting useful. It solves the problem of your
  proxy "eating" the fact that a request came in via HTTPS. But only use this
  setting if you know what you're doing.
  
  * A new, plain-text, version of the HTTP 500 status code internal error page
  served when :setting:`DEBUG` is ``True`` is now sent to the client when
  Django detects that the request has originated in JavaScript code.
  (``is_ajax()`` is used for this.)
  
  Like its HTML counterpart, it contains a collection of different
  pieces of information about the state of the application.
  
  This should make it easier to read when debugging interaction with
  client-side JavaScript.
  
  * Added the :option:`makemessages --no-location` option.
  
  * Changed the ``locmem`` cache backend to use
  ``pickle.HIGHEST_PROTOCOL`` for better compatibility with the other
  cache backends.
  
  * Added support in the ORM for generating ``SELECT`` queries containing
  ``DISTINCT ON``.
  
  The ``distinct()`` ``QuerySet`` method now accepts an optional list of model
  field names. If specified, then the ``DISTINCT`` statement is limited to these
  fields. This is only supported in PostgreSQL.
  
  For more details, see the documentation for
  :meth:`~django.db.models.query.QuerySet.distinct`.
  
  * The admin login page will add a password reset link if you include a URL with
  the name ``'admin_password_reset'`` in your urls.py, so plugging in the
  built-in password reset mechanism and making it available is now much easier.
  For details, see :ref:`auth_password_reset`.
  
  * The MySQL database backend can now make use of the savepoint feature
  implemented by MySQL version 5.0.3 or newer with the InnoDB storage engine.
  
  * It's now possible to pass initial values to the model forms that are part of
  both model formsets and inline model formsets as returned from factory
  functions ``modelformset_factory`` and ``inlineformset_factory`` respectively
  just like with regular formsets. However, initial values only apply to extra
  forms, i.e. those which are not bound to an existing model instance.
  
  * The sitemaps framework can now handle HTTPS links using the new
  :attr:`Sitemap.protocol <django.contrib.sitemaps.Sitemap.protocol>` class
  attribute.
  
  * A new :class:`django.test.SimpleTestCase` subclass of
  :class:`unittest.TestCase`
  that's lighter than :class:`django.test.TestCase` and company. It can be
  useful in tests that don't need to hit a database. See
  :ref:`testcase_hierarchy_diagram`.
  
  .. _backwards-incompatible-1.4:
  
  Backwards incompatible changes in 1.4
  =====================================
  
  SECRET_KEY setting is required
  ------------------------------
  
  Running Django with an empty or known :setting:`SECRET_KEY` disables many of
  Django's security protections and can lead to remote-code-execution
  vulnerabilities. No Django site should ever be run without a
  :setting:`SECRET_KEY`.
  
  In Django 1.4, starting Django with an empty :setting:`SECRET_KEY` will raise a
  ``DeprecationWarning``. In Django 1.5, it will raise an exception and Django
  will refuse to start. This is slightly accelerated from the usual deprecation
  path due to the severity of the consequences of running Django with no
  :setting:`SECRET_KEY`.
  
  ``django.contrib.admin``
  ------------------------
  
  The included administration app ``django.contrib.admin`` has for a long time
  shipped with a default set of static files such as JavaScript, images and
  stylesheets. Django 1.3 added a new contrib app ``django.contrib.staticfiles``
  to handle such files in a generic way and defined conventions for static
  files included in apps.
  
  Starting in Django 1.4, the admin's static files also follow this
  convention, to make the files easier to deploy. In previous versions of Django,
  it was also common to define an ``ADMIN_MEDIA_PREFIX`` setting to point to the
  URL where the admin's static files live on a Web server. This setting has now
  been deprecated and replaced by the more general setting :setting:`STATIC_URL`.
  Django will now expect to find the admin static files under the URL
  ``<STATIC_URL>/admin/``.
  
  If you've previously used a URL path for ``ADMIN_MEDIA_PREFIX`` (e.g.
  ``/media/``) simply make sure :setting:`STATIC_URL` and :setting:`STATIC_ROOT`
  are configured and your Web server serves those files correctly. The
  development server continues to serve the admin files just like before. Read
  the :doc:`static files howto </howto/static-files/index>` for more details.
  
  If your ``ADMIN_MEDIA_PREFIX`` is set to a specific domain (e.g.
  ``http://media.example.com/admin/``), make sure to also set your
  :setting:`STATIC_URL` setting to the correct URL -- for example,
  ``http://media.example.com/``.
  
  .. warning::
  
  If you're implicitly relying on the path of the admin static files within
  Django's source code, you'll need to update that path. The files were moved
  from :file:`django/contrib/admin/media/` to
  :file:`django/contrib/admin/static/admin/`.
  
  Supported browsers for the admin
  --------------------------------
  
  Django hasn't had a clear policy on which browsers are supported by the
  admin app. Our new policy formalizes existing practices: `YUI's A-grade`_
  browsers should provide a fully-functional admin experience, with the notable
  exception of Internet Explorer 6, which is no longer supported.
  
  Released over 10 years ago, IE6 imposes many limitations on modern Web
  development. The practical implications of this policy are that contributors
  are free to improve the admin without consideration for these limitations.
  
  This new policy **has no impact** on sites you develop using Django. It only
  applies to the Django admin. Feel free to develop apps compatible with any
  range of browsers.
  
  .. _YUI's A-grade: https://github.com/yui/yui3/wiki/Graded-Browser-Support
  
  Removed admin icons
  -------------------
  
  As part of an effort to improve the performance and usability of the admin's
  change-list sorting interface and :attr:`horizontal
  <django.contrib.admin.ModelAdmin.filter_horizontal>` and :attr:`vertical
  <django.contrib.admin.ModelAdmin.filter_vertical>` "filter" widgets, some icon
  files were removed and grouped into two sprite files.
  
  Specifically: ``selector-add.gif``, ``selector-addall.gif``,
  ``selector-remove.gif``, ``selector-removeall.gif``,
  ``selector_stacked-add.gif`` and ``selector_stacked-remove.gif`` were
  combined into ``selector-icons.gif``; and ``arrow-up.gif`` and
  ``arrow-down.gif`` were combined into ``sorting-icons.gif``.
  
  If you used those icons to customize the admin, then you'll need to replace
  them with your own icons or get the files from a previous release.
  
  CSS class names in admin forms
  ------------------------------
  
  To avoid conflicts with other common CSS class names (e.g. "button"), we added
  a prefix ("field-") to all CSS class names automatically generated from the
  form field names in the main admin forms, stacked inline forms and tabular
  inline cells. You'll need to take that prefix into account in your custom
  style sheets or JavaScript files if you previously used plain field names as
  selectors for custom styles or JavaScript transformations.
  
  Compatibility with old signed data
  ----------------------------------
  
  Django 1.3 changed the cryptographic signing mechanisms used in a number of
  places in Django. While Django 1.3 kept fallbacks that would accept hashes
  produced by the previous methods, these fallbacks are removed in Django 1.4.
  
  So, if you upgrade to Django 1.4 directly from 1.2 or earlier, you may
  lose/invalidate certain pieces of data that have been cryptographically signed
  using an old method. To avoid this, use Django 1.3 first for a period of time
  to allow the signed data to expire naturally. The affected parts are detailed
  below, with 1) the consequences of ignoring this advice and 2) the amount of
  time you need to run Django 1.3 for the data to expire or become irrelevant.
  
  * ``contrib.sessions`` data integrity check
  
  * Consequences: The user will be logged out, and session data will be lost.
  
  * Time period: Defined by :setting:`SESSION_COOKIE_AGE`.
  
  * ``contrib.auth`` password reset hash
  
  * Consequences: Password reset links from before the upgrade will not work.
  
  * Time period: Defined by :setting:`PASSWORD_RESET_TIMEOUT_DAYS`.
  
  Form-related hashes: these have a much shorter lifetime and are relevant
  only for the short window where a user might fill in a form generated by the
  pre-upgrade Django instance and try to submit it to the upgraded Django
  instance:
  
  * ``contrib.comments`` form security hash
  
  * Consequences: The user will see the validation error "Security hash failed."
  
  * Time period: The amount of time you expect users to take filling out comment
  forms.
  
  * ``FormWizard`` security hash
  
  * Consequences: The user will see an error about the form having expired
  and will be sent back to the first page of the wizard, losing the data
  entered so far.
  
  * Time period: The amount of time you expect users to take filling out the
  affected forms.
  
  * CSRF check
  
  * Note: This is actually a Django 1.1 fallback, not Django 1.2,
  and it applies only if you're upgrading from 1.1.
  
  * Consequences: The user will see a 403 error with any CSRF-protected POST
  form.
  
  * Time period: The amount of time you expect user to take filling out
  such forms.
  
  * ``contrib.auth`` user password hash-upgrade sequence
  
  * Consequences: Each user's password will be updated to a stronger password
  hash when it's written to the database in 1.4. This means that if you
  upgrade to 1.4 and then need to downgrade to 1.3, version 1.3 won't be able
  to read the updated passwords.
  
  * Remedy: Set :setting:`PASSWORD_HASHERS` to use your original password
  hashing when you initially upgrade to 1.4. After you confirm your app works
  well with Django 1.4 and you won't have to roll back to 1.3, enable the new
  password hashes.
  
  ``django.contrib.flatpages``
  ----------------------------
  
  Starting in 1.4, the
  :class:`~django.contrib.flatpages.middleware.FlatpageFallbackMiddleware` only
  adds a trailing slash and redirects if the resulting URL refers to an existing
  flatpage. For example, requesting ``/notaflatpageoravalidurl`` in a previous
  version would redirect to ``/notaflatpageoravalidurl/``, which would
  subsequently raise a 404. Requesting ``/notaflatpageoravalidurl`` now will
  immediately raise a 404.
  
  Also, redirects returned by flatpages are now permanent (with 301 status code),
  to match the behavior of :class:`~django.middleware.common.CommonMiddleware`.
  
  Serialization of :class:`~datetime.datetime` and :class:`~datetime.time`
  ------------------------------------------------------------------------
  
  As a consequence of time-zone support, and according to the ECMA-262
  specification, we made changes to the JSON serializer:
  
  * It includes the time zone for aware datetime objects. It raises an exception
  for aware time objects.
  * It includes milliseconds for datetime and time objects. There is still
  some precision loss, because Python stores microseconds (6 digits) and JSON
  only supports milliseconds (3 digits). However, it's better than discarding
  microseconds entirely.
  
  We changed the XML serializer to use the ISO8601 format for datetimes.
  The letter ``T`` is used to separate the date part from the time part, instead
  of a space. Time zone information is included in the ``[+-]HH:MM`` format.
  
  Though the serializers now use these new formats when creating fixtures, they
  can still load fixtures that use the old format.
  
  ``supports_timezone`` changed to ``False`` for SQLite
  -----------------------------------------------------
  
  The database feature ``supports_timezone`` used to be ``True`` for SQLite.
  Indeed, if you saved an aware datetime object, SQLite stored a string that
  included an UTC offset. However, this offset was ignored when loading the value
  back from the database, which could corrupt the data.
  
  In the context of time-zone support, this flag was changed to ``False``, and
  datetimes are now stored without time-zone information in SQLite. When
  :setting:`USE_TZ` is ``False``, if you attempt to save an aware datetime
  object, Django raises an exception.
  
  ``MySQLdb``-specific exceptions
  -------------------------------
  
  The MySQL backend historically has raised ``MySQLdb.OperationalError``
  when a query triggered an exception. We've fixed this bug, and we now raise
  :exc:`django.db.DatabaseError` instead. If you were testing for
  ``MySQLdb.OperationalError``, you'll need to update your ``except``
  clauses.
  
  Database connection's thread-locality
  -------------------------------------
  
  ``DatabaseWrapper`` objects (i.e. the connection objects referenced by
  ``django.db.connection`` and ``django.db.connections["some_alias"]``) used to
  be thread-local. They are now global objects in order to be potentially shared
  between multiple threads. While the individual connection objects are now
  global, the ``django.db.connections`` dictionary referencing those objects is
  still thread-local. Therefore if you just use the ORM or
  ``DatabaseWrapper.cursor()`` then the behavior is still the same as before.
  Note, however, that ``django.db.connection`` does not directly reference the
  default ``DatabaseWrapper`` object anymore and is now a proxy to access that
  object's attributes. If you need to access the actual ``DatabaseWrapper``
  object, use ``django.db.connections[DEFAULT_DB_ALIAS]`` instead.
  
  As part of this change, all underlying SQLite connections are now enabled for
  potential thread-sharing (by passing the ``check_same_thread=False`` attribute
  to pysqlite). ``DatabaseWrapper`` however preserves the previous behavior by
  disabling thread-sharing by default, so this does not affect any existing
  code that purely relies on the ORM or on ``DatabaseWrapper.cursor()``.
  
  Finally, while it's now possible to pass connections between threads, Django
  doesn't make any effort to synchronize access to the underlying backend.
  Concurrency behavior is defined by the underlying backend implementation.
  Check their documentation for details.
  
  ``COMMENTS_BANNED_USERS_GROUP`` setting
  ---------------------------------------
  
  Django's comments has historically
  supported excluding the comments of a special user group, but we've never
  documented the feature properly and didn't enforce the exclusion in other parts
  of the app such as the template tags. To fix this problem, we removed the code
  from the feed class.
  
  If you rely on the feature and want to restore the old behavior, use a custom
  comment model manager to exclude the user group, like this::
  
  from django.conf import settings
  from django.contrib.comments.managers import CommentManager
  
  class BanningCommentManager(CommentManager):
  def get_query_set(self):
  qs = super().get_query_set()
  if getattr(settings, 'COMMENTS_BANNED_USERS_GROUP', None):
  where = ['user_id NOT IN (SELECT user_id FROM auth_user_groups WHERE group_id = %s)']
  params = [settings.COMMENTS_BANNED_USERS_GROUP]
  qs = qs.extra(where=where, params=params)
  return qs
  
  Save this model manager in your custom comment app (e.g., in
  ``my_comments_app/managers.py``) and add it your custom comment app model::
  
  from django.db import models
  from django.contrib.comments.models import Comment
  
  from my_comments_app.managers import BanningCommentManager
  
  class CommentWithTitle(Comment):
  title = models.CharField(max_length=300)
  
  objects = BanningCommentManager()
  
  ``IGNORABLE_404_STARTS`` and ``IGNORABLE_404_ENDS`` settings
  ------------------------------------------------------------
  
  Until Django 1.3, it was possible to exclude some URLs from Django's
  :doc:`404 error reporting</howto/error-reporting>` by adding prefixes to
  ``IGNORABLE_404_STARTS`` and suffixes to ``IGNORABLE_404_ENDS``.
  
  In Django 1.4, these two settings are superseded by
  :setting:`IGNORABLE_404_URLS`, which is a list of compiled regular
  expressions. Django won't send an email for 404 errors on URLs that match any
  of them.
  
  Furthermore, the previous settings had some rather arbitrary default values::
  
  IGNORABLE_404_STARTS = ('/cgi-bin/', '/_vti_bin', '/_vti_inf')
  IGNORABLE_404_ENDS = ('mail.pl', 'mailform.pl', 'mail.cgi', 'mailform.cgi',
  'favicon.ico', '.php')
  
  It's not Django's role to decide if your website has a legacy ``/cgi-bin/``
  section or a ``favicon.ico``. As a consequence, the default values of
  :setting:`IGNORABLE_404_URLS`, ``IGNORABLE_404_STARTS``, and
  ``IGNORABLE_404_ENDS`` are all now empty.
  
  If you have customized ``IGNORABLE_404_STARTS`` or ``IGNORABLE_404_ENDS``, or
  if you want to keep the old default value, you should add the following lines
  in your settings file::
  
  import re
  IGNORABLE_404_URLS = (
  for each <prefix> in IGNORABLE_404_STARTS
  re.compile(r'^<prefix>'),
  for each <suffix> in IGNORABLE_404_ENDS
  re.compile(r'<suffix>$'),
  )
  
  Don't forget to escape characters that have a special meaning in a regular
  expression, such as periods.
  
  CSRF protection extended to PUT and DELETE
  ------------------------------------------
  
  Previously, Django's :doc:`CSRF protection </ref/csrf/>` provided
  protection only against POST requests. Since use of PUT and DELETE methods in
  AJAX applications is becoming more common, we now protect all methods not
  defined as safe by :rfc:`2616` -- i.e., we exempt GET, HEAD, OPTIONS and TRACE,
  and we enforce protection on everything else.
  
  If you're using PUT or DELETE methods in AJAX applications, please see the
  :ref:`instructions about using AJAX and CSRF <csrf-ajax>`.
  
  Password reset view now accepts ``subject_template_name``
  ---------------------------------------------------------
  
  The ``password_reset`` view in ``django.contrib.auth`` now accepts a
  ``subject_template_name`` parameter, which is passed to the password save form
  as a keyword argument. If you are using this view with a custom password reset
  form, then you will need to ensure your form's ``save()`` method accepts this
  keyword argument.
  
  ``django.core.template_loaders``
  --------------------------------
  
  This was an alias to ``django.template.loader`` since 2005, and we've removed it
  without emitting a warning due to the length of the deprecation. If your code
  still referenced this, please use ``django.template.loader`` instead.
  
  ``django.db.models.fields.URLField.verify_exists``
  --------------------------------------------------
  
  This functionality has been removed due to intractable performance and
  security issues. Any existing usage of ``verify_exists`` should be
  removed.
  
  ``django.core.files.storage.Storage.open``
  ------------------------------------------
  
  The ``open`` method of the base Storage class used to take an obscure parameter
  ``mixin`` that allowed you to dynamically change the base classes of the
  returned file object. This has been removed. In the rare case you relied on the
  ``mixin`` parameter, you can easily achieve the same by overriding the ``open``
  method, like this::
  
  from django.core.files import File
  from django.core.files.storage import FileSystemStorage
  
  class Spam(File):
  """
  Spam, spam, spam, spam and spam.
  """
  def ham(self):
  return 'eggs'
  
  class SpamStorage(FileSystemStorage):
  """
  A custom file storage backend.
  """
  def open(self, name, mode='rb'):
  return Spam(open(self.path(name), mode))
  
  YAML deserializer now uses ``yaml.safe_load``
  ---------------------------------------------
  
  ``yaml.load`` is able to construct any Python object, which may trigger
  arbitrary code execution if you process a YAML document that comes from an
  untrusted source. This feature isn't necessary for Django's YAML deserializer,
  whose primary use is to load fixtures consisting of simple objects. Even though
  fixtures are trusted data, the YAML deserializer now uses ``yaml.safe_load``
  for additional security.
  
  Session cookies now have the ``httponly`` flag by default
  ---------------------------------------------------------
  
  Session cookies now include the ``httponly`` attribute by default to
  help reduce the impact of potential XSS attacks. As a consequence of
  this change, session cookie data, including sessionid, is no longer
  accessible from JavaScript in many browsers. For strict backwards
  compatibility, use ``SESSION_COOKIE_HTTPONLY = False`` in your
  settings file.
  
  The :tfilter:`urlize` filter no longer escapes every URL
  --------------------------------------------------------
  
  When a URL contains a ``%xx`` sequence, where ``xx`` are two hexadecimal
  digits, :tfilter:`urlize` now assumes that the URL is already escaped and
  doesn't apply URL escaping again. This is wrong for URLs whose unquoted form
  contains a ``%xx`` sequence, but such URLs are very unlikely to happen in the
  wild, because they would confuse browsers too.
  
  ``assertTemplateUsed`` and ``assertTemplateNotUsed`` as context manager
  -----------------------------------------------------------------------
  
  It's now possible to check whether a template was used within a block of
  code with :meth:`~django.test.SimpleTestCase.assertTemplateUsed` and
  :meth:`~django.test.SimpleTestCase.assertTemplateNotUsed`. And they
  can be used as a context manager::
  
  with self.assertTemplateUsed('index.html'):
  render_to_string('index.html')
  with self.assertTemplateNotUsed('base.html'):
  render_to_string('index.html')
  
  See the :ref:`assertion documentation<assertions>` for more.
  
  Database connections after running the test suite
  -------------------------------------------------
  
  The default test runner no longer restores the database connections after
  tests' execution. This prevents the production database from being exposed to
  potential threads that would still be running and attempting to create new
  connections.
  
  If your code relied on connections to the production database being created
  after tests' execution, then you can restore the previous behavior by
  subclassing ``DjangoTestRunner`` and overriding its ``teardown_databases()``
  method.
  
  Output of :djadmin:`manage.py help <help>`
  ------------------------------------------
  
  :djadmin:`manage.py help <help>` now groups available commands by application.
  If you depended on the output of this command -- if you parsed it, for example
  -- then you'll need to update your code. To get a list of all available
  management commands in a script, use
  :djadmin:`manage.py help --commands <help>` instead.
  
  ``extends`` template tag
  ------------------------
  
  Previously, the :ttag:`extends` tag used a buggy method of parsing arguments,
  which could lead to it erroneously considering an argument as a string literal
  when it wasn't. It now uses ``parser.compile_filter``, like other tags.
  
  The internals of the tag aren't part of the official stable API, but in the
  interests of full disclosure, the ``ExtendsNode.__init__`` definition has
  changed, which may break any custom tags that use this class.
  
  Loading some incomplete fixtures no longer works
  ------------------------------------------------
  
  Prior to 1.4, a default value was inserted for fixture objects that were missing
  a specific date or datetime value when auto_now or auto_now_add was set for the
  field. This was something that should not have worked, and in 1.4 loading such
  incomplete fixtures will fail. Because fixtures are a raw import, they should
  explicitly specify all field values, regardless of field options on the model.
  
  Development Server Multithreading
  ---------------------------------
  
  The development server is now is multithreaded by default. Use the
  :option:`runserver --nothreading` option to disable the use of threading in the
  development server::
  
  django-admin.py runserver --nothreading
  
  Attributes disabled in markdown when safe mode set
  --------------------------------------------------
  
  Prior to Django 1.4, attributes were included in any markdown output regardless
  of safe mode setting of the filter. With version > 2.1 of the Python-Markdown
  library, an enable_attributes option was added. When the safe argument is
  passed to the markdown filter, both the ``safe_mode=True`` and
  ``enable_attributes=False`` options are set. If using a version of the
  Python-Markdown library less than 2.1, a warning is issued that the output is
  insecure.
  
  FormMixin get_initial returns an instance-specific dictionary
  -------------------------------------------------------------
  
  In Django 1.3, the ``get_initial`` method of the
  :class:`django.views.generic.edit.FormMixin` class was returning the
  class ``initial`` dictionary. This has been fixed to return a copy of this
  dictionary, so form instances can modify their initial data without messing
  with the class variable.
  
  .. _deprecated-features-1.4:
  
  Features deprecated in 1.4
  ==========================
  
  Old styles of calling ``cache_page`` decorator
  ----------------------------------------------
  
  Some legacy ways of calling :func:`~django.views.decorators.cache.cache_page`
  have been deprecated. Please see the documentation for the correct way to use
  this decorator.
  
  Support for PostgreSQL versions older than 8.2
  ----------------------------------------------
  
  Django 1.3 dropped support for PostgreSQL versions older than 8.0, and we
  suggested using a more recent version because of performance improvements
  and, more importantly, the end of upstream support periods for 8.0 and 8.1
  was near (November 2010).
  
  Django 1.4 takes that policy further and sets 8.2 as the minimum PostgreSQL
  version it officially supports.
  
  Request exceptions are now always logged
  ----------------------------------------
  
  When we added :doc:`logging support </topics/logging/>` in Django in 1.3, the
  admin error email support was moved into the
  :class:`django.utils.log.AdminEmailHandler`, attached to the
  ``'django.request'`` logger. In order to maintain the established behavior of
  error emails, the ``'django.request'`` logger was called only when
  :setting:`DEBUG` was ``False``.
  
  To increase the flexibility of error logging for requests, the
  ``'django.request'`` logger is now called regardless of the value of
  :setting:`DEBUG`, and the default settings file for new projects now includes a
  separate filter attached to :class:`django.utils.log.AdminEmailHandler` to
  prevent admin error emails in ``DEBUG`` mode::
  
  'filters': {
  'require_debug_false': {
  '()': 'django.utils.log.RequireDebugFalse'
  }
  },
  'handlers': {
  'mail_admins': {
  'level': 'ERROR',
  'filters': ['require_debug_false'],
  'class': 'django.utils.log.AdminEmailHandler'
  }
  },
  
  If your project was created prior to this change, your :setting:`LOGGING`
  setting will not include this new filter. In order to maintain
  backwards-compatibility, Django will detect that your ``'mail_admins'`` handler
  configuration includes no ``'filters'`` section and will automatically add
  this filter for you and issue a pending-deprecation warning. This will become a
  deprecation warning in Django 1.5, and in Django 1.6 the
  backwards-compatibility shim will be removed entirely.
  
  The existence of any ``'filters'`` key under the ``'mail_admins'`` handler will
  disable this backward-compatibility shim and deprecation warning.
  
  ``django.conf.urls.defaults``
  -----------------------------
  
  Until Django 1.3, the ``include()``, ``patterns()``, and ``url()`` functions,
  plus :data:`~django.conf.urls.handler404` and :data:`~django.conf.urls.handler500`
  were located in a ``django.conf.urls.defaults`` module.
  
  In Django 1.4, they live in :mod:`django.conf.urls`.
  
  ``django.contrib.databrowse``
  -----------------------------
  
  Databrowse has not seen active development for some time, and this does not show
  any sign of changing. There had been a suggestion for a `GSOC project`_ to
  integrate the functionality of databrowse into the admin, but no progress was
  made. While Databrowse has been deprecated, an enhancement of
  ``django.contrib.admin`` providing a similar feature set is still possible.
  
  .. _GSOC project: https://code.djangoproject.com/wiki/SummerOfCode2011Integratedatabrowseintotheadmin
  
  The code that powers Databrowse is licensed under the same terms as Django
  itself, so it's available to be adopted by an individual or group as
  a third-party project.
  
  ``django.core.management.setup_environ``
  ----------------------------------------
  
  This function temporarily modified ``sys.path`` in order to make the parent
  "project" directory importable under the old flat :djadmin:`startproject`
  layout. This function is now deprecated, as its path workarounds are no longer
  needed with the new ``manage.py`` and default project layout.
  
  This function was never documented or part of the public API, but it was widely
  recommended for use in setting up a "Django environment" for a user script.
  These uses should be replaced by setting the :envvar:`DJANGO_SETTINGS_MODULE`
  environment variable or using :func:`django.conf.settings.configure`.
  
  ``django.core.management.execute_manager``
  ------------------------------------------
  
  This function was previously used by ``manage.py`` to execute a management
  command. It is identical to
  ``django.core.management.execute_from_command_line``, except that it first
  calls ``setup_environ``, which is now deprecated. As such, ``execute_manager``
  is also deprecated; ``execute_from_command_line`` can be used instead. Neither
  of these functions is documented as part of the public API, but a deprecation
  path is needed due to use in existing ``manage.py`` files.
  
  ``is_safe`` and ``needs_autoescape`` attributes of template filters
  -------------------------------------------------------------------
  
  Two flags, ``is_safe`` and ``needs_autoescape``, define how each template filter
  interacts with Django's auto-escaping behavior. They used to be attributes of
  the filter function::
  
  register.filter
  def noop(value):
  return value
  noop.is_safe = True
  
  However, this technique caused some problems in combination with decorators,
  especially :func:`stringfilter <django.template.defaultfilters.stringfilter>`.
  Now, the flags are keyword arguments of :meth:`register.filter
  <django.template.Library.filter>`::
  
  register.filter(is_safe=True)
  def noop(value):
  return value
  
  See :ref:`filters and auto-escaping <filters-auto-escaping>` for more information.
  
  Wildcard expansion of application names in ``INSTALLED_APPS``
  -------------------------------------------------------------
  
  Until Django 1.3, :setting:`INSTALLED_APPS` accepted wildcards in application
  names, like ``django.contrib.*``. The expansion was performed by a
  filesystem-based implementation of ``from <package> import *``. Unfortunately,
  this can't be done reliably.
  
  This behavior was never documented. Since it is unpythonic, it was removed in
  Django 1.4. If you relied on it, you must edit your settings file to list all
  your applications explicitly.
  
  ``HttpRequest.raw_post_data`` renamed to ``HttpRequest.body``
  -------------------------------------------------------------
  
  This attribute was confusingly named ``HttpRequest.raw_post_data``, but it
  actually provided the body of the HTTP request. It's been renamed to
  ``HttpRequest.body``, and ``HttpRequest.raw_post_data`` has been deprecated.
  
  ``django.contrib.sitemaps`` bug fix with potential performance implications
  ---------------------------------------------------------------------------
  
  In previous versions, ``Paginator`` objects used in sitemap classes were
  cached, which could result in stale site maps. We've removed the caching, so
  each request to a site map now creates a new Paginator object and calls the
  :attr:`~django.contrib.sitemaps.Sitemap.items()` method of the
  :class:`~django.contrib.sitemaps.Sitemap` subclass. Depending on what your
  ``items()`` method is doing, this may have a negative performance impact.
  To mitigate the performance impact, consider using the :doc:`caching
  framework </topics/cache>` within your ``Sitemap`` subclass.
  
  Versions of Python-Markdown earlier than 2.1
  --------------------------------------------
  
  Versions of Python-Markdown earlier than 2.1 do not support the option to
  disable attributes. As a security issue, earlier versions of this library will
  not be supported by the markup contrib app in 1.5 under an accelerated
  deprecation timeline.
  
  
  ==========================

1.3.7 not secure

==========================
  
  *February 20, 2013*
  
  Django 1.3.7 corrects a packaging problem with yesterday's :doc:`1.3.6 release
  </releases/1.3.6>`.
  
  The release contained stray ``.pyc`` files that caused "bad magic number"
  errors when running with some versions of Python. This releases corrects this,
  and also fixes a bad documentation link in the project template ``settings.py``
  file generated by ``manage.py startproject``.
  
  
  ==========================

1.3.6 not secure

==========================
  
  *February 19, 2013*
  
  Django 1.3.6 fixes four security issues present in previous Django releases in
  the 1.3 series.
  
  This is the sixth bugfix/security release in the Django 1.3 series.
  
  
  Host header poisoning
  =====================
  
  Some parts of Django -- independent of end-user-written applications -- make
  use of full URLs, including domain name, which are generated from the HTTP Host
  header. Django's documentation has for some time contained notes advising users
  on how to configure Web servers to ensure that only valid Host headers can reach
  the Django application. However, it has been reported to us that even with the
  recommended Web server configurations there are still techniques available for
  tricking many common Web servers into supplying the application with an
  incorrect and possibly malicious Host header.
  
  For this reason, Django 1.3.6 adds a new setting, ``ALLOWED_HOSTS``, which
  should contain an explicit list of valid host/domain names for this site. A
  request with a Host header not matching an entry in this list will raise
  ``SuspiciousOperation`` if ``request.get_host()`` is called. For full details
  see the documentation for the :setting:`ALLOWED_HOSTS` setting.
  
  The default value for this setting in Django 1.3.6 is ``['*']`` (matching any
  host), for backwards-compatibility, but we strongly encourage all sites to set
  a more restrictive value.
  
  This host validation is disabled when ``DEBUG`` is ``True`` or when running tests.
  
  
  XML deserialization
  ===================
  
  The XML parser in the Python standard library is vulnerable to a number of
  attacks via external entities and entity expansion. Django uses this parser for
  deserializing XML-formatted database fixtures. The fixture deserializer is not
  intended for use with untrusted data, but in order to err on the side of safety
  in Django 1.3.6 the XML deserializer refuses to parse an XML document with a
  DTD (DOCTYPE definition), which closes off these attack avenues.
  
  These issues in the Python standard library are CVE-2013-1664 and
  CVE-2013-1665. More information available `from the Python security team`_.
  
  Django's XML serializer does not create documents with a DTD, so this should
  not cause any issues with the typical round-trip from ``dumpdata`` to
  ``loaddata``, but if you feed your own XML documents to the ``loaddata``
  management command, you will need to ensure they do not contain a DTD.
  
  .. _from the Python security team: https://blog.python.org/2013/02/announcing-defusedxml-fixes-for-xml.html
  
  
  Formset memory exhaustion
  =========================
  
  Previous versions of Django did not validate or limit the form-count data
  provided by the client in a formset's management form, making it possible to
  exhaust a server's available memory by forcing it to create very large numbers
  of forms.
  
  In Django 1.3.6, all formsets have a strictly-enforced maximum number of forms
  (1000 by default, though it can be set higher via the ``max_num`` formset
  factory argument).
  
  
  Admin history view information leakage
  ======================================
  
  In previous versions of Django, an admin user without change permission on a
  model could still view the Unicode representation of instances via their admin
  history log. Django 1.3.6 now limits the admin history log view for an object
  to users with change permission for that model.
  
  
  ==========================

1.3.5 not secure

==========================
  
  *December 10, 2012*
  
  Django 1.3.5 addresses two security issues present in previous Django releases
  in the 1.3 series.
  
  Please be aware that this security release is slightly different from previous
  ones. Both issues addressed here have been dealt with in prior security updates
  to Django. In one case, we have received ongoing reports of problems, and in
  the other we've chosen to take further steps to tighten up Django's code in
  response to independent discovery of potential problems from multiple sources.
  
  Host header poisoning
  =====================
  
  Several earlier Django security releases focused on the issue of poisoning the
  HTTP Host header, causing Django to generate URLs pointing to arbitrary,
  potentially-malicious domains.
  
  In response to further input received and reports of continuing issues
  following the previous release, we're taking additional steps to tighten Host
  header validation. Rather than attempt to accommodate all features HTTP
  supports here, Django's Host header validation attempts to support a smaller,
  but far more common, subset:
  
  * Hostnames must consist of characters ``[A-Za-z0-9]`` plus hyphen ('-') or dot
  ('.').
  * IP addresses -- both IPv4 and IPv6 -- are permitted.
  * Port, if specified, is numeric.
  
  Any deviation from this will now be rejected, raising the exception
  :exc:`django.core.exceptions.SuspiciousOperation`.
  
  Redirect poisoning
  ==================
  
  Also following up on a previous issue: in July of this year, we made changes to
  Django's HTTP redirect classes, performing additional validation of the scheme
  of the URL to redirect to (since, both within Django's own supplied
  applications and many third-party applications, accepting a user-supplied
  redirect target is a common pattern).
  
  Since then, two independent audits of the code turned up further potential
  problems. So, similar to the Host-header issue, we are taking steps to provide
  tighter validation in response to reported problems (primarily with third-party
  applications, but to a certain extent also within Django itself). This comes in
  two parts:
  
  1. A new utility function, ``django.utils.http.is_safe_url``, is added; this
  function takes a URL and a hostname, and checks that the URL is either
  relative, or if absolute matches the supplied hostname. This function is
  intended for use whenever user-supplied redirect targets are accepted, to
  ensure that such redirects cannot lead to arbitrary third-party sites.
  
  2. All of Django's own built-in views -- primarily in the authentication system
  -- which allow user-supplied redirect targets now use ``is_safe_url`` to
  validate the supplied URL.
  
  
  ==========================

1.3.4 not secure

==========================
  
  *October 17, 2012*
  
  This is the fourth release in the Django 1.3 series.
  
  Host header poisoning
  =====================
  
  Some parts of Django -- independent of end-user-written applications -- make
  use of full URLs, including domain name, which are generated from the HTTP Host
  header. Some attacks against this are beyond Django's ability to control, and
  require the web server to be properly configured; Django's documentation has
  for some time contained notes advising users on such configuration.
  
  Django's own built-in parsing of the Host header is, however, still vulnerable,
  as was reported to us recently. The Host header parsing in Django 1.3.3 and
  Django 1.4.1 -- specifically, ``django.http.HttpRequest.get_host()`` -- was
  incorrectly handling username/password information in the header. Thus, for
  example, the following Host header would be accepted by Django when running on
  "validsite.com"::
  
  Host: validsite.com:randomevilsite.com
  
  Using this, an attacker can cause parts of Django -- particularly the
  password-reset mechanism -- to generate and display arbitrary URLs to users.
  
  To remedy this, the parsing in ``HttpRequest.get_host()`` is being modified;
  Host headers which contain potentially dangerous content (such as
  username/password pairs) now raise the exception
  :exc:`django.core.exceptions.SuspiciousOperation`.
  
  Details of this issue were initially posted online as a `security advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2012/oct/17/security/
  
  
  ==========================

1.3.3 not secure

==========================
  
  *August 1, 2012*
  
  Following Monday's security release of :doc:`Django 1.3.2 </releases/1.3.2>`,
  we began receiving reports that one of the fixes applied was breaking Python
  2.4 compatibility for Django 1.3. Since Python 2.4 is a supported Python
  version for that release series, this release fixes compatibility with
  Python 2.4.
  
  
  ==========================

1.3.2 not secure

==========================
  
  *July 30, 2012*
  
  This is the second security release in the Django 1.3 series, fixing several
  security issues in Django 1.3. Django 1.3.2 is a recommended upgrade for
  all users of Django 1.3.
  
  For a full list of issues addressed in this release, see the `security
  advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2012/jul/30/security-releases-issued/
  
  
  ==========================

1.3.1 not secure

==========================
  
  *September 9, 2011*
  
  Welcome to Django 1.3.1!
  
  This is the first security release in the Django 1.3 series, fixing several
  security issues in Django 1.3.  Django 1.3.1 is a recommended upgrade for
  all users of Django 1.3.
  
  For a full list of issues addressed in this release, see the `security
  advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2011/sep/09/security-releases-issued/
  
  
  ========================

1.3 not secure

========================
  
  *March 23, 2011*
  
  Welcome to Django 1.3!
  
  Nearly a year in the making, Django 1.3 includes quite a few :ref:`new features
  <whats-new-1.3>` and plenty of bug fixes and improvements to existing features.
  These release notes cover the new features in 1.3, as well as some
  :ref:`backwards-incompatible changes <backwards-incompatible-changes-1.3>`
  you'll want to be aware of when upgrading from Django 1.2 or older versions.
  
  Overview
  ========
  
  Django 1.3's focus has mostly been on resolving smaller, long-standing
  feature requests, but that hasn't prevented a few fairly significant
  new features from landing, including:
  
  * A framework for writing `class-based views`_.
  
  * Built-in support for `using Python's logging facilities`_.
  
  * Contrib support for `easy handling of static files`_.
  
  * Django's testing framework now supports (and ships with a copy of)
  `the unittest2 library`_.
  
  Wherever possible, new features are introduced in a backwards-compatible manner
  per :doc:`our API stability policy </misc/api-stability>` policy. As a result
  of this policy, Django 1.3 :ref:`begins the deprecation process for some
  features <deprecated-features-1.3>`.
  
  .. _using Python's logging facilities: `Logging`_
  .. _easy handling of static files: `Extended static files handling`_
  .. _the unittest2 library: `unittest2 support`_
  
  Python compatibility
  ====================
  
  The release of Django 1.2 was notable for having the first shift in
  Django's Python compatibility policy; prior to Django 1.2, Django
  supported any 2.x version of Python from 2.3 up. As of Django 1.2, the
  minimum requirement was raised to Python 2.4.
  
  Django 1.3 continues to support Python 2.4, but will be the final
  Django release series to do so; beginning with Django 1.4, the minimum
  supported Python version will be 2.5. A document outlining our full
  timeline for deprecating Python 2.x and moving to Python 3.x will be
  published shortly after the release of Django 1.3.
  
  .. _whats-new-1.3:
  
  What's new in Django 1.3
  ========================
  
  Class-based views
  -----------------
  
  Django 1.3 adds a framework that allows you to use a class as a view.
  This means you can compose a view out of a collection of methods that
  can be subclassed and overridden to provide common views of data without
  having to write too much code.
  
  Analogs of all the old function-based generic views have been
  provided, along with a completely generic view base class that can be
  used as the basis for reusable applications that can be easily
  extended.
  
  See :doc:`the documentation on class-based generic views</topics/class-based-views/index>`
  for more details. There is also a document to help you `convert
  your function-based generic views to class-based
  views <https://docs.djangoproject.com/en/1.4/topics/generic-views-migration/>`_.
  
  Logging
  -------
  
  Django 1.3 adds framework-level support for Python's ``logging``
  module.  This means you can now easily configure and control logging
  as part of your Django project. A number of logging handlers and
  logging calls have been added to Django's own code as well -- most
  notably, the error emails sent on a HTTP 500 server error are now
  handled as a logging activity. See :doc:`the documentation on Django's
  logging interface </topics/logging>` for more details.
  
  Extended static files handling
  ------------------------------
  
  Django 1.3 ships with a new contrib app --
  ``django.contrib.staticfiles`` -- to help developers handle the static
  media files (images, CSS, JavaScript, etc.) that are needed to render
  a complete web page.
  
  In previous versions of Django, it was common to place static assets
  in :setting:`MEDIA_ROOT` along with user-uploaded files, and serve
  them both at :setting:`MEDIA_URL`. Part of the purpose of introducing
  the ``staticfiles`` app is to make it easier to keep static files
  separate from user-uploaded files. Static assets should now go in
  ``static/`` subdirectories of your apps or in other static assets
  directories listed in :setting:`STATICFILES_DIRS`, and will be served
  at :setting:`STATIC_URL`.
  
  See the :doc:`reference documentation of the app </ref/contrib/staticfiles>`
  for more details or learn how to :doc:`manage static files
  </howto/static-files/index>`.
  
  ``unittest2`` support
  ----------------------
  
  Python 2.7 introduced some major changes to the ``unittest`` library,
  adding some extremely useful features. To ensure that every Django
  project can benefit from these new features, Django ships with a copy
  of unittest2_, a copy of the Python 2.7 ``unittest`` library, backported
  for Python 2.4 compatibility.
  
  To access this library, Django provides the ``django.utils.unittest``
  module alias. If you are using Python 2.7, or you have installed
  ``unittest2`` locally, Django will map the alias to the installed
  version of the ``unittest`` library. Otherwise, Django will use its own
  bundled version of ``unittest2``.
  
  To take advantage of this alias, simply use::
  
  from django.utils import unittest
  
  wherever you would have historically used::
  
  import unittest
  
  If you want to continue to use the base ``unittest`` library, you can --
  you just won't get any of the nice new ``unittest2`` features.
  
  .. _unittest2: https://pypi.org/project/unittest2/
  
  Transaction context managers
  ----------------------------
  
  Users of Python 2.5 and above may now use transaction management functions as
  context managers. For example::
  
  with transaction.autocommit():
  ...
  
  Configurable delete-cascade
  ---------------------------
  
  :class:`~django.db.models.ForeignKey` and
  :class:`~django.db.models.OneToOneField` now accept an
  :attr:`~django.db.models.ForeignKey.on_delete` argument to customize behavior
  when the referenced object is deleted. Previously, deletes were always
  cascaded; available alternatives now include set null, set default, set to any
  value, protect, or do nothing.
  
  For more information, see the :attr:`~django.db.models.ForeignKey.on_delete`
  documentation.
  
  Contextual markers and comments for translatable strings
  --------------------------------------------------------
  
  For translation strings with ambiguous meaning, you can now
  use the ``pgettext`` function to specify the context of the string.
  
  And if you just want to add some information for translators, you
  can also add special translator comments in the source.
  
  For more information, see :ref:`contextual-markers` and
  :ref:`translator-comments`.
  
  Improvements to built-in template tags
  --------------------------------------
  
  A number of improvements have been made to Django's built-in template tags:
  
  * The :ttag:`include` tag now accepts a ``with`` option, allowing
  you to specify context variables to the included template
  
  * The :ttag:`include` tag now accepts an ``only`` option, allowing
  you to exclude the current context from the included context
  
  * The :ttag:`with` tag now allows you to define multiple context
  variables in a single :ttag:`with` block.
  
  * The :ttag:`load` tag now accepts a ``from`` argument, allowing
  you to load a single tag or filter from a library.
  
  TemplateResponse
  ----------------
  
  It can sometimes be beneficial to allow decorators or middleware to
  modify a response *after* it has been constructed by the view. For
  example, you may want to change the template that is used, or put
  additional data into the context.
  
  However, you can't (easily) modify the content of a basic
  :class:`~django.http.HttpResponse` after it has been constructed. To
  overcome this limitation, Django 1.3 adds a new
  :class:`~django.template.response.TemplateResponse` class. Unlike basic
  :class:`~django.http.HttpResponse` objects,
  :class:`~django.template.response.TemplateResponse` objects retain the details
  of the template and context that was provided by the view to compute
  the response. The final output of the response is not computed until
  it is needed, later in the response process.
  
  For more details, see the :doc:`documentation </ref/template-response>`
  on the :class:`~django.template.response.TemplateResponse` class.
  
  Caching changes
  ---------------
  
  Django 1.3 sees the introduction of several improvements to the
  Django's caching infrastructure.
  
  Firstly, Django now supports multiple named caches. In the same way
  that Django 1.2 introduced support for multiple database connections,
  Django 1.3 allows you to use the new :setting:`CACHES` setting to
  define multiple named cache connections.
  
  Secondly, :ref:`versioning <cache_versioning>`, :ref:`site-wide
  prefixing <cache_key_prefixing>` and :ref:`transformation
  <cache_key_transformation>` have been added to the cache API.
  
  Thirdly, :ref:`cache key creation <using-vary-headers>` has been
  updated to take the request query string into account on ``GET``
  requests.
  
  Finally, support for pylibmc_ has been added to the memcached cache
  backend.
  
  For more details, see the :doc:`documentation on
  caching in Django</topics/cache>`.
  
  .. _pylibmc: http://sendapatch.se/projects/pylibmc/
  
  Permissions for inactive users
  ------------------------------
  
  If you provide a custom auth backend with ``supports_inactive_user``
  set to ``True``, an inactive ``User`` instance will check the backend
  for permissions.  This is useful for further centralizing the
  permission handling. See the :doc:`authentication docs </topics/auth/index>`
  for more details.
  
  GeoDjango
  ---------
  
  The GeoDjango test suite is now included when
  :ref:`running the Django test suite <running-unit-tests>` with ``runtests.py``
  when using :ref:`spatial database backends <spatial-backends>`.
  
  :setting:`MEDIA_URL` and :setting:`STATIC_URL` must end in a slash
  ------------------------------------------------------------------
  
  Previously, the :setting:`MEDIA_URL` setting only required a trailing slash if
  it contained a suffix beyond the domain name.
  
  A trailing slash is now *required* for :setting:`MEDIA_URL` and the new
  :setting:`STATIC_URL` setting as long as it is not blank. This ensures there is
  a consistent way to combine paths in templates.
  
  Project settings which provide either of both settings without a trailing
  slash will now raise a ``PendingDeprecationWarning``.
  
  In Django 1.4 this same condition will raise ``DeprecationWarning``,
  and in Django 1.5 will raise an ``ImproperlyConfigured`` exception.
  
  Everything else
  ---------------
  
  Django :doc:`1.1 <1.1>` and :doc:`1.2 <1.2>` added
  lots of big ticket items to Django, like multiple-database support,
  model validation, and a session-based messages framework. However,
  this focus on big features came at the cost of lots of smaller
  features.
  
  To compensate for this, the focus of the Django 1.3 development
  process has been on adding lots of smaller, long standing feature
  requests. These include:
  
  * Improved tools for accessing and manipulating the current
  :class:`~django.contrib.sites.models.Site` object in
  :doc:`the sites framework </ref/contrib/sites>`.
  
  * A :class:`~django.test.RequestFactory` for mocking requests
  in tests.
  
  * A new test assertion --
  :meth:`~django.test.TransactionTestCase.assertNumQueries` -- making it
  easier to test the database activity associated with a view.
  
  * Support for lookups spanning relations in admin's
  :attr:`~django.contrib.admin.ModelAdmin.list_filter`.
  
  * Support for HttpOnly_ cookies.
  
  * :meth:`~django.core.mail.mail_admins()` and
  :meth:`~django.core.mail.mail_managers()` now support easily attaching
  HTML content to messages.
  
  * :class:`~django.core.mail.EmailMessage` now supports CC's.
  
  * Error emails now include more of the detail and formatting of the
  debug server error page.
  
  * :meth:`~django.template.Library.simple_tag` now accepts a
  ``takes_context`` argument, making it easier to write simple
  template tags that require access to template context.
  
  * A new :meth:`~django.shortcuts.render()` shortcut -- an alternative
  to ``django.shortcuts.render_to_response()`` providing a
  :class:`~django.template.RequestContext` by default.
  
  * Support for combining :class:`F expressions <django.db.models.F>`
  with ``timedelta`` values when retrieving or updating database values.
  
  .. _HttpOnly: https://owasp.org/www-community/HttpOnly
  
  .. _backwards-incompatible-changes-1.3:
  
  Backwards-incompatible changes in 1.3
  =====================================
  
  CSRF validation now applies to AJAX requests
  --------------------------------------------
  
  Prior to Django 1.2.5, Django's CSRF-prevention system exempted AJAX
  requests from CSRF verification; due to `security issues`_ reported to
  us, however, *all* requests are now subjected to CSRF
  verification. Consult :doc:`the Django CSRF documentation
  </ref/csrf>` for details on how to handle CSRF verification in
  AJAX requests.
  
  .. _security issues: https://www.djangoproject.com/weblog/2011/feb/08/security/
  
  Restricted filters in admin interface
  -------------------------------------
  
  Prior to Django 1.2.5, the Django administrative interface allowed
  filtering on any model field or relation -- not just those specified
  in ``list_filter`` -- via query string manipulation. Due to security
  issues reported to us, however, query string lookup arguments in the
  admin must be for fields or relations specified in ``list_filter`` or
  ``date_hierarchy``.
  
  Deleting a model doesn't delete associated files
  ------------------------------------------------
  
  In earlier Django versions, when a model instance containing a
  :class:`~django.db.models.FileField` was deleted,
  :class:`~django.db.models.FileField` took it upon itself to also delete the
  file from the backend storage. This opened the door to several data-loss
  scenarios, including rolled-back transactions and fields on different models
  referencing the same file. In Django 1.3, when a model is deleted the
  :class:`~django.db.models.FileField`’s ``delete()`` method won't be called. If
  you need cleanup of orphaned files, you'll need to handle it yourself (for
  instance, with a custom management command that can be run manually or
  scheduled to run periodically via e.g. cron).
  
  PasswordInput default rendering behavior
  ----------------------------------------
  
  The :class:`~django.forms.PasswordInput` form widget, intended for use
  with form fields which represent passwords, accepts a boolean keyword
  argument ``render_value`` indicating whether to send its data back to
  the browser when displaying a submitted form with errors. Prior to
  Django 1.3, this argument defaulted to ``True``, meaning that the
  submitted password would be sent back to the browser as part of the
  form. Developers who wished to add a bit of additional security by
  excluding that value from the redisplayed form could instantiate a
  :class:`~django.forms.PasswordInput` passing ``render_value=False`` .
  
  Due to the sensitive nature of passwords, however, Django 1.3 takes
  this step automatically; the default value of ``render_value`` is now
  ``False``, and developers who want the password value returned to the
  browser on a submission with errors (the previous behavior) must now
  explicitly indicate this. For example::
  
  class LoginForm(forms.Form):
  username = forms.CharField(max_length=100)
  password = forms.CharField(widget=forms.PasswordInput(render_value=True))
  
  Clearable default widget for FileField
  --------------------------------------
  
  Django 1.3 now includes a :class:`~django.forms.ClearableFileInput` form widget
  in addition to :class:`~django.forms.FileInput`. ``ClearableFileInput`` renders
  with a checkbox to clear the field's value (if the field has a value and is not
  required); ``FileInput`` provided no means for clearing an existing file from
  a ``FileField``.
  
  ``ClearableFileInput`` is now the default widget for a ``FileField``, so
  existing forms including ``FileField`` without assigning a custom widget will
  need to account for the possible extra checkbox in the rendered form output.
  
  To return to the previous rendering (without the ability to clear the
  ``FileField``), use the ``FileInput`` widget in place of
  ``ClearableFileInput``. For instance, in a ``ModelForm`` for a hypothetical
  ``Document`` model with a ``FileField`` named ``document``::
  
  from django import forms
  from myapp.models import Document
  
  class DocumentForm(forms.ModelForm):
  class Meta:
  model = Document
  widgets = {'document': forms.FileInput}
  
  New index on database session table
  -----------------------------------
  
  Prior to Django 1.3, the database table used by the database backend
  for the :doc:`sessions </topics/http/sessions>` app had no index on
  the ``expire_date`` column. As a result, date-based queries on the
  session table -- such as the query that is needed to purge old
  sessions -- would be very slow if there were lots of sessions.
  
  If you have an existing project that is using the database session
  backend, you don't have to do anything to accommodate this change.
  However, you may get a significant performance boost if you manually
  add the new index to the session table. The SQL that will add the
  index can be found by running the ``sqlindexes`` admin command::
  
  python manage.py sqlindexes sessions
  
  No more naughty words
  ---------------------
  
  Django has historically provided (and enforced) a list of profanities.
  The comments app has enforced this list of profanities, preventing people from
  submitting comments that contained one of those profanities.
  
  Unfortunately, the technique used to implement this profanities list
  was woefully naive, and prone to the `Scunthorpe problem`_. Improving
  the built-in filter to fix this problem would require significant
  effort, and since natural language processing isn't the normal domain
  of a web framework, we have "fixed" the problem by making the list of
  prohibited words an empty list.
  
  If you want to restore the old behavior, simply put a
  ``PROFANITIES_LIST`` setting in your settings file that includes the
  words that you want to prohibit (see the `commit that implemented this
  change`_ if you want to see the list of words that was historically
  prohibited). However, if avoiding profanities is important to you, you
  would be well advised to seek out a better, less naive approach to the
  problem.
  
  .. _Scunthorpe problem: https://en.wikipedia.org/wiki/Scunthorpe_problem
  .. _commit that implemented this change: https://code.djangoproject.com/changeset/13996
  
  Localflavor changes
  -------------------
  
  Django 1.3 introduces the following backwards-incompatible changes to
  local flavors:
  
  * Canada (ca) -- The province "Newfoundland and Labrador" has had its
  province code updated to "NL", rather than the older "NF". In
  addition, the Yukon Territory has had its province code corrected to
  "YT", instead of "YK".
  
  * Indonesia (id) -- The province "Nanggroe Aceh Darussalam (NAD)" has
  been removed from the province list in favor of the new official
  designation "Aceh (ACE)".
  
  * United States of America (us) -- The list of "states" used by
  ``USStateField`` has expanded to include Armed Forces postal
  codes. This is backwards-incompatible if you were relying on
  ``USStateField`` not including them.
  
  FormSet updates
  ---------------
  
  In Django 1.3 ``FormSet`` creation behavior is modified slightly. Historically
  the class didn't make a distinction between not being passed data and being
  passed empty dictionary. This was inconsistent with behavior in other parts of
  the framework. Starting with 1.3 if you pass in empty dictionary the
  ``FormSet`` will raise a ``ValidationError``.
  
  For example with a ``FormSet``::
  
  >>> class ArticleForm(Form):
  ...     title = CharField()
  ...     pub_date = DateField()
  >>> ArticleFormSet = formset_factory(ArticleForm)
  
  the following code will raise a ``ValidationError``::
  
  >>> ArticleFormSet({})
  Traceback (most recent call last):
  ...
  ValidationError: [u'ManagementForm data is missing or has been tampered with']
  
  if you need to instantiate an empty ``FormSet``, don't pass in the data or use
  ``None``::
  
  >>> formset = ArticleFormSet()
  >>> formset = ArticleFormSet(data=None)
  
  Callables in templates
  ----------------------
  
  Previously, a callable in a template would only be called automatically as part
  of the variable resolution process if it was retrieved via attribute
  lookup. This was an inconsistency that could result in confusing and unhelpful
  behavior::
  
  >>> Template("{{ user.get_full_name }}").render(Context({'user': user}))
  u'Joe Bloggs'
  >>> Template("{{ full_name }}").render(Context({'full_name': user.get_full_name}))
  u'&lt;bound method User.get_full_name of &lt;...
  
  This has been resolved in Django 1.3 - the result in both cases will be ``u'Joe
  Bloggs'``. Although the previous behavior was not useful for a template language
  designed for web designers, and was never deliberately supported, it is possible
  that some templates may be broken by this change.
  
  Use of custom SQL to load initial data in tests
  -----------------------------------------------
  
  Django provides a custom SQL hooks as a way to inject hand-crafted SQL
  into the database synchronization process. One of the possible uses
  for this custom SQL is to insert data into your database. If your
  custom SQL contains ``INSERT`` statements, those insertions will be
  performed every time your database is synchronized. This includes the
  synchronization of any test databases that are created when you run a
  test suite.
  
  However, in the process of testing the Django 1.3, it was discovered
  that this feature has never completely worked as advertised. When
  using database backends that don't support transactions, or when using
  a TransactionTestCase, data that has been inserted using custom SQL
  will not be visible during the testing process.
  
  Unfortunately, there was no way to rectify this problem without
  introducing a backwards incompatibility. Rather than leave
  SQL-inserted initial data in an uncertain state, Django now enforces
  the policy that data inserted by custom SQL will *not* be visible
  during testing.
  
  This change only affects the testing process. You can still use custom
  SQL to load data into your production database as part of the ``syncdb``
  process. If you require data to exist during test conditions, you
  should either insert it using :ref:`test fixtures
  <topics-testing-fixtures>`, or using the ``setUp()`` method of your
  test case.
  
  Changed priority of translation loading
  ---------------------------------------
  
  Work has been done to simplify, rationalize and properly document the algorithm
  used by Django at runtime to build translations from the different translations
  found on disk, namely:
  
  For translatable literals found in Python code and templates (``'django'``
  gettext domain):
  
  * Priorities of translations included with applications listed in the
  :setting:`INSTALLED_APPS` setting were changed. To provide a behavior
  consistent with other parts of Django that also use such setting (templates,
  etc.) now, when building the translation that will be made available, the
  apps listed first have higher precedence than the ones listed later.
  
  * Now it is possible to override the translations shipped with applications by
  using the :setting:`LOCALE_PATHS` setting whose translations have now higher
  precedence than the translations of :setting:`INSTALLED_APPS` applications.
  The relative priority among the values listed in this setting has also been
  modified so the paths listed first have higher precedence than the
  ones listed later.
  
  * The ``locale`` subdirectory of the directory containing the settings, that
  usually coincides with and is known as the *project directory* is being
  deprecated in this release as a source of translations. (the precedence of
  these translations is intermediate between applications and :setting:`LOCALE_PATHS`
  translations). See the `corresponding deprecated features section`_
  of this document.
  
  For translatable literals found in JavaScript code (``'djangojs'`` gettext
  domain):
  
  * Similarly to the ``'django'`` domain translations: Overriding of
  translations shipped with applications by using the :setting:`LOCALE_PATHS`
  setting is now possible for this domain too. These translations have higher
  precedence than the translations of Python packages passed to the
  ``javascript_catalog()`` view. Paths listed first have higher precedence than
  the ones listed later.
  
  * Translations under the ``locale`` subdirectory of the *project directory*
  have never been taken in account for JavaScript translations and remain in
  the same situation considering the deprecation of such location.
  
  .. _corresponding deprecated features section: loading_of_project_level_translations_
  
  Transaction management
  ----------------------
  
  When using managed transactions -- that is, anything but the default
  autocommit mode -- it is important when a transaction is marked as
  "dirty". Dirty transactions are committed by the ``commit_on_success``
  decorator or the ``django.middleware.transaction.TransactionMiddleware``, and
  ``commit_manually`` forces them to be closed explicitly; clean transactions
  "get a pass", which means they are usually rolled back at the end of a request
  when the connection is closed.
  
  Until Django 1.3, transactions were only marked dirty when Django was
  aware of a modifying operation performed in them; that is, either some
  model was saved, some bulk update or delete was performed, or the user
  explicitly called ``transaction.set_dirty()``. In Django 1.3, a
  transaction is marked dirty when *any* database operation is
  performed.
  
  As a result of this change, you no longer need to set a transaction
  dirty explicitly when you execute raw SQL or use a data-modifying
  ``SELECT``. However, you *do* need to explicitly close any read-only
  transactions that are being managed using ``commit_manually()``. For example::
  
  transaction.commit_manually
  def my_view(request, name):
  obj = get_object_or_404(MyObject, name__iexact=name)
  return render_to_response('template', {'object':obj})
  
  Prior to Django 1.3, this would work without error. However, under
  Django 1.3, this will raise a
  :class:`~django.db.transaction.TransactionManagementError` because
  the read operation that retrieves the ``MyObject`` instance leaves the
  transaction in a dirty state.
  
  No password reset for inactive users
  ------------------------------------
  
  Prior to Django 1.3, inactive users were able to request a password reset email
  and reset their password. In Django 1.3 inactive users will receive the same
  message as a nonexistent account.
  
  Password reset view now accepts ``from_email``
  ----------------------------------------------
  
  The ``django.contrib.auth.views.password_reset()`` view now accepts a
  ``from_email`` parameter, which is passed to the ``password_reset_form``’s
  ``save()`` method as a keyword argument. If you are using this view with a
  custom password reset form, then you will need to ensure your form's ``save()``
  method accepts this keyword argument.
  
  .. _deprecated-features-1.3:
  
  Features deprecated in 1.3
  ==========================
  
  Django 1.3 deprecates some features from earlier releases.
  These features are still supported, but will be gradually phased out
  over the next few release cycles.
  
  Code taking advantage of any of the features below will raise a
  ``PendingDeprecationWarning`` in Django 1.3. This warning will be
  silent by default, but may be turned on using Python's :mod:`warnings`
  module, or by running Python with a ``-Wd`` or ``-Wall`` flag.
  
  In Django 1.4, these warnings will become a ``DeprecationWarning``,
  which is *not* silent. In Django 1.5 support for these features will
  be removed entirely.
  
  .. seealso::
  
  For more details, see the documentation :doc:`Django's release process
  </internals/release-process>` and our :doc:`deprecation timeline
  </internals/deprecation>`.
  
  ``mod_python`` support
  ----------------------
  
  The ``mod_python`` library has not had a release since 2007 or a commit since
  2008. The Apache Foundation board voted to remove ``mod_python`` from the set
  of active projects in its version control repositories, and its lead developer
  has shifted all of his efforts toward the lighter, slimmer, more stable, and
  more flexible ``mod_wsgi`` backend.
  
  If you are currently using the ``mod_python`` request handler, you
  should redeploy your Django projects using another request handler.
  :doc:`mod_wsgi </howto/deployment/wsgi/modwsgi>` is the request handler
  recommended by the Django project, but FastCGI is also supported. Support for
  ``mod_python`` deployment will be removed in Django 1.5.
  
  Function-based generic views
  ----------------------------
  
  As a result of the introduction of class-based generic views, the
  function-based generic views provided by Django have been deprecated.
  The following modules and the views they contain have been deprecated:
  
  * ``django.views.generic.create_update``
  * ``django.views.generic.date_based``
  * ``django.views.generic.list_detail``
  * ``django.views.generic.simple``
  
  Test client response ``template`` attribute
  -------------------------------------------
  
  Django's :ref:`test client <test-client>` returns
  :class:`~django.test.Response` objects annotated with extra testing
  information. In Django versions prior to 1.3, this included a ``template``
  attribute containing information about templates rendered in generating the
  response: either None, a single :class:`~django.template.Template` object, or a
  list of :class:`~django.template.Template` objects. This inconsistency in
  return values (sometimes a list, sometimes not) made the attribute difficult
  to work with.
  
  In Django 1.3 the ``template`` attribute is deprecated in favor of a new
  :attr:`~django.test.Response.templates` attribute, which is always a
  list, even if it has only a single element or no elements.
  
  ``DjangoTestRunner``
  --------------------
  
  As a result of the introduction of support for ``unittest2``, the features
  of ``django.test.simple.DjangoTestRunner`` (including fail-fast
  and Ctrl-C test termination) have been made redundant. In view of this
  redundancy, ``DjangoTestRunner`` has been turned into an empty placeholder
  class, and will be removed entirely in Django 1.5.
  
  Changes to ``url`` and ``ssi``
  ------------------------------
  
  Most template tags will allow you to pass in either constants or
  variables as arguments -- for example::
  
  {% extends "base.html" %}
  
  allows you to specify a base template as a constant, but if you have a
  context variable ``templ`` that contains the value ``base.html``::
  
  {% extends templ %}
  
  is also legal.
  
  However, due to an accident of history, the ``url`` and ``ssi`` are different.
  These tags use the second, quoteless syntax, but interpret the argument as a
  constant. This means it isn't possible to use a context variable as the target
  of a ``url`` and ``ssi`` tag.
  
  Django 1.3 marks the start of the process to correct this historical
  accident. Django 1.3 adds a new template library -- ``future`` -- that
  provides alternate implementations of the ``url`` and ``ssi``
  template tags. This ``future`` library implement behavior that makes
  the handling of the first argument consistent with the handling of all
  other variables. So, an existing template that contains::
  
  {% url sample %}
  
  should be replaced with::
  
  {% load url from future %}
  {% url 'sample' %}
  
  The tags implementing the old behavior have been deprecated, and in
  Django 1.5, the old behavior will be replaced with the new behavior.
  To ensure compatibility with future versions of Django, existing
  templates should be modified to use the new ``future`` libraries and
  syntax.
  
  Changes to the login methods of the admin
  -----------------------------------------
  
  In previous version the admin app defined login methods in multiple locations
  and ignored the almost identical implementation in the already used auth app.
  A side effect of this duplication was the missing adoption of the changes made
  in r12634_ to support a broader set of characters for usernames.
  
  This release refactors the admin's login mechanism to use a subclass of the
  :class:`~django.contrib.auth.forms.AuthenticationForm` instead of a manual
  form validation. The previously undocumented method
  ``'django.contrib.admin.sites.AdminSite.display_login_form'`` has been removed
  in favor of a new :attr:`~django.contrib.admin.AdminSite.login_form`
  attribute.
  
  .. _r12634: https://code.djangoproject.com/changeset/12634
  
  ``reset`` and ``sqlreset`` management commands
  ----------------------------------------------
  
  Those commands have been deprecated. The ``flush`` and ``sqlflush`` commands
  can be used to delete everything. You can also use ALTER TABLE or DROP TABLE
  statements manually.
  
  
  GeoDjango
  ---------
  
  * The function-based :setting:`TEST_RUNNER` previously used to execute
  the GeoDjango test suite, ``django.contrib.gis.tests.run_gis_tests``, was
  deprecated for the class-based runner,
  ``django.contrib.gis.tests.GeoDjangoTestSuiteRunner``.
  
  * Previously, calling
  :meth:`~django.contrib.gis.geos.GEOSGeometry.transform` would
  silently do nothing when GDAL wasn't available.  Now, a
  :class:`~django.contrib.gis.geos.GEOSException` is properly raised
  to indicate possible faulty application code.  A warning is now
  raised if :meth:`~django.contrib.gis.geos.GEOSGeometry.transform` is
  called when the SRID of the geometry is less than 0 or ``None``.
  
  ``CZBirthNumberField.clean``
  ----------------------------
  
  Previously this field's ``clean()`` method accepted a second, gender, argument
  which allowed stronger validation checks to be made, however since this
  argument could never actually be passed from the Django form machinery it is
  now pending deprecation.
  
  ``CompatCookie``
  ----------------
  
  Previously, ``django.http`` exposed an undocumented ``CompatCookie`` class,
  which was a bugfix wrapper around the standard library ``SimpleCookie``. As the
  fixes are moving upstream, this is now deprecated - you should use ``from
  django.http import SimpleCookie`` instead.
  
  .. _loading_of_project_level_translations:
  
  Loading of *project-level* translations
  ---------------------------------------
  
  This release of Django starts the deprecation process for inclusion of
  translations located under the so-called *project path* in the translation
  building process performed at runtime. The :setting:`LOCALE_PATHS` setting can
  be used for the same task by adding the filesystem path to a ``locale``
  directory containing project-level translations to the value of that setting.
  
  Rationale for this decision:
  
  * The *project path* has always been a loosely defined concept
  (actually, the directory used for locating project-level
  translations is the directory containing the settings module) and
  there has been a shift in other parts of the framework to stop using
  it as a reference for location of assets at runtime.
  
  * Detection of the ``locale`` subdirectory tends to fail when the
  deployment scenario is more complex than the basic one. e.g. it
  fails when the settings module is a directory (ticket 10765).
  
  * There are potential strange development- and deployment-time
  problems like the fact that the ``project_dir/locale/`` subdir can
  generate spurious error messages when the project directory is added
  to the Python path (``manage.py runserver`` does this) and then it
  clashes with the equally named standard library module, this is a
  typical warning message::
  
  /usr/lib/python2.6/gettext.py:49: ImportWarning: Not importing directory '/path/to/project/locale': missing __init__.py.
  import locale, copy, os, re, struct, sys
  
  * This location wasn't included in the translation building process
  for JavaScript literals. This deprecation removes such
  inconsistency.
  
  ``PermWrapper`` moved to ``django.contrib.auth.context_processors``
  -------------------------------------------------------------------
  
  In Django 1.2, we began the process of changing the location of the
  ``auth`` context processor from ``django.core.context_processors`` to
  ``django.contrib.auth.context_processors``. However, the
  ``PermWrapper`` support class was mistakenly omitted from that
  migration. In Django 1.3, the ``PermWrapper`` class has also been
  moved to ``django.contrib.auth.context_processors``, along with the
  ``PermLookupDict`` support class. The new classes are functionally
  identical to their old versions; only the module location has changed.
  
  Removal of ``XMLField``
  -----------------------
  
  When Django was first released, Django included an ``XMLField`` that performed
  automatic XML validation for any field input. However, this validation function
  hasn't been performed since the introduction of ``newforms``, prior to the 1.0
  release. As a result, ``XMLField`` as currently implemented is functionally
  indistinguishable from a simple :class:`~django.db.models.TextField`.
  
  For this reason, Django 1.3 has fast-tracked the deprecation of
  ``XMLField`` -- instead of a two-release deprecation, ``XMLField``
  will be removed entirely in Django 1.4.
  
  It's easy to update your code to accommodate this change -- just
  replace all uses of ``XMLField`` with ``TextField``, and remove the
  ``schema_path`` keyword argument (if it is specified).
  
  
  ==========================

1.2.7 not secure

==========================
  
  *September 10, 2011*
  
  Welcome to Django 1.2.7!
  
  This is the seventh bugfix/security release in the Django 1.2 series. It
  replaces Django 1.2.6 due to problems with the 1.2.6 release tarball.
  Django 1.2.7 is a recommended upgrade for all users of any Django release in
  the 1.2.X series.
  
  For more information, see the `release advisory`_.
  
  .. _release advisory: https://www.djangoproject.com/weblog/2011/sep/10/127/
  
  
  ==========================

1.2.6 not secure

==========================
  
  *September 9, 2011*
  
  Welcome to Django 1.2.6!
  
  This is the sixth bugfix/security release in the Django 1.2 series, fixing
  several security issues present in Django 1.2.5.  Django 1.2.6 is a
  recommended upgrade for all users of any Django release in the 1.2.X series.
  
  For a full list of issues addressed in this release, see the `security
  advisory`_.
  
  .. _security advisory: https://www.djangoproject.com/weblog/2011/sep/09/security-releases-issued/
  
  
  ==========================

1.2.5 not secure

==========================
  
  Welcome to Django 1.2.5!
  
  This is the fifth "bugfix" release in the Django 1.2 series,
  improving the stability and performance of the Django 1.2 codebase.
  
  With four exceptions, Django 1.2.5 maintains backwards compatibility
  with Django 1.2.4. It also contains a number of fixes and other
  improvements. Django 1.2.5 is a recommended upgrade for any
  development or deployment currently using or targeting Django 1.2.
  
  For full details on the new features, backwards incompatibilities, and
  deprecated features in the 1.2 branch, see the :doc:`/releases/1.2`.
  
  Backwards incompatible changes
  ==============================
  
  CSRF exception for AJAX requests
  --------------------------------
  
  Django includes a CSRF-protection mechanism, which makes use of a
  token inserted into outgoing forms. Middleware then checks for the
  token's presence on form submission, and validates it.
  
  Prior to Django 1.2.5, our CSRF protection made an exception for AJAX
  requests, on the following basis:
  
  * Many AJAX toolkits add an X-Requested-With header when using
  XMLHttpRequest.
  
  * Browsers have strict same-origin policies regarding
  XMLHttpRequest.
  
  * In the context of a browser, the only way that a custom header
  of this nature can be added is with XMLHttpRequest.
  
  Therefore, for ease of use, we did not apply CSRF checks to requests
  that appeared to be AJAX on the basis of the X-Requested-With header.
  The Ruby on Rails web framework had a similar exemption.
  
  Recently, engineers at Google made members of the Ruby on Rails
  development team aware of a combination of browser plugins and
  redirects which can allow an attacker to provide custom HTTP headers
  on a request to any website. This can allow a forged request to appear
  to be an AJAX request, thereby defeating CSRF protection which trusts
  the same-origin nature of AJAX requests.
  
  Michael Koziarski of the Rails team brought this to our attention, and
  we were able to produce a proof-of-concept demonstrating the same
  vulnerability in Django's CSRF handling.
  
  To remedy this, Django will now apply full CSRF validation to all
  requests, regardless of apparent AJAX origin. This is technically
  backwards-incompatible, but the security risks have been judged to
  outweigh the compatibility concerns in this case.
  
  Additionally, Django will now accept the CSRF token in the custom HTTP
  header X-CSRFTOKEN, as well as in the form submission itself, for ease
  of use with popular JavaScript toolkits which allow insertion of
  custom headers into all AJAX requests.
  
  Please see the :ref:`CSRF docs for example jQuery code <csrf-ajax>`
  that demonstrates this technique, ensuring that you are looking at the
  documentation for your version of Django, as the exact code necessary
  is different for some older versions of Django.
  
  FileField no longer deletes files
  ---------------------------------
  
  In earlier Django versions, when a model instance containing a
  :class:`~django.db.models.FileField` was deleted,
  :class:`~django.db.models.FileField` took it upon itself to also delete the
  file from the backend storage. This opened the door to several potentially
  serious data-loss scenarios, including rolled-back transactions and fields on
  different models referencing the same file. In Django 1.2.5,
  :class:`~django.db.models.FileField` will never delete files from the backend
  storage. If you need cleanup of orphaned files, you'll need to handle it
  yourself (for instance, with a custom management command that can be run
  manually or scheduled to run periodically via e.g. cron).
  
  Use of custom SQL to load initial data in tests
  -----------------------------------------------
  
  Django provides a custom SQL hooks as a way to inject hand-crafted SQL
  into the database synchronization process. One of the possible uses
  for this custom SQL is to insert data into your database. If your
  custom SQL contains ``INSERT`` statements, those insertions will be
  performed every time your database is synchronized. This includes the
  synchronization of any test databases that are created when you run a
  test suite.
  
  However, in the process of testing the Django 1.3, it was discovered
  that this feature has never completely worked as advertised. When
  using database backends that don't support transactions, or when using
  a TransactionTestCase, data that has been inserted using custom SQL
  will not be visible during the testing process.
  
  Unfortunately, there was no way to rectify this problem without
  introducing a backwards incompatibility. Rather than leave
  SQL-inserted initial data in an uncertain state, Django now enforces
  the policy that data inserted by custom SQL will *not* be visible
  during testing.
  
  This change only affects the testing process. You can still use custom
  SQL to load data into your production database as part of the ``syncdb``
  process. If you require data to exist during test conditions, you
  should either insert it using :ref:`test fixtures
  <topics-testing-fixtures>`, or using the ``setUp()`` method of your
  test case.
  
  ModelAdmin.lookup_allowed signature changed
  -------------------------------------------
  
  Django 1.2.4 introduced a method ``lookup_allowed`` on ``ModelAdmin``, to cope
  with a security issue (changeset `[15033]
  <https://code.djangoproject.com/changeset/15033>`_). Although this method was
  never documented, it seems some people have overridden ``lookup_allowed``,
  especially to cope with regressions introduced by that changeset. While the
  method is still undocumented and not marked as stable, it may be helpful to know
  that the signature of this function has changed.
  
  
  ==========================

1.2.4 not secure

==========================
  
  Welcome to Django 1.2.4!
  
  This is the fourth "bugfix" release in the Django 1.2 series,
  improving the stability and performance of the Django 1.2 codebase.
  
  With one exception, Django 1.2.4 maintains backwards compatibility
  with Django 1.2.3. It also contains a number of fixes and other
  improvements. Django 1.2.4 is a recommended upgrade for any
  development or deployment currently using or targeting Django 1.2.
  
  For full details on the new features, backwards incompatibilities, and
  deprecated features in the 1.2 branch, see the :doc:`/releases/1.2`.
  
  Backwards incompatible changes
  ==============================
  
  Restricted filters in admin interface
  -------------------------------------
  
  The Django administrative interface, ``django.contrib.admin``, supports
  filtering of displayed lists of objects by fields on the corresponding
  models, including across database-level relationships. This is
  implemented by passing lookup arguments in the querystring portion of
  the URL, and options on the ModelAdmin class allow developers to
  specify particular fields or relationships which will generate
  automatic links for filtering.
  
  One historically-undocumented and -unofficially-supported feature has
  been the ability for a user with sufficient knowledge of a model's
  structure and the format of these lookup arguments to invent useful
  new filters on the fly by manipulating the querystring.
  
  However, it has been demonstrated that this can be abused to gain
  access to information outside of an admin user's permissions; for
  example, an attacker with access to the admin and sufficient knowledge
  of model structure and relations could construct query strings which --
  with repeated use of regular-expression lookups supported by the
  Django database API -- expose sensitive information such as users'
  password hashes.
  
  To remedy this, ``django.contrib.admin`` will now validate that
  querystring lookup arguments either specify only fields on the model
  being viewed, or cross relations which have been explicitly
  allowed by the application developer using the pre-existing
  mechanism mentioned above. This is backwards-incompatible for any
  users relying on the prior ability to insert arbitrary lookups.
  
  One new feature
  ===============
  
  Ordinarily, a point release would not include new features, but in the
  case of Django 1.2.4, we have made an exception to this rule.
  
  One of the bugs fixed in Django 1.2.4 involves a set of
  circumstances whereby a running a test suite on a multiple database
  configuration could cause the original source database (i.e., the
  actual production database) to be dropped, causing catastrophic loss
  of data. In order to provide a fix for this problem, it was necessary
  to introduce a new setting -- :setting:`TEST_DEPENDENCIES` -- that
  allows you to define any creation order dependencies in your database
  configuration.
  
  Most users -- even users with multiple-database configurations -- need
  not be concerned about the data loss bug, or the manual configuration of
  :setting:`TEST_DEPENDENCIES`. See the :ticket:`original problem report <14415>`
  documentation on :ref:`controlling the creation order of test
  databases <topics-testing-creation-dependencies>` for details.
  
  GeoDjango
  =========
  
  The function-based :setting:`TEST_RUNNER` previously used to execute
  the GeoDjango test suite, ``django.contrib.gis.tests.run_gis_tests``,
  was finally deprecated in favor of a class-based test runner,
  ``django.contrib.gis.tests.GeoDjangoTestSuiteRunner``, added in this
  release.
  
  In addition, the GeoDjango test suite is now included when
  :ref:`running the Django test suite <running-unit-tests>` with ``runtests.py``
  and using :ref:`spatial database backends <spatial-backends>`.
  
  
  ==========================

1.2.3 not secure

==========================
  
  Django 1.2.3 fixed a couple of release problems in the 1.2.2 release and was
  released two days after 1.2.2.
  
  This release corrects the following problems:
  
  * The patch_ applied for the security issue covered in Django 1.2.2 caused
  issues with non-ASCII responses using CSRF tokens.
  
  * The patch also caused issues with some forms, most notably the user-editing
  forms in the Django administrative interface.
  
  * The packaging manifest did not contain the full list of required files.
  
  .. _patch: https://code.djangoproject.com/changeset/13699
  
  
  
  ==========================

1.2.2 not secure

==========================
  
  Welcome to Django 1.2.2!
  
  This is the second "bugfix" release in the Django 1.2 series,
  improving the stability and performance of the Django 1.2 codebase.
  
  Django 1.2.2 maintains backwards compatibility with Django
  1.2.1, but contain a number of fixes and other
  improvements. Django 1.2.2 is a recommended upgrade for any
  development or deployment currently using or targeting Django 1.2.
  
  For full details on the new features, backwards incompatibilities, and
  deprecated features in the 1.2 branch, see the :doc:`/releases/1.2`.
  
  One new feature
  ===============
  
  Ordinarily, a point release would not include new features, but in the
  case of Django 1.2.2, we have made an exception to this rule.
  
  In order to test a bug fix that forms part of the 1.2.2 release, it
  was necessary to add a feature -- the ``enforce_csrf_checks`` flag --
  to the :ref:`test client <test-client>`. This flag forces
  the test client to perform full CSRF checks on forms. The default
  behavior of the test client hasn't changed, but if you want to do
  CSRF checks with the test client, it is now possible to do so.
  
  
  ==========================

1.2.1 not secure

==========================
  
  Django 1.2.1 was released almost immediately after 1.2.0 to correct two small
  bugs: one was in the documentation packaging script, the other was a
  :ticket:`bug <13560>` that affected datetime form field widgets when
  localization was enabled.
  
  
  ========================

1.2 not secure

========================
  
  *May 17, 2010.*
  
  Welcome to Django 1.2!
  
  Nearly a year in the making, Django 1.2 packs an impressive list of :ref:`new
  features <whats-new-1.2>` and lots of bug fixes. These release notes cover
  the new features, as well as important changes you'll want to be aware of when
  upgrading from Django 1.1 or older versions.
  
  Overview
  ========
  
  Django 1.2 introduces several large, important new features, including:
  
  * Support for `multiple database connections`_ in a single Django instance.
  
  * `Model validation`_ inspired by Django's form validation.
  
  * Vastly `improved protection against Cross-Site Request Forgery`_ (CSRF).
  
  * A new `user "messages" framework`_ with support for cookie- and session-based
  message for both anonymous and authenticated users.
  
  * Hooks for `object-level permissions`_, `permissions for anonymous users`_,
  and `more flexible username requirements`_.
  
  * Customization of email sending via `email backends`_.
  
  * New :ref:`"smart" if template tag <new-in-1.2-smart-if>` which supports
  comparison operators.
  
  .. _multiple database connections: `support for multiple databases`_
  .. _improved protection against Cross-Site Request Forgery: `improved CSRF protection`_
  .. _user "messages" framework: `messages framework`_
  .. _more flexible username requirements: `relaxed requirements for usernames`_
  
  These are just the highlights; full details and a complete list of features `may
  be found below`_.
  
  .. _may be found below: `What's new in Django 1.2`_
  
  .. seealso::
  
  `Django Advent`_ covered the release of Django 1.2 with a series of
  articles and tutorials that cover some of the new features in depth.
  
  .. _django advent: https://github.com/djangoadvent/djangoadvent-articles
  
  Wherever possible these features have been introduced in a backwards-compatible
  manner per :doc:`our API stability policy </misc/api-stability>` policy.
  
  However, a handful of features *have* changed in ways that, for some users, will be
  backwards-incompatible. The big changes are:
  
  * Support for Python 2.3 has been dropped. See the full notes
  below.
  
  * The new CSRF protection framework is not backwards-compatible with
  the old system. Users of the old system will not be affected until
  the old system is removed in Django 1.4.
  
  However, upgrading to the new CSRF protection framework requires a few
  important backwards-incompatible changes, detailed in `CSRF Protection`_,
  below.
  
  * Authors of custom :class:`~django.db.models.Field` subclasses should be
  aware that a number of methods have had a change in prototype, detailed
  under `get_db_prep_*() methods on Field`_, below.
  
  * The internals of template tags have changed somewhat; authors of custom
  template tags that need to store state (e.g. custom control flow tags)
  should ensure that their code follows the new rules for `stateful template
  tags`_
  
  * The :func:`~django.contrib.auth.decorators.user_passes_test`,
  :func:`~django.contrib.auth.decorators.login_required`, and
  :func:`~django.contrib.auth.decorators.permission_required`, decorators
  from :mod:`django.contrib.auth` only apply to functions and no longer
  work on methods. There's a simple one-line fix `detailed below`_.
  
  .. _detailed below: `user_passes_test, login_required and permission_required`_
  
  Again, these are just the big features that will affect the most users. Users
  upgrading from previous versions of Django are heavily encouraged to consult
  the complete list of :ref:`backwards-incompatible changes
  <backwards-incompatible-changes-1.2>` and the list of :ref:`deprecated
  features <deprecated-features-1.2>`.
  
  Python compatibility
  ====================
  
  While not a new feature, it's important to note that Django 1.2
  introduces the first shift in our Python compatibility policy since
  Django's initial public debut. Previous Django releases were tested
  and supported on 2.x Python versions from 2.3 up; Django 1.2, however,
  drops official support for Python 2.3. As such, the minimum Python
  version required for Django is now 2.4, and Django is tested and
  supported on Python 2.4, 2.5 and 2.6, and will be supported on the
  as-yet-unreleased Python 2.7.
  
  This change should affect only a small number of Django users, as most
  operating-system vendors today are shipping Python 2.4 or newer as
  their default version. If you're still using Python 2.3, however,
  you'll need to stick to Django 1.1 until you can upgrade; per
  :doc:`our support policy </internals/release-process>`, Django 1.1 will
  continue to receive security support until the release of Django 1.3.
  
  A roadmap for Django's overall 2.x Python support, and eventual
  transition to Python 3.x, is currently being developed, and will be
  announced prior to the release of Django 1.3.
  
  .. _whats-new-1.2:
  
  What's new in Django 1.2
  ========================
  
  Support for multiple databases
  ------------------------------
  
  Django 1.2 adds the ability to use :doc:`more than one database
  </topics/db/multi-db>` in your Django project. Queries can be issued at a
  specific database with the ``using()`` method on ``QuerySet`` objects.
  Individual objects can be saved to a specific database by providing a ``using``
  argument when you call ``save()``.
  
  Model validation
  ----------------
  
  Model instances now have support for :ref:`validating their own data
  <validating-objects>`, and both model and form fields now accept configurable
  lists of :doc:`validators </ref/validators>` specifying reusable, encapsulated
  validation behavior. Note, however, that validation must still be performed
  explicitly. Simply invoking a model instance's ``save()`` method will not
  perform any validation of the instance's data.
  
  Improved CSRF protection
  ------------------------
  
  Django now has much improved protection against :doc:`Cross-Site Request Forgery
  (CSRF) attacks</ref/csrf>`. This type of attack occurs when a malicious
  website contains a link, a form button or some JavaScript that is intended to
  perform some action on your website, using the credentials of a logged-in user
  who visits the malicious site in their browser. A related type of attack, "login
  CSRF," where an attacking site tricks a user's browser into logging into a site
  with someone else's credentials, is also covered.
  
  Messages framework
  ------------------
  
  Django now includes a robust and configurable :doc:`messages framework
  </ref/contrib/messages>` with built-in support for cookie- and session-based
  messaging, for both anonymous and authenticated clients. The messages framework
  replaces the deprecated user message API and allows you to temporarily store
  messages in one request and retrieve them for display in a subsequent request
  (usually the next one).
  
  Object-level permissions
  ------------------------
  
  A foundation for specifying permissions at the per-object level has been added.
  Although there is no implementation of this in core, a custom authentication
  backend can provide this implementation and it will be used by
  :class:`django.contrib.auth.models.User`. See the :doc:`authentication docs
  </topics/auth/index>` for more information.
  
  Permissions for anonymous users
  -------------------------------
  
  If you provide a custom auth backend with ``supports_anonymous_user`` set to
  ``True``, AnonymousUser will check the backend for permissions, just like
  User already did.  This is useful for centralizing permission handling - apps
  can always delegate the question of whether something is allowed or not to
  the authorization/authentication backend. See the :doc:`authentication
  docs </topics/auth/index>` for more details.
  
  Relaxed requirements for usernames
  ----------------------------------
  
  The built-in :class:`~django.contrib.auth.models.User` model's
  :attr:`~django.contrib.auth.models.User.username` field now allows a wider range
  of characters, including `, ``+``, ``.`` and ``-`` characters.
  
  Email backends
  --------------
  
  You can now :ref:`configure the way that Django sends email
  <topic-email-backends>`. Instead of using SMTP to send all email, you
  can now choose a configurable email backend to send messages. If your
  hosting provider uses a sandbox or some other non-SMTP technique for
  sending mail, you can now construct an email backend that will allow
  Django's standard :doc:`mail sending methods</topics/email>` to use
  those facilities.
  
  This also makes it easier to debug mail sending. Django ships with
  backend implementations that allow you to send email to a
  :ref:`file<topic-email-file-backend>`, to the
  :ref:`console<topic-email-console-backend>`, or to
  :ref:`memory<topic-email-memory-backend>`. You can even configure all
  email to be :ref:`thrown away<topic-email-dummy-backend>`.
  
  .. _new-in-1.2-smart-if:
  
  "Smart" :ttag:`if` tag
  ----------------------
  
  The :ttag:`if` tag has been upgraded to be much more powerful. First, we've
  added support for comparison operators. No longer will you have to type:
  
  .. code-block:: html+django
  
  {% ifnotequal a b %}
  ...
  {% endifnotequal %}
  
  You can now do this:
  
  .. code-block:: html+django
  
  {% if a != b %}
  ...
  {% endif %}
  
  There's really no reason to use ``{% ifequal %}`` or ``{% ifnotequal %}``
  anymore, unless you're the nostalgic type.
  
  The operators supported are ``==``, ``!=``, ``<``, ``>``, ``<=``, ``>=``,
  ``in`` and ``not in``, all of which work like the Python operators, in addition
  to ``and``, ``or`` and ``not``, which were already supported.
  
  Also, filters may now be used in the ``if`` expression. For example:
  
  .. code-block:: html+django
  
  <div
  {% if user.email|lower == message.recipient|lower %}
  class="highlight"
  {% endif %}
  >{{ message }}</div>
  
  Template caching
  ----------------
  
  In previous versions of Django, every time you rendered a template, it
  would be reloaded from disk. In Django 1.2, you can use a :ref:`cached
  template loader <template-loaders>` to load templates once, then
  cache the result for every subsequent render. This can lead to a
  significant performance improvement if your templates are broken into
  lots of smaller subtemplates (using the ``{% extends %}`` or ``{%
  include %}`` tags).
  
  As a side effect, it is now much easier to support non-Django template
  languages.
  
  Class-based template loaders
  ----------------------------
  
  As part of the changes made to introduce `Template caching`_  and following
  a general trend in Django, the template loaders API has been modified
  to use template loading mechanisms that are encapsulated in Python classes as
  opposed to functions, the only method available until Django 1.1.
  
  All the template loaders :ref:`shipped with Django <template-loaders>` have
  been ported to the new API but they still implement the function-based API and
  the template core machinery still accepts function-based loaders (builtin or
  third party) so there is no immediate need to modify your ``TEMPLATE_LOADERS``
  setting in existing projects, things will keep working if you leave it
  untouched up to and including the Django 1.3 release.
  
  If you have developed your own custom template loaders we suggest to consider
  porting them to a class-based implementation because the code for backwards
  compatibility with function-based loaders starts its deprecation process in
  Django 1.2 and will be removed in Django 1.4.  There is a description of the
  API these loader classes must implement in the template API reference and you
  can also examine the source code of the loaders shipped with Django.
  
  Natural keys in fixtures
  ------------------------
  
  Fixtures can now refer to remote objects using
  :ref:`topics-serialization-natural-keys`. This lookup scheme is an
  alternative to the normal primary-key based object references in a
  fixture, improving readability and resolving problems referring to
  objects whose primary key value may not be predictable or known.
  
  Fast failure for tests
  ----------------------
  
  Both the :djadmin:`test` subcommand of ``django-admin.py`` and the
  ``runtests.py`` script used to run Django's own test suite now support a
  ``--failfast`` option. When specified, this option causes the test runner to
  exit after encountering a failure instead of continuing with the test run. In
  addition, the handling of ``Ctrl-C`` during a test run has been improved to
  trigger a graceful exit from the test run that reports details of the tests that
  were run before the interruption.
  
  ``BigIntegerField``
  -------------------
  
  Models can now use a 64-bit :class:`~django.db.models.BigIntegerField` type.
  
  Improved localization
  ---------------------
  
  Django's :doc:`internationalization framework </topics/i18n/index>` has been expanded
  with locale-aware formatting and form processing. That means, if enabled, dates
  and numbers on templates will be displayed using the format specified for the
  current locale. Django will also use localized formats when parsing data in
  forms. See :doc:`/topics/i18n/formatting` for more details.
  
  ``readonly_fields`` in ``ModelAdmin``
  -------------------------------------
  
  :attr:`django.contrib.admin.ModelAdmin.readonly_fields` has been added to
  enable non-editable fields in add/change pages for models and inlines. Field
  and calculated values can be displayed alongside editable fields.
  
  Customizable syntax highlighting
  --------------------------------
  
  You can now use a :envvar:`DJANGO_COLORS` environment variable to modify or
  disable the colors used by ``django-admin.py`` to provide :ref:`syntax
  highlighting <syntax-coloring>`.
  
  Syndication feeds as views
  --------------------------
  
  :doc:`Syndication feeds </ref/contrib/syndication>` can now be used directly as
  views in your :doc:`URLconf </topics/http/urls>`. This means that you can
  maintain complete control over the URL structure of your feeds. Like any other
  view, feeds views are passed a ``request`` object, so you can do anything you
  would normally do with a view, like user based access control, or making a feed
  a named URL.
  
  GeoDjango
  ---------
  
  The most significant new feature for :doc:`GeoDjango </ref/contrib/gis/index>`
  in 1.2 is support for multiple spatial databases.  As a result,
  the following :ref:`spatial database backends <spatial-backends>`
  are now included:
  
  * ``django.contrib.gis.db.backends.postgis``
  * ``django.contrib.gis.db.backends.mysql``
  * ``django.contrib.gis.db.backends.oracle``
  * ``django.contrib.gis.db.backends.spatialite``
  
  GeoDjango now supports the rich capabilities added in the PostGIS 1.5 release.
  New features include support for the :ref:`geography type <geography-type>`
  and enabling of :ref:`distance queries <distance-queries>`
  with non-point geometries on geographic coordinate systems.
  
  Support for 3D