diff --git a/django/contrib/sites/middleware.py b/django/contrib/sites/middleware.py new file mode 100644 index 0000000000..eb34d2ecdb --- /dev/null +++ b/django/contrib/sites/middleware.py @@ -0,0 +1,10 @@ +from .models import Site + + +class CurrentSiteMiddleware(object): + """ + Middleware that sets `site` attribute to request object. + """ + + def process_request(self, request): + request.site = Site.objects.get_current() diff --git a/django/contrib/sites/tests.py b/django/contrib/sites/tests.py index 8f014df638..8f80087c5b 100644 --- a/django/contrib/sites/tests.py +++ b/django/contrib/sites/tests.py @@ -5,6 +5,7 @@ from django.core.exceptions import ObjectDoesNotExist, ValidationError from django.http import HttpRequest from django.test import TestCase, modify_settings, override_settings +from .middleware import CurrentSiteMiddleware from .models import Site from .requests import RequestSite from .shortcuts import get_current_site @@ -79,3 +80,13 @@ class SitesFrameworkTests(TestCase): self.assertRaises(ValidationError, site.full_clean) site.domain = "test\ntest" self.assertRaises(ValidationError, site.full_clean) + + +class MiddlewareTest(TestCase): + + def test_request(self): + """ Makes sure that the request has correct `site` attribute. """ + middleware = CurrentSiteMiddleware() + request = HttpRequest() + middleware.process_request(request) + self.assertEqual(request.site.id, settings.SITE_ID) diff --git a/docs/ref/contrib/sites.txt b/docs/ref/contrib/sites.txt index b0da9fdabd..36426af5a8 100644 --- a/docs/ref/contrib/sites.txt +++ b/docs/ref/contrib/sites.txt @@ -373,6 +373,26 @@ your admin site to have access to all objects (not just site-specific ones), put ``objects = models.Manager()`` in your model, before you define :class:`~django.contrib.sites.managers.CurrentSiteManager`. +.. _site-middleware: + +Site middleware +=============== + +.. versionadded:: 1.7 + +If you often use this pattern:: + + from django.contrib.sites.models import Site + + def my_view(request): + site = Site.objects.get_current() + ... + +there is simple way to avoid repetitions. Add +:class:`django.contrib.site.middleware.CurrentSiteMiddleware` to +:setting:`MIDDLEWARE_CLASSES`. The middleware sets the ``site`` attribute on +every request object, so you can use ``request.site`` to get the current site. + How Django uses the sites framework =================================== diff --git a/docs/ref/middleware.txt b/docs/ref/middleware.txt index 9799db0865..04ee1fa89e 100644 --- a/docs/ref/middleware.txt +++ b/docs/ref/middleware.txt @@ -179,6 +179,19 @@ Session middleware Enables session support. See the :doc:`session documentation `. +Site middleware +--------------- + +.. module:: django.contrib.site.middleware + :synopsis: Site middleware. + +.. class:: CurrentSiteMiddleware + +.. versionadded:: 1.7 + +Adds the ``site`` attribute representing the current site to every incoming +``HttpRequest`` object. See the :ref:`sites documentation `. + Authentication middleware ------------------------- diff --git a/docs/releases/1.7.txt b/docs/releases/1.7.txt index 1bd38d9c8e..e802f257ae 100644 --- a/docs/releases/1.7.txt +++ b/docs/releases/1.7.txt @@ -358,6 +358,12 @@ Minor features :class:`~django.middleware.http.ConditionalGetMiddleware` to handle conditional ``GET`` requests for sitemaps which set ``lastmod``. +:mod:`django.contrib.sites` +^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +* The new :class:`django.contrib.site.middleware.CurrentSiteMiddleware` allows + setting the current site on each request. + :mod:`django.contrib.staticfiles` ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^