summaryrefslogtreecommitdiffstats
path: root/Lib/test
diff options
context:
space:
mode:
authorBarry Warsaw <barry@python.org>2004-09-10 03:08:08 (GMT)
committerBarry Warsaw <barry@python.org>2004-09-10 03:08:08 (GMT)
commit12827c1fa9e6c87248fa1e5e4341066e41ce4ffb (patch)
tree2c8f5a24b7b3ff3cd231ad0d5b09e4bde1594f72 /Lib/test
parent961c2882a920f137543585175db9957bf48223f3 (diff)
downloadcpython-12827c1fa9e6c87248fa1e5e4341066e41ce4ffb.zip
cpython-12827c1fa9e6c87248fa1e5e4341066e41ce4ffb.tar.gz
cpython-12827c1fa9e6c87248fa1e5e4341066e41ce4ffb.tar.bz2
Many updates to PEP 292 templates. Summary:
- Template no longer inherits from unicode. - SafeTemplate is removed. Now Templates have both a substitute() and a safe_substitute() method, so we don't need separate classes. No more __mod__() operator. - Adopt Tim Peter's idea for giving Template a metaclass, which makes the delimiter, the identifier pattern, or the entire pattern easy to override and document, while retaining efficiency of class-time compilation of the regexp. - More informative ValueError messages which will help a user narrow down the bogus delimiter to the line and column in the original string (helpful for long triple quoted strings).
Diffstat (limited to 'Lib/test')
-rw-r--r--Lib/test/test_pep292.py114
1 files changed, 82 insertions, 32 deletions
diff --git a/Lib/test/test_pep292.py b/Lib/test/test_pep292.py
index 7eff309..56eb417 100644
--- a/Lib/test/test_pep292.py
+++ b/Lib/test/test_pep292.py
@@ -3,70 +3,120 @@
# License: http://www.opensource.org/licenses/PythonSoftFoundation.php
import unittest
-from string import Template, SafeTemplate
+from string import Template
+
+
+class Bag:
+ pass
+
+class Mapping:
+ def __getitem__(self, name):
+ obj = self
+ for part in name.split('.'):
+ try:
+ obj = getattr(obj, part)
+ except AttributeError:
+ raise KeyError(name)
+ return obj
-class TestTemplate(unittest.TestCase):
+class TestTemplate(unittest.TestCase):
def test_regular_templates(self):
s = Template('$who likes to eat a bag of $what worth $$100')
- self.assertEqual(s % dict(who='tim', what='ham'),
+ self.assertEqual(s.substitute(dict(who='tim', what='ham')),
'tim likes to eat a bag of ham worth $100')
- self.assertRaises(KeyError, lambda s, d: s % d, s, dict(who='tim'))
+ self.assertRaises(KeyError, s.substitute, dict(who='tim'))
def test_regular_templates_with_braces(self):
s = Template('$who likes ${what} for ${meal}')
- self.assertEqual(s % dict(who='tim', what='ham', meal='dinner'),
- 'tim likes ham for dinner')
- self.assertRaises(KeyError, lambda s, d: s % d,
- s, dict(who='tim', what='ham'))
+ d = dict(who='tim', what='ham', meal='dinner')
+ self.assertEqual(s.substitute(d), 'tim likes ham for dinner')
+ self.assertRaises(KeyError, s.substitute,
+ dict(who='tim', what='ham'))
def test_escapes(self):
eq = self.assertEqual
s = Template('$who likes to eat a bag of $$what worth $$100')
- eq(s % dict(who='tim', what='ham'),
+ eq(s.substitute(dict(who='tim', what='ham')),
'tim likes to eat a bag of $what worth $100')
s = Template('$who likes $$')
- eq(s % dict(who='tim', what='ham'), 'tim likes $')
+ eq(s.substitute(dict(who='tim', what='ham')), 'tim likes $')
def test_percents(self):
+ eq = self.assertEqual
s = Template('%(foo)s $foo ${foo}')
- self.assertEqual(s % dict(foo='baz'), '%(foo)s baz baz')
- s = SafeTemplate('%(foo)s $foo ${foo}')
- self.assertEqual(s % dict(foo='baz'), '%(foo)s baz baz')
+ d = dict(foo='baz')
+ eq(s.substitute(d), '%(foo)s baz baz')
+ eq(s.safe_substitute(d), '%(foo)s baz baz')
def test_stringification(self):
+ eq = self.assertEqual
s = Template('tim has eaten $count bags of ham today')
- self.assertEqual(s % dict(count=7),
- 'tim has eaten 7 bags of ham today')
- s = SafeTemplate('tim has eaten $count bags of ham today')
- self.assertEqual(s % dict(count=7),
- 'tim has eaten 7 bags of ham today')
- s = SafeTemplate('tim has eaten ${count} bags of ham today')
- self.assertEqual(s % dict(count=7),
- 'tim has eaten 7 bags of ham today')
+ d = dict(count=7)
+ eq(s.substitute(d), 'tim has eaten 7 bags of ham today')
+ eq(s.safe_substitute(d), 'tim has eaten 7 bags of ham today')
+ s = Template('tim has eaten ${count} bags of ham today')
+ eq(s.substitute(d), 'tim has eaten 7 bags of ham today')
def test_SafeTemplate(self):
eq = self.assertEqual
- s = SafeTemplate('$who likes ${what} for ${meal}')
- eq(s % dict(who='tim'),
- 'tim likes ${what} for ${meal}')
- eq(s % dict(what='ham'),
- '$who likes ham for ${meal}')
- eq(s % dict(what='ham', meal='dinner'),
+ s = Template('$who likes ${what} for ${meal}')
+ eq(s.safe_substitute(dict(who='tim')), 'tim likes ${what} for ${meal}')
+ eq(s.safe_substitute(dict(what='ham')), '$who likes ham for ${meal}')
+ eq(s.safe_substitute(dict(what='ham', meal='dinner')),
'$who likes ham for dinner')
- eq(s % dict(who='tim', what='ham'),
+ eq(s.safe_substitute(dict(who='tim', what='ham')),
'tim likes ham for ${meal}')
- eq(s % dict(who='tim', what='ham', meal='dinner'),
+ eq(s.safe_substitute(dict(who='tim', what='ham', meal='dinner')),
'tim likes ham for dinner')
def test_invalid_placeholders(self):
raises = self.assertRaises
s = Template('$who likes $')
- raises(ValueError, lambda s, d: s % d, s, dict(who='tim'))
+ raises(ValueError, s.substitute, dict(who='tim'))
s = Template('$who likes ${what)')
- raises(ValueError, lambda s, d: s % d, s, dict(who='tim'))
+ raises(ValueError, s.substitute, dict(who='tim'))
s = Template('$who likes $100')
- raises(ValueError, lambda s, d: s % d, s, dict(who='tim'))
+ raises(ValueError, s.substitute, dict(who='tim'))
+
+ def test_delimiter_override(self):
+ class PieDelims(Template):
+ delimiter = '@'
+ s = PieDelims('@who likes to eat a bag of @{what} worth $100')
+ self.assertEqual(s.substitute(dict(who='tim', what='ham')),
+ 'tim likes to eat a bag of ham worth $100')
+
+ def test_idpattern_override(self):
+ class PathPattern(Template):
+ idpattern = r'[_a-z][._a-z0-9]*'
+ m = Mapping()
+ m.bag = Bag()
+ m.bag.foo = Bag()
+ m.bag.foo.who = 'tim'
+ m.bag.what = 'ham'
+ s = PathPattern('$bag.foo.who likes to eat a bag of $bag.what')
+ self.assertEqual(s.substitute(m), 'tim likes to eat a bag of ham')
+
+ def test_pattern_override(self):
+ class MyPattern(Template):
+ pattern = r"""
+ (?P<escaped>@{2}) |
+ @(?P<named>[_a-z][._a-z0-9]*) |
+ @{(?P<braced>[_a-z][._a-z0-9]*)} |
+ (?P<bogus>@)
+ """
+ m = Mapping()
+ m.bag = Bag()
+ m.bag.foo = Bag()
+ m.bag.foo.who = 'tim'
+ m.bag.what = 'ham'
+ s = MyPattern('@bag.foo.who likes to eat a bag of @bag.what')
+ self.assertEqual(s.substitute(m), 'tim likes to eat a bag of ham')
+
+ def test_unicode_values(self):
+ s = Template('$who likes $what')
+ d = dict(who=u't\xffm', what=u'f\xfe\fed')
+ self.assertEqual(s.substitute(d), u't\xffm likes f\xfe\x0ced')
def suite():