Fixed #3766 -- Added in-memory caching for the sites framework. Will speed up all the "current site" lookups. Thanks, Matt Riggott.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@6180 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
bc21612012
commit
36396fb430
|
@ -2,15 +2,32 @@ from django.db import models
|
||||||
from django.utils.translation import ugettext_lazy as _
|
from django.utils.translation import ugettext_lazy as _
|
||||||
from django.http import get_host
|
from django.http import get_host
|
||||||
|
|
||||||
|
SITE_CACHE = {}
|
||||||
|
|
||||||
class SiteManager(models.Manager):
|
class SiteManager(models.Manager):
|
||||||
def get_current(self):
|
def get_current(self):
|
||||||
|
"""
|
||||||
|
Returns the current ``Site`` based on the SITE_ID in the
|
||||||
|
project's settings. The ``Site`` object is cached the first
|
||||||
|
time it's retrieved from the database.
|
||||||
|
"""
|
||||||
from django.conf import settings
|
from django.conf import settings
|
||||||
try:
|
try:
|
||||||
sid = settings.SITE_ID
|
sid = settings.SITE_ID
|
||||||
except AttributeError:
|
except AttributeError:
|
||||||
from django.core.exceptions import ImproperlyConfigured
|
from django.core.exceptions import ImproperlyConfigured
|
||||||
raise ImproperlyConfigured("You're using the Django \"sites framework\" without having set the SITE_ID setting. Create a site in your database and set the SITE_ID setting to fix this error.")
|
raise ImproperlyConfigured("You're using the Django \"sites framework\" without having set the SITE_ID setting. Create a site in your database and set the SITE_ID setting to fix this error.")
|
||||||
return self.get(pk=sid)
|
try:
|
||||||
|
current_site = SITE_CACHE[sid]
|
||||||
|
except KeyError:
|
||||||
|
current_site = self.get(pk=sid)
|
||||||
|
SITE_CACHE[sid] = current_site
|
||||||
|
return current_site
|
||||||
|
|
||||||
|
def clear_cache(self):
|
||||||
|
"""Clears the ``Site`` object cache."""
|
||||||
|
global SITE_CACHE
|
||||||
|
SITE_CACHE = {}
|
||||||
|
|
||||||
class Site(models.Model):
|
class Site(models.Model):
|
||||||
domain = models.CharField(_('domain name'), max_length=100)
|
domain = models.CharField(_('domain name'), max_length=100)
|
||||||
|
|
|
@ -213,6 +213,31 @@ To do this, you can use the sites framework. A simple example::
|
||||||
>>> 'http://%s%s' % (Site.objects.get_current().domain, obj.get_absolute_url())
|
>>> 'http://%s%s' % (Site.objects.get_current().domain, obj.get_absolute_url())
|
||||||
'http://example.com/mymodel/objects/3/'
|
'http://example.com/mymodel/objects/3/'
|
||||||
|
|
||||||
|
Caching the current ``Site`` object
|
||||||
|
===================================
|
||||||
|
|
||||||
|
**New in Django development version**
|
||||||
|
|
||||||
|
As the current site is stored in the database, each call to
|
||||||
|
``Site.objects.get_current()`` could result in a database query. But Django is a
|
||||||
|
little cleverer than that: on the first request, the current site is cached, and
|
||||||
|
any subsequent call returns the cached data instead of hitting the database.
|
||||||
|
|
||||||
|
If for any reason you want to force a database query, you can tell Django to
|
||||||
|
clear the cache using ``Site.objects.clear_cache()``::
|
||||||
|
|
||||||
|
# First call; current site fetched from database.
|
||||||
|
current_site = Site.objects.get_current()
|
||||||
|
# ...
|
||||||
|
|
||||||
|
# Second call; current site fetched from cache.
|
||||||
|
current_site = Site.objects.get_current()
|
||||||
|
# ...
|
||||||
|
|
||||||
|
# Force a database query for the third call.
|
||||||
|
Site.objects.clear_cache()
|
||||||
|
current_site = Site.objects.get_current()
|
||||||
|
|
||||||
The ``CurrentSiteManager``
|
The ``CurrentSiteManager``
|
||||||
==========================
|
==========================
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue