summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAymeric Augustin <aymeric.augustin@m4x.org>2014-11-10 21:40:26 +0100
committerAymeric Augustin <aymeric.augustin@m4x.org>2014-12-28 14:47:31 +0100
commit7eefdbf7ab9f5bafe5baae2b877d93efc90e3044 (patch)
tree4b9430487a775ad62415d983d56531cee7f5d0d1
parentbfa21ddf7649799a2254b50cb83eb5276cb7f129 (diff)
Cleaned up the django.template namespace.
Since this package is going to hold both the implementation of the Django Template Language and the infrastructure for Multiple Template Engines, it should be untied from the DTL as much as possible within our backwards-compatibility policy. Only public APIs (i.e. APIs mentioned in the documentation) were left.
-rw-r--r--django/contrib/admindocs/views.py21
-rw-r--r--django/template/__init__.py83
-rw-r--r--django/template/base.py51
-rw-r--r--django/templatetags/i18n.py5
-rw-r--r--django/utils/translation/trans_real.py4
-rw-r--r--docs/releases/1.8.txt10
-rw-r--r--tests/template_tests/test_nodelist.py3
-rw-r--r--tests/template_tests/test_parser.py4
-rw-r--r--tests/template_tests/test_unicode.py3
-rw-r--r--tests/template_tests/tests.py5
-rw-r--r--tests/template_tests/utils.py10
11 files changed, 99 insertions, 100 deletions
diff --git a/django/contrib/admindocs/views.py b/django/contrib/admindocs/views.py
index bf706d0307..2c77a24f63 100644
--- a/django/contrib/admindocs/views.py
+++ b/django/contrib/admindocs/views.py
@@ -3,7 +3,6 @@ import inspect
import os
import re
-from django import template
from django.apps import apps
from django.conf import settings
from django.contrib import admin
@@ -13,6 +12,8 @@ from django.core.exceptions import ViewDoesNotExist
from django.http import Http404
from django.core import urlresolvers
from django.contrib.admindocs import utils
+from django.template.base import (builtins, get_library,
+ get_templatetags_modules, InvalidTemplateLibrary, libraries)
from django.template.engine import Engine
from django.utils.decorators import method_decorator
from django.utils._os import upath
@@ -61,8 +62,8 @@ class TemplateTagIndexView(BaseAdminDocsView):
load_all_installed_template_libraries()
tags = []
- app_libs = list(six.iteritems(template.libraries))
- builtin_libs = [(None, lib) for lib in template.builtins]
+ app_libs = list(six.iteritems(libraries))
+ builtin_libs = [(None, lib) for lib in builtins]
for module_name, library in builtin_libs + app_libs:
for tag_name, tag_func in library.tags.items():
title, body, metadata = utils.parse_docstring(tag_func.__doc__)
@@ -72,7 +73,7 @@ class TemplateTagIndexView(BaseAdminDocsView):
body = utils.parse_rst(body, 'tag', _('tag:') + tag_name)
for key in metadata:
metadata[key] = utils.parse_rst(metadata[key], 'tag', _('tag:') + tag_name)
- if library in template.builtins:
+ if library in builtins:
tag_library = ''
else:
tag_library = module_name.split('.')[-1]
@@ -94,8 +95,8 @@ class TemplateFilterIndexView(BaseAdminDocsView):
load_all_installed_template_libraries()
filters = []
- app_libs = list(six.iteritems(template.libraries))
- builtin_libs = [(None, lib) for lib in template.builtins]
+ app_libs = list(six.iteritems(libraries))
+ builtin_libs = [(None, lib) for lib in builtins]
for module_name, library in builtin_libs + app_libs:
for filter_name, filter_func in library.filters.items():
title, body, metadata = utils.parse_docstring(filter_func.__doc__)
@@ -105,7 +106,7 @@ class TemplateFilterIndexView(BaseAdminDocsView):
body = utils.parse_rst(body, 'filter', _('filter:') + filter_name)
for key in metadata:
metadata[key] = utils.parse_rst(metadata[key], 'filter', _('filter:') + filter_name)
- if library in template.builtins:
+ if library in builtins:
tag_library = ''
else:
tag_library = module_name.split('.')[-1]
@@ -313,7 +314,7 @@ class TemplateDetailView(BaseAdminDocsView):
def load_all_installed_template_libraries():
# Load/register all template tag libraries from installed apps.
- for module_name in template.get_templatetags_modules():
+ for module_name in get_templatetags_modules():
mod = import_module(module_name)
if not hasattr(mod, '__file__'):
# e.g. packages installed as eggs
@@ -330,8 +331,8 @@ def load_all_installed_template_libraries():
else:
for library_name in libraries:
try:
- template.get_library(library_name)
- except template.InvalidTemplateLibrary:
+ get_library(library_name)
+ except InvalidTemplateLibrary:
pass
diff --git a/django/template/__init__.py b/django/template/__init__.py
index a43ff50f01..24a51ac20d 100644
--- a/django/template/__init__.py
+++ b/django/template/__init__.py
@@ -1,80 +1,17 @@
-"""
-This is the Django template system.
-
-How it works:
-
-The Lexer.tokenize() function converts a template string (i.e., a string containing
-markup with custom template tags) to tokens, which can be either plain text
-(TOKEN_TEXT), variables (TOKEN_VAR) or block statements (TOKEN_BLOCK).
-
-The Parser() class takes a list of tokens in its constructor, and its parse()
-method returns a compiled template -- which is, under the hood, a list of
-Node objects.
-
-Each Node is responsible for creating some sort of output -- e.g. simple text
-(TextNode), variable values in a given context (VariableNode), results of basic
-logic (IfNode), results of looping (ForNode), or anything else. The core Node
-types are TextNode, VariableNode, IfNode and ForNode, but plugin modules can
-define their own custom node types.
-
-Each Node has a render() method, which takes a Context and returns a string of
-the rendered node. For example, the render() method of a Variable Node returns
-the variable's value as a string. The render() method of a ForNode returns the
-rendered output of whatever was inside the loop, recursively.
-
-The Template class is a convenient wrapper that takes care of template
-compilation and rendering.
-
-Usage:
-
-The only thing you should ever use directly in this file is the Template class.
-Create a compiled template object with a template_string, then call render()
-with a context. In the compilation stage, the TemplateSyntaxError exception
-will be raised if the template doesn't have proper syntax.
-
-Sample code:
-
->>> from django import template
->>> s = u'<html>{% if test %}<h1>{{ varvalue }}</h1>{% endif %}</html>'
->>> t = template.Template(s)
-
-(t is now a compiled template, and its render() method can be called multiple
-times with multiple contexts)
-
->>> c = template.Context({'test':True, 'varvalue': 'Hello'})
->>> t.render(c)
-u'<html><h1>Hello</h1></html>'
->>> c = template.Context({'test':False, 'varvalue': 'Hello'})
->>> t.render(c)
-u'<html></html>'
-"""
-
-# Template lexing symbols
-from django.template.base import (ALLOWED_VARIABLE_CHARS, BLOCK_TAG_END, # NOQA
- BLOCK_TAG_START, COMMENT_TAG_END, COMMENT_TAG_START,
- FILTER_ARGUMENT_SEPARATOR, FILTER_SEPARATOR, SINGLE_BRACE_END,
- SINGLE_BRACE_START, TOKEN_BLOCK, TOKEN_COMMENT, TOKEN_TEXT, TOKEN_VAR,
- TRANSLATOR_COMMENT_MARK, UNKNOWN_SOURCE, VARIABLE_ATTRIBUTE_SEPARATOR,
- VARIABLE_TAG_END, VARIABLE_TAG_START, filter_re, tag_re)
-
-# Exceptions
-from django.template.base import (ContextPopException, InvalidTemplateLibrary, # NOQA
- TemplateDoesNotExist, TemplateEncodingError, TemplateSyntaxError,
- VariableDoesNotExist)
+# Public exceptions
+from .base import (TemplateDoesNotExist, TemplateSyntaxError, # NOQA
+ VariableDoesNotExist)
+from .context import ContextPopException # NOQA
# Template parts
-from django.template.base import (Context, FilterExpression, Lexer, Node, # NOQA
- NodeList, Parser, RequestContext, Origin, StringOrigin, Template,
- TextNode, Token, TokenParser, Variable, VariableNode, constant_string,
- filter_raw_string)
+from .base import (Context, Node, NodeList, RequestContext, # NOQA
+ StringOrigin, Template, Variable)
-# Compiling templates
-from django.template.base import (resolve_variable, # NOQA
- unescape_string_literal, generic_tag_compiler)
+# Deprecated in Django 1.8, will be removed in Django 2.0.
+from .base import resolve_variable # NOQA
# Library management
-from django.template.base import (Library, add_to_builtins, builtins, # NOQA
- get_library, get_templatetags_modules, get_text_list, import_library,
- libraries)
+from .base import Library # NOQA
+
__all__ = ('Template', 'Context', 'RequestContext')
diff --git a/django/template/base.py b/django/template/base.py
index 4ac20b13e1..2917d8323d 100644
--- a/django/template/base.py
+++ b/django/template/base.py
@@ -1,3 +1,54 @@
+"""
+This is the Django template system.
+
+How it works:
+
+The Lexer.tokenize() function converts a template string (i.e., a string containing
+markup with custom template tags) to tokens, which can be either plain text
+(TOKEN_TEXT), variables (TOKEN_VAR) or block statements (TOKEN_BLOCK).
+
+The Parser() class takes a list of tokens in its constructor, and its parse()
+method returns a compiled template -- which is, under the hood, a list of
+Node objects.
+
+Each Node is responsible for creating some sort of output -- e.g. simple text
+(TextNode), variable values in a given context (VariableNode), results of basic
+logic (IfNode), results of looping (ForNode), or anything else. The core Node
+types are TextNode, VariableNode, IfNode and ForNode, but plugin modules can
+define their own custom node types.
+
+Each Node has a render() method, which takes a Context and returns a string of
+the rendered node. For example, the render() method of a Variable Node returns
+the variable's value as a string. The render() method of a ForNode returns the
+rendered output of whatever was inside the loop, recursively.
+
+The Template class is a convenient wrapper that takes care of template
+compilation and rendering.
+
+Usage:
+
+The only thing you should ever use directly in this file is the Template class.
+Create a compiled template object with a template_string, then call render()
+with a context. In the compilation stage, the TemplateSyntaxError exception
+will be raised if the template doesn't have proper syntax.
+
+Sample code:
+
+>>> from django import template
+>>> s = u'<html>{% if test %}<h1>{{ varvalue }}</h1>{% endif %}</html>'
+>>> t = template.Template(s)
+
+(t is now a compiled template, and its render() method can be called multiple
+times with multiple contexts)
+
+>>> c = template.Context({'test':True, 'varvalue': 'Hello'})
+>>> t.render(c)
+u'<html><h1>Hello</h1></html>'
+>>> c = template.Context({'test':False, 'varvalue': 'Hello'})
+>>> t.render(c)
+u'<html></html>'
+"""
+
from __future__ import unicode_literals
import re
diff --git a/django/templatetags/i18n.py b/django/templatetags/i18n.py
index 0bfb4a9eff..ecaf84a035 100644
--- a/django/templatetags/i18n.py
+++ b/django/templatetags/i18n.py
@@ -3,9 +3,8 @@ import re
import sys
from django.conf import settings
-from django.template import (Node, Variable, TemplateSyntaxError,
- TokenParser, Library, TOKEN_TEXT, TOKEN_VAR)
-from django.template.base import render_value_in_context
+from django.template import Library, Node, TemplateSyntaxError, Variable
+from django.template.base import render_value_in_context, TokenParser, TOKEN_TEXT, TOKEN_VAR
from django.template.defaulttags import token_kwargs
from django.utils import six
from django.utils import translation
diff --git a/django/utils/translation/trans_real.py b/django/utils/translation/trans_real.py
index 2af2f1dd35..1d4d100206 100644
--- a/django/utils/translation/trans_real.py
+++ b/django/utils/translation/trans_real.py
@@ -544,8 +544,8 @@ def templatize(src, origin=None):
does so by translating the Django translation tags into standard gettext
function invocations.
"""
- from django.template import (Lexer, TOKEN_TEXT, TOKEN_VAR, TOKEN_BLOCK,
- TOKEN_COMMENT, TRANSLATOR_COMMENT_MARK)
+ from django.template.base import (Lexer, TOKEN_TEXT, TOKEN_VAR,
+ TOKEN_BLOCK, TOKEN_COMMENT, TRANSLATOR_COMMENT_MARK)
src = force_text(src, settings.FILE_CHARSET)
out = StringIO('')
message_context = None
diff --git a/docs/releases/1.8.txt b/docs/releases/1.8.txt
index 6a164821b6..a4bc14332c 100644
--- a/docs/releases/1.8.txt
+++ b/docs/releases/1.8.txt
@@ -832,6 +832,14 @@ Django previously closed database connections between each test within a
``TestCase`` within a transaction. If some of your tests relied on the old
behavior, you should have them inherit from ``TransactionTestCase`` instead.
+Cleanup of the ``django.template`` namespace
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+If you've been relying on private APIs exposed in the ``django.template``
+module, you may have to import them from ``django.template.base`` instead.
+
+Also ``django.template.base.compile_string()`` was removed.
+
Miscellaneous
~~~~~~~~~~~~~
@@ -906,8 +914,6 @@ Miscellaneous
delete a key if ``set()`` fails. This is necessary to ensure the ``cache_db``
session store always fetches the most current session data.
-* Private API ``django.template.compile_string`` was removed.
-
* Private APIs ``override_template_loaders`` and ``override_with_test_loader``
in ``django.test.utils`` were removed. Override ``TEMPLATE_LOADERS`` with
``override_settings`` instead.
diff --git a/tests/template_tests/test_nodelist.py b/tests/template_tests/test_nodelist.py
index bce75aeecb..836d1b6db9 100644
--- a/tests/template_tests/test_nodelist.py
+++ b/tests/template_tests/test_nodelist.py
@@ -1,6 +1,7 @@
from unittest import TestCase
-from django.template import Context, Template, VariableNode
+from django.template import Context, Template
+from django.template.base import VariableNode
from django.test import override_settings
diff --git a/tests/template_tests/test_parser.py b/tests/template_tests/test_parser.py
index 017e78a863..348428513b 100644
--- a/tests/template_tests/test_parser.py
+++ b/tests/template_tests/test_parser.py
@@ -5,8 +5,8 @@ from __future__ import unicode_literals
from unittest import TestCase
-from django.template import (TokenParser, FilterExpression, Parser, Variable,
- Template, TemplateSyntaxError, Library)
+from django.template import Library, Template, TemplateSyntaxError
+from django.template.base import FilterExpression, Parser, TokenParser, Variable
from django.test import override_settings
from django.utils import six
diff --git a/tests/template_tests/test_unicode.py b/tests/template_tests/test_unicode.py
index 1f333bfed2..02d3d0a51d 100644
--- a/tests/template_tests/test_unicode.py
+++ b/tests/template_tests/test_unicode.py
@@ -3,7 +3,8 @@ from __future__ import unicode_literals
from unittest import TestCase
-from django.template import Template, TemplateEncodingError, Context
+from django.template import Template, Context
+from django.template.base import TemplateEncodingError
from django.utils.safestring import SafeData
from django.utils import six
diff --git a/tests/template_tests/tests.py b/tests/template_tests/tests.py
index 2ba1cdb18a..80f926ea6f 100644
--- a/tests/template_tests/tests.py
+++ b/tests/template_tests/tests.py
@@ -8,7 +8,8 @@ import unittest
from django import template
from django.contrib.auth.models import Group
from django.core import urlresolvers
-from django.template import loader, Context, RequestContext, Template, TemplateSyntaxError
+from django.template import (base as template_base, loader,
+ Context, RequestContext, Template, TemplateSyntaxError)
from django.template.engine import Engine
from django.template.loaders import app_directories, filesystem
from django.test import RequestFactory, SimpleTestCase
@@ -245,7 +246,7 @@ class TemplateRegressionTests(SimpleTestCase):
def test_token_smart_split(self):
# Regression test for #7027
- token = template.Token(template.TOKEN_BLOCK, 'sometag _("Page not found") value|yesno:_("yes,no")')
+ token = template_base.Token(template_base.TOKEN_BLOCK, 'sometag _("Page not found") value|yesno:_("yes,no")')
split = token.split_contents()
self.assertEqual(split, ["sometag", '_("Page not found")', 'value|yesno:_("yes,no")'])
diff --git a/tests/template_tests/utils.py b/tests/template_tests/utils.py
index 168eca73f8..ba8dcdd46f 100644
--- a/tests/template_tests/utils.py
+++ b/tests/template_tests/utils.py
@@ -6,7 +6,7 @@ import functools
from django import template
from django.template import Library
-from django.template.base import Context
+from django.template.base import Context, libraries
from django.template.engine import Engine
from django.template.loader import get_template
from django.test.utils import override_settings
@@ -100,9 +100,11 @@ def upper(value):
def register_test_tags(func):
@functools.wraps(func)
def inner(self):
- template.libraries['testtags'] = register
- func(self)
- del template.libraries['testtags']
+ libraries['testtags'] = register
+ try:
+ func(self)
+ finally:
+ del libraries['testtags']
return inner