2011-03-30 17:34:01 +00:00
|
|
|
============================================
|
|
|
|
Django 1.4 release notes - UNDER DEVELOPMENT
|
|
|
|
============================================
|
|
|
|
|
|
|
|
This page documents release notes for the as-yet-unreleased Django
|
|
|
|
1.4. As such, it's tentative and subject to change. It provides
|
|
|
|
up-to-date information for those who are following trunk.
|
|
|
|
|
|
|
|
Django 1.4 includes various `new features`_ and some minor `backwards
|
2011-12-30 19:18:03 +00:00
|
|
|
incompatible changes`_. We've also dropped some features, which are detailed
|
|
|
|
in :doc:`our deprecation plan </internals/deprecation>`, and we've
|
|
|
|
`begun the deprecation process for some features`_.
|
2011-06-08 11:12:01 +00:00
|
|
|
|
2011-12-23 12:19:05 +00:00
|
|
|
.. _`new features`: `What's new in Django 1.4`_
|
|
|
|
.. _`backwards incompatible changes`: `Backwards incompatible changes in 1.4`_
|
|
|
|
.. _`begun the deprecation process for some features`: `Features deprecated in 1.4`_
|
2011-03-30 17:34:01 +00:00
|
|
|
|
2011-06-09 20:01:28 +00:00
|
|
|
Python compatibility
|
|
|
|
====================
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-06-09 20:01:28 +00:00
|
|
|
|
|
|
|
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
|
2011-12-30 19:18:03 +00:00
|
|
|
Django 1.3 until you can upgrade. Per :doc:`our support policy
|
2011-06-09 20:01:28 +00:00
|
|
|
</internals/release-process>`, Django 1.3 will continue to receive security
|
|
|
|
support until the release of Django 1.5.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-06-09 20:01:28 +00:00
|
|
|
|
2011-03-30 17:34:01 +00:00
|
|
|
What's new in Django 1.4
|
|
|
|
========================
|
|
|
|
|
Fixed #2879 -- Added support for the integration with Selenium and other in-browser testing frameworks. Also added the first Selenium tests for `contrib.admin`. Many thanks to everyone for their contributions and feedback: Mikeal Rogers, Dirk Datzert, mir, Simon G., Almad, Russell Keith-Magee, Denis Golomazov, devin, robertrv, andrewbadr, Idan Gazit, voidspace, Tom Christie, hjwp2, Adam Nelson, Jannis Leidel, Anssi Kääriäinen, Preston Holmes, Bruno Renié and Jacob Kaplan-Moss.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@17241 bcc190cf-cafb-0310-a4f2-bffc1f526a37
2011-12-22 08:33:58 +00:00
|
|
|
Support for in-browser testing frameworks
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-15 17:33:51 +00:00
|
|
|
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
|
Fixed #2879 -- Added support for the integration with Selenium and other in-browser testing frameworks. Also added the first Selenium tests for `contrib.admin`. Many thanks to everyone for their contributions and feedback: Mikeal Rogers, Dirk Datzert, mir, Simon G., Almad, Russell Keith-Magee, Denis Golomazov, devin, robertrv, andrewbadr, Idan Gazit, voidspace, Tom Christie, hjwp2, Adam Nelson, Jannis Leidel, Anssi Kääriäinen, Preston Holmes, Bruno Renié and Jacob Kaplan-Moss.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@17241 bcc190cf-cafb-0310-a4f2-bffc1f526a37
2011-12-22 08:33:58 +00:00
|
|
|
:class:`documentation<django.test.LiveServerTestCase>` for more details and
|
|
|
|
concrete examples.
|
|
|
|
|
|
|
|
.. _Selenium: http://seleniumhq.org/
|
|
|
|
|
2011-04-20 21:00:24 +00:00
|
|
|
``SELECT FOR UPDATE`` support
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Django 1.4 includes a :meth:`QuerySet.select_for_update()
|
|
|
|
<django.db.models.query.QuerySet.select_for_update>` method, which generates a
|
2011-04-20 21:00:24 +00:00
|
|
|
``SELECT ... FOR UPDATE`` SQL query. This will lock rows until the end of the
|
2011-12-30 19:18:03 +00:00
|
|
|
transaction, meaning other transactions cannot modify or delete rows matched by
|
|
|
|
a ``FOR UPDATE`` query.
|
2011-04-20 21:00:24 +00:00
|
|
|
|
|
|
|
For more details, see the documentation for
|
|
|
|
:meth:`~django.db.models.query.QuerySet.select_for_update`.
|
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
``Model.objects.bulk_create`` in the ORM
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
This method lets you create multiple objects more efficiently. It can result in
|
|
|
|
significant performance increases if you have many objects.
|
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
Django makes use of this internally, meaning some operations (such as database
|
2011-10-22 06:13:01 +00:00
|
|
|
setup for test suites) have seen a performance benefit as a result.
|
2011-10-01 15:43:01 +00:00
|
|
|
|
|
|
|
See the :meth:`~django.db.models.query.QuerySet.bulk_create` docs for more
|
|
|
|
information.
|
|
|
|
|
2011-10-05 23:14:52 +00:00
|
|
|
``QuerySet.prefetch_related``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-10-07 16:05:53 +00:00
|
|
|
Similar to :meth:`~django.db.models.query.QuerySet.select_related` but with a
|
|
|
|
different strategy and broader scope,
|
2011-10-05 23:14:52 +00:00
|
|
|
:meth:`~django.db.models.query.QuerySet.prefetch_related` has been added to
|
2011-10-07 16:05:53 +00:00
|
|
|
:class:`~django.db.models.query.QuerySet`. This method returns a new
|
2011-12-23 01:49:32 +00:00
|
|
|
``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,
|
|
|
|
:class:`~django.contrib.contenttypes.generic.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``
|
2011-12-30 19:18:03 +00:00
|
|
|
each have many related objects that you also need to fetch.
|
2011-12-23 01:49:32 +00:00
|
|
|
|
2011-12-23 03:46:06 +00:00
|
|
|
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: http://en.wikipedia.org/wiki/SHA1
|
|
|
|
.. _pbkdf2: http://en.wikipedia.org/wiki/PBKDF2
|
|
|
|
.. _nist: http://csrc.nist.gov/publications/nistpubs/800-132/nist-sp800-132.pdf
|
|
|
|
.. _bcrypt: http://en.wikipedia.org/wiki/Bcrypt
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
HTML5 doctype
|
2011-12-23 01:49:32 +00:00
|
|
|
~~~~~~~~~~~~~
|
2011-04-21 00:00:32 +00:00
|
|
|
|
|
|
|
We've switched the admin and other bundled templates to use the HTML5
|
2011-12-23 01:49:32 +00:00
|
|
|
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.
|
2011-04-21 00:00:32 +00:00
|
|
|
|
2011-05-03 10:44:23 +00:00
|
|
|
List filters in admin interface
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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`.
|
2011-05-03 10:44:23 +00:00
|
|
|
|
2011-06-02 16:18:47 +00:00
|
|
|
Multiple sort in admin interface
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
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
|
2011-12-30 19:18:03 +00:00
|
|
|
behavior of desktop GUIs. We also added a
|
2011-12-23 01:49:32 +00:00
|
|
|
:meth:`~django.contrib.admin.ModelAdmin.get_ordering` method for specifying the
|
2011-12-30 19:18:03 +00:00
|
|
|
ordering dynamically (i.e., depending on the request).
|
2011-06-02 16:18:47 +00:00
|
|
|
|
2011-10-26 12:19:18 +00:00
|
|
|
New ``ModelAdmin`` methods
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~
|
2011-07-03 17:56:43 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
We added a :meth:`~django.contrib.admin.ModelAdmin.save_related` method to
|
2011-12-23 01:49:32 +00:00
|
|
|
:mod:`~django.contrib.admin.ModelAdmin` to ease customization of how
|
2011-07-03 17:56:43 +00:00
|
|
|
related objects are saved in the admin.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Two other new :class:`~django.contrib.admin.ModelAdmin` methods,
|
2011-10-26 12:19:18 +00:00
|
|
|
:meth:`~django.contrib.admin.ModelAdmin.get_list_display` and
|
|
|
|
:meth:`~django.contrib.admin.ModelAdmin.get_list_display_links`
|
2011-12-30 19:18:03 +00:00
|
|
|
enable dynamic customization of fields and links displayed on the admin
|
|
|
|
change list.
|
2011-10-26 12:19:18 +00:00
|
|
|
|
2011-10-07 00:41:25 +00:00
|
|
|
Admin inlines respect user permissions
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Admin inlines now only allow those actions for which the user has
|
2011-10-07 00:41:25 +00:00
|
|
|
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.
|
|
|
|
|
2011-05-21 14:41:14 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
See the :doc:`cryptographic signing </topics/signing>` docs for more
|
|
|
|
information.
|
2011-05-21 14:41:14 +00:00
|
|
|
|
2011-06-26 17:00:24 +00:00
|
|
|
Cookie-based session backend
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-06-26 17:00:24 +00:00
|
|
|
|
2012-02-17 20:04:11 +00:00
|
|
|
.. 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.
|
2012-02-16 02:08:11 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
See the :ref:`cookie-based session backend <cookie-session-backend>` docs for
|
2011-06-26 17:00:24 +00:00
|
|
|
more information.
|
|
|
|
|
2011-06-01 13:47:00 +00:00
|
|
|
New form wizard
|
|
|
|
~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
The previous ``FormWizard`` from the formtools contrib app has been
|
|
|
|
replaced with a new implementation based on the class-based views
|
2011-06-01 13:47:00 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
Django 1.4 ships with a session-based storage backend and a cookie-based
|
2011-06-01 13:47:00 +00:00
|
|
|
storage backend. The latter uses the tools for
|
|
|
|
:doc:`cryptographic signing </topics/signing>` also introduced in
|
2011-12-23 01:49:32 +00:00
|
|
|
Django 1.4 to store the wizard's state in the user's cookies.
|
2011-06-01 13:47:00 +00:00
|
|
|
|
|
|
|
See the :doc:`form wizard </ref/contrib/formtools/form-wizard>` docs for
|
|
|
|
more information.
|
|
|
|
|
2011-04-29 11:49:59 +00:00
|
|
|
``reverse_lazy``
|
|
|
|
~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
A lazily evaluated version of :func:`django.core.urlresolvers.reverse` was
|
2011-12-30 19:18:03 +00:00
|
|
|
added to allow using URL reversals before the project's URLconf gets loaded.
|
2011-04-29 11:49:59 +00:00
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
Translating URL patterns
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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
|
2011-10-01 15:43:01 +00:00
|
|
|
:func:`~django.utils.translation.ugettext_lazy`. See
|
|
|
|
:ref:`url-internationalization` for more information about the language prefix
|
|
|
|
and how to internationalize URL patterns.
|
|
|
|
|
2011-10-19 04:59:47 +00:00
|
|
|
Contextual translation support for ``{% trans %}`` and ``{% blocktrans %}``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
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.
|
2011-10-19 04:59:47 +00:00
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
Customizable ``SingleObjectMixin`` URLConf kwargs
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Two new attributes,
|
2011-12-23 01:49:32 +00:00
|
|
|
:attr:`pk_url_kwarg<django.views.generic.detail.SingleObjectMixin.pk_url_kwarg>`
|
|
|
|
and
|
2011-10-01 15:43:01 +00:00
|
|
|
:attr:`slug_url_kwarg<django.views.generic.detail.SingleObjectMixin.slug_url_kwarg>`,
|
2011-12-23 01:49:32 +00:00
|
|
|
have been added to :class:`~django.views.generic.detail.SingleObjectMixin` to
|
2011-12-30 19:18:03 +00:00
|
|
|
enable the customization of URLconf keyword arguments used for single
|
2011-10-01 15:43:01 +00:00
|
|
|
object generic views.
|
|
|
|
|
2011-05-03 11:52:42 +00:00
|
|
|
Assignment template tags
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
A new :ref:`assignment_tag<howto-custom-template-tags-assignment-tags>` helper
|
|
|
|
function was added to ``template.Library`` to ease the creation of template
|
|
|
|
tags that store data in a specified context variable.
|
2011-05-03 11:52:42 +00:00
|
|
|
|
2011-09-27 12:15:15 +00:00
|
|
|
``*args`` and ``**kwargs`` support for template tag helper functions
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
The :ref:`simple_tag<howto-custom-template-tags-simple-tags>`,
|
|
|
|
:ref:`inclusion_tag <howto-custom-template-tags-inclusion-tags>` and
|
|
|
|
newly introduced
|
2011-09-27 12:15:15 +00:00
|
|
|
:ref:`assignment_tag<howto-custom-template-tags-assignment-tags>` template
|
|
|
|
helper functions may now accept any number of positional or keyword arguments.
|
|
|
|
For example:
|
|
|
|
|
|
|
|
.. code-block:: python
|
|
|
|
|
|
|
|
@register.simple_tag
|
|
|
|
def my_tag(a, b, *args, **kwargs):
|
|
|
|
warning = kwargs['warning']
|
|
|
|
profile = kwargs['profile']
|
|
|
|
...
|
|
|
|
return ...
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Then, in the template, any number of arguments may be passed to the template tag.
|
2011-09-27 12:15:15 +00:00
|
|
|
For example:
|
|
|
|
|
|
|
|
.. code-block:: html+django
|
|
|
|
|
|
|
|
{% my_tag 123 "abcd" book.title warning=message|lower profile=user.profile %}
|
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
No wrapping of exceptions in ``TEMPLATE_DEBUG`` mode
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
In previous versions of Django, whenever the :setting:`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
|
|
|
|
:setting:`TEMPLATE_DEBUG`, and there's no need to catch and unwrap
|
|
|
|
``TemplateSyntaxError`` in order to catch other errors.
|
|
|
|
|
2011-07-14 13:47:10 +00:00
|
|
|
``truncatechars`` template filter
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
This new filter truncates a string to be no longer than the specified
|
2011-07-14 13:47:10 +00:00
|
|
|
number of characters. Truncated strings end with a translatable ellipsis
|
2011-12-23 01:49:32 +00:00
|
|
|
sequence ("..."). See the documentation for :tfilter:`truncatechars` for
|
2011-07-14 13:47:10 +00:00
|
|
|
more details.
|
|
|
|
|
2011-10-01 15:43:01 +00:00
|
|
|
``static`` template tag
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~
|
2011-07-29 09:41:00 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
The :mod:`staticfiles<django.contrib.staticfiles>` contrib app has a new
|
|
|
|
:ttag:`static<staticfiles-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
|
2011-10-01 15:43:01 +00:00
|
|
|
:ref:`serving files from a cloud service<staticfiles-from-cdn>`.
|
|
|
|
|
|
|
|
``CachedStaticFilesStorage`` storage backend
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
The :mod:`staticfiles<django.contrib.staticfiles>` contrib app now has a
|
2011-12-23 01:49:32 +00:00
|
|
|
:class:`~django.contrib.staticfiles.storage.CachedStaticFilesStorage` backend
|
2011-12-30 19:18:03 +00:00
|
|
|
that caches the files it saves (when running the :djadmin:`collectstatic`
|
2011-10-01 15:43:01 +00:00
|
|
|
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``
|
|
|
|
|
|
|
|
See the :class:`~django.contrib.staticfiles.storage.CachedStaticFilesStorage`
|
|
|
|
docs for more information.
|
|
|
|
|
|
|
|
Simple clickjacking protection
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
We've added a middleware to provide easy protection against `clickjacking
|
2011-12-23 01:49:32 +00:00
|
|
|
<http://en.wikipedia.org/wiki/Clickjacking>`_ using the ``X-Frame-Options``
|
2011-10-01 15:43:01 +00:00
|
|
|
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.
|
2011-07-29 09:41:00 +00:00
|
|
|
|
2011-05-31 21:29:35 +00:00
|
|
|
CSRF improvements
|
|
|
|
~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
We've made various improvements to our CSRF features, including the
|
2011-12-30 19:18:03 +00:00
|
|
|
: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
|
2011-12-23 01:49:32 +00:00
|
|
|
docs </ref/contrib/csrf>` for more information.
|
2011-05-31 21:29:35 +00:00
|
|
|
|
2011-06-08 22:18:46 +00:00
|
|
|
Error report filtering
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
We added two function decorators, :func:`sensitive_variables` and
|
|
|
|
:func:`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.
|
2011-06-08 22:18:46 +00:00
|
|
|
|
|
|
|
All POST parameters are now systematically filtered out of error reports for
|
2011-12-30 19:18:03 +00:00
|
|
|
certain views (``login``, ``password_reset_confirm``, ``password_change`` and
|
2011-12-23 01:49:32 +00:00
|
|
|
``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.
|
2011-06-08 22:18:46 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
You can override or customize the default filtering by writing a :ref:`custom
|
2011-12-23 01:49:32 +00:00
|
|
|
filter<custom-error-reports>`. For more information see the docs on
|
2011-06-08 22:18:46 +00:00
|
|
|
:ref:`Filtering error reports<filtering-error-reports>`.
|
|
|
|
|
2011-06-11 13:48:24 +00:00
|
|
|
Extended IPv6 support
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
The previously added support for IPv6 addresses when using the runserver
|
2011-12-30 19:18:03 +00:00
|
|
|
management command in Django 1.3 has been extended with
|
2011-06-11 13:48:24 +00:00
|
|
|
a :class:`~django.db.models.fields.GenericIPAddressField` model field,
|
|
|
|
a :class:`~django.forms.fields.GenericIPAddressField` form field and
|
|
|
|
the validators :data:`~django.core.validators.validate_ipv46_address` and
|
|
|
|
:data:`~django.core.validators.validate_ipv6_address`
|
2011-06-08 22:18:46 +00:00
|
|
|
|
2011-10-13 05:56:15 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
The previous ``manage.py`` called functions that are now deprecated, and thus
|
2011-10-13 05:56:15 +00:00
|
|
|
projects upgrading to Django 1.4 should update their ``manage.py``. (The
|
2011-12-30 19:18:03 +00:00
|
|
|
old-style ``manage.py`` will continue to work as before until Django 1.6. In
|
2011-10-13 05:56:15 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
If settings, URLconfs and apps within the project are imported or referenced
|
2011-12-23 01:49:32 +00:00
|
|
|
using the project name prefix (e.g. ``myproject.settings``, ``ROOT_URLCONF =
|
2011-10-13 06:41:40 +00:00
|
|
|
"myproject.urls"``, etc), the new ``manage.py`` will need to be moved one
|
2011-10-13 05:56:15 +00:00
|
|
|
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``.
|
|
|
|
|
2011-10-22 04:30:10 +00:00
|
|
|
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
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-10-22 04:30:10 +00:00
|
|
|
|
|
|
|
(The :djadmin:`runfcgi` management command also internally wraps the WSGI
|
|
|
|
callable configured via :setting:`WSGI_APPLICATION`.)
|
|
|
|
|
2011-12-22 22:38:02 +00:00
|
|
|
Custom project and app templates
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
The :djadmin:`startapp` and :djadmin:`startproject` management commands
|
2011-12-30 19:18:03 +00:00
|
|
|
now have a ``--template`` option for specifying a path or URL to a custom app
|
|
|
|
or project template.
|
2011-12-22 22:38:02 +00:00
|
|
|
|
2011-12-23 19:13:10 +00:00
|
|
|
For example, Django will use the ``/path/to/my_project_template`` directory
|
2011-12-30 19:18:03 +00:00
|
|
|
when you run the following command::
|
2011-12-22 22:38:02 +00:00
|
|
|
|
|
|
|
django-admin.py startproject --template=/path/to/my_project_template myproject
|
|
|
|
|
2011-12-30 18:14:31 +00:00
|
|
|
You can also now provide a destination directory as the second
|
2011-12-22 22:38:02 +00:00
|
|
|
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
|
|
|
|
|
2011-12-30 18:14:31 +00:00
|
|
|
For more information, see the :djadmin:`startapp` and :djadmin:`startproject`
|
2011-12-22 22:38:02 +00:00
|
|
|
documentation.
|
|
|
|
|
2011-11-18 13:01:06 +00:00
|
|
|
Support for time zones
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Django 1.4 adds :ref:`support for time zones <time-zones>`. When it's enabled,
|
2011-12-30 19:18:03 +00:00
|
|
|
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
|
2011-11-18 13:01:06 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
Time zone support is enabled by default in new projects created with
|
2011-11-18 13:01:06 +00:00
|
|
|
:djadmin:`startproject`. If you want to use this feature in an existing
|
2012-03-03 22:54:55 +00:00
|
|
|
project, read the :ref:`migration guide <time-zones-migration-guide>`. If you
|
|
|
|
encounter problems, there's a helpful :ref:`FAQ <time-zones-faq>`.
|
2011-10-22 04:30:10 +00:00
|
|
|
|
2012-01-31 20:36:11 +00:00
|
|
|
HTML comparisons in tests
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-03-03 21:50:49 +00:00
|
|
|
The base classes in :mod:`django.test` now have some helpers to
|
2012-01-31 20:36:11 +00:00
|
|
|
compare HTML without tripping over irrelevant differences in whitespace,
|
2012-02-03 20:45:45 +00:00
|
|
|
argument quoting/ordering and closing of self-closing tags. You can either
|
|
|
|
compare HTML directly with the new
|
2012-03-03 21:50:49 +00:00
|
|
|
:meth:`~django.test.SimpleTestCase.assertHTMLEqual` and
|
|
|
|
:meth:`~django.test.SimpleTestCase.assertHTMLNotEqual` assertions, or use
|
2012-01-31 20:36:11 +00:00
|
|
|
the ``html=True`` flag with
|
2012-03-03 21:50:49 +00:00
|
|
|
:meth:`~django.test.TestCase.assertContains` and
|
|
|
|
:meth:`~django.test.TestCase.assertNotContains` to test whether the
|
|
|
|
client's response contains a given HTML fragment. See the :ref:`assertions
|
|
|
|
documentation <assertions>` for more.
|
2012-01-31 20:36:11 +00:00
|
|
|
|
2012-02-13 20:57:44 +00:00
|
|
|
Two new date format strings
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-16 02:06:59 +00:00
|
|
|
Two new :tfilter:`date` formats were added for use in template filters,
|
|
|
|
template tags and :ref:`format-localization`:
|
2012-02-13 20:57:44 +00:00
|
|
|
|
|
|
|
- ``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.
|
|
|
|
|
2011-06-09 12:45:11 +00:00
|
|
|
Minor features
|
|
|
|
~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Django 1.4 also includes several smaller improvements worth noting:
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* 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.
|
2011-06-09 12:45:11 +00:00
|
|
|
|
2011-10-14 21:49:43 +00:00
|
|
|
* :doc:`Tablespace support </topics/db/tablespaces>` in PostgreSQL.
|
|
|
|
|
2011-06-11 16:05:28 +00:00
|
|
|
* Customizable names for :meth:`~django.template.Library.simple_tag`.
|
2011-06-09 12:45:11 +00:00
|
|
|
|
2011-06-14 23:37:12 +00:00
|
|
|
* In the documentation, a helpful :doc:`security overview </topics/security>`
|
|
|
|
page.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* The :func:`django.contrib.auth.models.check_password` function has been moved
|
2012-03-02 05:03:52 +00:00
|
|
|
to the :mod:`django.contrib.auth.hashers` module. Importing it from the old
|
2011-06-26 16:51:46 +00:00
|
|
|
location will still work, but you should update your imports.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* The :djadmin:`collectstatic` management command now has a ``--clear`` option
|
2011-07-04 21:34:29 +00:00
|
|
|
to delete all files at the destination before copying or linking the static
|
|
|
|
files.
|
2011-06-26 16:51:46 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* It's now possible to load fixtures containing forward references when using
|
2011-08-07 00:43:26 +00:00
|
|
|
MySQL with the InnoDB database engine.
|
|
|
|
|
2011-08-12 14:15:31 +00:00
|
|
|
* A new 403 response handler has been added as
|
2011-09-11 22:36:16 +00:00
|
|
|
``'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.
|
2011-08-12 14:15:31 +00:00
|
|
|
|
2012-02-12 15:10:08 +00:00
|
|
|
* 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
|
|
|
|
|
2011-08-30 12:09:45 +00:00
|
|
|
* 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.
|
|
|
|
|
2011-12-09 22:13:27 +00:00
|
|
|
* The :ttag:`if` template tag now supports ``{% elif %}`` clauses.
|
|
|
|
|
2011-12-30 21:13:53 +00:00
|
|
|
* 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.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* A new, plain-text, version of the HTTP 500 status code internal error page
|
2011-10-02 02:53:58 +00:00
|
|
|
served when :setting:`DEBUG` is ``True`` is now sent to the client when
|
2011-12-30 19:18:03 +00:00
|
|
|
Django detects that the request has originated in JavaScript code.
|
|
|
|
(:meth:`~django.http.HttpRequest.is_ajax` is used for this.)
|
2011-10-02 02:53:58 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Like its HTML counterpart, it contains a collection of different
|
|
|
|
pieces of information about the state of the application.
|
2011-10-02 02:53:58 +00:00
|
|
|
|
|
|
|
This should make it easier to read when debugging interaction with
|
2011-12-30 19:18:03 +00:00
|
|
|
client-side JavaScript.
|
2011-10-02 02:53:58 +00:00
|
|
|
|
2011-11-11 13:07:14 +00:00
|
|
|
* Added the :djadminopt:`--no-location` option to the :djadmin:`makemessages`
|
|
|
|
command.
|
|
|
|
|
2011-11-21 22:25:49 +00:00
|
|
|
* Changed the ``locmem`` cache backend to use
|
|
|
|
``pickle.HIGHEST_PROTOCOL`` for better compatibility with the other
|
|
|
|
cache backends.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* Added support in the ORM for generating ``SELECT`` queries containing
|
|
|
|
``DISTINCT ON``.
|
2011-12-22 20:42:40 +00:00
|
|
|
|
2011-12-30 18:01:34 +00:00
|
|
|
The ``distinct()`` ``QuerySet`` method now accepts an optional list of model
|
2011-12-22 20:42:40 +00:00
|
|
|
field names. If specified, then the ``DISTINCT`` statement is limited to these
|
2011-12-30 18:01:34 +00:00
|
|
|
fields. This is only supported in PostgreSQL.
|
2011-12-22 20:42:40 +00:00
|
|
|
|
|
|
|
For more details, see the documentation for
|
|
|
|
:meth:`~django.db.models.query.QuerySet.distinct`.
|
|
|
|
|
2011-12-24 00:14:45 +00:00
|
|
|
* The admin login page will add a password reset link if you include a URL with
|
2011-12-30 19:18:03 +00:00
|
|
|
the name `'admin_password_reset'` in your urls.py, so plugging in the built-in
|
2011-12-24 00:14:45 +00:00
|
|
|
password reset mechanism and making it available is now much easier. For
|
|
|
|
details, see :ref:`auth_password_reset`.
|
|
|
|
|
2012-01-05 00:45:31 +00:00
|
|
|
* 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.
|
|
|
|
|
2012-02-03 20:45:45 +00:00
|
|
|
* 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
|
2012-01-15 01:36:14 +00:00
|
|
|
functions ``modelformset_factory`` and ``inlineformset_factory`` respectively
|
|
|
|
just like with regular formsets. However, initial values only apply to extra
|
2012-02-03 20:45:45 +00:00
|
|
|
forms, i.e. those which are not bound to an existing model instance.
|
2012-01-15 01:36:14 +00:00
|
|
|
|
2012-01-29 19:24:32 +00:00
|
|
|
* The sitemaps framework can now handle HTTPS links using the new
|
|
|
|
:attr:`Sitemap.protocol <django.contrib.sitemaps.Sitemap.protocol>` class
|
|
|
|
attribute.
|
|
|
|
|
2012-03-03 21:50:49 +00:00
|
|
|
* A new :class:`django.test.SimpleTestCase` subclass of
|
|
|
|
:class:`unittest.TestCase`
|
2012-03-12 20:05:48 +00:00
|
|
|
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`.
|
2012-03-03 21:50:49 +00:00
|
|
|
|
2011-03-30 17:34:01 +00:00
|
|
|
Backwards incompatible changes in 1.4
|
|
|
|
=====================================
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2012-03-02 04:04:56 +00:00
|
|
|
SECRET_KEY setting is required
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Running Django with an empty or known :setting:`SECRET_KEY` disables many of
|
2012-03-02 17:16:52 +00:00
|
|
|
Django's security protections and can lead to remote-code-execution
|
|
|
|
vulnerabilities. No Django site should ever be run without a
|
2012-03-02 04:04:56 +00:00
|
|
|
: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`.
|
|
|
|
|
2011-06-30 09:06:19 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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/``.
|
2011-06-30 09:06:19 +00:00
|
|
|
|
|
|
|
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`
|
2011-12-30 19:18:03 +00:00
|
|
|
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>` for more details.
|
|
|
|
|
|
|
|
If your ``ADMIN_MEDIA_PREFIX`` is set to an 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,
|
2011-06-30 09:06:19 +00:00
|
|
|
``http://media.example.com/``.
|
|
|
|
|
|
|
|
.. warning::
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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/`.
|
2011-06-30 09:06:19 +00:00
|
|
|
|
2011-12-22 20:18:54 +00:00
|
|
|
Supported browsers for the admin
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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`_
|
2011-12-22 20:18:54 +00:00
|
|
|
browsers should provide a fully-functional admin experience, with the notable
|
2011-12-30 19:18:03 +00:00
|
|
|
exception of Internet Explorer 6, which is no longer supported.
|
2011-12-22 20:18:54 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Released over 10 years ago, IE6 imposes many limitations on modern Web
|
2011-12-22 20:18:54 +00:00
|
|
|
development. The practical implications of this policy are that contributors
|
|
|
|
are free to improve the admin without consideration for these limitations.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Obviously, 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.
|
2011-12-22 20:18:54 +00:00
|
|
|
|
|
|
|
.. _YUI's A-grade: http://yuilibrary.com/yui/docs/tutorials/gbs/
|
|
|
|
|
2011-08-31 08:07:07 +00:00
|
|
|
Removed admin icons
|
|
|
|
~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
As part of an effort to improve the performance and usability of the admin's
|
2011-12-30 19:18:03 +00:00
|
|
|
change-list sorting interface and :attr:`horizontal
|
2011-09-24 06:17:53 +00:00
|
|
|
<django.contrib.admin.ModelAdmin.filter_horizontal>` and :attr:`vertical
|
|
|
|
<django.contrib.admin.ModelAdmin.filter_vertical>` "filter" widgets, some icon
|
2011-12-23 01:49:32 +00:00
|
|
|
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``.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-08-31 08:07:07 +00:00
|
|
|
|
2011-10-10 12:35:06 +00:00
|
|
|
CSS class names in admin forms
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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
|
2011-10-10 12:35:06 +00:00
|
|
|
form field names in the main admin forms, stacked inline forms and tabular
|
2011-12-30 19:18:03 +00:00
|
|
|
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.
|
2011-10-10 12:35:06 +00:00
|
|
|
|
2011-03-30 17:35:32 +00:00
|
|
|
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
|
2011-12-23 01:49:32 +00:00
|
|
|
using an old method. To avoid this, use Django 1.3 first for a period of time
|
2011-03-30 17:35:32 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* ``contrib.sessions`` data integrity check
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Consequences: The user will be logged out, and session data will be lost.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Time period: Defined by :setting:`SESSION_COOKIE_AGE`.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* ``contrib.auth`` password reset hash
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Consequences: Password reset links from before the upgrade will not work.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Time period: Defined by :setting:`PASSWORD_RESET_TIMEOUT_DAYS`.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Form-related hashes: these have a are 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:
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* ``contrib.comments`` form security hash
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Consequences: The user will see the validation error "Security hash failed."
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Time period: The amount of time you expect users to take filling out comment
|
2011-03-30 17:35:32 +00:00
|
|
|
forms.
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
* ``FormWizard`` security hash
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Consequences: The user will see an error about the form having expired
|
2011-03-30 17:35:32 +00:00
|
|
|
and will be sent back to the first page of the wizard, losing the data
|
2011-12-30 19:18:03 +00:00
|
|
|
he has entered so far.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Time period: The amount of time you expect users to take filling out the
|
2011-03-30 17:35:32 +00:00
|
|
|
affected forms.
|
|
|
|
|
|
|
|
* CSRF check
|
|
|
|
|
|
|
|
* Note: This is actually a Django 1.1 fallback, not Django 1.2,
|
2011-12-30 19:18:03 +00:00
|
|
|
and it applies only if you're upgrading from 1.1.
|
2011-03-30 17:35:32 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Consequences: The user will see a 403 error with any CSRF-protected POST
|
2011-03-30 17:35:32 +00:00
|
|
|
form.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* Time period: The amount of time you expect user to take filling out
|
2011-03-30 17:35:32 +00:00
|
|
|
such forms.
|
2011-04-20 14:41:47 +00:00
|
|
|
|
2012-03-12 20:14:58 +00:00
|
|
|
* ``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.
|
2012-03-02 04:04:56 +00:00
|
|
|
|
2011-04-20 14:41:47 +00:00
|
|
|
django.contrib.flatpages
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Starting in 1.4, the
|
2011-04-20 14:41:47 +00:00
|
|
|
: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
|
2011-12-30 19:18:03 +00:00
|
|
|
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`.
|
2011-04-29 15:11:17 +00:00
|
|
|
|
2011-11-18 13:01:06 +00:00
|
|
|
Serialization of :class:`~datetime.datetime` and :class:`~datetime.time`
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
As a consequence of time-zone support, and according to the ECMA-262
|
|
|
|
specification, we made changes to the JSON serializer:
|
2011-11-18 13:01:06 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
* It includes the time zone for aware datetime objects. It raises an exception
|
2011-11-18 13:01:06 +00:00
|
|
|
for aware time objects.
|
2011-12-30 19:18:03 +00:00
|
|
|
* It includes milliseconds for datetime and time objects. There is still
|
2011-11-18 13:01:06 +00:00
|
|
|
some precision loss, because Python stores microseconds (6 digits) and JSON
|
|
|
|
only supports milliseconds (3 digits). However, it's better than discarding
|
|
|
|
microseconds entirely.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
We changed the XML serializer to use the ISO8601 format for datetimes.
|
2011-12-23 01:49:32 +00:00
|
|
|
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.
|
2011-11-18 13:01:06 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Though the serializers now use these new formats when creating fixtures, they
|
2011-11-18 13:01:06 +00:00
|
|
|
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.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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
|
2011-11-18 13:01:06 +00:00
|
|
|
:setting:`USE_TZ` is ``False``, if you attempt to save an aware datetime
|
|
|
|
object, Django raises an exception.
|
|
|
|
|
2012-01-07 21:42:37 +00:00
|
|
|
``MySQLdb``-specific exceptions
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-03 20:13:16 +00:00
|
|
|
The MySQL backend historically has raised :class:`MySQLdb.OperationalError`
|
|
|
|
when a query triggered an exception. We've fixed this bug, and we now raise
|
|
|
|
:class:`django.db.utils.DatabaseError` instead. If you were testing for
|
|
|
|
:class:`MySQLdb.OperationalError`, you'll need to update your ``except``
|
|
|
|
clauses.
|
2012-01-07 21:42:37 +00:00
|
|
|
|
2011-12-16 13:40:19 +00:00
|
|
|
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
|
2011-12-23 01:49:32 +00:00
|
|
|
default ``DatabaseWrapper`` object anymore and is now a proxy to access that
|
2011-12-16 13:40:19 +00:00
|
|
|
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()``.
|
|
|
|
|
2012-02-03 20:45:45 +00:00
|
|
|
Finally, while it's now possible to pass connections between threads, Django
|
|
|
|
doesn't make any effort to synchronize access to the underlying backend.
|
2011-12-16 13:40:19 +00:00
|
|
|
Concurrency behavior is defined by the underlying backend implementation.
|
|
|
|
Check their documentation for details.
|
|
|
|
|
2011-04-29 15:11:17 +00:00
|
|
|
`COMMENTS_BANNED_USERS_GROUP` setting
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Django's :doc:`comments app </ref/contrib/comments/index>` has historically
|
2011-05-14 17:58:32 +00:00
|
|
|
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
|
2011-12-23 01:49:32 +00:00
|
|
|
of the app such as the template tags. To fix this problem, we removed the code
|
2011-05-14 17:58:32 +00:00
|
|
|
from the feed class.
|
2011-04-29 15:11:17 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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::
|
2011-04-29 15:11:17 +00:00
|
|
|
|
|
|
|
from django.conf import settings
|
|
|
|
from django.contrib.comments.managers import CommentManager
|
|
|
|
|
|
|
|
class BanningCommentManager(CommentManager):
|
|
|
|
def get_query_set(self):
|
|
|
|
qs = super(BanningCommentManager, self).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
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Save this model manager in your custom comment app (e.g., in
|
2011-04-29 15:11:17 +00:00
|
|
|
``my_comments_app/managers.py``) and add it your
|
|
|
|
:ref:`custom comment app model <custom-comment-app-api>`::
|
|
|
|
|
|
|
|
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()
|
|
|
|
|
2011-05-14 17:58:32 +00:00
|
|
|
For more details, see the documentation about
|
2011-04-29 15:11:17 +00:00
|
|
|
:doc:`customizing the comments framework </ref/contrib/comments/custom>`.
|
2011-05-05 20:49:26 +00:00
|
|
|
|
|
|
|
`IGNORABLE_404_STARTS` and `IGNORABLE_404_ENDS` settings
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
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
|
|
|
|
:setting:`IGNORABLE_404_STARTS` and suffixes to :setting:`IGNORABLE_404_ENDS`.
|
2011-05-05 20:49:26 +00:00
|
|
|
|
|
|
|
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`, :setting:`IGNORABLE_404_STARTS` and
|
|
|
|
:setting:`IGNORABLE_404_ENDS` are all now empty.
|
|
|
|
|
|
|
|
If you have customized :setting:`IGNORABLE_404_STARTS` or
|
|
|
|
:setting:`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
|
2011-12-30 19:18:03 +00:00
|
|
|
expression, such as periods.
|
2011-05-09 23:45:54 +00:00
|
|
|
|
|
|
|
CSRF protection extended to PUT and DELETE
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Previously, Django's :doc:`CSRF protection </ref/contrib/csrf/>` provided
|
2011-12-30 19:18:03 +00:00
|
|
|
protection only against POST requests. Since use of PUT and DELETE methods in
|
2011-05-09 23:45:54 +00:00
|
|
|
AJAX applications is becoming more common, we now protect all methods not
|
2011-12-30 19:18:03 +00:00
|
|
|
defined as safe by :rfc:`2616` -- i.e., we exempt GET, HEAD, OPTIONS and TRACE,
|
|
|
|
and we enforce protection on everything else.
|
2011-05-09 23:45:54 +00:00
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
If you're using PUT or DELETE methods in AJAX applications, please see the
|
2011-05-09 23:45:54 +00:00
|
|
|
:ref:`instructions about using AJAX and CSRF <csrf-ajax>`.
|
2011-06-07 21:17:41 +00:00
|
|
|
|
|
|
|
``django.core.template_loaders``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
This was an alias to ``django.template.loader`` since 2005, and we've removed it
|
2011-06-07 21:17:41 +00:00
|
|
|
without emitting a warning due to the length of the deprecation. If your code
|
2011-12-30 19:18:03 +00:00
|
|
|
still referenced this, please use ``django.template.loader`` instead.
|
2011-06-08 11:12:01 +00:00
|
|
|
|
2011-09-10 00:47:00 +00:00
|
|
|
``django.db.models.fields.URLField.verify_exists``
|
2011-12-30 19:18:03 +00:00
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
2011-09-10 00:47:00 +00:00
|
|
|
|
|
|
|
This functionality has been removed due to intractable performance and
|
|
|
|
security issues. Any existing usage of ``verify_exists`` should be
|
|
|
|
removed.
|
|
|
|
|
2011-09-13 15:10:49 +00:00
|
|
|
``django.core.files.storage.Storage.open``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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
|
2011-11-29 12:01:38 +00:00
|
|
|
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`
|
2011-12-30 19:18:03 +00:00
|
|
|
method, like this::
|
2011-09-13 15:10:49 +00:00
|
|
|
|
|
|
|
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))
|
2011-09-10 00:47:00 +00:00
|
|
|
|
2011-11-01 20:07:42 +00:00
|
|
|
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
|
2011-12-30 19:18:03 +00:00
|
|
|
fixtures are trusted data, the YAML deserializer now uses ``yaml.safe_load``
|
|
|
|
for additional security.
|
2011-11-01 20:07:42 +00:00
|
|
|
|
2012-01-07 21:47:38 +00:00
|
|
|
Session cookies now have the ``httponly`` flag by default
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Session cookies now include the ``httponly`` attribute by default to
|
2012-03-02 04:22:16 +00:00
|
|
|
help reduce the impact of potential XSS attacks. As a consequence of
|
|
|
|
this change, session cookie data, including sessionid, is no longer
|
2012-03-02 17:16:52 +00:00
|
|
|
accessible from JavaScript in many browsers. For strict backwards
|
2012-03-02 04:22:16 +00:00
|
|
|
compatibility, use ``SESSION_COOKIE_HTTPONLY = False`` in your
|
|
|
|
settings file.
|
2012-01-07 21:47:38 +00:00
|
|
|
|
|
|
|
The :tfilter:`urlize` filter no longer escapes every URL
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-03 20:14:14 +00:00
|
|
|
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.
|
2012-01-07 21:47:38 +00:00
|
|
|
|
2012-01-31 19:23:09 +00:00
|
|
|
``assertTemplateUsed`` and ``assertTemplateNotUsed`` as context manager
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-03 20:45:45 +00:00
|
|
|
It's now possible to check whether a template was used within a block of
|
2012-03-03 21:50:49 +00:00
|
|
|
code with :meth:`~django.test.test.TestCase.assertTemplateUsed` and
|
|
|
|
:meth:`~django.test.test.TestCase.assertTemplateNotUsed`. And they
|
2012-01-31 19:23:09 +00:00
|
|
|
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')
|
|
|
|
|
2012-02-03 20:45:45 +00:00
|
|
|
See the :ref:`assertion documentation<assertions>` for more.
|
2012-01-31 19:23:09 +00:00
|
|
|
|
2012-01-30 08:27:50 +00:00
|
|
|
Database connections after running the test suite
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2012-02-03 20:45:45 +00:00
|
|
|
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.
|
2012-01-30 08:27:50 +00:00
|
|
|
|
|
|
|
If your code relied on connections to the production database being created
|
2012-02-03 20:45:45 +00:00
|
|
|
after tests' execution, then you can restore the previous behavior by
|
2012-01-30 08:27:50 +00:00
|
|
|
subclassing ``DjangoTestRunner`` and overriding its ``teardown_databases()``
|
|
|
|
method.
|
|
|
|
|
2012-02-07 18:46:29 +00:00
|
|
|
Output of :djadmin:`manage.py help <help>`
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
:djadmin:`manage.py help <help>` now groups available commands by application.
|
2012-02-17 20:04:11 +00:00
|
|
|
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.
|
2012-02-07 18:46:29 +00:00
|
|
|
|
2012-02-21 02:59:05 +00:00
|
|
|
``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
|
2012-03-02 17:16:52 +00:00
|
|
|
when it wasn't. It now uses ``parser.compile_filter``, like other tags.
|
2012-02-21 02:59:05 +00:00
|
|
|
|
|
|
|
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
|
2012-03-02 17:16:52 +00:00
|
|
|
changed, which may break any custom tags that use this class.
|
2012-02-21 02:59:05 +00:00
|
|
|
|
2011-06-08 11:12:01 +00:00
|
|
|
Features deprecated in 1.4
|
|
|
|
==========================
|
|
|
|
|
|
|
|
Old styles of calling ``cache_page`` decorator
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
|
|
|
Some legacy ways of calling :func:`~django.views.decorators.cache.cache_page`
|
2011-12-30 19:18:03 +00:00
|
|
|
have been deprecated. Please see the documentation for the correct way to use
|
|
|
|
this decorator.
|
2011-06-16 20:05:25 +00:00
|
|
|
|
|
|
|
Support for PostgreSQL versions older than 8.2
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
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).
|
2011-06-16 20:05:25 +00:00
|
|
|
|
|
|
|
Django 1.4 takes that policy further and sets 8.2 as the minimum PostgreSQL
|
|
|
|
version it officially supports.
|
2011-06-22 06:01:44 +00:00
|
|
|
|
|
|
|
Request exceptions are now always logged
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
When we added :doc:`logging support </topics/logging/>` in Django in 1.3, the
|
2011-06-22 06:01:44 +00:00
|
|
|
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
|
2011-12-23 01:49:32 +00:00
|
|
|
:setting:`DEBUG` was ``False``.
|
2011-06-22 06:01:44 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
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::
|
2011-06-22 06:01:44 +00:00
|
|
|
|
|
|
|
'filters': {
|
|
|
|
'require_debug_false': {
|
2011-09-16 16:41:38 +00:00
|
|
|
'()': 'django.utils.log.RequireDebugFalse'
|
2011-06-22 06:01:44 +00:00
|
|
|
}
|
|
|
|
},
|
|
|
|
'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
|
2011-12-30 19:18:03 +00:00
|
|
|
configuration includes no ``'filters'`` section and will automatically add
|
2011-06-22 06:01:44 +00:00
|
|
|
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.
|
2011-09-11 22:36:16 +00:00
|
|
|
|
|
|
|
``django.conf.urls.defaults``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
Until Django 1.3, the functions :func:`~django.conf.urls.include`,
|
2011-09-11 22:36:16 +00:00
|
|
|
:func:`~django.conf.urls.patterns` and :func:`~django.conf.urls.url` plus
|
|
|
|
:data:`~django.conf.urls.handler404`, :data:`~django.conf.urls.handler500`
|
|
|
|
were located in a ``django.conf.urls.defaults`` module.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
In Django 1.4, they live in :mod:`django.conf.urls`.
|
2011-09-22 04:10:02 +00:00
|
|
|
|
|
|
|
``django.contrib.databrowse``
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
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
|
2011-09-22 04:10:02 +00:00
|
|
|
integrate the functionality of databrowse into the admin, but no progress was
|
|
|
|
made. While Databrowse has been deprecated, an enhancement of
|
2011-12-23 01:49:32 +00:00
|
|
|
``django.contrib.admin`` providing a similar feature set is still possible.
|
2011-09-22 04:10:02 +00:00
|
|
|
|
2011-12-23 01:49:32 +00:00
|
|
|
.. _GSOC project: https://code.djangoproject.com/wiki/SummerOfCode2011#Integratedatabrowseintotheadmin
|
2011-09-22 04:10:02 +00:00
|
|
|
|
|
|
|
The code that powers Databrowse is licensed under the same terms as Django
|
2011-12-30 19:18:03 +00:00
|
|
|
itself, so it's available to be adopted by an individual or group as
|
2011-09-22 04:10:02 +00:00
|
|
|
a third-party project.
|
|
|
|
|
2011-10-13 05:56:15 +00:00
|
|
|
``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.
|
|
|
|
|
2011-12-30 19:18:03 +00:00
|
|
|
This function was never documented or part of the public API, but it was widely
|
2011-12-23 01:49:32 +00:00
|
|
|
recommended for use in setting up a "Django environment" for a user script.
|
|
|
|
These uses should be replaced by setting the ``DJANGO_SETTINGS_MODULE``
|
|
|
|
environment variable or using :func:`django.conf.settings.configure`.
|
2011-10-13 05:56:15 +00:00
|
|
|
|
|
|
|
``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
|
2011-12-23 01:49:32 +00:00
|
|
|
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.
|
2011-10-31 09:10:25 +00:00
|
|
|
|
|
|
|
``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.
|
2011-11-22 01:05:14 +00:00
|
|
|
|
2011-11-27 20:13:37 +00:00
|
|
|
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 un-pythonic and not obviously
|
|
|
|
useful, it was removed in Django 1.4. If you relied on it, you must edit your
|
|
|
|
settings file to list all your applications explicitly.
|
|
|
|
|
|
|
|
.. _this can't be done reliably: http://docs.python.org/tutorial/modules.html#importing-from-a-package
|
2011-12-16 23:40:32 +00:00
|
|
|
|
|
|
|
``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.
|
2012-02-09 18:56:49 +00:00
|
|
|
|
2012-02-17 20:04:11 +00:00
|
|
|
``django.contrib.sitemaps`` bug fix with potential performance implications
|
|
|
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
2012-02-09 18:56:49 +00:00
|
|
|
|
2012-02-17 20:04:11 +00:00
|
|
|
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
|
2012-02-09 18:56:49 +00:00
|
|
|
:attr:`~django.contrib.sitemaps.Sitemap.items()` method of the
|
2012-02-17 20:04:11 +00:00
|
|
|
: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.
|