diff options
| author | martin.bohacek <bohacekm@gmail.com> | 2012-06-05 13:29:33 +0200 |
|---|---|---|
| committer | martin.bohacek <bohacekm@gmail.com> | 2012-06-05 13:29:33 +0200 |
| commit | eee791e9b216333ad0b4c6c441a88828bf9aee62 (patch) | |
| tree | 3f01e97ea9b0ac28e9c9718b35ae92d163865b1c /docs | |
| parent | fbb73894395b728ec96c661da6f87523718c5398 (diff) | |
| parent | 840ffd80baad85c05670d6b642f654cffaa93cc3 (diff) | |
Merge branch 'master' of https://github.com/django/django
Diffstat (limited to 'docs')
26 files changed, 289 insertions, 137 deletions
diff --git a/docs/howto/custom-management-commands.txt b/docs/howto/custom-management-commands.txt index ba8765b253..4a27bdf7a9 100644 --- a/docs/howto/custom-management-commands.txt +++ b/docs/howto/custom-management-commands.txt @@ -61,7 +61,7 @@ look like this: poll.opened = False poll.save() - self.stdout.write('Successfully closed poll "%s"\n' % poll_id) + self.stdout.write('Successfully closed poll "%s"' % poll_id) .. note:: When you are using management commands and wish to provide console @@ -317,8 +317,12 @@ Exception class indicating a problem while executing a management command. If this exception is raised during the execution of a management -command, it will be caught and turned into a nicely-printed error -message to the appropriate output stream (i.e., stderr); as a -result, raising this exception (with a sensible description of the +command from a command line console, it will be caught and turned into a +nicely-printed error message to the appropriate output stream (i.e., stderr); +as a result, raising this exception (with a sensible description of the error) is the preferred way to indicate that something has gone wrong in the execution of a command. + +If a management command is called from code through +:ref:`call_command <call-command>`, it's up to you to catch the exception +when needed. diff --git a/docs/intro/_images/admin10.png b/docs/intro/_images/admin10.png Binary files differindex d720bafc6a..fc30df9fb8 100644 --- a/docs/intro/_images/admin10.png +++ b/docs/intro/_images/admin10.png diff --git a/docs/intro/_images/admin11.png b/docs/intro/_images/admin11.png Binary files differindex 54412836f8..8576fcb883 100644 --- a/docs/intro/_images/admin11.png +++ b/docs/intro/_images/admin11.png diff --git a/docs/intro/_images/admin11t.png b/docs/intro/_images/admin11t.png Binary files differindex 7140265172..81accc9d49 100644 --- a/docs/intro/_images/admin11t.png +++ b/docs/intro/_images/admin11t.png diff --git a/docs/intro/_images/admin12.png b/docs/intro/_images/admin12.png Binary files differindex 622123da4a..2b4b1abc71 100644 --- a/docs/intro/_images/admin12.png +++ b/docs/intro/_images/admin12.png diff --git a/docs/intro/tutorial01.txt b/docs/intro/tutorial01.txt index d8258c00f8..250c0f1f41 100644 --- a/docs/intro/tutorial01.txt +++ b/docs/intro/tutorial01.txt @@ -13,9 +13,19 @@ It'll consist of two parts: * An admin site that lets you add, change and delete polls. We'll assume you have :doc:`Django installed </intro/install>` already. You can -tell Django is installed by running the Python interactive interpreter and -typing ``import django``. If that command runs successfully, with no errors, -Django is installed. +tell Django is installed and which version by running the following command: + +.. code-block:: bash + + python -c "import django; print(django.get_version())" + +You should see either the version of your Django installation or an error +telling "No module named django". Check also that the version number matches +the version of this tutorial. If they don't match, you can refer to the +tutorial for your version of Django or update Django to the newest version. + +See :doc:`How to install Django </topics/install>` for advice on how to remove +older versions of Django and install a newer one. .. admonition:: Where to get help: @@ -339,9 +349,10 @@ The first step in writing a database Web app in Django is to define your models the :ref:`DRY Principle <dry>`. The goal is to define your data model in one place and automatically derive things from it. -In our simple poll app, we'll create two models: polls and choices. A poll has -a question and a publication date. A choice has two fields: the text of the -choice and a vote tally. Each choice is associated with a poll. +In our simple poll app, we'll create two models: ``Poll`` and ``Choice``. +A ``Poll`` has a question and a publication date. A ``Choice`` has two fields: +the text of the choice and a vote tally. Each ``Choice`` is associated with a +``Poll``. These concepts are represented by simple Python classes. Edit the :file:`polls/models.py` file so it looks like this:: @@ -354,7 +365,7 @@ These concepts are represented by simple Python classes. Edit the class Choice(models.Model): poll = models.ForeignKey(Poll) - choice = models.CharField(max_length=200) + choice_text = models.CharField(max_length=200) votes = models.IntegerField() The code is straightforward. Each model is represented by a class that @@ -384,8 +395,8 @@ Some :class:`~django.db.models.Field` classes have required elements. schema, but in validation, as we'll soon see. Finally, note a relationship is defined, using -:class:`~django.db.models.ForeignKey`. That tells Django each Choice is related -to a single Poll. Django supports all the common database relationships: +:class:`~django.db.models.ForeignKey`. That tells Django each ``Choice`` is related +to a single ``Poll``. Django supports all the common database relationships: many-to-ones, many-to-manys and one-to-ones. .. _`Python path`: http://docs.python.org/tutorial/modules.html#the-module-search-path @@ -397,7 +408,7 @@ That small bit of model code gives Django a lot of information. With it, Django is able to: * Create a database schema (``CREATE TABLE`` statements) for this app. -* Create a Python database-access API for accessing Poll and Choice objects. +* Create a Python database-access API for accessing ``Poll`` and ``Choice`` objects. But first we need to tell our project that the ``polls`` app is installed. @@ -446,7 +457,7 @@ statements for the polls app): CREATE TABLE "polls_choice" ( "id" serial NOT NULL PRIMARY KEY, "poll_id" integer NOT NULL REFERENCES "polls_poll" ("id") DEFERRABLE INITIALLY DEFERRED, - "choice" varchar(200) NOT NULL, + "choice_text" varchar(200) NOT NULL, "votes" integer NOT NULL ); COMMIT; @@ -597,7 +608,7 @@ of this object. Let's fix that by editing the polls model (in the class Choice(models.Model): # ... def __unicode__(self): - return self.choice + return self.choice_text It's important to add :meth:`~django.db.models.Model.__unicode__` methods to your models, not only for your own sanity when dealing with the interactive @@ -678,7 +689,7 @@ Save these changes and start a new Python interactive shell by running True # Give the Poll a couple of Choices. The create call constructs a new - # choice object, does the INSERT statement, adds the choice to the set + # Choice object, does the INSERT statement, adds the choice to the set # of available choices and returns the new Choice object. Django creates # a set to hold the "other side" of a ForeignKey relation # (e.g. a poll's choices) which can be accessed via the API. @@ -689,11 +700,11 @@ Save these changes and start a new Python interactive shell by running [] # Create three choices. - >>> p.choice_set.create(choice='Not much', votes=0) + >>> p.choice_set.create(choice_text='Not much', votes=0) <Choice: Not much> - >>> p.choice_set.create(choice='The sky', votes=0) + >>> p.choice_set.create(choice_text='The sky', votes=0) <Choice: The sky> - >>> c = p.choice_set.create(choice='Just hacking again', votes=0) + >>> c = p.choice_set.create(choice_text='Just hacking again', votes=0) # Choice objects have API access to their related Poll objects. >>> c.poll @@ -713,7 +724,7 @@ Save these changes and start a new Python interactive shell by running [<Choice: Not much>, <Choice: The sky>, <Choice: Just hacking again>] # Let's delete one of the choices. Use delete() for that. - >>> c = p.choice_set.filter(choice__startswith='Just hacking') + >>> c = p.choice_set.filter(choice_text__startswith='Just hacking') >>> c.delete() For more information on model relations, see :doc:`Accessing related objects diff --git a/docs/intro/tutorial02.txt b/docs/intro/tutorial02.txt index ee9e3d0d12..0d95f6ff37 100644 --- a/docs/intro/tutorial02.txt +++ b/docs/intro/tutorial02.txt @@ -276,11 +276,11 @@ in that window and click "Save," Django will save the poll to the database and dynamically add it as the selected choice on the "Add choice" form you're looking at. -But, really, this is an inefficient way of adding Choice objects to the system. +But, really, this is an inefficient way of adding ``Choice`` objects to the system. It'd be better if you could add a bunch of Choices directly when you create the -Poll object. Let's make that happen. +``Poll`` object. Let's make that happen. -Remove the ``register()`` call for the Choice model. Then, edit the ``Poll`` +Remove the ``register()`` call for the ``Choice`` model. Then, edit the ``Poll`` registration code to read:: class ChoiceInline(admin.StackedInline): @@ -296,7 +296,7 @@ registration code to read:: admin.site.register(Poll, PollAdmin) -This tells Django: "Choice objects are edited on the Poll admin page. By +This tells Django: "``Choice`` objects are edited on the ``Poll`` admin page. By default, provide enough fields for 3 choices." Load the "Add poll" page to see how that looks, you may need to restart your development server: @@ -309,7 +309,7 @@ by ``extra`` -- and each time you come back to the "Change" page for an already-created object, you get another three extra slots. One small problem, though. It takes a lot of screen space to display all the -fields for entering related Choice objects. For that reason, Django offers a +fields for entering related ``Choice`` objects. For that reason, Django offers a tabular way of displaying inline related objects; you just need to change the ``ChoiceInline`` declaration to read:: @@ -397,7 +397,7 @@ search terms, Django will search the ``question`` field. You can use as many fields as you'd like -- although because it uses a ``LIKE`` query behind the scenes, keep it reasonable, to keep your database happy. -Finally, because Poll objects have dates, it'd be convenient to be able to +Finally, because ``Poll`` objects have dates, it'd be convenient to be able to drill down by date. Add this line:: date_hierarchy = 'pub_date' diff --git a/docs/intro/tutorial03.txt b/docs/intro/tutorial03.txt index c45c944acb..fd3a04ba93 100644 --- a/docs/intro/tutorial03.txt +++ b/docs/intro/tutorial03.txt @@ -400,7 +400,7 @@ like: <h1>{{ poll.question }}</h1> <ul> {% for choice in poll.choice_set.all %} - <li>{{ choice.choice }}</li> + <li>{{ choice.choice_text }}</li> {% endfor %} </ul> @@ -412,7 +412,7 @@ list-index lookup. Method-calling happens in the :ttag:`{% for %}<for>` loop: ``poll.choice_set.all`` is interpreted as the Python code -``poll.choice_set.all()``, which returns an iterable of Choice objects and is +``poll.choice_set.all()``, which returns an iterable of ``Choice`` objects and is suitable for use in the :ttag:`{% for %}<for>` tag. See the :doc:`template guide </topics/templates>` for more about templates. diff --git a/docs/intro/tutorial04.txt b/docs/intro/tutorial04.txt index 8a9f4ee380..fac1433a8d 100644 --- a/docs/intro/tutorial04.txt +++ b/docs/intro/tutorial04.txt @@ -22,7 +22,7 @@ tutorial, so that the template contains an HTML ``<form>`` element: {% csrf_token %} {% for choice in poll.choice_set.all %} <input type="radio" name="choice" id="choice{{ forloop.counter }}" value="{{ choice.id }}" /> - <label for="choice{{ forloop.counter }}">{{ choice.choice }}</label><br /> + <label for="choice{{ forloop.counter }}">{{ choice.choice_text }}</label><br /> {% endfor %} <input type="submit" value="Vote" /> </form> @@ -168,7 +168,7 @@ Now, create a ``results.html`` template: <ul> {% for choice in poll.choice_set.all %} - <li>{{ choice.choice }} -- {{ choice.votes }} vote{{ choice.votes|pluralize }}</li> + <li>{{ choice.choice_text }} -- {{ choice.votes }} vote{{ choice.votes|pluralize }}</li> {% endfor %} </ul> diff --git a/docs/ref/class-based-views.txt b/docs/ref/class-based-views.txt index 174539d162..acd9db2d66 100644 --- a/docs/ref/class-based-views.txt +++ b/docs/ref/class-based-views.txt @@ -1171,7 +1171,15 @@ YearArchiveView have objects available according to ``queryset``, represented as ``datetime.datetime`` objects, in ascending order. - * ``year``: The given year, as a four-character string. + * ``year``: A ``datetime.date`` object representing the given year. + + * ``next_year``: A ``datetime.date`` object representing the first day + of the next year. If the next year is in the future, this will be + ``None``. + + * ``previous_year``: A ``datetime.date`` object representing the first + day of the previous year. Unlike ``next_year``, this will never be + ``None``. **Notes** @@ -1255,6 +1263,14 @@ WeekArchiveView * ``week``: A ``datetime.date`` object representing the first day of the given week. + * ``next_week``: A ``datetime.date`` object representing the first day + of the next week. If the next week is in the future, this will be + ``None``. + + * ``previous_week``: A ``datetime.date`` object representing the first + day of the previous week. Unlike ``next_week``, this will never be + ``None``. + **Notes** * Uses a default ``template_name_suffix`` of ``_archive_week``. diff --git a/docs/ref/contrib/formtools/form-wizard.txt b/docs/ref/contrib/formtools/form-wizard.txt index a3d9673db9..7aafbe89f3 100644 --- a/docs/ref/contrib/formtools/form-wizard.txt +++ b/docs/ref/contrib/formtools/form-wizard.txt @@ -186,6 +186,7 @@ Here's a full example template: .. code-block:: html+django {% extends "base.html" %} + {% load i18n %} {% block head %} {{ wizard.form.media }} diff --git a/docs/ref/contrib/gis/geoquerysets.txt b/docs/ref/contrib/gis/geoquerysets.txt index 7501fb3ec8..b9e3a7acd3 100644 --- a/docs/ref/contrib/gis/geoquerysets.txt +++ b/docs/ref/contrib/gis/geoquerysets.txt @@ -941,7 +941,7 @@ of the geometry field in each model converted to the requested output format. ``geohash`` ~~~~~~~~~~~ -.. method:: GeoQuerySet.geohash(preceision=20, **kwargs) +.. method:: GeoQuerySet.geohash(precision=20, **kwargs) .. versionadded:: 1.2 diff --git a/docs/ref/contrib/staticfiles.txt b/docs/ref/contrib/staticfiles.txt index 1dbd00b299..2bdf825316 100644 --- a/docs/ref/contrib/staticfiles.txt +++ b/docs/ref/contrib/staticfiles.txt @@ -348,6 +348,15 @@ CachedStaticFilesStorage :setting:`CACHES` setting named ``'staticfiles'``. It falls back to using the ``'default'`` cache backend. + .. method:: file_hash(name, content=None) + + .. versionadded:: 1.5 + + The method that is used when creating the hashed name of a file. + Needs to return a hash for the given file name and content. + By default it calculates a MD5 hash from the content's chunks as + mentioned above. + .. _`far future Expires headers`: http://developer.yahoo.com/performance/rules.html#expires .. _`@import`: http://www.w3.org/TR/CSS2/cascade.html#at-import .. _`url()`: http://www.w3.org/TR/CSS2/syndata.html#uri diff --git a/docs/ref/files/file.txt b/docs/ref/files/file.txt index 013d113c84..10108d1f4f 100644 --- a/docs/ref/files/file.txt +++ b/docs/ref/files/file.txt @@ -96,7 +96,7 @@ The ``ContentFile`` Class from django.core.files.base import ContentFile - f1 = ContentFile("my string content") + f1 = ContentFile(b"my string content") f2 = ContentFile(u"my unicode content encoded as UTF-8".encode('UTF-8')) .. currentmodule:: django.core.files.images diff --git a/docs/ref/settings.txt b/docs/ref/settings.txt index 398c90661b..a1b76f65e1 100644 --- a/docs/ref/settings.txt +++ b/docs/ref/settings.txt @@ -1605,7 +1605,8 @@ method. This takes some explanation. By default, ``is_secure()`` is able to determine whether a request is secure by looking at whether the requested URL uses -"https://". +"https://". This is important for Django's CSRF protection, and may be used +by your own code or third-party apps. If your Django app is behind a proxy, though, the proxy may be "swallowing" the fact that a request is HTTPS, using a non-HTTPS connection between the proxy @@ -1635,7 +1636,7 @@ available in ``request.META``.) .. warning:: - **You will probably open security holes in your site if you set this without knowing what you're doing. Seriously.** + **You will probably open security holes in your site if you set this without knowing what you're doing. And if you fail to set it when you should. Seriously.** Make sure ALL of the following are true before setting this (assuming the values from the example above): diff --git a/docs/ref/templates/api.txt b/docs/ref/templates/api.txt index aece572e07..e945e0d4ca 100644 --- a/docs/ref/templates/api.txt +++ b/docs/ref/templates/api.txt @@ -790,9 +790,10 @@ templating functions, call :func:`django.conf.settings.configure()` with any settings you wish to specify. You might want to consider setting at least :setting:`TEMPLATE_DIRS` (if you're going to use template loaders), :setting:`DEFAULT_CHARSET` (although the default of ``utf-8`` is probably fine) -and :setting:`TEMPLATE_DEBUG`. All available settings are described in the -:doc:`settings documentation </ref/settings>`, and any setting starting with -``TEMPLATE_`` is of obvious interest. +and :setting:`TEMPLATE_DEBUG`. If you plan to use the :ttag:`url` template tag, +you will also need to set the :setting:`ROOT_URLCONF` setting. All available +settings are described in the :doc:`settings documentation </ref/settings>`, +and any setting starting with ``TEMPLATE_`` is of obvious interest. .. _topic-template-alternate-language: diff --git a/docs/ref/unicode.txt b/docs/ref/unicode.txt index 1286dcfdd0..46ce4138a4 100644 --- a/docs/ref/unicode.txt +++ b/docs/ref/unicode.txt @@ -269,7 +269,7 @@ You can pass either Unicode strings or UTF-8 bytestrings as arguments to querysets are identical:: qs = People.objects.filter(name__contains=u'Å') - qs = People.objects.filter(name__contains='\xc3\x85') # UTF-8 encoding of Å + qs = People.objects.filter(name__contains=b'\xc3\x85') # UTF-8 encoding of Å Templates ========= @@ -277,7 +277,7 @@ Templates You can use either Unicode or bytestrings when creating templates manually:: from django.template import Template - t1 = Template('This is a bytestring template.') + t1 = Template(b'This is a bytestring template.') t2 = Template(u'This is a Unicode template.') But the common case is to read templates from the filesystem, and this creates diff --git a/docs/releases/1.5.txt b/docs/releases/1.5.txt index be06fe58d8..0d86a52670 100644 --- a/docs/releases/1.5.txt +++ b/docs/releases/1.5.txt @@ -44,6 +44,24 @@ reasons or when trying to avoid overwriting concurrent changes. 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``. + Minor features ~~~~~~~~~~~~~~ @@ -55,6 +73,15 @@ Django 1.5 also includes several smaller improvements worth noting: * :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 :ref:`call_command <call-command>`. Any exception raised by the command + (mostly :ref:`CommandError <ref-command-exceptions>`) is propagated. + +* The 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. @@ -69,6 +96,38 @@ Backwards incompatible changes in 1.5 deprecation timeline for a given feature, its removal may appear as a backwards incompatible change. +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``. + +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. + Features deprecated in 1.5 ========================== @@ -84,4 +143,4 @@ our own copy of ``simplejson``. You can safely change any use of ~~~~~~~~~~~~~~~~~~~~~~ The :func:`~django.utils.itercompat.product` function has been deprecated. Use -the built-in `itertools.product` instead. +the built-in :func:`itertools.product` instead. diff --git a/docs/topics/class-based-views.txt b/docs/topics/class-based-views.txt index abac22000f..13c2b994e4 100644 --- a/docs/topics/class-based-views.txt +++ b/docs/topics/class-based-views.txt @@ -35,9 +35,6 @@ Django ships with generic views to do the following: * Present date-based objects in year/month/day archive pages, associated detail, and "latest" pages. - `The Django Weblog <https://www.djangoproject.com/weblog/>`_'s - year, month, and day archives are built with these, as would be a typical - newspaper's archives. * Allow users to create, update, and delete objects -- with or without authorization. diff --git a/docs/topics/forms/formsets.txt b/docs/topics/forms/formsets.txt index ac45c50aa8..42b9d1f490 100644 --- a/docs/topics/forms/formsets.txt +++ b/docs/topics/forms/formsets.txt @@ -152,6 +152,8 @@ As we can see, ``formset.errors`` is a list whose entries correspond to the forms in the formset. Validation was performed for each of the two forms, and the expected error message appears for the second item. +.. versionadded:: 1.4 + We can also check if form data differs from the initial data (i.e. the form was sent without any data):: diff --git a/docs/topics/forms/index.txt b/docs/topics/forms/index.txt index 18e55f5eb6..4870ffc094 100644 --- a/docs/topics/forms/index.txt +++ b/docs/topics/forms/index.txt @@ -99,7 +99,7 @@ The standard pattern for processing a form in a view looks like this: else: form = ContactForm() # An unbound form - return render_to_response('contact.html', { + return render(request, 'contact.html', { 'form': form, }) diff --git a/docs/topics/i18n/timezones.txt b/docs/topics/i18n/timezones.txt index 89d5ef217e..1d9dd4b3c6 100644 --- a/docs/topics/i18n/timezones.txt +++ b/docs/topics/i18n/timezones.txt @@ -656,7 +656,7 @@ Usage >>> from django.utils.dateparse import parse_datetime >>> naive = parse_datetime("2012-02-21 10:28:45") >>> import pytz - >>> pytz.timezone("Europe/Helsinki").localize(naive) + >>> pytz.timezone("Europe/Helsinki").localize(naive, is_dst=None) datetime.datetime(2012, 2, 21, 10, 28, 45, tzinfo=<DstTzInfo 'Europe/Helsinki' EET+2:00:00 STD>) Note that ``localize`` is a pytz extension to the :class:`~datetime.tzinfo` diff --git a/docs/topics/install.txt b/docs/topics/install.txt index 4fd745d22b..5e2eefe139 100644 --- a/docs/topics/install.txt +++ b/docs/topics/install.txt @@ -154,34 +154,19 @@ If you are upgrading your installation of Django from a previous version, you will need to uninstall the old Django version before installing the new version. -If you installed Django using ``setup.py install``, uninstalling -is as simple as deleting the ``django`` directory from your Python -``site-packages``. +If you installed Django using pip_ or ``easy_install`` previously, installing +with pip_ or ``easy_install`` again will automatically take care of the old +version, so you don't need to do it yourself. -If you installed Django from a Python egg, remove the Django ``.egg`` file, -and remove the reference to the egg in the file named ``easy-install.pth``. -This file should also be located in your ``site-packages`` directory. +If you previously installed Django using ``python setup.py install``, +uninstalling is as simple as deleting the ``django`` directory from your Python +``site-packages``. To find the directory you need to remove, you can run the +following at your shell prompt (not the interactive Python prompt): -.. _finding-site-packages: +.. code-block:: bash -.. admonition:: Where are my ``site-packages`` stored? + python -c "import sys; sys.path = sys.path[1:]; import django; print(django.__path__)" - The location of the ``site-packages`` directory depends on the operating - system, and the location in which Python was installed. To find out your - system's ``site-packages`` location, execute the following: - - .. code-block:: bash - - python -c "from distutils.sysconfig import get_python_lib; print(get_python_lib())" - - (Note that this should be run from a shell prompt, not a Python interactive - prompt.) - - Some Debian-based Linux distributions have separate ``site-packages`` - directories for user-installed packages, such as when installing Django - from a downloaded tarball. The command listed above will give you the - system's ``site-packages``, the user's directory can be found in - ``/usr/local/lib/`` instead of ``/usr/lib/``. .. _install-django-code: @@ -253,6 +238,15 @@ Installing an official release manually run the command ``python setup.py install``. This will install Django in your Python installation's ``site-packages`` directory. + .. admonition:: Removing an old version + + If you use this installation technique, it is particularly important + that you :ref:`remove any existing + installations<removing-old-versions-of-django>` of Django + first. Otherwise, you can end up with a broken installation that + includes files from previous versions that have since been removed from + Django. + .. _download page: https://www.djangoproject.com/download/ .. _bsdtar: http://gnuwin32.sourceforge.net/packages/bsdtar.htm .. _7-zip: http://www.7-zip.org/ @@ -291,44 +285,26 @@ latest bug fixes and improvements, follow these instructions: This will create a directory ``django-trunk`` in your current directory. -3. Next, make sure that the Python interpreter can load Django's code. The most - convenient way to do this is to `modify Python's search path`_. Add a ``.pth`` - file containing the full path to the ``django-trunk`` directory to your - system's ``site-packages`` directory. For example, on a Unix-like system: +3. Make sure that the Python interpreter can load Django's code. The most + convenient way to do this is via pip_. Run the following command: .. code-block:: bash - echo WORKING-DIR/django-trunk > SITE-PACKAGES-DIR/django.pth + sudo pip install -e django-trunk/ - (In the above line, change ``SITE-PACKAGES-DIR`` to match the location of - your system's ``site-packages`` directory, as explained in the - :ref:`Where are my site-packages stored? <finding-site-packages>` section - above. Change ``WORKING-DIR/django-trunk`` to match the full path to your - new ``django-trunk`` directory.) + (If using a virtualenv_ you can omit ``sudo``.) -4. On Unix-like systems, create a symbolic link to the file - ``django-trunk/django/bin/django-admin.py`` in a directory on your system - path, such as ``/usr/local/bin``. For example: - - .. code-block:: bash + This will make Django's code importable, and will also make the + ``django-admin.py`` utility command available. In other words, you're all + set! - ln -s WORKING-DIR/django-trunk/django/bin/django-admin.py /usr/local/bin/ - - (In the above line, change WORKING-DIR to match the full path to your new - ``django-trunk`` directory.) - - This simply lets you type ``django-admin.py`` from within any directory, - rather than having to qualify the command with the full path to the file. - - On Windows systems, the same result can be achieved by copying the file - ``django-trunk/django/bin/django-admin.py`` to somewhere on your system - path, for example ``C:\Python27\Scripts``. + If you don't have pip_ available, see the alternative instructions for + `installing the development version without pip`_. .. warning:: Don't run ``sudo python setup.py install``, because you've already - carried out the equivalent actions in steps 3 and 4. Furthermore, this is - known to cause problems when updating to a more recent version of Django. + carried out the equivalent actions in step 3. When you want to update your copy of the Django source code, just run the command ``git pull`` from within the ``django-trunk`` directory. When you do @@ -336,3 +312,61 @@ this, Git will automatically download any changes. .. _Git: http://git-scm.com/ .. _`modify Python's search path`: http://docs.python.org/install/index.html#modifying-python-s-search-path +.. _installing-the-development-version-without-pip: + +Installing the development version without pip +---------------------------------------------- + +If you don't have pip_, you can instead manually `modify Python's search +path`_. + +First follow steps 1 and 2 above, so that you have a ``django-trunk`` directory +with a checkout of Django's latest code in it. Then add a ``.pth`` file +containing the full path to the ``django-trunk`` directory to your system's +``site-packages`` directory. For example, on a Unix-like system: + +.. code-block:: bash + + echo WORKING-DIR/django-trunk > SITE-PACKAGES-DIR/django.pth + +In the above line, change ``WORKING-DIR/django-trunk`` to match the full path +to your new ``django-trunk`` directory, and change ``SITE-PACKAGES-DIR`` to +match the location of your system's ``site-packages`` directory. + +The location of the ``site-packages`` directory depends on the operating +system, and the location in which Python was installed. To find your system's +``site-packages`` location, execute the following: + +.. code-block:: bash + + python -c "from distutils.sysconfig import get_python_lib; print(get_python_lib())" + +(Note that this should be run from a shell prompt, not a Python interactive +prompt.) + +Some Debian-based Linux distributions have separate ``site-packages`` +directories for user-installed packages, such as when installing Django from +a downloaded tarball. The command listed above will give you the system's +``site-packages``, the user's directory can be found in ``/usr/local/lib/`` +instead of ``/usr/lib/``. + +Next you need to make the ``django-admin.py`` utility available in your +shell PATH. + +On Unix-like systems, create a symbolic link to the file +``django-trunk/django/bin/django-admin.py`` in a directory on your system +path, such as ``/usr/local/bin``. For example: + +.. code-block:: bash + + ln -s WORKING-DIR/django-trunk/django/bin/django-admin.py /usr/local/bin/ + +(In the above line, change WORKING-DIR to match the full path to your new +``django-trunk`` directory.) + +This simply lets you type ``django-admin.py`` from within any directory, +rather than having to qualify the command with the full path to the file. + +On Windows systems, the same result can be achieved by copying the file +``django-trunk/django/bin/django-admin.py`` to somewhere on your system +path, for example ``C:\Python27\Scripts``. diff --git a/docs/topics/security.txt b/docs/topics/security.txt index 193d0029a4..151853d4ac 100644 --- a/docs/topics/security.txt +++ b/docs/topics/security.txt @@ -122,22 +122,19 @@ transferred between client and server, and in some cases -- **active** network attackers -- to alter data that is sent in either direction. If you want the protection that HTTPS provides, and have enabled it on your -server, there are some additional steps to consider to ensure that sensitive -information is not leaked: +server, there are some additional steps you may need: -* Set up redirection so that requests over HTTP are redirected to HTTPS. +* If necessary, set :setting:`SECURE_PROXY_SSL_HEADER`, ensuring that you have + understood the warnings there thoroughly. Failure to do this can result + in CSRF vulnerabilities, and failure to do it correctly can also be + dangerous! - It is possible to do this with a piece of Django middleware. However, this has - problems for the common case of a Django app running behind a reverse - proxy. Often, reverse proxies are configured to set the ``X-Forwarded-SSL`` - header (or equivalent) if the incoming connection was HTTPS, and the absence - of this header could be used to detect a request that was not HTTPS. However, - this method usually cannot be relied on, as a client, or a malicious active - network attacker, could also set this header. +* Set up redirection so that requests over HTTP are redirected to HTTPS. - So, for the case of a reverse proxy, it is recommended that the main Web - server should be configured to do the redirect to HTTPS, or configured to send - HTTP requests to an app that unconditionally redirects to HTTPS. + This could be done using a custom middleware. Please note the caveats under + :setting:`SECURE_PROXY_SSL_HEADER`. For the case of a reverse proxy, it may be + easier or more secure to configure the main Web server to do the redirect to + HTTPS. * Use 'secure' cookies. diff --git a/docs/topics/settings.txt b/docs/topics/settings.txt index 52cc06da56..88fa7b6864 100644 --- a/docs/topics/settings.txt +++ b/docs/topics/settings.txt @@ -220,7 +220,7 @@ In this example, default settings are taken from ``myapp_defaults``, and the The following example, which uses ``myapp_defaults`` as a positional argument, is equivalent:: - settings.configure(myapp_defaults, DEBUG = True) + settings.configure(myapp_defaults, DEBUG=True) Normally, you will not need to override the defaults in this fashion. The Django defaults are sufficiently tame that you can safely use them. Be aware @@ -242,7 +242,16 @@ is accessed. If you set ``DJANGO_SETTINGS_MODULE``, access settings values somehow, *then* call ``configure()``, Django will raise a ``RuntimeError`` indicating -that settings have already been configured. +that settings have already been configured. There is a property just for this +purpose: + +.. attribute: django.conf.settings.configured + +For example:: + + from django.conf import settings + if not settings.configured: + settings.configure(myapp_defaults, DEBUG=True) Also, it's an error to call ``configure()`` more than once, or to call ``configure()`` after any setting has been accessed. diff --git a/docs/topics/testing.txt b/docs/topics/testing.txt index d5ccc2d8fc..f35c545c30 100644 --- a/docs/topics/testing.txt +++ b/docs/topics/testing.txt @@ -805,45 +805,56 @@ arguments at time of construction: .. method:: Client.head(path, data={}, follow=False, **extra) - Makes a HEAD request on the provided ``path`` and returns a ``Response`` - object. Useful for testing RESTful interfaces. Acts just like - :meth:`Client.get` except it does not return a message body. + Makes a HEAD request on the provided ``path`` and returns a + ``Response`` object. This method works just like :meth:`Client.get`, + including the ``follow`` and ``extra`` arguments, except it does not + return a message body. - If you set ``follow`` to ``True`` the client will follow any redirects - and a ``redirect_chain`` attribute will be set in the response object - containing tuples of the intermediate urls and status codes. - - .. method:: Client.options(path, data={}, follow=False, **extra) + .. method:: Client.options(path, data='', content_type='application/octet-stream', follow=False, **extra) Makes an OPTIONS request on the provided ``path`` and returns a ``Response`` object. Useful for testing RESTful interfaces. - If you set ``follow`` to ``True`` the client will follow any redirects - and a ``redirect_chain`` attribute will be set in the response object - containing tuples of the intermediate urls and status codes. + When ``data`` is provided, it is used as the request body, and + a ``Content-Type`` header is set to ``content_type``. - The ``extra`` argument acts the same as for :meth:`Client.get`. + .. versionchanged:: 1.5 + :meth:`Client.options` used to process ``data`` like + :meth:`Client.get`. + + The ``follow`` and ``extra`` arguments act the same as for + :meth:`Client.get`. - .. method:: Client.put(path, data={}, content_type=MULTIPART_CONTENT, follow=False, **extra) + .. method:: Client.put(path, data='', content_type='application/octet-stream', follow=False, **extra) Makes a PUT request on the provided ``path`` and returns a - ``Response`` object. Useful for testing RESTful interfaces. Acts just - like :meth:`Client.post` except with the PUT request method. + ``Response`` object. Useful for testing RESTful interfaces. - If you set ``follow`` to ``True`` the client will follow any redirects - and a ``redirect_chain`` attribute will be set in the response object - containing tuples of the intermediate urls and status codes. + When ``data`` is provided, it is used as the request body, and + a ``Content-Type`` header is set to ``content_type``. + + .. versionchanged:: 1.5 + :meth:`Client.put` used to process ``data`` like + :meth:`Client.post`. - .. method:: Client.delete(path, follow=False, **extra) + The ``follow`` and ``extra`` arguments act the same as for + :meth:`Client.get`. + + .. method:: Client.delete(path, data='', content_type='application/octet-stream', follow=False, **extra) Makes an DELETE request on the provided ``path`` and returns a ``Response`` object. Useful for testing RESTful interfaces. - If you set ``follow`` to ``True`` the client will follow any redirects - and a ``redirect_chain`` attribute will be set in the response object - containing tuples of the intermediate urls and status codes. + When ``data`` is provided, it is used as the request body, and + a ``Content-Type`` header is set to ``content_type``. + + .. versionchanged:: 1.5 + :meth:`Client.delete` used to process ``data`` like + :meth:`Client.get`. + + The ``follow`` and ``extra`` arguments act the same as for + :meth:`Client.get`. - The ``extra`` argument acts the same as for :meth:`Client.get`. .. method:: Client.login(**credentials) |
