summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Wanstrath <chris@ozmm.org>2009-11-12 21:58:39 -0800
committerChris Wanstrath <chris@ozmm.org>2009-11-12 21:58:39 -0800
commitab31eadcde0bd2d096733055ee7148bd8f1cf1ce (patch)
treec66de21d550367e72f07e6bf914145fc3d33295f
parent76b3c5d13cd35a7a202930f071b7c80f4fac716d (diff)
downloadpystache-ab31eadcde0bd2d096733055ee7148bd8f1cf1ce.tar.gz
delimiter support
-rw-r--r--examples/delimiters.mustache6
-rw-r--r--examples/delimiters.py13
-rw-r--r--pystache/template.py40
-rw-r--r--tests/test_examples.py11
4 files changed, 64 insertions, 6 deletions
diff --git a/examples/delimiters.mustache b/examples/delimiters.mustache
new file mode 100644
index 0000000..92bea6d
--- /dev/null
+++ b/examples/delimiters.mustache
@@ -0,0 +1,6 @@
+{{=<% %>=}}
+* <% first %>
+<%=| |=%>
+* | second |
+|={{ }}=|
+* {{ third }}
diff --git a/examples/delimiters.py b/examples/delimiters.py
new file mode 100644
index 0000000..53f65f2
--- /dev/null
+++ b/examples/delimiters.py
@@ -0,0 +1,13 @@
+import pystache
+
+class Delimiters(pystache.View):
+ template_path = 'examples'
+
+ def first(self):
+ return "It worked the first time."
+
+ def second(self):
+ return "And it worked the second time."
+
+ def third(self):
+ return "Then, surprisingly, it worked the third time."
diff --git a/pystache/template.py b/pystache/template.py
index 6e6901c..27192d6 100644
--- a/pystache/template.py
+++ b/pystache/template.py
@@ -1,20 +1,32 @@
import re
import cgi
-SECTION_RE = re.compile(r"{{\#([^\}]*)}}\s*(.+?)\s*{{/\1}}", re.M | re.S)
-TAG_RE = re.compile(r"{{(#|=|!|<|>|\{)?(.+?)\1?}}+")
-
class Template(object):
+ # The regular expression used to find a #section
+ section_re = None
+
+ # The regular expression used to find a tag.
+ tag_re = None
+
+ # Opening tag delimiter
+ otag = '{{'
+
+ # Closing tag delimiter
+ ctag = '}}'
+
+ # Names of different tag modifiers, used to render them.
tag_types = {
None: 'tag',
'!': 'comment',
'{': 'unescaped',
- '>': 'partial'
+ '>': 'partial',
+ '=': 'delimiter'
}
def __init__(self, template, context=None):
self.template = template
self.context = context or {}
+ self.compile_regexps()
def render(self, template=None, context=None):
"""Turns a Mustache template into something wonderful."""
@@ -24,10 +36,20 @@ class Template(object):
template = self.render_sections(template, context)
return self.render_tags(template, context)
+ def compile_regexps(self):
+ """Compiles our section and tag regular expressions."""
+ tags = { 'otag': re.escape(self.otag), 'ctag': re.escape(self.ctag) }
+
+ section = r"%(otag)s\#([^\}]*)%(ctag)s\s*(.+?)\s*%(otag)s/\1%(ctag)s"
+ self.section_re = re.compile(section % tags, re.M|re.S)
+
+ tag = r"%(otag)s(#|=|!|>|\{)?\s*(.+?)\s*\1?%(ctag)s+"
+ self.tag_re = re.compile(tag % tags)
+
def render_sections(self, template, context):
"""Expands sections."""
while 1:
- match = SECTION_RE.search(template)
+ match = self.section_re.search(template)
if match is None:
break
@@ -50,7 +72,7 @@ class Template(object):
def render_tags(self, template, context):
"""Renders all the tags in a template for a context."""
while 1:
- match = TAG_RE.search(template)
+ match = self.tag_re.search(template)
if match is None:
break
@@ -84,3 +106,9 @@ class Template(object):
view.template_name = tag_name
return view.render()
+
+ def render_delimiter(self, tag_name=None, context=None):
+ """Changes the Mustache delimiter."""
+ self.otag, self.ctag = tag_name.split(' ')
+ self.compile_regexps()
+ return ''
diff --git a/tests/test_examples.py b/tests/test_examples.py
index fa9c4e5..81edc7c 100644
--- a/tests/test_examples.py
+++ b/tests/test_examples.py
@@ -6,6 +6,7 @@ from examples.double_section import DoubleSection
from examples.escaped import Escaped
from examples.unescaped import Unescaped
from examples.template_partial import TemplatePartial
+from examples.delimiters import Delimiters
class TestView(unittest.TestCase):
def test_comments(self):
@@ -35,3 +36,13 @@ Again, Welcome!""")
Again, Welcome!
""")
+
+
+ def test_delimiters(self):
+ self.assertEquals(Delimiters().render(), """
+* It worked the first time.
+
+* And it worked the second time.
+
+* Then, surprisingly, it worked the third time.
+""")