* Parameters with non-integer keys can no longer be created with showkey=False, nor have the value of this attribute be set to False later. * Calling Template.remove() with a Parameter object that is not part of the template now raises ValueError instead of doing nothing. * Added tests for HTMLEntity._unichr() being called with out-of-range codepoints. * Added tests for Tag.__children__() and Tag.__showtree__() involving attributes that have no values.tags/v0.4
@@ -2,3 +2,7 @@ | |||
exclude_lines = | |||
pragma: no cover | |||
raise NotImplementedError() | |||
partial_branches = | |||
pragma: no branch | |||
if py3k: | |||
if not py3k: |
@@ -10,10 +10,15 @@ v0.4 (unreleased): | |||
option, RECURSE_OTHERS, which recurses over all children except instances of | |||
'forcetype' (for example, `code.filter_templates(code.RECURSE_OTHERS)` | |||
returns all un-nested templates). | |||
- Calling Template.remove() with a Parameter object that is not part of the | |||
template now raises ValueError instead of doing nothing. | |||
- Parameters with non-integer keys can no longer be created with | |||
'showkey=False', nor have the value of this attribute be set to False later. | |||
- If something goes wrong while parsing, ParserError will now be raised. | |||
Previously, the parser would produce an unclear BadRoute exception or allow | |||
an incorrect node tree to be build. | |||
- Fixed a parser bug involving nested tags. | |||
- Test coverage has been improved, and some minor related bugs have been fixed. | |||
- Updated and fixed some documentation. | |||
v0.3.3 (released April 22, 2014): | |||
@@ -18,10 +18,17 @@ Unreleased | |||
which recurses over all children except instances of *forcetype* (for | |||
example, ``code.filter_templates(code.RECURSE_OTHERS)`` returns all un-nested | |||
templates). | |||
- Calling :py:meth:`.Template.remove` with a :py:class:`.Parameter` object that | |||
is not part of the template now raises :py:exc:`ValueError` instead of doing | |||
nothing. | |||
- :py:class:`.Parameter`\ s with non-integer keys can no longer be created with | |||
*showkey=False*, nor have the value of this attribute be set to *False* | |||
later. | |||
- If something goes wrong while parsing, :py:exc:`.ParserError` will now be | |||
raised. Previously, the parser would produce an unclear :py:exc:`.BadRoute` | |||
exception or allow an incorrect node tree to be build. | |||
- Fixed a parser bug involving nested tags. | |||
- Test coverage has been improved, and some minor related bugs have been fixed. | |||
- Updated and fixed some documentation. | |||
v0.3.3 | |||
@@ -21,6 +21,7 @@ | |||
# SOFTWARE. | |||
from __future__ import unicode_literals | |||
import re | |||
from ...compat import str | |||
from ...string_mixin import StringMixIn | |||
@@ -39,6 +40,8 @@ class Parameter(StringMixIn): | |||
def __init__(self, name, value, showkey=True): | |||
super(Parameter, self).__init__() | |||
if not showkey and not self.can_hide_key(name): | |||
raise ValueError("key {0!r} cannot be hidden".format(name)) | |||
self._name = name | |||
self._value = value | |||
self._showkey = showkey | |||
@@ -48,6 +51,11 @@ class Parameter(StringMixIn): | |||
return str(self.name) + "=" + str(self.value) | |||
return str(self.value) | |||
@staticmethod | |||
def can_hide_key(key): | |||
"""Return whether or not the given key can be hidden.""" | |||
return re.match(r"[1-9][0-9]*$", str(key).strip()) | |||
@property | |||
def name(self): | |||
"""The name of the parameter as a :py:class:`~.Wikicode` object.""" | |||
@@ -73,4 +81,7 @@ class Parameter(StringMixIn): | |||
@showkey.setter | |||
def showkey(self, newval): | |||
self._showkey = bool(newval) | |||
newval = bool(newval) | |||
if not newval and not self.can_hide_key(self.name): | |||
raise ValueError("parameter key cannot be hidden") | |||
self._showkey = newval |
@@ -77,17 +77,17 @@ class HTMLEntity(Node): | |||
# Test whether we're on the wide or narrow Python build. Check | |||
# the length of a non-BMP code point | |||
# (U+1F64A, SPEAK-NO-EVIL MONKEY): | |||
if len("\U0001F64A") == 2: | |||
# Ensure this is within the range we can encode: | |||
if value > 0x10FFFF: | |||
raise ValueError("unichr() arg not in range(0x110000)") | |||
code = value - 0x10000 | |||
if value < 0: # Invalid code point | |||
raise | |||
lead = 0xD800 + (code >> 10) | |||
trail = 0xDC00 + (code % (1 << 10)) | |||
return unichr(lead) + unichr(trail) | |||
raise | |||
if len("\U0001F64A") == 1: # pragma: no cover | |||
raise | |||
# Ensure this is within the range we can encode: | |||
if value > 0x10FFFF: | |||
raise ValueError("unichr() arg not in range(0x110000)") | |||
code = value - 0x10000 | |||
if value < 0: # Invalid code point | |||
raise | |||
lead = 0xD800 + (code >> 10) | |||
trail = 0xDC00 + (code % (1 << 10)) | |||
return unichr(lead) + unichr(trail) | |||
@property | |||
def value(self): | |||
@@ -155,6 +155,7 @@ class Template(Node): | |||
else: | |||
self.params.pop(i) | |||
return | |||
raise ValueError(needle) | |||
@property | |||
def name(self): | |||
@@ -254,21 +255,19 @@ class Template(Node): | |||
return existing | |||
if showkey is None: | |||
try: | |||
if Parameter.can_hide_key(name): | |||
int_name = int(str(name)) | |||
except ValueError: | |||
showkey = True | |||
else: | |||
int_keys = set() | |||
for param in self.params: | |||
if not param.showkey: | |||
if re.match(r"[1-9][0-9]*$", param.name.strip()): | |||
int_keys.add(int(str(param.name))) | |||
int_keys.add(int(str(param.name))) | |||
expected = min(set(range(1, len(int_keys) + 2)) - int_keys) | |||
if expected == int_name: | |||
showkey = False | |||
else: | |||
showkey = True | |||
else: | |||
showkey = True | |||
if not showkey: | |||
self._surface_escape(value, "=") | |||
@@ -27,6 +27,7 @@ try: | |||
except ImportError: | |||
import unittest | |||
from mwparserfromhell.compat import py3k | |||
from mwparserfromhell.nodes import (Argument, Comment, ExternalLink, Heading, | |||
HTMLEntity, Tag, Template, Text, Wikilink) | |||
from mwparserfromhell.nodes.extras import Attribute, Parameter | |||
@@ -422,9 +423,9 @@ class TestBuilder(TreeEqualityTestCase): | |||
def test_parser_error(self): | |||
"""test whether ParserError gets thrown for bad input""" | |||
func = self.assertRaisesRegex if py3k else self.assertRaisesRegexp | |||
msg = r"_handle_token\(\) got unexpected TemplateClose" | |||
self.assertRaisesRegexp( | |||
ParserError, msg, self.builder.build, [tokens.TemplateClose()]) | |||
func(ParserError, msg, self.builder.build, [tokens.TemplateClose()]) | |||
if __name__ == "__main__": | |||
unittest.main(verbosity=2) |
@@ -108,6 +108,7 @@ class TestHTMLEntity(TreeEqualityTestCase): | |||
self.assertRaises(ValueError, setattr, node3, "value", -1) | |||
self.assertRaises(ValueError, setattr, node1, "value", 110000) | |||
self.assertRaises(ValueError, setattr, node1, "value", "1114112") | |||
self.assertRaises(ValueError, setattr, node1, "value", "12FFFF") | |||
def test_named(self): | |||
"""test getter/setter for the named attribute""" | |||
@@ -163,10 +164,14 @@ class TestHTMLEntity(TreeEqualityTestCase): | |||
node2 = HTMLEntity("107") | |||
node3 = HTMLEntity("e9") | |||
node4 = HTMLEntity("1f648") | |||
node5 = HTMLEntity("-2") | |||
node6 = HTMLEntity("110000", named=False, hexadecimal=True) | |||
self.assertEqual("\xa0", node1.normalize()) | |||
self.assertEqual("k", node2.normalize()) | |||
self.assertEqual("é", node3.normalize()) | |||
self.assertEqual("\U0001F648", node4.normalize()) | |||
self.assertRaises(ValueError, node5.normalize) | |||
self.assertRaises(ValueError, node6.normalize) | |||
if __name__ == "__main__": | |||
unittest.main(verbosity=2) |
@@ -71,9 +71,10 @@ class TestParameter(TreeEqualityTestCase): | |||
self.assertFalse(node1.showkey) | |||
self.assertTrue(node2.showkey) | |||
node1.showkey = True | |||
node2.showkey = "" | |||
self.assertTrue(node1.showkey) | |||
self.assertFalse(node2.showkey) | |||
node1.showkey = "" | |||
self.assertFalse(node1.showkey) | |||
self.assertRaises(ValueError, setattr, node2, "showkey", False) | |||
if __name__ == "__main__": | |||
unittest.main(verbosity=2) |
@@ -33,6 +33,7 @@ from mwparserfromhell.nodes.extras import Attribute | |||
from ._test_tree_equality import TreeEqualityTestCase, wrap, wraptext | |||
agen = lambda name, value: Attribute(wraptext(name), wraptext(value)) | |||
agennv = lambda name: Attribute(wraptext(name)) | |||
agennq = lambda name, value: Attribute(wraptext(name), wraptext(value), False) | |||
agenp = lambda name, v, a, b, c: Attribute(wraptext(name), v, True, a, b, c) | |||
agenpnv = lambda name, a, b, c: Attribute(wraptext(name), None, True, a, b, c) | |||
@@ -74,10 +75,10 @@ class TestTag(TreeEqualityTestCase): | |||
node1 = Tag(wraptext("ref"), wraptext("foobar")) | |||
# '''bold text''' | |||
node2 = Tag(wraptext("b"), wraptext("bold text"), wiki_markup="'''") | |||
# <img id="foo" class="bar" /> | |||
# <img id="foo" class="bar" selected /> | |||
node3 = Tag(wraptext("img"), | |||
attrs=[Attribute(wraptext("id"), wraptext("foo")), | |||
Attribute(wraptext("class"), wraptext("bar"))], | |||
attrs=[agen("id", "foo"), agen("class", "bar"), | |||
agennv("selected")], | |||
self_closing=True, padding=" ") | |||
gen1 = node1.__children__() | |||
@@ -89,6 +90,7 @@ class TestTag(TreeEqualityTestCase): | |||
self.assertEqual(node3.attributes[0].value, next(gen3)) | |||
self.assertEqual(node3.attributes[1].name, next(gen3)) | |||
self.assertEqual(node3.attributes[1].value, next(gen3)) | |||
self.assertEqual(node3.attributes[2].name, next(gen3)) | |||
self.assertEqual(node1.contents, next(gen1)) | |||
self.assertEqual(node2.contents, next(gen2)) | |||
self.assertEqual(node1.closing_tag, next(gen1)) | |||
@@ -113,7 +115,8 @@ class TestTag(TreeEqualityTestCase): | |||
getter, marker = object(), object() | |||
get = lambda code: output.append((getter, code)) | |||
mark = lambda: output.append(marker) | |||
node1 = Tag(wraptext("ref"), wraptext("text"), [agen("name", "foo")]) | |||
node1 = Tag(wraptext("ref"), wraptext("text"), | |||
[agen("name", "foo"), agennv("selected")]) | |||
node2 = Tag(wraptext("br"), self_closing=True, padding=" ") | |||
node3 = Tag(wraptext("br"), self_closing=True, invalid=True, | |||
implicit=True, padding=" ") | |||
@@ -122,9 +125,10 @@ class TestTag(TreeEqualityTestCase): | |||
node3.__showtree__(output.append, get, mark) | |||
valid = [ | |||
"<", (getter, node1.tag), (getter, node1.attributes[0].name), | |||
" = ", marker, (getter, node1.attributes[0].value), ">", | |||
(getter, node1.contents), "</", (getter, node1.closing_tag), ">", | |||
"<", (getter, node2.tag), "/>", "</", (getter, node3.tag), ">"] | |||
" = ", marker, (getter, node1.attributes[0].value), | |||
(getter, node1.attributes[1].name), ">", (getter, node1.contents), | |||
"</", (getter, node1.closing_tag), ">", "<", (getter, node2.tag), | |||
"/>", "</", (getter, node3.tag), ">"] | |||
self.assertEqual(valid, output) | |||
def test_tag(self): | |||
@@ -130,6 +130,8 @@ class TestTemplate(TreeEqualityTestCase): | |||
self.assertTrue(node4.has("b", False)) | |||
self.assertTrue(node3.has("b", True)) | |||
self.assertFalse(node4.has("b", True)) | |||
self.assertFalse(node1.has_param("foobar", False)) | |||
self.assertTrue(node2.has_param(1, False)) | |||
def test_get(self): | |||
"""test Template.get()""" | |||
@@ -176,52 +178,41 @@ class TestTemplate(TreeEqualityTestCase): | |||
pgens("b ", " c\n"), pgens("\nd ", " e"), pgens("\nf ", "g ")]) | |||
node16 = Template(wraptext("a"), [ | |||
pgens("\nb ", " c"), pgens("\nd ", " e"), pgens("\nf ", " g")]) | |||
node17 = Template(wraptext("a"), [ | |||
pgens("\nb ", " c"), pgens("\nd ", " e"), pgens("\nf ", " g")]) | |||
node18 = Template(wraptext("a\n"), [ | |||
pgens("b ", "c\n"), pgens("d ", " e"), pgens("f ", "g\n"), | |||
pgens("h ", " i\n")]) | |||
node19 = Template(wraptext("a"), [ | |||
pgens("b ", " c\n"), pgens("\nd ", " e"), pgens("\nf ", "g ")]) | |||
node20 = Template(wraptext("a"), [ | |||
pgens("\nb ", " c"), pgens("\nd ", " e"), pgens("\nf ", " g")]) | |||
node21 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node22 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node23 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node24 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
node17 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node18 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node19 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node20 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
pgenh("3", "d"), pgenh("4", "e")]) | |||
node25 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
node21 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
pgens("4", "d"), pgens("5", "e")]) | |||
node26 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
node22 = Template(wraptext("a"), [pgenh("1", "b"), pgenh("2", "c"), | |||
pgens("4", "d"), pgens("5", "e")]) | |||
node23 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node24 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node25 = Template(wraptext("a"), [pgens("b", "c")]) | |||
node26 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node27 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node28 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node29 = Template(wraptext("a"), [pgens("b", "c")]) | |||
node30 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node31 = Template(wraptext("a"), [pgenh("1", "b")]) | |||
node32 = Template(wraptext("a"), [pgens("1", "b")]) | |||
node33 = Template(wraptext("a"), [ | |||
node28 = Template(wraptext("a"), [pgens("1", "b")]) | |||
node29 = Template(wraptext("a"), [ | |||
pgens("\nb ", " c"), pgens("\nd ", " e"), pgens("\nf ", " g")]) | |||
node34 = Template(wraptext("a\n"), [ | |||
node30 = Template(wraptext("a\n"), [ | |||
pgens("b ", "c\n"), pgens("d ", " e"), pgens("f ", "g\n"), | |||
pgens("h ", " i\n")]) | |||
node35 = Template(wraptext("a"), [ | |||
node31 = Template(wraptext("a"), [ | |||
pgens("b ", " c\n"), pgens("\nd ", " e"), pgens("\nf ", "g ")]) | |||
node36 = Template(wraptext("a"), [ | |||
node32 = Template(wraptext("a"), [ | |||
pgens("\nb ", " c "), pgens("\nd ", " e "), pgens("\nf ", " g ")]) | |||
node37 = Template(wraptext("a"), [pgens("b", "c"), pgens("d", "e"), | |||
pgens("b", "f"), pgens("b", "h"), | |||
pgens("i", "j")]) | |||
node37 = Template(wraptext("a"), [pgens("b", "c"), pgens("d", "e"), | |||
node33 = Template(wraptext("a"), [pgens("b", "c"), pgens("d", "e"), | |||
pgens("b", "f"), pgens("b", "h"), | |||
pgens("i", "j")]) | |||
node38 = Template(wraptext("a"), [pgens("1", "b"), pgens("x", "y"), | |||
node34 = Template(wraptext("a"), [pgens("1", "b"), pgens("x", "y"), | |||
pgens("1", "c"), pgens("2", "d")]) | |||
node39 = Template(wraptext("a"), [pgens("1", "b"), pgens("x", "y"), | |||
node35 = Template(wraptext("a"), [pgens("1", "b"), pgens("x", "y"), | |||
pgenh("1", "c"), pgenh("2", "d")]) | |||
node40 = Template(wraptext("a"), [pgens("b", "c"), pgens("d", "e"), | |||
node36 = Template(wraptext("a"), [pgens("b", "c"), pgens("d", "e"), | |||
pgens("f", "g")]) | |||
node41 = Template(wraptext("a"), [pgenh("1", "")]) | |||
node37 = Template(wraptext("a"), [pgenh("1", "")]) | |||
node38 = Template(wraptext("abc")) | |||
node1.add("e", "f", showkey=True) | |||
node2.add(2, "g", showkey=False) | |||
@@ -241,31 +232,29 @@ class TestTemplate(TreeEqualityTestCase): | |||
node14.add("j", "k", showkey=True) | |||
node15.add("h", "i", showkey=True) | |||
node16.add("h", "i", showkey=True, preserve_spacing=False) | |||
node17.add("h", "i", showkey=False) | |||
node18.add("j", "k", showkey=False) | |||
node19.add("h", "i", showkey=False) | |||
node20.add("h", "i", showkey=False, preserve_spacing=False) | |||
node21.add("2", "c") | |||
node22.add("3", "c") | |||
node23.add("c", "d") | |||
node24.add("5", "f") | |||
node25.add("3", "f") | |||
node26.add("6", "f") | |||
node27.add("c", "foo=bar") | |||
node28.add("2", "foo=bar") | |||
node29.add("b", "d") | |||
node30.add("1", "foo=bar") | |||
node31.add("1", "foo=bar", showkey=True) | |||
node32.add("1", "foo=bar", showkey=False) | |||
node33.add("d", "foo") | |||
node34.add("f", "foo") | |||
node35.add("f", "foo") | |||
node36.add("d", "foo", preserve_spacing=False) | |||
node37.add("b", "k") | |||
node38.add("1", "e") | |||
node39.add("1", "e") | |||
node40.add("d", "h", before="b") | |||
node41.add(1, "b") | |||
node17.add("2", "c") | |||
node18.add("3", "c") | |||
node19.add("c", "d") | |||
node20.add("5", "f") | |||
node21.add("3", "f") | |||
node22.add("6", "f") | |||
node23.add("c", "foo=bar") | |||
node24.add("2", "foo=bar") | |||
node25.add("b", "d") | |||
node26.add("1", "foo=bar") | |||
node27.add("1", "foo=bar", showkey=True) | |||
node28.add("1", "foo=bar", showkey=False) | |||
node29.add("d", "foo") | |||
node30.add("f", "foo") | |||
node31.add("f", "foo") | |||
node32.add("d", "foo", preserve_spacing=False) | |||
node33.add("b", "k") | |||
node34.add("1", "e") | |||
node35.add("1", "e") | |||
node36.add("d", "h", before="b") | |||
node37.add(1, "b") | |||
node38.add("1", "foo") | |||
self.assertRaises(ValueError, node38.add, "z", "bar", showkey=False) | |||
self.assertEqual("{{a|b=c|d|e=f}}", node1) | |||
self.assertEqual("{{a|b=c|d|g}}", node2) | |||
@@ -285,34 +274,31 @@ class TestTemplate(TreeEqualityTestCase): | |||
self.assertEqual("{{a\n|b =c\n|d = e|f =g\n|h = i\n|j =k\n}}", node14) | |||
self.assertEqual("{{a|b = c\n|\nd = e|\nf =g |h =i}}", node15) | |||
self.assertEqual("{{a|\nb = c|\nd = e|\nf = g|h=i}}", node16) | |||
self.assertEqual("{{a|\nb = c|\nd = e|\nf = g| i}}", node17) | |||
self.assertEqual("{{a\n|b =c\n|d = e|f =g\n|h = i\n|k\n}}", node18) | |||
self.assertEqual("{{a|b = c\n|\nd = e|\nf =g |i}}", node19) | |||
self.assertEqual("{{a|\nb = c|\nd = e|\nf = g|i}}", node20) | |||
self.assertEqual("{{a|b|c}}", node21) | |||
self.assertEqual("{{a|b|3=c}}", node22) | |||
self.assertEqual("{{a|b|c=d}}", node23) | |||
self.assertEqual("{{a|b|c|d|e|f}}", node24) | |||
self.assertEqual("{{a|b|c|4=d|5=e|f}}", node25) | |||
self.assertEqual("{{a|b|c|4=d|5=e|6=f}}", node26) | |||
self.assertEqual("{{a|b|c=foo=bar}}", node27) | |||
self.assertEqual("{{a|b|foo=bar}}", node28) | |||
self.assertIsInstance(node28.params[1].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|b=d}}", node29) | |||
self.assertEqual("{{a|foo=bar}}", node30) | |||
self.assertIsInstance(node30.params[0].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|1=foo=bar}}", node31) | |||
self.assertEqual("{{a|foo=bar}}", node32) | |||
self.assertIsInstance(node32.params[0].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|\nb = c|\nd = foo|\nf = g}}", node33) | |||
self.assertEqual("{{a\n|b =c\n|d = e|f =foo\n|h = i\n}}", node34) | |||
self.assertEqual("{{a|b = c\n|\nd = e|\nf =foo }}", node35) | |||
self.assertEqual("{{a|\nb = c |\nd =foo|\nf = g }}", node36) | |||
self.assertEqual("{{a|b=k|d=e|i=j}}", node37) | |||
self.assertEqual("{{a|1=e|x=y|2=d}}", node38) | |||
self.assertEqual("{{a|x=y|e|d}}", node39) | |||
self.assertEqual("{{a|b=c|d=h|f=g}}", node40) | |||
self.assertEqual("{{a|b}}", node41) | |||
self.assertEqual("{{a|b|c}}", node17) | |||
self.assertEqual("{{a|b|3=c}}", node18) | |||
self.assertEqual("{{a|b|c=d}}", node19) | |||
self.assertEqual("{{a|b|c|d|e|f}}", node20) | |||
self.assertEqual("{{a|b|c|4=d|5=e|f}}", node21) | |||
self.assertEqual("{{a|b|c|4=d|5=e|6=f}}", node22) | |||
self.assertEqual("{{a|b|c=foo=bar}}", node23) | |||
self.assertEqual("{{a|b|foo=bar}}", node24) | |||
self.assertIsInstance(node24.params[1].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|b=d}}", node25) | |||
self.assertEqual("{{a|foo=bar}}", node26) | |||
self.assertIsInstance(node26.params[0].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|1=foo=bar}}", node27) | |||
self.assertEqual("{{a|foo=bar}}", node28) | |||
self.assertIsInstance(node28.params[0].value.get(1), HTMLEntity) | |||
self.assertEqual("{{a|\nb = c|\nd = foo|\nf = g}}", node29) | |||
self.assertEqual("{{a\n|b =c\n|d = e|f =foo\n|h = i\n}}", node30) | |||
self.assertEqual("{{a|b = c\n|\nd = e|\nf =foo }}", node31) | |||
self.assertEqual("{{a|\nb = c |\nd =foo|\nf = g }}", node32) | |||
self.assertEqual("{{a|b=k|d=e|i=j}}", node33) | |||
self.assertEqual("{{a|1=e|x=y|2=d}}", node34) | |||
self.assertEqual("{{a|x=y|e|d}}", node35) | |||
self.assertEqual("{{a|b=c|d=h|f=g}}", node36) | |||
self.assertEqual("{{a|b}}", node37) | |||
self.assertEqual("{{abc|foo}}", node38) | |||
def test_remove(self): | |||
"""test Template.remove()""" | |||
@@ -373,6 +359,8 @@ class TestTemplate(TreeEqualityTestCase): | |||
node26 = Template(wraptext("foo"), [ | |||
pgens("a", "b"), pgens("c", "d"), pgens("e", "f"), pgens("a", "b"), | |||
pgens("a", "b")]) | |||
node27 = Template(wraptext("foo"), [pgenh("1", "bar")]) | |||
node28 = Template(wraptext("foo"), [pgenh("1", "bar")]) | |||
node2.remove("1") | |||
node2.remove("abc") | |||
@@ -430,6 +418,7 @@ class TestTemplate(TreeEqualityTestCase): | |||
self.assertEqual("{{foo|a=|c=d|e=f|a=b|a=b}}", node24) | |||
self.assertEqual("{{foo|a=b|c=d|e=f|a=b}}", node25) | |||
self.assertEqual("{{foo|a=b|c=d|e=f|a=|a=b}}", node26) | |||
self.assertRaises(ValueError, node27.remove, node28.get(1)) | |||
if __name__ == "__main__": | |||
unittest.main(verbosity=2) |