# -*- coding: utf-8 -*-
"""
Test cases related to XSLT processing
"""
import unittest, copy, sys, os.path
this_dir = os.path.dirname(__file__)
if this_dir not in sys.path:
sys.path.insert(0, this_dir) # needed for Py3
is_python3 = sys.version_info[0] >= 3
try:
unicode
except NameError: # Python 3
unicode = str
try:
basestring
except NameError: # Python 3
basestring = str
from common_imports import etree, BytesIO, HelperTestCase, fileInTestDir
from common_imports import doctest, _bytes, _str, make_doctest, skipif
class ETreeXSLTTestCase(HelperTestCase):
"""XSLT tests etree"""
def test_xslt(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals('''\
B
''',
str(res))
def test_xslt_elementtree_error(self):
self.assertRaises(ValueError, etree.XSLT, etree.ElementTree())
def test_xslt_input_none(self):
self.assertRaises(TypeError, etree.XSLT, None)
if False and etree.LIBXSLT_VERSION >= (1,1,15):
# earlier versions generate no error
if etree.LIBXSLT_VERSION > (1,1,17):
def test_xslt_invalid_stylesheet(self):
style = self.parse('''\
''')
self.assertRaises(
etree.XSLTParseError, etree.XSLT, style)
def test_xslt_copy(self):
tree = self.parse('BC')
style = self.parse('''\
''')
transform = etree.XSLT(style)
res = transform(tree)
self.assertEquals('''\
B
''',
str(res))
transform_copy = copy.deepcopy(transform)
res = transform_copy(tree)
self.assertEquals('''\
B
''',
str(res))
transform = etree.XSLT(style)
res = transform(tree)
self.assertEquals('''\
B
''',
str(res))
def test_xslt_utf8(self):
tree = self.parse(_bytes('\\uF8D2\\uF8D2'
).decode("unicode_escape"))
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
expected = _bytes('''\
\\uF8D2
''').decode("unicode_escape")
if is_python3:
self.assertEquals(expected,
str(bytes(res), 'UTF-8'))
else:
self.assertEquals(expected,
unicode(str(res), 'UTF-8'))
def test_xslt_encoding(self):
tree = self.parse(_bytes('\\uF8D2\\uF8D2'
).decode("unicode_escape"))
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
expected = _bytes('''\
\\uF8D2
''').decode("unicode_escape")
if is_python3:
self.assertEquals(expected,
str(bytes(res), 'UTF-16'))
else:
self.assertEquals(expected,
unicode(str(res), 'UTF-16'))
def test_xslt_encoding_override(self):
tree = self.parse(_bytes('\\uF8D2\\uF8D2'
).decode("unicode_escape"))
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
expected = _bytes("""\
\
\\uF8D2""").decode("unicode_escape")
f = BytesIO()
res.write(f, encoding='UTF-16')
if is_python3:
result = str(f.getvalue(), 'UTF-16').replace('\n', '')
else:
result = unicode(str(f.getvalue()), 'UTF-16').replace('\n', '')
self.assertEquals(expected, result)
def test_xslt_unicode(self):
tree = self.parse(_bytes('\\uF8D2\\uF8D2'
).decode("unicode_escape"))
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
expected = _bytes('''\
\\uF8D2
''').decode("unicode_escape")
self.assertEquals(expected,
unicode(res))
def test_exslt_str(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals('''\
*B**C*
''',
str(res))
if etree.LIBXSLT_VERSION >= (1,1,21):
def test_exslt_str_attribute_replace(self):
tree = self.parse('BC')
style = self.parse('''\
test
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals('''\
test
''',
str(res))
def test_exslt_math(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals('''\
BC
''',
str(res))
def test_xslt_input(self):
style = self.parse('''\
''')
st = etree.XSLT(style)
st = etree.XSLT(style.getroot())
def test_xslt_input_partial_doc(self):
style = self.parse('''\
''')
self.assertRaises(etree.XSLTParseError, etree.XSLT, style)
root_node = style.getroot()
self.assertRaises(etree.XSLTParseError, etree.XSLT, root_node)
st = etree.XSLT(root_node[0])
def test_xslt_broken(self):
tree = self.parse('')
style = self.parse('''\
''')
self.assertRaises(etree.XSLTParseError,
etree.XSLT, style)
def test_xslt_parameters(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar="'Bar'")
self.assertEquals('''\
Bar
''',
str(res))
def test_xslt_string_parameters(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar=etree.XSLT.strparam('''it's me, "Bar"'''))
self.assertEquals('''\
it's me, "Bar"
''',
str(res))
def test_xslt_parameter_invalid(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = self.assertRaises(etree.XSLTApplyError,
st, tree, bar="")
res = self.assertRaises(etree.XSLTApplyError,
st, tree, bar="....")
if etree.LIBXSLT_VERSION < (1,1,18):
# later versions produce no error
def test_xslt_parameter_missing(self):
# apply() without needed parameter will lead to XSLTApplyError
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
self.assertRaises(etree.XSLTApplyError,
st.apply, tree)
def test_xslt_multiple_parameters(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar="'Bar'", baz="'Baz'")
self.assertEquals('''\
BarBaz
''',
str(res))
def test_xslt_parameter_xpath(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar="/a/b/text()")
self.assertEquals('''\
B
''',
str(res))
def test_xslt_parameter_xpath_object(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar=etree.XPath("/a/b/text()"))
self.assertEquals('''\
B
''',
str(res))
def test_xslt_default_parameters(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree, bar="'Bar'")
self.assertEquals('''\
Bar
''',
str(res))
res = st(tree)
self.assertEquals('''\
Default
''',
str(res))
def test_xslt_html_output(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals('B',
str(res).strip())
def test_xslt_include(self):
tree = etree.parse(fileInTestDir('test1.xslt'))
st = etree.XSLT(tree)
def test_xslt_include_from_filelike(self):
f = open(fileInTestDir('test1.xslt'), 'rb')
tree = etree.parse(f)
f.close()
st = etree.XSLT(tree)
def test_xslt_multiple_transforms(self):
xml = ''
xslt = '''\
Some text
'''
source = self.parse(xml)
styledoc = self.parse(xslt)
style = etree.XSLT(styledoc)
result = style(source)
etree.tostring(result.getroot())
source = self.parse(xml)
styledoc = self.parse(xslt)
style = etree.XSLT(styledoc)
result = style(source)
etree.tostring(result.getroot())
def test_xslt_repeat_transform(self):
xml = ''
xslt = '''\
Some text
'''
source = self.parse(xml)
styledoc = self.parse(xslt)
transform = etree.XSLT(styledoc)
result = transform(source)
result = transform(source)
etree.tostring(result.getroot())
result = transform(source)
etree.tostring(result.getroot())
str(result)
result1 = transform(source)
result2 = transform(source)
self.assertEquals(str(result1), str(result2))
result = transform(source)
str(result)
def test_xslt_empty(self):
# could segfault if result contains "empty document"
xml = ''
xslt = '''
'''
source = self.parse(xml)
styledoc = self.parse(xslt)
style = etree.XSLT(styledoc)
result = style(source)
self.assertEqual('', str(result))
def test_xslt_message(self):
xml = ''
xslt = '''
TEST TEST TEST
'''
source = self.parse(xml)
styledoc = self.parse(xslt)
style = etree.XSLT(styledoc)
result = style(source)
self.assertEqual('', str(result))
self.assert_("TEST TEST TEST" in [entry.message
for entry in style.error_log])
def test_xslt_message_terminate(self):
xml = ''
xslt = '''
TEST TEST TEST
'''
source = self.parse(xml)
styledoc = self.parse(xslt)
style = etree.XSLT(styledoc)
self.assertRaises(etree.XSLTApplyError, style, source)
self.assert_("TEST TEST TEST" in [entry.message
for entry in style.error_log])
def test_xslt_shortcut(self):
tree = self.parse('BC')
style = self.parse('''\
''')
result = tree.xslt(style, bar="'Bar'", baz="'Baz'")
self.assertEquals(
_bytes('BarBaz'),
etree.tostring(result.getroot()))
def test_multiple_elementrees(self):
tree = self.parse('BC')
style = self.parse('''\
''')
self.assertEquals(self._rootstring(tree),
_bytes('BC'))
result = tree.xslt(style)
self.assertEquals(self._rootstring(tree),
_bytes('BC'))
self.assertEquals(self._rootstring(result),
_bytes('BC'))
b_tree = etree.ElementTree(tree.getroot()[0])
self.assertEquals(self._rootstring(b_tree),
_bytes('B'))
result = b_tree.xslt(style)
self.assertEquals(self._rootstring(tree),
_bytes('BC'))
self.assertEquals(self._rootstring(result),
_bytes('B'))
c_tree = etree.ElementTree(tree.getroot()[1])
self.assertEquals(self._rootstring(c_tree),
_bytes('C'))
result = c_tree.xslt(style)
self.assertEquals(self._rootstring(tree),
_bytes('BC'))
self.assertEquals(self._rootstring(result),
_bytes('C'))
def test_xslt_document_XML(self):
# make sure document('') works from parsed strings
xslt = etree.XSLT(etree.XML("""\
TEXT
"""))
result = xslt(etree.XML(''))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(root[0].tag,
'test')
self.assertEquals(root[0].text,
'TEXT')
self.assertEquals(root[0][0].tag,
'{http://www.w3.org/1999/XSL/Transform}copy-of')
def test_xslt_document_parse(self):
# make sure document('') works from loaded files
xslt = etree.XSLT(etree.parse(fileInTestDir("test-document.xslt")))
result = xslt(etree.XML(''))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(root[0].tag,
'{http://www.w3.org/1999/XSL/Transform}stylesheet')
def test_xslt_document_elementtree(self):
# make sure document('') works from loaded files
xslt = etree.XSLT(etree.ElementTree(file=fileInTestDir("test-document.xslt")))
result = xslt(etree.XML(''))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(root[0].tag,
'{http://www.w3.org/1999/XSL/Transform}stylesheet')
def test_xslt_document_error(self):
xslt = etree.XSLT(etree.XML("""\
TEXT
"""))
self.assertRaises(etree.XSLTApplyError, xslt, etree.XML(''))
def test_xslt_document_XML_resolver(self):
# make sure document('') works when custom resolvers are in use
assertEquals = self.assertEquals
called = {'count' : 0}
class TestResolver(etree.Resolver):
def resolve(self, url, id, context):
assertEquals(url, 'file://ANYTHING')
called['count'] += 1
return self.resolve_string('', context)
parser = etree.XMLParser()
parser.resolvers.add(TestResolver())
xslt = etree.XSLT(etree.XML(_bytes("""\
A
B
"""), parser))
self.assertEquals(called['count'], 0)
result = xslt(etree.XML(''))
self.assertEquals(called['count'], 1)
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(len(root), 4)
self.assertEquals(root[0].tag,
'CALLED')
self.assertEquals(root[1].tag,
'{local}entry')
self.assertEquals(root[1].text,
None)
self.assertEquals(root[1].get("value"),
'A')
self.assertEquals(root[2].tag,
'CALLED')
self.assertEquals(root[3].tag,
'{local}entry')
self.assertEquals(root[3].text,
None)
self.assertEquals(root[3].get("value"),
'B')
def test_xslt_resolver_url_building(self):
assertEquals = self.assertEquals
called = {'count' : 0}
expected_url = None
class TestResolver(etree.Resolver):
def resolve(self, url, id, context):
assertEquals(url, expected_url)
called['count'] += 1
return self.resolve_string('', context)
stylesheet_xml = _bytes("""\
""")
parser = etree.XMLParser()
parser.resolvers.add(TestResolver())
# test without base_url => relative path only
expected_url = 'test.xml'
xslt = etree.XSLT(etree.XML(stylesheet_xml, parser))
self.assertEquals(called['count'], 0)
result = xslt(etree.XML(''))
self.assertEquals(called['count'], 1)
# now the same thing with a stylesheet base URL on the filesystem
called['count'] = 0
expected_url = os.path.join('MY', 'BASE', 'test.xml')
xslt = etree.XSLT(etree.XML(stylesheet_xml, parser,
base_url=os.path.join('MY', 'BASE', 'FILE')))
self.assertEquals(called['count'], 0)
result = xslt(etree.XML(''))
self.assertEquals(called['count'], 1)
# now the same thing with a stylesheet base URL
called['count'] = 0
expected_url = 'http://server.com/BASE/DIR/test.xml'
xslt = etree.XSLT(etree.XML(stylesheet_xml, parser,
base_url='http://server.com/BASE/DIR/FILE'))
self.assertEquals(called['count'], 0)
result = xslt(etree.XML(''))
self.assertEquals(called['count'], 1)
def test_xslt_document_parse_allow(self):
access_control = etree.XSLTAccessControl(read_file=True)
xslt = etree.XSLT(etree.parse(fileInTestDir("test-document.xslt")),
access_control = access_control)
result = xslt(etree.XML(''))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(root[0].tag,
'{http://www.w3.org/1999/XSL/Transform}stylesheet')
def test_xslt_document_parse_deny(self):
access_control = etree.XSLTAccessControl(read_file=False)
xslt = etree.XSLT(etree.parse(fileInTestDir("test-document.xslt")),
access_control = access_control)
self.assertRaises(etree.XSLTApplyError, xslt, etree.XML(''))
def test_xslt_document_parse_deny_all(self):
access_control = etree.XSLTAccessControl.DENY_ALL
xslt = etree.XSLT(etree.parse(fileInTestDir("test-document.xslt")),
access_control = access_control)
self.assertRaises(etree.XSLTApplyError, xslt, etree.XML(''))
def test_xslt_move_result(self):
root = etree.XML(_bytes('''\
'''))
xslt = etree.XSLT(etree.XML(_bytes('''\
''')))
result = xslt(root[0])
root[:] = result.getroot()[:]
del root # segfaulted before
def test_xslt_pi(self):
tree = self.parse('''\
B
C
''' % fileInTestDir("test1.xslt"))
style_root = tree.getroot().getprevious().parseXSL().getroot()
self.assertEquals("{http://www.w3.org/1999/XSL/Transform}stylesheet",
style_root.tag)
def test_xslt_pi_embedded_xmlid(self):
# test xml:id dictionary lookup mechanism
tree = self.parse('''\
B
C
''')
style_root = tree.getroot().getprevious().parseXSL().getroot()
self.assertEquals("{http://www.w3.org/1999/XSL/Transform}stylesheet",
style_root.tag)
st = etree.XSLT(style_root)
res = st(tree)
self.assertEquals('''\
B
''',
str(res))
def test_xslt_pi_embedded_id(self):
# test XPath lookup mechanism
tree = self.parse('''\
B
C
''')
style = self.parse('''\
''')
tree.getroot().append(style.getroot())
style_root = tree.getroot().getprevious().parseXSL().getroot()
self.assertEquals("{http://www.w3.org/1999/XSL/Transform}stylesheet",
style_root.tag)
st = etree.XSLT(style_root)
res = st(tree)
self.assertEquals('''\
B
''',
str(res))
def test_xslt_pi_get(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals("TEST", pi.get("href"))
def test_xslt_pi_get_all(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals("TEST", pi.get("href"))
self.assertEquals("text/xsl", pi.get("type"))
self.assertEquals(None, pi.get("motz"))
def test_xslt_pi_get_all_reversed(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals("TEST", pi.get("href"))
self.assertEquals("text/xsl", pi.get("type"))
self.assertEquals(None, pi.get("motz"))
def test_xslt_pi_get_unknown(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals(None, pi.get("unknownattribute"))
def test_xslt_pi_set_replace(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals("TEST", pi.get("href"))
pi.set("href", "TEST123")
self.assertEquals("TEST123", pi.get("href"))
def test_xslt_pi_set_new(self):
tree = self.parse('''\
B
C
''')
pi = tree.getroot().getprevious()
self.assertEquals(None, pi.get("href"))
pi.set("href", "TEST")
self.assertEquals("TEST", pi.get("href"))
def test_exslt_regexp_test(self):
xslt = etree.XSLT(etree.XML(_bytes("""\
""")))
result = xslt(etree.XML(_bytes('123098987')))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(len(root), 1)
self.assertEquals(root[0].tag,
'b')
self.assertEquals(root[0].text,
'987')
def test_exslt_regexp_replace(self):
xslt = etree.XSLT(etree.XML("""\
-
"""))
result = xslt(etree.XML(_bytes('abdCdEeDed')))
root = result.getroot()
self.assertEquals(root.tag,
'test')
self.assertEquals(len(root), 0)
self.assertEquals(root.text, 'abXXdEeDed-abXXXXeXXd')
def test_exslt_regexp_match(self):
xslt = etree.XSLT(etree.XML("""\
"""))
result = xslt(etree.XML(_bytes('abdCdEeDed')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 3)
self.assertEquals(len(root[0]), 1)
self.assertEquals(root[0][0].tag, 'match')
self.assertEquals(root[0][0].text, 'dC')
self.assertEquals(len(root[1]), 2)
self.assertEquals(root[1][0].tag, 'match')
self.assertEquals(root[1][0].text, 'dC')
self.assertEquals(root[1][1].tag, 'match')
self.assertEquals(root[1][1].text, 'dE')
self.assertEquals(len(root[2]), 3)
self.assertEquals(root[2][0].tag, 'match')
self.assertEquals(root[2][0].text, 'dC')
self.assertEquals(root[2][1].tag, 'match')
self.assertEquals(root[2][1].text, 'dE')
self.assertEquals(root[2][2].tag, 'match')
self.assertEquals(root[2][2].text, 'De')
def test_exslt_regexp_match_groups(self):
xslt = etree.XSLT(etree.XML(_bytes("""\
""")))
result = xslt(etree.XML(_bytes('')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 4)
self.assertEquals(root[0].text, "123abc567")
self.assertEquals(root[1].text, "123")
self.assertEquals(root[2].text, "abc")
self.assertEquals(root[3].text, "567")
def test_exslt_regexp_match1(self):
# taken from http://www.exslt.org/regexp/functions/match/index.html
xslt = etree.XSLT(etree.XML(_bytes("""\
""")))
result = xslt(etree.XML(_bytes('')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 5)
self.assertEquals(
root[0].text,
"http://www.bayes.co.uk/xml/index.xml?/xml/utils/rechecker.xml")
self.assertEquals(
root[1].text,
"http")
self.assertEquals(
root[2].text,
"www.bayes.co.uk")
self.assertFalse(root[3].text)
self.assertEquals(
root[4].text,
"/xml/index.xml?/xml/utils/rechecker.xml")
def test_exslt_regexp_match2(self):
# taken from http://www.exslt.org/regexp/functions/match/index.html
xslt = etree.XSLT(self.parse("""\
"""))
result = xslt(etree.XML(_bytes('')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 5)
self.assertEquals(root[0].text, "This")
self.assertEquals(root[1].text, "is")
self.assertEquals(root[2].text, "a")
self.assertEquals(root[3].text, "test")
self.assertEquals(root[4].text, "string")
def _test_exslt_regexp_match3(self):
# taken from http://www.exslt.org/regexp/functions/match/index.html
# THIS IS NOT SUPPORTED!
xslt = etree.XSLT(etree.XML(_bytes("""\
""")))
result = xslt(etree.XML(_bytes('')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 4)
self.assertEquals(root[0].text, "his")
self.assertEquals(root[1].text, "is")
self.assertEquals(root[2].text, "a")
self.assertEquals(root[3].text, "test")
def _test_exslt_regexp_match4(self):
# taken from http://www.exslt.org/regexp/functions/match/index.html
# THIS IS NOT SUPPORTED!
xslt = etree.XSLT(etree.XML(_bytes("""\
""")))
result = xslt(etree.XML(_bytes('')))
root = result.getroot()
self.assertEquals(root.tag, 'test')
self.assertEquals(len(root), 4)
self.assertEquals(root[0].text, "This")
self.assertEquals(root[1].text, "is")
self.assertEquals(root[2].text, "a")
self.assertEquals(root[3].text, "test")
class ETreeXSLTExtFuncTestCase(HelperTestCase):
"""Tests for XPath extension functions in XSLT."""
def test_extensions1(self):
tree = self.parse('B')
style = self.parse('''\
''')
def mytext(ctxt, values):
return 'X' * len(values)
result = tree.xslt(style, {('testns', 'mytext') : mytext})
self.assertEquals(self._rootstring(result),
_bytes('X'))
def test_extensions2(self):
tree = self.parse('B')
style = self.parse('''\
''')
def mytext(ctxt, values):
return 'X' * len(values)
namespace = etree.FunctionNamespace('testns')
namespace['mytext'] = mytext
result = tree.xslt(style)
self.assertEquals(self._rootstring(result),
_bytes('X'))
def test_variable_result_tree_fragment(self):
tree = self.parse('B')
style = self.parse('''\
BBB
''')
def mytext(ctxt, values):
for value in values:
self.assert_(hasattr(value, 'tag'),
"%s is not an Element" % type(value))
self.assertEquals(value.tag, 'b')
self.assertEquals(value.text, 'BBB')
return 'X'.join([el.tag for el in values])
namespace = etree.FunctionNamespace('testns')
namespace['mytext'] = mytext
result = tree.xslt(style)
self.assertEquals(self._rootstring(result),
_bytes('bXb'))
class ETreeXSLTExtElementTestCase(HelperTestCase):
"""Tests for extension elements in XSLT."""
def test_extension_element(self):
tree = self.parse('B')
style = self.parse('''\
b
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
child = etree.Element(self_node.text)
child.text = 'X'
output_parent.append(child)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes('X'))
def test_extension_element_doc_context(self):
tree = self.parse('B')
style = self.parse('''\
b
''')
tags = []
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
tags.append(input_node.tag)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(tags, ['a'])
def test_extension_element_comment_pi_context(self):
tree = self.parse('')
style = self.parse('''\
b
b
''')
text = []
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
text.append(input_node.text)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(text, ['toast', 'a comment', 'pi'])
def _test_extension_element_attribute_context(self):
# currently not supported
tree = self.parse('')
style = self.parse('''\
b
b
''')
text = []
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, attr_value, output_parent):
text.append(attr_value)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(text, ['A', 'B'])
def test_extension_element_content(self):
tree = self.parse('B')
style = self.parse('''\
XY
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
output_parent.extend(list(self_node)[1:])
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes('Y'))
def test_extension_element_apply_templates(self):
tree = self.parse('B')
style = self.parse('''\
XY
XYZ
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
for child in self_node:
for result in self.apply_templates(context, child):
if isinstance(result, basestring):
el = etree.Element("T")
el.text = result
else:
el = result
output_parent.append(el)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes('YXYZ'))
def test_extension_element_apply_templates_target_node(self):
tree = self.parse('B')
style = self.parse('''\
XY
XYZ
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
for child in self_node:
self.apply_templates(context, child, output_parent)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes('YXYZ'))
def test_extension_element_apply_templates_target_node_doc(self):
tree = self.parse('B')
style = self.parse('''\
XY
TEST
XYZ
TEST
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
for child in self_node:
self.apply_templates(context, child, output_parent)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(etree.tostring(result),
_bytes('XYZ'))
def test_extension_element_process_children(self):
tree = self.parse('E')
style = self.parse('''\
yo
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
el = etree.Element('MY')
self.process_children(context, el)
output_parent.append(el)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes('E'))
def test_extension_element_process_children_to_append_only(self):
tree = self.parse('')
style = self.parse('''\
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
self.process_children(context, output_parent)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes(''))
def test_extension_element_process_children_to_read_only_raise(self):
tree = self.parse('')
style = self.parse('''\
''')
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
self.process_children(context, self_node)
extensions = { ('testns', 'myext') : MyExt() }
self.assertRaises(TypeError, tree.xslt, style, extensions=extensions)
def test_extension_element_process_children_with_subextension_element(self):
tree = self.parse('')
style = self.parse('''\
''')
class MyExt(etree.XSLTExtension):
callback_call_counter = 0
def execute(self, context, self_node, input_node, output_parent):
self.callback_call_counter += 1
el = etree.Element('MY', n=str(self.callback_call_counter))
self.process_children(context, el)
output_parent.append(el)
extensions = { ('testns', 'myext') : MyExt() }
result = tree.xslt(style, extensions=extensions)
self.assertEquals(self._rootstring(result),
_bytes(''))
def test_extension_element_raise(self):
tree = self.parse('B')
style = self.parse('''\
b
''')
class MyError(Exception):
pass
class MyExt(etree.XSLTExtension):
def execute(self, context, self_node, input_node, output_parent):
raise MyError("expected!")
extensions = { ('testns', 'myext') : MyExt() }
self.assertRaises(MyError, tree.xslt, style, extensions=extensions)
class Py3XSLTTestCase(HelperTestCase):
"""XSLT tests for etree under Python 3"""
pytestmark = skipif('sys.version_info < (3,0)')
def test_xslt_result_bytes(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals(_bytes('''\
B
'''),
bytes(res))
def test_xslt_result_bytearray(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals(_bytes('''\
B
'''),
bytearray(res))
def test_xslt_result_memoryview(self):
tree = self.parse('BC')
style = self.parse('''\
''')
st = etree.XSLT(style)
res = st(tree)
self.assertEquals(_bytes('''\
B
'''),
bytes(memoryview(res)))
def test_suite():
suite = unittest.TestSuite()
suite.addTests([unittest.makeSuite(ETreeXSLTTestCase)])
suite.addTests([unittest.makeSuite(ETreeXSLTExtFuncTestCase)])
suite.addTests([unittest.makeSuite(ETreeXSLTExtElementTestCase)])
if is_python3:
suite.addTests([unittest.makeSuite(Py3XSLTTestCase)])
suite.addTests(
[make_doctest('../../../doc/extensions.txt')])
suite.addTests(
[make_doctest('../../../doc/xpathxslt.txt')])
return suite
if __name__ == '__main__':
print('to test use test.py %s' % __file__)