Deleted utils.py

This commit is contained in:
Kevin Mooney 2015-04-03 16:37:59 +00:00
commit 5d3a392e4c
62 changed files with 1437 additions and 744 deletions

3
.gitignore vendored
View file

@ -7,4 +7,5 @@ dist
example/example.db
docs/_build
.tox/
*.egg/
*.egg/
.coverage

View file

@ -1,9 +0,0 @@
syntax: glob
*.pyc
.*.swp
MANIFEST
build
dist
django_dbtemplates.egg-info/
example/example.db
docs/_build

24
.hgtags
View file

@ -1,24 +0,0 @@
bd537cd8beba30f1a26328e02126d3d1b14ebf8f 0.2.5
1b426859f05b8a003411964883ed5d42ec6c1b01 0.3.0
97da228cc698bfae05f60a68ec978030722b0777 0.3.1
50c69325d3758d2e82541b13be2794ebbe9ee449 0.4.0
d35a41ea96d3604a3c2654590c5c76b8865c4251 0.4.1
a4bd56a7c2ea4c6f16a726e47bb185101934fe08 0.4.2
447247c1ce1fbc77ac79c5855630af306f4f8c42 0.4.3
5b2e4f7fc267daf71325991e913f98e6f96259bb 0.4.4
ea4d636f3459ddbb51d87e921cf23f87e41d658d 0.4.5
9a30f34bc5b07376ed6752eed94d9d58e791fbac 0.4.6
9dc2a0e48494d6a354f5ca25db31638cede4bae4 0.4.7
a3be97628ed8633e2fe232e6680474e7fd3e9fea 0.5.0
bf3db2fe192d4a02bf531e61e23df342c36d6b1b 0.5.1
67a86cf9f7c8ac8d9da855c13abbef2547033cce 0.5.2
6967bbbee378f470e4b1df02b57112dd050d424b 0.5.3
5965315c03c1a8c1cfb34752cca3802d68156e27 0.5.4
4109e0db4340042cb85ea8a7d2b6ce37245738c6 0.5.5
ade167225d06cb6888ea8bfa84e7d020590171c6 0.5.6
dff01be9c8af328f8fcbc2fc97edcbe8d97840e2 0.5.7
f8f7eaf275c5e8ac52174642265af55691abef7c 0.5.8
4b36382cdfd756f45f81b0d042aaf331c3eabe30 0.6.0
0ac352fec2c2a03ac801ff0c40f0649ef16e1f64 0.6.1
34a0511928629872ce8cc5f94c6bed65f82ac343 0.7.0
74c22fa8c4a64ea37f9b6b2515a4162b8b8b1a2a 0.7.1

21
.travis.yml Normal file
View file

@ -0,0 +1,21 @@
language: python
python:
- "2.6"
- "2.7"
before_install:
- export DJANGO_SETTINGS_MODULE=dbtemplates.test_settings
install:
- pip install -e .
- pip install -r requirements/tests.txt Django==$DJANGO
before_script:
- flake8 dbtemplates --ignore=E501
script:
- coverage run --branch --source=dbtemplates `which django-admin.py` test dbtemplates
- coverage report --omit="dbtemplates/test*,dbtemplates/migrations*"
env:
- DJANGO=1.3.7
- DJANGO=1.4.5
- DJANGO=1.5.1
branches:
only:
- develop

View file

@ -1,4 +1,4 @@
[django-dbtemplates.django]
[django-dbtemplates.main]
file_filter = dbtemplates/locale/<lang>/LC_MESSAGES/django.po
source_file = dbtemplates/locale/en/LC_MESSAGES/django.po
source_lang = en

18
AUTHORS Normal file
View file

@ -0,0 +1,18 @@
Alen Mujezinovic
Alex Gaynor
Alex Kamedov
Alexander Artemenko
Arne Brodowski
David Paccoud
Diego Búrigo Zacarão
Dmitry Falk
Jannis Leidel
Jure Cuhalev
Jason Mayfield
Kevin Mooney
Mark Stahler
Matt Dorn
Oliver George
Selwin Ong
Stephan Peijnik <spe@anexia.at>, ANEXIA Internetdienstleistungs GmbH, http://www.anexia.at/
Zhang Kun

17
INSTALL
View file

@ -1,17 +0,0 @@
To install it, run the following command inside this directory:
python setup.py install
Or if you'd prefer you can simply place the included ``dbtemplates``
directory somewhere on your Python path, or symlink to it from
somewhere on your Python path; this is useful if you're working from a
Subversion checkout. Since ``dbtemplates`` is registered in the
Python Package Index you can also run ``easy_install django-dbtemplates``
or ``pip install django-dbtemplates`` optionally.
Note that this application requires Python 2.3 or later, and a recent
Subversion checkout of Django. You can obtain Python from
http://www.python.org/ and Django from http://www.djangoproject.com/.
This install notice was bluntly stolen from James Bennett's registration
package, http://www.bitbucket.org/ubernostrum/django-registration/

View file

@ -1,4 +1,4 @@
Copyright (c) 2007-2010, Jannis Leidel and contributors
Copyright (c) 2007-2012, Jannis Leidel and contributors
All rights reserved.
Redistribution and use in source and binary forms, with or without

View file

@ -1,5 +1,5 @@
include INSTALL
include LICENSE
include AUTHORS
include README.rst
include MANIFEST.in
recursive-include docs *.txt

View file

@ -1,6 +1,10 @@
django-dbtemplates
==================
.. image:: https://secure.travis-ci.org/jezdez/django-dbtemplates.png?branch=develop
:alt: Build Status
:target: http://travis-ci.org/jezdez/django-dbtemplates
``dbtemplates`` is a Django app that consists of two parts:
1. It allows you to store templates in your database
@ -12,4 +16,8 @@ command, integrates with Django's caching system and the admin actions.
Please see http://django-dbtemplates.readthedocs.org/ for more details.
The source code and issue tracker can be found on Github:
https://github.com/jezdez/django-dbtemplates
.. _template loader: http://docs.djangoproject.com/en/dev/ref/templates/api/#loader-types

View file

@ -1,16 +1,2 @@
VERSION = (1, 0, 1, "f", 0) # following PEP 386
DEV_N = None
def get_version():
version = "%s.%s" % (VERSION[0], VERSION[1])
if VERSION[2]:
version = "%s.%s" % (version, VERSION[2])
if VERSION[3] != "f":
version = "%s%s%s" % (version, VERSION[3], VERSION[4])
if DEV_N:
version = "%s.dev%s" % (version, DEV_N)
return version
__version__ = get_version()
# following PEP 386
__version__ = "1.3"

View file

@ -1,19 +1,21 @@
import posixpath
from django import forms
from django.contrib import admin
from django.core.exceptions import ImproperlyConfigured
from django.utils.translation import ungettext, ugettext_lazy as _
from django.utils.safestring import mark_safe
from dbtemplates import settings
from dbtemplates.models import (Template,
remove_cached_template, add_template_to_cache)
from dbtemplates.conf import settings
from dbtemplates.models import (Template, remove_cached_template,
add_template_to_cache)
from dbtemplates.utils.template import check_template_syntax
# Check if django-reversion is installed and use reversions' VersionAdmin
# as the base admin class if yes
if settings.USE_REVERSION:
if settings.DBTEMPLATES_USE_REVERSION:
from reversion.admin import VersionAdmin as TemplateModelAdmin
else:
from django.contrib.admin import ModelAdmin as TemplateModelAdmin
from django.contrib.admin import ModelAdmin as TemplateModelAdmin # noqa
class CodeMirrorTextArea(forms.Textarea):
@ -22,9 +24,9 @@ class CodeMirrorTextArea(forms.Textarea):
content field of the Template model.
"""
class Media:
css = dict(screen=[
posixpath.join(settings.MEDIA_PREFIX, 'css/editor.css')])
js = [posixpath.join(settings.MEDIA_PREFIX, 'js/codemirror.js')]
css = dict(screen=[posixpath.join(
settings.DBTEMPLATES_MEDIA_PREFIX, 'css/editor.css')])
js = [posixpath.join(settings.DBTEMPLATES_MEDIA_PREFIX, 'js/codemirror.js')]
def render(self, name, value, attrs=None):
result = []
@ -43,21 +45,30 @@ class CodeMirrorTextArea(forms.Textarea):
lineNumbers: true
});
</script>
""" % dict(media_prefix=settings.MEDIA_PREFIX, name=name))
""" % dict(media_prefix=settings.DBTEMPLATES_MEDIA_PREFIX, name=name))
return mark_safe(u"".join(result))
if settings.USE_CODEMIRROR:
if settings.DBTEMPLATES_USE_CODEMIRROR:
TemplateContentTextArea = CodeMirrorTextArea
else:
TemplateContentTextArea = forms.Textarea
if settings.AUTO_POPULATE_CONTENT:
if settings.DBTEMPLATES_AUTO_POPULATE_CONTENT:
content_help_text = _("Leaving this empty causes Django to look for a "
"template with the given name and populate this field with its "
"content.")
"template with the given name and populate this "
"field with its content.")
else:
content_help_text = ""
if settings.DBTEMPLATES_USE_CODEMIRROR and settings.DBTEMPLATES_USE_TINYMCE:
raise ImproperlyConfigured("You may use either CodeMirror or TinyMCE "
"with dbtemplates, not both. Please disable "
"one of them.")
if settings.DBTEMPLATES_USE_TINYMCE:
from tinymce.widgets import AdminTinyMCE
TemplateContentTextArea = AdminTinyMCE
class TemplateAdminForm(forms.ModelForm):
"""
@ -69,6 +80,7 @@ class TemplateAdminForm(forms.ModelForm):
class Meta:
model = Template
fields = ('name', 'content', 'sites', 'creation_date', 'last_changed')
class TemplateAdmin(TemplateModelAdmin):
@ -86,33 +98,59 @@ class TemplateAdmin(TemplateModelAdmin):
'classes': ('collapse',),
}),
)
filter_horizontal = ('sites',)
list_display = ('name', 'creation_date', 'last_changed', 'site_list')
list_filter = ('sites',)
save_as = True
search_fields = ('name', 'content')
actions = ['invalidate_cache', 'repopulate_cache']
actions = ['invalidate_cache', 'repopulate_cache', 'check_syntax']
def invalidate_cache(self, request, queryset):
for template in queryset:
remove_cached_template(template)
count = queryset.count()
message = ungettext(
"Cache of one template successfully invalidated.",
"Cache of %(count)d templates successfully invalidated.",
len(queryset))
self.message_user(request, message % {'count': len(queryset)})
count)
self.message_user(request, message % {'count': count})
invalidate_cache.short_description = _("Invalidate cache of "
"selected templates")
def repopulate_cache(self, request, queryset):
for template in queryset:
add_template_to_cache(template)
count = queryset.count()
message = ungettext(
"Cache successfully repopulated with one template.",
"Cache successfully repopulated with %(count)d templates.",
len(queryset))
self.message_user(request, message % {'count': len(queryset)})
count)
self.message_user(request, message % {'count': count})
repopulate_cache.short_description = _("Repopulate cache with "
"selected templates")
def check_syntax(self, request, queryset):
errors = []
for template in queryset:
valid, error = check_template_syntax(template)
if not valid:
errors.append('%s: %s' % (template.name, error))
if errors:
count = len(errors)
message = ungettext(
"Template syntax check FAILED for %(names)s.",
"Template syntax check FAILED for %(count)d templates: %(names)s.",
count)
self.message_user(request, message %
{'count': count, 'names': ', '.join(errors)})
else:
count = queryset.count()
message = ungettext(
"Template syntax OK.",
"Template syntax OK for %(count)d templates.", count)
self.message_user(request, message % {'count': count})
check_syntax.short_description = _("Check template syntax")
def site_list(self, template):
return ", ".join([site.name for site in template.sites.all()])
site_list.short_description = _('sites')

51
dbtemplates/conf.py Normal file
View file

@ -0,0 +1,51 @@
import posixpath
from django.core.exceptions import ImproperlyConfigured
from django.conf import settings
from appconf import AppConf
class DbTemplatesConf(AppConf):
USE_CODEMIRROR = False
USE_REVERSION = False
USE_TINYMCE = False
ADD_DEFAULT_SITE = True
AUTO_POPULATE_CONTENT = True
MEDIA_PREFIX = None
CACHE_BACKEND = None
def configure_media_prefix(self, value):
if value is None:
base_url = getattr(settings, "STATIC_URL", None)
if base_url is None:
base_url = settings.MEDIA_URL
value = posixpath.join(base_url, "dbtemplates/")
return value
def configure_cache_backend(self, value):
# If we are on Django 1.3 AND using the new CACHES setting..
if hasattr(settings, "CACHES"):
if "dbtemplates" in settings.CACHES:
return "dbtemplates"
else:
return "default"
if isinstance(value, basestring) and value.startswith("dbtemplates."):
raise ImproperlyConfigured("Please upgrade to one of the "
"supported backends as defined "
"in the Django docs.")
return value
def configure_use_reversion(self, value):
if value and 'reversion' not in settings.INSTALLED_APPS:
raise ImproperlyConfigured("Please add 'reversion' to your "
"INSTALLED_APPS setting to make "
"use of it in dbtemplates.")
return value
def configure_use_tinymce(self, value):
if value and 'tinymce' not in settings.INSTALLED_APPS:
raise ImproperlyConfigured("Please add 'tinymce' to your "
"INSTALLED_APPS setting to make "
"use of it in dbtemplates.")
return value

View file

@ -1,14 +1,14 @@
import warnings
from django import VERSION
from django.conf import settings
from django.contrib.sites.models import Site
from django.db import router
from django.template import TemplateDoesNotExist
from dbtemplates.models import Template
from dbtemplates.utils import cache, get_cache_key
from dbtemplates.utils.cache import (cache, get_cache_key,
set_and_return, get_cache_notfound_key)
from django.template.loader import BaseLoader
def load_template_source(template_name, template_dirs=None, annoy=True):
class Loader(BaseLoader):
"""
A custom template loader to load templates from the database.
@ -17,43 +17,59 @@ def load_template_source(template_name, template_dirs=None, annoy=True):
it falls back to query the database field ``name`` with the template path
and ``sites`` with the current site.
"""
if VERSION[:2] >= (1, 2) and annoy:
# For backward compatibility
warnings.warn(
"`dbtemplates.loader.load_template_source` is deprecated; "
"use `dbtemplates.loader.Loader` instead.", DeprecationWarning)
site = Site.objects.get_current()
display_name = 'db:%s:%s:%s' % (settings.DATABASE_ENGINE,
template_name, site.domain)
cache_key = get_cache_key(template_name)
if cache:
try:
backend_template = cache.get(cache_key)
if backend_template:
return backend_template, template_name
except:
pass
try:
template = Template.on_site.get(name__exact=template_name)
# Save in cache backend explicitly if manually deleted or invalidated
is_usable = True
def load_and_store_template(self, template_name, cache_key, site, **params):
template = Template.objects.get(name__exact=template_name, **params)
db = router.db_for_read(Template, instance=template)
display_name = 'dbtemplates:%s:%s:%s' % (db, template_name, site.domain)
return set_and_return(cache_key, template.content, display_name)
def load_template_source(self, template_name, template_dirs=None):
# The logic should work like this:
# * Try to find the template in the cache. If found, return it.
# * Now check the cache if a lookup for the given template
# has failed lately and hand over control to the next template
# loader waiting in line.
# * If this still did not fail we first try to find a site-specific
# template in the database.
# * On a failure from our last attempt we try to load the global
# template from the database.
# * If all of the above steps have failed we generate a new key
# in the cache indicating that queries failed, with the current
# timestamp.
site = Site.objects.get_current()
cache_key = get_cache_key(template_name)
if cache:
cache.set(cache_key, template.content)
return (template.content, display_name)
except:
pass
raise TemplateDoesNotExist(template_name)
load_template_source.is_usable = True
try:
backend_template = cache.get(cache_key)
if backend_template:
return backend_template, template_name
except:
pass
# Not found in cache, move on.
cache_notfound_key = get_cache_notfound_key(template_name)
if cache:
try:
notfound = cache.get(cache_notfound_key)
if notfound:
raise TemplateDoesNotExist(template_name)
except:
raise TemplateDoesNotExist(template_name)
if VERSION[:2] >= (1, 2):
# providing a class based loader for Django >= 1.2, yay!
from django.template.loader import BaseLoader
# Not marked as not-found, move on...
class Loader(BaseLoader):
__doc__ = load_template_source.__doc__
try:
return self.load_and_store_template(template_name, cache_key,
site, sites__in=[site.id])
except (Template.MultipleObjectsReturned, Template.DoesNotExist):
try:
return self.load_and_store_template(template_name, cache_key,
site, sites__isnull=True)
except (Template.MultipleObjectsReturned, Template.DoesNotExist):
pass
is_usable = True
def load_template_source(self, template_name, template_dirs=None):
return load_template_source(
template_name, template_dirs, annoy=False)
# Mark as not-found in cache.
cache.set(cache_notfound_key, '1')
raise TemplateDoesNotExist(template_name)

View file

@ -1,15 +1,14 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# Michael Lind Mortensen <illio@cs.au.dk>, 2009.
#
#
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2009-10-09 13:45+0200\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@ -17,72 +16,93 @@ msgstr ""
"Language: da\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr ""
"Hvis du efterlader dette felt tomt, så vil Django søge efter en template med "
"det givne navn og udfylde dette felt med dets indhold."
"Hvis du efterlader dette felt tomt, så vil Django søge efter en template med"
" det givne navn og udfylde dette felt med dets indhold."
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "Dato/tid"
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] ""
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr ""
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr ""
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "websider"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "navn"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Eksempel: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "indhold"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "oprettelsesdato"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "sidst ændret"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "skabelon"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "skabeloner"

View file

@ -1,19 +1,23 @@
#
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
#
# Jannis Leidel <jannis@leidel.info>, 2011.
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2010-11-07 00:01+0100\n"
"PO-Revision-Date: 2008-08-19 17:11+0100\n"
"Last-Translator: Jannis Leidel <jannis@leidel.info>\n"
"Language-Team: Jannis Leidel <jannis@leidel.info>\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language: de\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
@ -21,66 +25,86 @@ msgstr ""
"Wenn Sie dieses Feld leer lassen, wird Django versuchen, das Template mit "
"dem angegebenen Namen zu finden und mit dessen Inhalt das Feld zu füllen."
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr "Erweiterte Einstellungen"
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "Datum/Uhrzeit"
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] "Der Cache eines Templates wurde erfolgreich geleert."
msgstr[1] "Der Cache von %(count)d Templates wurde erfolgreich geleert."
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr "Cache der ausgewählten Templates leeren"
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
"Der Cache eines Templates wurde erfolgreich geleert und neu gefüllt."
msgstr[0] "Der Cache eines Templates wurde erfolgreich geleert und neu gefüllt."
msgstr[1] ""
"Der Cache von %(count)d Templates wurde erfolgreich geleert und neu gefüllt."
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr "Cache der ausgewählten Templates neu füllen"
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] "Template-Syntax von %(names)s ist FEHLERHAFT."
msgstr[1] "Template-Syntax von %(count)d Templates (%(names)s) ist FEHLERHAFT."
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] "Template-Syntax ist OK."
msgstr[1] "Template-Syntax von %(count)d Templates ist OK."
#: admin.py:141
msgid "Check template syntax"
msgstr "Template-Syntax überprüfen"
#: admin.py:145 models.py:25
msgid "sites"
msgstr "Seiten"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "Name"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Zum Beispiel: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "Inhalt"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "Erstellt"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "Geändert"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "Template"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "Templates"

View file

@ -8,78 +8,97 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2010-11-07 00:02+0100\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"Language: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr ""
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr ""
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] ""
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr ""
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr ""
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural "Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr ""
#: models.py:26
#: models.py:22
msgid "name"
msgstr ""
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr ""
#: models.py:28
#: models.py:24
msgid "content"
msgstr ""
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr ""
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr ""
#: models.py:40
#: models.py:37
msgid "template"
msgstr ""
#: models.py:41
#: models.py:38
msgid "templates"
msgstr ""

View file

@ -1,15 +1,15 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#
# Ville Säävuori <ville@syneus.fi>, 2011.
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: Jaakko Holster <holster@iki.fi>\n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@ -17,72 +17,93 @@ msgstr ""
"Language: fi\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr ""
"Mikäli kenttä on tyhjä, Django etsii samannimistä sivupohjaa ja täyttää "
"kentän sen sisällöllä."
"Jos tämä jätetään tyhjäksi, Django etsiin annetulla nimellä olevan "
"mallipohjan ja täyttää tähän kenttään sen sisällön."
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr "Lisäasetukset"
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "Päiväys/aika"
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] "Sivupohja poistettu välimuistista."
msgstr[1] "%(count)d sivupohjaa poistettu välimuistista."
msgstr[0] "Yhden mallipohjan välimuisti on onnistuneesti tyhjennetty."
msgstr[1] "%(count)d mallipohjan välimusti on onnistuneesti tyhjennetty."
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr "Poista valitut sivupohjat välimuistista."
msgstr "Tyhjennä valittujen mallipohjien välimuisti."
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] "Sivupohja lisätty välimuistiin."
msgstr[1] "%(count)d sivupohjaa lisätty välimuistiin."
msgstr[0] "Yhden mallipohjan välimuisti on täytetty onnistuneesti."
msgstr[1] "%(count)d mallipohjan välimuisti on täytetty onnistuneesti."
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr "Lisää valitut sivupohjat välimuistiin."
msgstr "Täytä valittujen mallipohjien välimuisti."
#: admin.py:119
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "sivustot"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "nimi"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Esimerkki: 'flatpages/default.html'"
msgstr "Esimerkiksi: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "sisältö"
msgstr "sisätö"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "luotu"
msgstr "luontipäivä"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "muokattu"
msgstr "viimeksi muutettu"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "sivupohja"
msgstr "mallipohja"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "sivupohjat"
msgstr "mallipohjat"

View file

@ -1,21 +1,22 @@
# Roland Frédéric <frederic.roland@creativeconvergence.be>, 2009.
#
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
#
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: David Paccoud <dpaccoud@gmail.com>\n"
"Language-Team: French\n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language: fr\n"
"Plural-Forms: nplurals=2; plural=(n > 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
@ -23,64 +24,85 @@ msgstr ""
"Si vous laissez ceci vide , Django recherchera un modèle avec le nom donné "
"et remplira ce champ avec son contenu."
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "Date/heure"
#: admin.py:98
#, python-format
#: admin.py:102
#, fuzzy, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] "Le cache d'un modèle a été invalidé avec succès."
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr "Invalidation du cache des modèles sélectionnés"
#: admin.py:111
#, python-format
#: admin.py:114
#, fuzzy, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] "Le cache d'un modèle a été rechargé avec succès."
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr "Rechargement du cache des modèles sélectionnés"
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "sites"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "nom"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Exemple : 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "contenu"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "date de création"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "dernier changement"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "modèle"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "modèles"

View file

@ -1,86 +1,106 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: <>\n"
"Language-Team: \n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language: he\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr "אם זה ריק אז ג'נגו מחפש תבנית עם שם סיפק וממלא את השדה עם תוכנו"
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "תאריך / זמן"
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] ""
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr ""
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr ""
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "אתרים"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "שם"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "דוגמא: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "תוכן"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "נוצר ב"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "שונה ב"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "תבנית"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "תבניות"

View file

@ -1,18 +1,22 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
#
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: Marco Beri <marcoberi@gmail.com>\n"
"Language-Team: Jannis Leidel <jannis@leidel.info>\n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language: it\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
@ -20,64 +24,85 @@ msgstr ""
"Lasciandolo vuoto, Django cercherà un template con lo stesso nome che avete "
"indicato sopra e userà il suo contenuto per riempire questo campo."
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr ""
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] ""
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr ""
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr ""
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr ""
#: models.py:26
#: models.py:22
msgid "name"
msgstr "nome"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Esempio: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "contenuto"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "data di creazione"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "ultimo cambiamento"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "template"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "template"

View file

@ -1,23 +1,23 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#
# Herson Hersonls <hersonls@gmail.com>, 2011.
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: Diego Búrigo Zacarão <diegobz@fedoraproject.org>\n"
"Language-Team: Brazilian Portuguese <fedora-trans-pt_br@redhat.com>\n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: Portuguese (Brazilian) (http://www.transifex.net/projects/p/django-dbtemplates/team/pt_BR/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Language: pt_BR\n"
"Plural-Forms: nplurals=2; plural=(n > 1)\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
@ -25,64 +25,85 @@ msgstr ""
"Manter isto vazio faz com que o Django procure por um modelo (template) com "
"o dado nome e preencha este campo com o seu conteúdo"
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
msgstr "Avançado"
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "Data/hora"
#: admin.py:98
#: admin.py:102
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] ""
msgstr[1] ""
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr ""
#: admin.py:111
#: admin.py:114
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr ""
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
msgstr[1] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
msgstr[1] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "sites"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "Name"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "Exemplo: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "conteúdo"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "Data de criação"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "ultima modificação"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "modelo"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "modelos"

Binary file not shown.

View file

@ -0,0 +1,107 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#, fuzzy
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2013-07-30 14:03+0600\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"Language: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n"
"Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n"
"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n"
#: admin.py:57
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr "Если вы оставите это поле незаполненным, Django будет искать шаблон с введённым именем и заполнит поле его содержимым."
#: admin.py:92
msgid "Advanced"
msgstr "Дополнительно"
#: admin.py:95
msgid "Date/time"
msgstr "Дата/время"
#: admin.py:112
#, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] "Кэш для шаблона успешно очищен."
msgstr[1] "Кэш для шаблонов (%(count)d шт.) успешно очищен."
#: admin.py:116
msgid "Invalidate cache of selected templates"
msgstr "Очистить кэш для выделенных шаблонов"
#: admin.py:124
#, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] "Кэш для шаблона успешно заполнен."
msgstr[1] "Кэш для шаблонов (%(count)d шт.) успешно заполнен."
#: admin.py:128
msgid "Repopulate cache with selected templates"
msgstr "Заполнить кэш для выделенных шаблонов"
#: admin.py:140
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural "Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] "Неверный синтаксис у шаблона %(names)s."
msgstr[1] "Неверный синтаксис у следующих шаблонов: %(names)s."
#: admin.py:148
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] "Синтаксис шаблона корректен."
msgstr[1] "Синтаксис шаблонов корректен."
#: admin.py:151
msgid "Check template syntax"
msgstr "Проверить синтаксис шаблона"
#: admin.py:155 models.py:29
msgid "sites"
msgstr "сайты"
#: models.py:26
msgid "name"
msgstr "название"
#: models.py:27
msgid "Example: 'flatpages/default.html'"
msgstr "Например: 'flatpages/default.html'"
#: models.py:28
msgid "content"
msgstr "содержимое"
#: models.py:31
msgid "creation date"
msgstr "дата создания"
#: models.py:33
msgid "last changed"
msgstr "последнее изменение"
#: models.py:41
msgid "template"
msgstr "шаблон"
#: models.py:42
msgid "templates"
msgstr "шаблоны"

View file

@ -1,15 +1,14 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
# FIRST AUTHOR <EMAIL@ADDRESS>, YEAR.
#
#
msgid ""
msgstr ""
"Project-Id-Version: django-dbtemplates\n"
"Report-Msgid-Bugs-To: \n"
"Last-Translator: 张昆 <zhangkun@web916.com>\n"
"POT-Creation-Date: 2011-01-31 11:10+0100\n"
"PO-Revision-Date: 2011-01-31 10:08+0000\n"
"Report-Msgid-Bugs-To: https://github.com/jezdez/django-dbtemplates/issues\n"
"POT-Creation-Date: 2011-08-15 13:13+0200\n"
"PO-Revision-Date: 2011-08-15 11:14+0000\n"
"Last-Translator: Jannis <jannis@leidel.info>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@ -17,68 +16,87 @@ msgstr ""
"Language: zh_CN\n"
"Plural-Forms: nplurals=1; plural=0\n"
#: admin.py:53
#: admin.py:56
msgid ""
"Leaving this empty causes Django to look for a template with the given name "
"and populate this field with its content."
msgstr "此项目留空将使系统用指定的名称寻找模板并应用到该项目。"
#: admin.py:77
#: admin.py:82
msgid "Advanced"
msgstr ""
#: admin.py:80
#: admin.py:85
msgid "Date/time"
msgstr "日期/时间"
#: admin.py:98
#, python-format
#: admin.py:102
#, fuzzy, python-format
msgid "Cache of one template successfully invalidated."
msgid_plural "Cache of %(count)d templates successfully invalidated."
msgstr[0] "该模板的缓存已经成功撤销。"
#: admin.py:102
#: admin.py:106
msgid "Invalidate cache of selected templates"
msgstr "撤销选中模板的缓存"
#: admin.py:111
#, python-format
#: admin.py:114
#, fuzzy, python-format
msgid "Cache successfully repopulated with one template."
msgid_plural "Cache successfully repopulated with %(count)d templates."
msgstr[0] "该模板的缓存已经成功启用。"
#: admin.py:115
#: admin.py:118
msgid "Repopulate cache with selected templates"
msgstr "重新启用选中模板的缓存"
#: admin.py:119 models.py:29
#: admin.py:130
#, python-format
msgid "Template syntax check FAILED for %(names)s."
msgid_plural ""
"Template syntax check FAILED for %(count)d templates: %(names)s."
msgstr[0] ""
#: admin.py:138
#, python-format
msgid "Template syntax OK."
msgid_plural "Template syntax OK for %(count)d templates."
msgstr[0] ""
#: admin.py:141
msgid "Check template syntax"
msgstr ""
#: admin.py:145 models.py:25
msgid "sites"
msgstr "站点"
#: models.py:26
#: models.py:22
msgid "name"
msgstr "名称"
#: models.py:27
#: models.py:23
msgid "Example: 'flatpages/default.html'"
msgstr "例如: 'flatpages/default.html'"
#: models.py:28
#: models.py:24
msgid "content"
msgstr "内容"
#: models.py:30
#: models.py:27
msgid "creation date"
msgstr "创建日期"
#: models.py:32
#: models.py:29
msgid "last changed"
msgstr "最新变更"
#: models.py:40
#: models.py:37
msgid "template"
msgstr "模板"
#: models.py:41
#: models.py:38
msgid "templates"
msgstr "模板"

View file

@ -0,0 +1,21 @@
from django.core.management.base import CommandError, NoArgsCommand
from dbtemplates.models import Template
from dbtemplates.utils.template import check_template_syntax
class Command(NoArgsCommand):
help = "Ensures templates stored in the database don't have syntax errors."
def handle_noargs(self, **options):
errors = []
for template in Template.objects.all():
valid, error = check_template_syntax(template)
if not valid:
errors.append('%s: %s' % (template.name, error))
if errors:
raise CommandError(
'Some templates contained errors\n%s' % '\n'.join(errors))
# NOTE: printing instead of using self.stdout.write to maintain
# Django 1.2 compatibility
print('OK')

View file

@ -30,7 +30,8 @@ class Command(NoArgsCommand):
help = "Creates the default error templates as database template objects."
option_list = NoArgsCommand.option_list + (
make_option("-f", "--force", action="store_true", dest="force",
default=False, help="overwrite existing database templates"),)
default=False,
help="overwrite existing database templates"),)
def handle_noargs(self, **options):
force = options.get('force')

View file

@ -1,36 +1,46 @@
import os
import codecs
from optparse import make_option
from django.conf import settings
from django.contrib.sites.models import Site
from django.core.management.base import CommandError, NoArgsCommand
from django.template.loaders.app_directories import app_template_dirs
from dbtemplates.conf import settings
from dbtemplates.models import Template
ALWAYS_ASK, FILES_TO_DATABASE, DATABASE_TO_FILES = ('0', '1', '2')
class Command(NoArgsCommand):
help = "Syncs file system templates with the database bidirectionally."
option_list = NoArgsCommand.option_list + (
make_option("-e", "--ext", dest="ext", action="store", default="html",
help="extension of the files you want to sync with the database "
"[default: %default]"),
make_option("-f", "--force", action="store_true", dest="force",
default=False, help="overwrite existing database templates"),
make_option("-o", "--overwrite", action="store", dest="overwrite",
default='0', help="'0' - ask always, '1' - overwrite database "
"templates from template files, '2' - overwrite template "
"files from database templates"),
make_option("-a", "--app-first", action="store_true", dest="app_first",
default=False, help="look for templates in applications "
"directories before project templates"))
make_option("-e", "--ext",
dest="ext", action="store", default="html",
help="extension of the files you want to "
"sync with the database [default: %default]"),
make_option("-f", "--force",
action="store_true", dest="force", default=False,
help="overwrite existing database templates"),
make_option("-o", "--overwrite",
action="store", dest="overwrite", default='0',
help="'0' - ask always, '1' - overwrite database "
"templates from template files, '2' - overwrite "
"template files from database templates"),
make_option("-a", "--app-first",
action="store_true", dest="app_first", default=False,
help="look for templates in applications "
"directories before project templates"),
make_option("-d", "--delete",
action="store_true", dest="delete", default=False,
help="Delete templates after syncing"))
def handle_noargs(self, **options):
extension = options.get('ext')
force = options.get('force')
overwrite = options.get('overwrite')
app_first = options.get('app_first')
delete = options.get('delete')
if not extension.startswith("."):
extension = ".%s" % extension
@ -53,10 +63,12 @@ class Command(NoArgsCommand):
for templatedir in templatedirs:
for dirpath, subdirs, filenames in os.walk(templatedir):
for f in [f for f in filenames if f.endswith(extension)
and not f.startswith(".")]:
for f in [f for f in filenames
if f.endswith(extension) and not f.startswith(".")]:
path = os.path.join(dirpath, f)
name = path.split(templatedir)[1][1:]
name = path.split(templatedir)[1]
if name.startswith('/'):
name = name[1:]
try:
t = Template.on_site.get(name__exact=name)
except Template.DoesNotExist:
@ -64,35 +76,40 @@ class Command(NoArgsCommand):
confirm = raw_input(
"\nA '%s' template doesn't exist in the "
"database.\nCreate it with '%s'?"
" (y/[n]): """ % (name, path))
" (y/[n]): """ % (name, path))
if force or confirm.lower().startswith('y'):
t = Template(name=name,
content=open(path, "r").read())
content=codecs.open(path, "r").read())
t.save()
t.sites.add(site)
else:
while 1:
if overwrite == ALWAYS_ASK:
confirm = raw_input(
"\n%s exists in the database.\n"
"(1) Overwrite %s with '%s'\n"
"(2) Overwrite '%s' with %s\n"
"Type 1 or 2 or press <Enter> to skip: "
% (t.__repr__(),
t.__repr__(), path,
path, t.__repr__()))
"\n%(template)s exists in the database.\n"
"(1) Overwrite %(template)s with '%(path)s'\n"
"(2) Overwrite '%(path)s' with %(template)s\n"
"Type 1 or 2 or press <Enter> to skip: " %
{'template': t.__repr__(), 'path': path})
else:
confirm = overwrite
if confirm == '' or confirm in (
FILES_TO_DATABASE, DATABASE_TO_FILES):
if confirm in ('', FILES_TO_DATABASE,
DATABASE_TO_FILES):
if confirm == FILES_TO_DATABASE:
t.content = open(path, 'r').read()
t.content = codecs.open(path, 'r').read()
t.save()
t.sites.add(site)
if delete:
try:
os.remove(path)
except OSError:
raise CommandError(u"Couldn't delete %s" % path)
elif confirm == DATABASE_TO_FILES:
f = codecs.open(path, 'w', 'utf-8')
try:
f = open(path, 'w')
f.write(t.content)
finally:
f.close()
if delete:
t.delete()
break

View file

@ -0,0 +1,55 @@
# encoding: utf-8
import datetime
from south.db import db
from south.v2 import SchemaMigration
from django.db import models
class Migration(SchemaMigration):
def forwards(self, orm):
# Adding model 'Template'
db.create_table('django_template', (
('id', self.gf('django.db.models.fields.AutoField')(primary_key=True)),
('name', self.gf('django.db.models.fields.CharField')(unique=True, max_length=100)),
('content', self.gf('django.db.models.fields.TextField')(blank=True)),
('creation_date', self.gf('django.db.models.fields.DateTimeField')(default=datetime.datetime.now)),
('last_changed', self.gf('django.db.models.fields.DateTimeField')(default=datetime.datetime.now)),
))
db.send_create_signal('dbtemplates', ['Template'])
# Adding M2M table for field sites on 'Template'
db.create_table('django_template_sites', (
('id', models.AutoField(verbose_name='ID', primary_key=True, auto_created=True)),
('template', models.ForeignKey(orm['dbtemplates.template'], null=False)),
('site', models.ForeignKey(orm['sites.site'], null=False))
))
db.create_unique('django_template_sites', ['template_id', 'site_id'])
def backwards(self, orm):
# Deleting model 'Template'
db.delete_table('django_template')
# Removing M2M table for field sites on 'Template'
db.delete_table('django_template_sites')
models = {
'dbtemplates.template': {
'Meta': {'ordering': "('name',)", 'object_name': 'Template', 'db_table': "'django_template'"},
'content': ('django.db.models.fields.TextField', [], {'blank': 'True'}),
'creation_date': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
'last_changed': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
'name': ('django.db.models.fields.CharField', [], {'unique': 'True', 'max_length': '100'}),
'sites': ('django.db.models.fields.related.ManyToManyField', [], {'to': "orm['sites.Site']", 'symmetrical': 'False'})
},
'sites.site': {
'Meta': {'ordering': "('domain',)", 'object_name': 'Site', 'db_table': "'django_site'"},
'domain': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
'name': ('django.db.models.fields.CharField', [], {'max_length': '50'})
}
}
complete_apps = ['dbtemplates']

View file

@ -0,0 +1,34 @@
# encoding: utf-8
from south.db import db
from south.v2 import SchemaMigration
class Migration(SchemaMigration):
def forwards(self, orm):
# Removing unique constraint on 'Template', fields ['name']
db.delete_unique('django_template', ['name'])
def backwards(self, orm):
# Adding unique constraint on 'Template', fields ['name']
db.create_unique('django_template', ['name'])
models = {
'dbtemplates.template': {
'Meta': {'ordering': "('name',)", 'object_name': 'Template', 'db_table': "'django_template'"},
'content': ('django.db.models.fields.TextField', [], {'blank': 'True'}),
'creation_date': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
'last_changed': ('django.db.models.fields.DateTimeField', [], {'default': 'datetime.datetime.now'}),
'name': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
'sites': ('django.db.models.fields.related.ManyToManyField', [], {'to': "orm['sites.Site']", 'symmetrical': 'False'})
},
'sites.site': {
'Meta': {'ordering': "('domain',)", 'object_name': 'Site', 'db_table': "'django_site'"},
'domain': ('django.db.models.fields.CharField', [], {'max_length': '100'}),
'id': ('django.db.models.fields.AutoField', [], {'primary_key': 'True'}),
'name': ('django.db.models.fields.CharField', [], {'max_length': '50'})
}
}
complete_apps = ['dbtemplates']

View file

View file

@ -1,17 +1,21 @@
# -*- coding: utf-8 -*-
from datetime import datetime
from django.db import models
from django.db.models import signals
from django.template import TemplateDoesNotExist
from django.utils.translation import gettext_lazy as _
from django.utils.translation import ugettext_lazy as _
from django.contrib.sites.models import Site
from django.contrib.sites.managers import CurrentSiteManager
from dbtemplates import settings
from dbtemplates.utils import (add_default_site, add_template_to_cache,
remove_cached_template, get_template_source)
from dbtemplates.conf import settings
from dbtemplates.utils.cache import add_template_to_cache, remove_cached_template
from dbtemplates.utils.template import get_template_source
try:
from django.utils.timezone import now
except ImportError:
from datetime import datetime
now = datetime.now
class Template(models.Model):
@ -19,14 +23,15 @@ class Template(models.Model):
Defines a template model for use with the database template loader.
The field ``name`` is the equivalent to the filename of a static template.
"""
name = models.CharField(_('name'), unique=True, max_length=100,
name = models.CharField(_('name'), max_length=100,
help_text=_("Example: 'flatpages/default.html'"))
content = models.TextField(_('content'), blank=True)
sites = models.ManyToManyField(Site, verbose_name=_('sites'))
sites = models.ManyToManyField(Site, verbose_name=_(u'sites'),
blank=True, null=True)
creation_date = models.DateTimeField(_('creation date'),
default=datetime.now)
default=now)
last_changed = models.DateTimeField(_('last changed'),
default=datetime.now)
default=now)
objects = models.Manager()
on_site = CurrentSiteManager('sites')
@ -55,14 +60,27 @@ class Template(models.Model):
pass
def save(self, *args, **kwargs):
self.last_changed = datetime.now()
self.last_changed = now()
# If content is empty look for a template with the given name and
# populate the template instance with its content.
if settings.AUTO_POPULATE_CONTENT and not self.content:
if settings.DBTEMPLATES_AUTO_POPULATE_CONTENT and not self.content:
self.populate()
super(Template, self).save(*args, **kwargs)
def add_default_site(instance, **kwargs):
"""
Called via Django's signals to cache the templates, if the template
in the database was added or changed, only if
DBTEMPLATES_ADD_DEFAULT_SITE setting is set.
"""
if not settings.DBTEMPLATES_ADD_DEFAULT_SITE:
return
current_site = Site.objects.get_current()
if current_site not in instance.sites.all():
instance.sites.add(current_site)
signals.post_save.connect(add_default_site, sender=Template)
signals.post_save.connect(add_template_to_cache, sender=Template)
signals.pre_delete.connect(remove_cached_template, sender=Template)

View file

@ -1,33 +0,0 @@
import posixpath
from django.conf import settings
from django.core.exceptions import ImproperlyConfigured
if "dbtemplates" in getattr(settings, "CACHES", {}):
# If we are on Django 1.3 AND using the new CACHES setting..
cache = "dbtemplates"
else:
# ..or fall back to the old CACHE_BACKEND setting
cache = getattr(settings, "DBTEMPLATES_CACHE_BACKEND", None)
if isinstance(cache, basestring) and cache.startswith("dbtemplates."):
raise ImproperlyConfigured("Please upgrade to one of the supported "
"backends as defined in the Django docs.")
CACHE_BACKEND = cache
ADD_DEFAULT_SITE = getattr(settings, 'DBTEMPLATES_ADD_DEFAULT_SITE', True)
AUTO_POPULATE_CONTENT = getattr(
settings, 'DBTEMPLATES_AUTO_POPULATE_CONTENT', True)
base_url = getattr(settings, "STATIC_URL", None)
if base_url is None:
base_url = settings.MEDIA_URL
MEDIA_PREFIX = getattr(settings, 'DBTEMPLATES_MEDIA_PREFIX',
posixpath.join(base_url, "dbtemplates/"))
USE_REVERSION = getattr(settings, 'DBTEMPLATES_USE_REVERSION', False)
if USE_REVERSION and 'reversion'not in settings.INSTALLED_APPS:
raise ImproperlyConfigured("Please add reversion to your "
"INSTALLED_APPS setting to make use of it in dbtemplates.")
USE_CODEMIRROR = getattr(settings, 'DBTEMPLATES_USE_CODEMIRROR', False)

147
dbtemplates/test_cases.py Normal file
View file

@ -0,0 +1,147 @@
import codecs
import os
import shutil
import tempfile
from django.conf import settings as django_settings
from django.core.cache.backends.base import BaseCache
from django.core.management import call_command
from django.template import loader, Context, TemplateDoesNotExist
from django.test import TestCase
from django.contrib.sites.models import Site
from dbtemplates.conf import settings
from dbtemplates.models import Template
from dbtemplates.utils.cache import get_cache_backend, get_cache_key
from dbtemplates.utils.template import (get_template_source,
check_template_syntax)
from dbtemplates.management.commands.sync_templates import (FILES_TO_DATABASE,
DATABASE_TO_FILES)
class DbTemplatesTestCase(TestCase):
def setUp(self):
self.old_template_loaders = settings.TEMPLATE_LOADERS
if 'dbtemplates.loader.Loader' not in settings.TEMPLATE_LOADERS:
loader.template_source_loaders = None
settings.TEMPLATE_LOADERS = (list(settings.TEMPLATE_LOADERS) +
['dbtemplates.loader.Loader'])
self.site1, created1 = Site.objects.get_or_create(
domain="example.com", name="example.com")
self.site2, created2 = Site.objects.get_or_create(
domain="example.org", name="example.org")
self.t1, _ = Template.objects.get_or_create(
name='base.html', content='base')
self.t2, _ = Template.objects.get_or_create(
name='sub.html', content='sub')
self.t2.sites.add(self.site2)
def tearDown(self):
loader.template_source_loaders = None
settings.TEMPLATE_LOADERS = self.old_template_loaders
def test_basiscs(self):
self.assertEqual(list(self.t1.sites.all()), [self.site1])
self.assertTrue("base" in self.t1.content)
self.assertEqual(list(Template.objects.filter(sites=self.site1)),
[self.t1, self.t2])
self.assertEqual(list(self.t2.sites.all()), [self.site1, self.site2])
def test_empty_sites(self):
old_add_default_site = settings.DBTEMPLATES_ADD_DEFAULT_SITE
try:
settings.DBTEMPLATES_ADD_DEFAULT_SITE = False
self.t3 = Template.objects.create(
name='footer.html', content='footer')
self.assertEqual(list(self.t3.sites.all()), [])
finally:
settings.DBTEMPLATES_ADD_DEFAULT_SITE = old_add_default_site
def test_load_templates_sites(self):
old_add_default_site = settings.DBTEMPLATES_ADD_DEFAULT_SITE
old_site_id = django_settings.SITE_ID
try:
settings.DBTEMPLATES_ADD_DEFAULT_SITE = False
t_site1 = Template.objects.create(
name='copyright.html', content='(c) example.com')
t_site1.sites.add(self.site1)
t_site2 = Template.objects.create(
name='copyright.html', content='(c) example.org')
t_site2.sites.add(self.site2)
django_settings.SITE_ID = Site.objects.create(
domain="example.net", name="example.net").id
Site.objects.clear_cache()
self.assertRaises(TemplateDoesNotExist,
loader.get_template, "copyright.html")
finally:
django_settings.SITE_ID = old_site_id
settings.DBTEMPLATES_ADD_DEFAULT_SITE = old_add_default_site
def test_load_templates(self):
result = loader.get_template("base.html").render(Context({}))
self.assertEqual(result, 'base')
result2 = loader.get_template("sub.html").render(Context({}))
self.assertEqual(result2, 'sub')
def test_error_templates_creation(self):
call_command('create_error_templates', force=True, verbosity=0)
self.assertEqual(list(Template.objects.filter(sites=self.site1)),
list(Template.objects.filter()))
self.assertTrue(Template.objects.filter(name='404.html').exists())
def test_automatic_sync(self):
admin_base_template = get_template_source('admin/base.html')
template = Template.objects.create(name='admin/base.html')
self.assertEqual(admin_base_template, template.content)
def test_sync_templates(self):
old_template_dirs = settings.TEMPLATE_DIRS
temp_template_dir = tempfile.mkdtemp('dbtemplates')
temp_template_path = os.path.join(temp_template_dir, 'temp_test.html')
temp_template = codecs.open(temp_template_path, 'w')
try:
temp_template.write('temp test')
settings.TEMPLATE_DIRS = (temp_template_dir,)
self.assertFalse(
Template.objects.filter(name='temp_test.html').exists())
call_command('sync_templates', force=True,
verbosity=0, overwrite=FILES_TO_DATABASE)
self.assertTrue(
Template.objects.filter(name='temp_test.html').exists())
t = Template.objects.get(name='temp_test.html')
t.content = 'temp test modified'
t.save()
call_command('sync_templates', force=True,
verbosity=0, overwrite=DATABASE_TO_FILES)
self.assertTrue(
'modified' in codecs.open(temp_template_path).read())
call_command('sync_templates', force=True, verbosity=0,
delete=True, overwrite=DATABASE_TO_FILES)
self.assertTrue(os.path.exists(temp_template_path))
self.assertFalse(
Template.objects.filter(name='temp_test.html').exists())
finally:
temp_template.close()
settings.TEMPLATE_DIRS = old_template_dirs
shutil.rmtree(temp_template_dir)
def test_get_cache(self):
self.assertTrue(isinstance(get_cache_backend(), BaseCache))
def test_check_template_syntax(self):
bad_template, _ = Template.objects.get_or_create(
name='bad.html', content='{% if foo %}Bar')
good_template, _ = Template.objects.get_or_create(
name='good.html', content='{% if foo %}Bar{% endif %}')
self.assertFalse(check_template_syntax(bad_template)[0])
self.assertTrue(check_template_syntax(good_template)[0])
def test_get_cache_name(self):
self.assertEqual(get_cache_key('name with spaces'),
'dbtemplates::name-with-spaces::1')

View file

@ -0,0 +1,32 @@
DBTEMPLATES_CACHE_BACKEND = 'dummy://'
DATABASE_ENGINE = 'sqlite3'
# SQLite does not support removing unique constraints (see #28)
SOUTH_TESTS_MIGRATE = False
SITE_ID = 1
SECRET_KEY = 'something-something'
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': ':memory:',
}
}
INSTALLED_APPS = [
'django.contrib.contenttypes',
'django.contrib.sites',
'django.contrib.admin',
'django.contrib.auth',
'dbtemplates',
]
TEMPLATE_LOADERS = (
'django.template.loaders.filesystem.Loader',
'django.template.loaders.app_directories.Loader',
'dbtemplates.loader.Loader',
)
TEST_RUNNER = 'discover_runner.DiscoverRunner'

View file

@ -1,66 +0,0 @@
from django import VERSION
from django.core.management import call_command
from django.template import loader, Context
from django.test import TestCase
from django.contrib.sites.models import Site
from dbtemplates import settings
from dbtemplates.loader import load_template_source
from dbtemplates.models import Template, get_template_source
class DbTemplatesTestCase(TestCase):
def setUp(self):
self.site1, created1 = Site.objects.get_or_create(domain="example.com", name="example.com")
self.site2, created2 = Site.objects.get_or_create(domain="example.org", name="example.org")
def test_basiscs(self):
t1 = Template(name='base.html', content='<html><head></head><body>{% block content %}Welcome at {{ title }}{% endblock %}</body></html>')
t1.save()
self.assertEqual(Site.objects.get_current(), t1.sites.all()[0])
self.assertTrue("Welcome at" in t1.content)
t2 = Template(name='sub.html', content='{% extends "base.html" %}{% block content %}This is {{ title }}{% endblock %}')
t2.save()
t2.sites.add(self.site2)
self.assertEqual(list(Template.objects.filter(sites=self.site1)), [t1, t2])
self.assertEqual(list(t2.sites.all()), [self.site1, self.site2])
def test_load_templates(self):
self.test_basiscs()
original_template_source_loaders = loader.template_source_loaders
loader.template_source_loaders = [load_template_source]
try:
result1 = loader.get_template("base.html").render(Context({'title':'MainPage'}))
self.assertEqual(result1, u'<html><head></head><body>Welcome at MainPage</body></html>')
result2 = loader.get_template("sub.html").render(Context({'title':'SubPage'}))
self.assertEqual(result2, u'<html><head></head><body>This is SubPage</body></html>')
if VERSION[:2] >= (1, 2):
from dbtemplates.loader import Loader
dbloader = Loader()
loader.template_source_loaders = [dbloader.load_template_source]
result = loader.get_template("base.html").render(Context({'title':'MainPage'}))
self.assertEqual(result, u'<html><head></head><body>Welcome at MainPage</body></html>')
result2 = loader.get_template("sub.html").render(Context({'title':'SubPage'}))
self.assertEqual(result2, u'<html><head></head><body>This is SubPage</body></html>')
finally:
loader.template_source_loaders = original_template_source_loaders
def test_error_templates_creation(self):
call_command('create_error_templates', force=True, verbosity=0)
self.assertEqual(list(Template.objects.filter(sites=self.site1)),
list(Template.objects.filter()))
def test_disabling_default_site(self):
old_add_default_site = settings.ADD_DEFAULT_SITE
settings.ADD_DEFAULT_SITE = False
t3 = Template.objects.create(name='footer.html', content='ohai')
self.assertEqual(list(t3.sites.all()), [])
settings.ADD_DEFAULT_SITE = old_add_default_site
def test_automatic_sync(self):
admin_base_template = get_template_source('admin/base.html')
template = Template.objects.create(name='admin/base.html')
self.assertEqual(admin_base_template, template.content)

View file

@ -1,95 +0,0 @@
from django import VERSION
from django.core.cache import get_cache
from django.template import TemplateDoesNotExist
from django.utils.importlib import import_module
from django.contrib.sites.models import Site
from dbtemplates import settings
def get_cache_backend():
return get_cache(settings.CACHE_BACKEND)
cache = get_cache_backend()
def add_default_site(instance, **kwargs):
"""
Called via Django's signals to cache the templates, if the template
in the database was added or changed, only if DBTEMPLATES_ADD_DEFAULT_SITE
setting is set.
"""
if settings.ADD_DEFAULT_SITE:
current_site = Site.objects.get_current()
if current_site not in instance.sites.all():
instance.sites.add(current_site)
def get_cache_key(name):
current_site = Site.objects.get_current()
return 'dbtemplates::%s::%s' % (name, current_site.pk)
def add_template_to_cache(instance, **kwargs):
"""
Called via Django's signals to cache the templates, if the template
in the database was added or changed.
"""
remove_cached_template(instance)
cache.set(get_cache_key(instance.name), instance.content)
def remove_cached_template(instance, **kwargs):
"""
Called via Django's signals to remove cached templates, if the template
in the database was changed or deleted.
"""
cache.delete(get_cache_key(instance.name))
def get_loaders():
from django.template.loader import template_source_loaders
if template_source_loaders is None:
try:
from django.template.loader import (
find_template as finder_func)
except ImportError:
from django.template.loader import (
find_template_source as finder_func)
try:
source, name = finder_func('test')
except TemplateDoesNotExist:
pass
from django.template.loader import template_source_loaders
return template_source_loaders or []
def get_template_source(name):
source = None
for loader in get_loaders():
if loader.__module__.startswith('dbtemplates.'):
# Don't give a damn about dbtemplates' own loader.
continue
module = import_module(loader.__module__)
load_template_source = getattr(module, 'load_template_source', None)
if load_template_source is None:
load_template_source = loader.load_template_source
try:
source, origin = load_template_source(name)
if source:
return source
except NotImplementedError:
pass
except TemplateDoesNotExist:
pass
if source is None and VERSION[:2] < (1, 2):
# Django supported template source extraction still :/
try:
from django.template.loader import find_template_source
template, origin = find_template_source(name, None)
if not hasattr(template, 'render'):
return template
except (ImportError, TemplateDoesNotExist):
pass
return None

View file

View file

@ -0,0 +1,51 @@
from django.core.cache import get_cache
from django.contrib.sites.models import Site
from django.template.defaultfilters import slugify
from dbtemplates.conf import settings
def get_cache_backend():
return get_cache(settings.DBTEMPLATES_CACHE_BACKEND)
cache = get_cache_backend()
def get_cache_key(name):
current_site = Site.objects.get_current()
return 'dbtemplates::%s::%s' % (slugify(name), current_site.pk)
def get_cache_notfound_key(name):
return get_cache_key(name) + '::notfound'
def remove_notfound_key(instance):
# Remove notfound key as soon as we save the template.
cache.delete(get_cache_notfound_key(instance.name))
def set_and_return(cache_key, content, display_name):
# Save in cache backend explicitly if manually deleted or invalidated
if cache:
cache.set(cache_key, content)
return (content, display_name)
def add_template_to_cache(instance, **kwargs):
"""
Called via Django's signals to cache the templates, if the template
in the database was added or changed.
"""
remove_cached_template(instance)
remove_notfound_key(instance)
cache.set(get_cache_key(instance.name), instance.content)
def remove_cached_template(instance, **kwargs):
"""
Called via Django's signals to remove cached templates, if the template
in the database was changed or deleted.
"""
cache.delete(get_cache_key(instance.name))

View file

@ -0,0 +1,57 @@
from django import VERSION
from django.template import (Template, TemplateDoesNotExist,
TemplateSyntaxError)
from django.utils.importlib import import_module
def get_loaders():
from django.template.loader import template_source_loaders
if template_source_loaders is None:
try:
from django.template.loader import find_template as finder
except ImportError:
from django.template.loader import find_template_source as finder # noqa
try:
source, name = finder('test')
except TemplateDoesNotExist:
pass
from django.template.loader import template_source_loaders
return template_source_loaders or []
def get_template_source(name):
source = None
for loader in get_loaders():
if loader.__module__.startswith('dbtemplates.'):
# Don't give a damn about dbtemplates' own loader.
continue
module = import_module(loader.__module__)
load_template_source = getattr(module, 'load_template_source', None)
if load_template_source is None:
load_template_source = loader.load_template_source
try:
source, origin = load_template_source(name)
if source:
return source
except NotImplementedError:
pass
except TemplateDoesNotExist:
pass
if source is None and VERSION[:2] < (1, 2):
# Django supported template source extraction still :/
try:
from django.template.loader import find_template_source
template, origin = find_template_source(name, None)
if not hasattr(template, 'render'):
return template
except (ImportError, TemplateDoesNotExist):
pass
return None
def check_template_syntax(template):
try:
Template(template.content)
except TemplateSyntaxError, e:
return (False, e)
return (True, None)

View file

@ -62,7 +62,7 @@ Short installation howto
4. Set ``DBTEMPLATES_USE_REVERSION`` setting to ``True``
.. _django-reversion: https://github.com/etianen/django-reversion
.. _django-reversion's documentation: https://github.com/etianen/django-reversion/wiki/getting-started
.. _django-reversion's documentation: http://django-reversion.readthedocs.org/en/latest/
.. _commands:
@ -82,6 +82,12 @@ Management commands
Tries to add the two templates ``404.html`` and ``500.html`` that are used
by Django when a error occurs.
* ``check_template_syntax``
.. versionadded:: 1.2
Checks the saved templates whether they are valid Django templates.
.. _Django management commands: http://docs.djangoproject.com/en/dev/ref/django-admin/
.. _admin_actions:
@ -101,4 +107,10 @@ Admin actions
Repopulates the cache with selected templates by invalidating it first and
filling then after that.
* ``check_syntax``
.. versionadded:: 1.2
Checks the selected tempaltes for syntax errors.
.. _admin actions: http://docs.djangoproject.com/en/dev/ref/contrib/admin/actions/

View file

@ -1,13 +1,116 @@
Changelog
=========
1.0.1 (04-14-11)
----------------
v1.3.1 (2012-05-23)
-------------------
* Minor release to move away from nose again and use own
`django-discover-runner`_.
.. _`django-discover-runner`: http://pypi.python.org/pypi/django-discover-runner
v1.3 (2012-05-07)
-----------------
* Dropped support for Django < 1.3 **backwards incompatible**
* Dropped using versiontools in favor of home made solution.
* Added optional support for TinyMCE editor instead of the CodeMirror
editor (just enable ``DBTEMPLATES_USE_TINYMCE``).
* Fixed compatibility to Django 1.4's handling of the ``DATABASES``
setting. Should also respect database routers now.
* Fixed an issue of the cache key generation in combination with
memcache's inability to stomach spaces.
* Moved test runner to use nose_ and a hosted CI project at Travis_:
http://travis-ci.org/jezdez/django-dbtemplates
.. _nose: http://nose.rtfd.org/
.. _Travis: http://travis-ci.org
v1.2.1 (2011-09-07)
-------------------
* Fixed a wrong use of the non-lazy localization tools.
* Fixed bugs in the documentation.
* Make use of django-appconf and versiontools.
v1.2 (2011-08-15)
-----------------
* Refactored the template loader to be even more cache effective.
* Added ``check_template_syntax`` management command and admin action
to make sure the saved templates are valid Django templates.
v1.1.1 (2011-07-08)
-------------------
* Fixed bug in cache loading (again).
* Fixed bugs in the documentation.
.. note::
Since ``dbtemplates`` removed support for Django lower than 1.2 you
have to use the template loader class in the ``TEMPLATE_LOADERS``
(``'dbtemplates.loader.Loader'``) and **not** the previosly included
function that ended with ``load_template_source``.
v1.1 (2011-07-06)
-----------------
* **BACKWARDS-INCOMPATIBLE** Requires Django 1.2 or higher.
For previous Django versions use an older versions of ``dbtemplates``,
e.g.::
$ pip install "django-dbtemplates<1.1"
* Added South migrations.
.. note::
If you are using South in your Django project, you can easily enable
dbtemplates' migrations, *faking* the first migration by using the
``--fake`` option of South's ``migrate`` management command::
$ manage.py migrate --fake 0001 dbtemplates
Then run the rest of the migrations::
$ manage.py migrate dbtemplates
* Removed uniqueness on the ``name`` field of the ``Template`` model. This is
needed because there isn't a ``unique_together`` for M2M fields in Django
such as the ``sites`` field in the ``Template`` model.
* Made the ``sites`` field optional to support a way to apply a template to
all sites.
* Added ``--delete`` option to ``sync_templates`` managment command to delete
the file or database entry after syncing (depending on used ``--overwrite``
mode).
* Updated translations.
* Fixed issue with incorrectly splitting paths in ``sync_templates``.
* Extended tests.
* Fixed issue with cache settings handling.
v1.0.1 (2011-04-14)
-------------------
* Minor bugfixes with regard to the new cache handling.
1.0 (04-11-11)
--------------
v1.0 (2011-04-11)
-----------------
.. warning::
This is the first stable release of django-dbtemplates which comes with a
@ -30,33 +133,33 @@ Changelog
* Use ReadTheDocs for documentation hosting.
0.8.0 (11-07-10)
----------------
v0.8.0 (2010-11-07)
-------------------
* Added Finnish translation (by jholster)
* Added --overwrite and --app-first options to sync_templates command (by Alex Kamedov).
0.7.4 (09-23-10)
----------------
v0.7.4 (2010-09-23)
-------------------
* Fixed tests.
0.7.3 (09-21-10)
----------------
v0.7.3 (2010-09-21)
-------------------
* Added ``DBTEMPLATES_AUTO_POPULATE_CONTENT`` setting to be able to disable
to auto-populating of template content.
* Fixed cosmetic issue in admin with collapsable fields.
0.7.2 (09-04-10)
----------------
v0.7.2 (2010-09-04)
-------------------
* Moved to Github again. Sigh.
0.7.1 (07-07-10)
----------------
v0.7.1 (2010-07-07)
-------------------
* Fixed problem with the CodeMirror textarea, which wasn't completely
disabled before.
@ -68,8 +171,8 @@ Changelog
and have the CodeMirror textarea enabled, dbtemplates will look in a
subdirectory of your site's ``MEDIA_ROOT`` for the CodeMirror media files.
0.7.0 (06-24-10)
----------------
v0.7.0 (2010-06-24)
-------------------
* Added CodeMirror_-based syntax highlighting textarea, based on the amaxing
work_ by `Nic Pottier`_. Set the ``DBTEMPLATES_USE_CODEMIRROR`` setting
@ -90,14 +193,14 @@ Changelog
.. _work: https://gist.github.com/368758/86bcafe53c438e2e2a0e3442c3b30f2c6011fbba
.. _`Nic Pottier`: http://github.com/nicpottier
0.6.1 (10-19-09):
-----------------
v0.6.1 (2009-10-19)
-------------------
* Fixed issue with default site of a template, added ability to disable
default site (``DBTEMPLATES_ADD_DEFAULT_SITE``).
0.6.0 (10-09-09):
-----------------
v0.6.0 (2009-10-09)
-------------------
* Updated and added locales (Danish, Brazilian Portuguese)
@ -107,8 +210,8 @@ Changelog
* Added Sphinx documentation
0.5.7
-----
v0.5.7
------
* Updates to the docs
@ -122,8 +225,8 @@ Changelog
* fixed bug in ``create_error_template`` command.
0.5.4
-----
v0.5.4
------
* Made loader and cache backends site-aware.
@ -135,16 +238,16 @@ Changelog
* Template is now saved explicitly to backend if not existent in cache
(e.g. if deleted manually or invalidated).
0.5.3
-----
v0.5.3
------
* Removed automatic creation of 404.html and 500.html templates and added a
* Removed automatic creation of 404.html and 50v0.html templates and added a
new management command for those cases called ``create_error_templates``
* Also reverted move to Bitbucket
0.5.2
-----
v0.5.2
------
* Fixed a problem with ``django.contrib.sites`` when its table hasn't been
populated yet on initialization of dbtemplates. Thanks for the report,
@ -152,8 +255,8 @@ Changelog
* Added an example Django project and docs for it
0.5.1
-----
v0.5.1
------
* Removed unneeded code that registered the model with reversion.
@ -164,8 +267,8 @@ Changelog
* Removed legacy ``sync_templates.py`` script, use ``django-admin.py
sync_templates`` from now on.
0.5.0
-----
v0.5.0
------
* Added support for `django-reversion`_
@ -182,60 +285,60 @@ Changelog
.. _django-reversion: http://code.google.com/p/django-reversion/
.. _blog post: http://jannisleidel.com/2008/11/updates-to-django-dbtemplates-and-half-assed-promise/
0.4.7
-----
v0.4.7
------
* Minor bugfix
0.4.6
-----
v0.4.6
------
* Minor doc change and PyPI support
0.4.5
-----
v0.4.5
------
* fixed the --force option of the sync_templates command
0.4.4
-----
v0.4.4
------
* fixed error in custom model save() after changes in Django `r8670`_.
.. _r8670: http://code.djangoproject.com/changeset/8670
0.4.3
-----
v0.4.3
------
* removed oldforms code
0.4.2
-----
v0.4.2
------
* added Hebrew translation (by mkriheli)
0.4.1
-----
v0.4.1
------
* added French (by Roland Frederic) and German locale
0.4.0
-----
v0.4.0
------
* adds better support for newforms-admin
* don't forget to load the dbtemplates.admin, e.g. by using
django.contrib.admin.autodiscover() in you urls.py
0.3.1
-----
v0.3.1
------
* adds a new management command *sync_templates* for bidirectional syncing
between filesystem and database (backwards-compatible) and
FilesystemCaching (thanks, Arne Brodowski!)
0.2.5
-----
v0.2.5
------
* adds support for newforms-admin

View file

@ -16,7 +16,7 @@ import sys, os
# If extensions (or modules to document with autodoc) are in another directory,
# add these directories to sys.path here. If the directory is relative to the
# documentation root, use os.path.abspath to make it absolute, like shown here.
#sys.path.append(os.path.abspath('.'))
sys.path.append(os.path.abspath('.'))
# -- General configuration -----------------------------------------------------
@ -38,16 +38,21 @@ master_doc = 'index'
# General information about the project.
project = u'django-dbtemplates'
copyright = u'2010, Jannis Leidel'
copyright = u'2007-2012, Jannis Leidel and contributors'
# The version info for the project you're documenting, acts as replacement for
# |version| and |release|, also used in various other places throughout the
# built documents.
#
# The short X.Y version.
version = '1.0'
# The full version, including alpha/beta/rc tags.
release = '1.0.1'
try:
from dbtemplates import __version__
# The short X.Y version.
version = '.'.join(__version__.split('.')[:2])
# The full version, including alpha/beta/rc tags.
release = __version__
except ImportError:
version = release = 'dev'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
@ -173,7 +178,7 @@ htmlhelp_basename = 'django-dbtemplatesdoc'
# (source start file, target name, title, author, documentclass [howto/manual]).
latex_documents = [
('index', 'django-dbtemplates.tex', u'django-dbtemplates Documentation',
u'Jannis Leidel', 'manual'),
u'Jannis Leidel and contributors', 'manual'),
]
# The name of an image file (relative to this directory) to place at the top of

View file

@ -11,6 +11,10 @@ It also features optional support for :ref:`versioned storage <versioned>`
and :ref:`django-admin command <commands>`, integrates with Django's
:ref:`caching system <caching>` and the :ref:`admin actions <admin_actions>`.
Please see http://django-dbtemplates.readthedocs.org/ for more details.
The source code and issue tracker can be found on Github: https://github.com/jezdez/django-dbtemplates
.. _template loader: http://docs.djangoproject.com/en/dev/ref/templates/api/#loading-templates
Contents:

View file

@ -2,7 +2,7 @@ Setup
=====
1. Get the source from the `Git repository`_ or install it from the
Python Package Index by running ``pip django-dbtemplates``.
Python Package Index by running ``pip install django-dbtemplates``.
2. Follow the instructions in the INSTALL file
3. Edit the settings.py of your Django site:
@ -30,11 +30,16 @@ Setup
It should look something like this::
TEMPLATE_LOADERS = (
'django.template.loaders.filesystem.load_template_source',
'django.template.loaders.app_directories.load_template_source',
'django.template.loaders.filesystem.Loader',
'django.template.loaders.app_directories.Loader',
'dbtemplates.loader.Loader',
)
Order of TEMPLATE_LOADERS is important. In the former example, templates from database
will be used as a fallback (ie. when template does not exists in other locations).
If you want template from database to be used to override templates in other locations,
put ``dbtemplates.loader.Loader`` at beginning of ``TEMPLATE_LOADERS`` settting.
4. Sync your database ``python manage.py syncdb``
5. Restart your Django server

View file

@ -4,8 +4,8 @@ Settings
``DBTEMPLATES_ADD_DEFAULT_SITE``
--------------------------------
``dbtemplates`` adds the current site (``settings.SITE_ID``) to the database
template when it is created by default. You can disable this feature by
``dbtemplates`` adds the current site (``settings.SITE_ID``) to the database
template when it is created by default. You can disable this feature by
setting ``DBTEMPLATES_ADD_DEFAULT_SITE`` to ``False``.
``DBTEMPLATES_AUTO_POPULATE_CONTENT``
@ -28,6 +28,14 @@ The dotted Python path to the cache backend class. See
A boolean, if enabled triggers the use of the CodeMirror based editor.
Set to ``False`` by default.
``DBTEMPLATES_USE_TINYMCE``
---------------------------
.. versionadded:: 1.3
A boolean, if enabled triggers the use of the TinyMCE based editor.
Set to ``False`` by default.
``DBTEMPLATES_USE_REVERSION``
-----------------------------

View file

@ -1 +1,2 @@
django-staticfiles
south
django>=1.3

View file

@ -70,10 +70,10 @@ SECRET_KEY = 'e-%(1e1f8ar2v)_8d!%-75a2ag(w(ht*l%n-wts5$li!5=97)8'
# List of callables that know how to import templates from various sources.
TEMPLATE_LOADERS = (
'django.template.loaders.filesystem.load_template_source',
'django.template.loaders.app_directories.load_template_source',
'django.template.loaders.eggs.load_template_source',
'dbtemplates.loader.load_template_source',
'django.template.loaders.filesystem.Loader',
'django.template.loaders.app_directories.Loader',
'django.template.loaders.eggs.Loader',
'dbtemplates.loader.Loader',
)
MIDDLEWARE_CLASSES = (
@ -98,8 +98,9 @@ INSTALLED_APPS = (
'django.contrib.sites',
'django.contrib.admin',
'django.contrib.flatpages',
'django.contrib.staticfiles',
'dbtemplates',
'staticfiles',
'south',
#'reversion',
)

View file

@ -16,9 +16,3 @@ urlpatterns = patterns('',
# Uncomment the next line to enable the admin:
(r'^admin/', include(admin.site.urls)),
)
# the following is used to serve up local media files like images
if settings.DEBUG:
urlpatterns += patterns("",
(r"", include("staticfiles.urls")),
)

3
requirements/tests.txt Normal file
View file

@ -0,0 +1,3 @@
flake8
django-discover-runner
coverage

View file

@ -1,32 +0,0 @@
#!/usr/bin/env python
import os
import sys
from django.conf import settings
if not settings.configured:
settings.configure(
DBTEMPLATES_CACHE_BACKEND = 'dummy://',
DATABASE_ENGINE='sqlite3',
SITE_ID=1,
INSTALLED_APPS=[
'django.contrib.contenttypes',
'django.contrib.sites',
'django.contrib.admin',
'dbtemplates',
],
)
from django.test.simple import run_tests
def runtests(*test_args):
if not test_args:
test_args = ['dbtemplates']
sys.path.insert(0, os.path.join(os.path.dirname(__file__), 'dbtemplates'))
failures = run_tests(test_args, verbosity=1, interactive=True)
sys.exit(failures)
if __name__ == '__main__':
runtests(*sys.argv[1:])

View file

@ -1,16 +1,33 @@
import os
import re
import codecs
from setuptools import setup, find_packages
def read(*parts):
return codecs.open(os.path.join(os.path.dirname(__file__), *parts)).read()
def find_version(*file_paths):
version_file = read(*file_paths)
version_match = re.search(r"^__version__ = ['\"]([^'\"]*)['\"]",
version_file, re.M)
if version_match:
return version_match.group(1)
raise RuntimeError("Unable to find version string.")
setup(
name='django-dbtemplates',
version=__import__('dbtemplates').__version__,
version=find_version('dbtemplates', '__init__.py'),
description='Template loader for templates stored in the database',
long_description=open('README.rst').read(),
long_description=read('README.rst'),
author='Jannis Leidel',
author_email='jannis@leidel.info',
url='http://django-dbtemplates.readthedocs.org/',
packages=find_packages(exclude=['example']),
zip_safe=False,
package_data = {
package_data={
'dbtemplates': [
'locale/*/LC_MESSAGES/*',
'static/dbtemplates/css/*.css',
@ -18,12 +35,17 @@ setup(
],
},
classifiers=[
'Development Status :: 4 - Beta',
'Development Status :: 5 - Production/Stable',
'Environment :: Web Environment',
'Intended Audience :: Developers',
'License :: OSI Approved :: BSD License',
'Operating System :: OS Independent',
'Programming Language :: Python',
'Programming Language :: Python :: 2',
'Programming Language :: Python :: 2.5',
'Programming Language :: Python :: 2.6',
'Programming Language :: Python :: 2.7',
'Framework :: Django',
],
install_requires=['django-appconf >= 0.4'],
)

58
tox.ini
View file

@ -1,58 +0,0 @@
[tox]
downloadcache = .tox/_download/
distribute = False
envlist =
py25-1.1.X, py26-1.1.X, py27-1.1.X,
py25-1.2.X, py26-1.2.X, py27-1.2.X,
py25-1.3.X, py26-1.3.X, py27-1.3.X
[testenv]
commands =
python runtests.py
[testenv:py25-1.1.X]
basepython = python2.5
deps =
django==1.1.4
[testenv:py26-1.1.X]
basepython = python2.6
deps =
django==1.1.4
[testenv:py27-1.1.X]
basepython = python2.7
deps =
django==1.1.4
[testenv:py25-1.2.X]
basepython = python2.5
deps =
django==1.2.5
[testenv:py26-1.2.X]
basepython = python2.6
deps =
django==1.2.5
[testenv:py27-1.2.X]
basepython = python2.7
deps =
django==1.2.5
[testenv:py25-1.3.X]
basepython = python2.5
deps =
django==1.3
[testenv:py26-1.3.X]
basepython = python2.6
deps =
django==1.3
[testenv:py27-1.3.X]
basepython = python2.7
deps =
django==1.3