1
2
3 """
4 Tests specific to the Python based class lookup.
5 """
6
7 from __future__ import absolute_import
8
9 import unittest
10
11 from .common_imports import etree, HelperTestCase, _bytes
12
13 from lxml.etree import PythonElementClassLookup
14
15
16 xml_str = _bytes('''\
17 <obj:root xmlns:obj="objectified" xmlns:other="otherNS">
18 <obj:c1 a1="A1" a2="A2" other:a3="A3">
19 <obj:c2>0</obj:c2>
20 <obj:c2>1</obj:c2>
21 <obj:c2>2</obj:c2>
22 <other:c2>3</other:c2>
23 <c2>3</c2>
24 </obj:c1>
25 </obj:root>''')
26
27
43 self.parser.set_element_class_lookup( Lookup() )
44
46 class LocalElement(etree.ElementBase):
47 pass
48 return LocalElement
49
52
53
54
56 el_class = self._buildElementClass()
57 el_class.i = 1
58 def lookup(*args):
59 if el_class.i == 1:
60 el_class.i = 2
61 return el_class
62 self._setClassLookup(lookup)
63 root = self.XML(xml_str)
64 self.assertEqual(2, el_class.i)
65
67 el_class = self._buildElementClass()
68 el_class.EL = None
69 def lookup(doc, el):
70 if el_class.EL is None:
71 el_class.EL = el
72 return el_class
73 self._setClassLookup(lookup)
74 root = self.XML(xml_str)
75 self.assertNotEqual(None, el_class.EL)
76 self.assertRaises(ReferenceError, el_class.EL.getchildren)
77
79 el_class = self._buildElementClass()
80 el_class.TAG = None
81 def lookup(doc, el):
82 if el_class.TAG is None:
83 el_class.TAG = el.tag
84 return el_class
85 self._setClassLookup(lookup)
86 root = self.XML(xml_str)
87 self.assertNotEqual(None, root.TAG)
88 self.assertEqual(root.tag, root.TAG)
89
91 el_class = self._buildElementClass()
92 el_class.TEXT = None
93 def lookup(doc, el):
94 if el_class.TEXT is None:
95 el_class.TEXT = el.text
96 return el_class
97 self._setClassLookup(lookup)
98 root = self.XML(xml_str)
99 self.assertNotEqual(None, root.TEXT)
100 self.assertEqual(root.text, root.TEXT)
101
103 el_class = self._buildElementClass()
104 el_class.TAIL = None
105 def lookup(doc, el):
106 if el_class.TAIL is None:
107 el_class.TAIL = el.tail
108 return el_class
109 self._setClassLookup(lookup)
110 root = self.XML(xml_str)
111 self.assertEqual(root.tail, root.TAIL)
112
114 el_class = self._buildElementClass()
115 el_class.ATTRIB = None
116 def lookup(doc, el):
117 if el_class.ATTRIB is None:
118 el_class.ATTRIB = el[0].attrib
119 return el_class
120 self._setClassLookup(lookup)
121 root = self.XML(xml_str)
122 items1 = list(root[0].attrib.items())
123 items1.sort()
124 items2 = list(root.ATTRIB.items())
125 items2.sort()
126 self.assertEqual(items1, items2)
127
129 el_class = self._buildElementClass()
130 el_class.PREFIX = None
131 def lookup(doc, el):
132 if el_class.PREFIX is None:
133 el_class.PREFIX = el.prefix
134 return el_class
135 self._setClassLookup(lookup)
136 root = self.XML(xml_str)
137 self.assertEqual(root.prefix, root.PREFIX)
138
140 el_class = self._buildElementClass()
141 el_class.LINE = None
142 def lookup(doc, el):
143 if el_class.LINE is None:
144 el_class.LINE = el.sourceline
145 return el_class
146 self._setClassLookup(lookup)
147 root = self.XML(xml_str)
148 self.assertEqual(root.sourceline, root.LINE)
149
151 el_class = self._buildElementClass()
152 el_class.CHILD_TAG = None
153 def lookup(doc, el):
154 el_class.CHILD_TAG = el[0].tag
155 return el_class
156 self._setClassLookup(lookup)
157 root = self.XML(xml_str)
158 child_tag = root.CHILD_TAG
159 self.assertNotEqual(None, child_tag)
160 self.assertEqual(root[0].tag, child_tag)
161
163 el_class = self._buildElementClass()
164 el_class.CHILD_TAG = None
165 def lookup(doc, el):
166 if el_class.CHILD_TAG is None:
167 el_class.CHILD_TAG = el[-1].tag
168 return el_class
169 self._setClassLookup(lookup)
170 root = self.XML(xml_str)
171 child_tag = root.CHILD_TAG
172 self.assertNotEqual(None, child_tag)
173 self.assertEqual(root[-1].tag, child_tag)
174
176 el_class = self._buildElementClass()
177 el_class.CHILD_TAGS = None
178 def lookup(doc, el):
179 if el_class.CHILD_TAGS is None:
180 el_class.CHILD_TAGS = [ c.tag for c in el[1:-1] ]
181 return el_class
182 self._setClassLookup(lookup)
183 root = self.XML(xml_str)
184 child_tags = root.CHILD_TAGS
185 self.assertNotEqual(None, child_tags)
186 self.assertEqual([ c.tag for c in root[1:-1] ],
187 child_tags)
188
190 el_class = self._buildElementClass()
191 el_class.LEN = None
192 def lookup(doc, el):
193 if el_class.LEN is None:
194 el_class.LEN = len(el)
195 return el_class
196 self._setClassLookup(lookup)
197 root = self.XML(xml_str)
198 self.assertEqual(1, el_class.LEN)
199
201 el_class = self._buildElementClass()
202 el_class.TRUE = None
203 def lookup(doc, el):
204 if el_class.TRUE is None:
205 el_class.TRUE = bool(el)
206 return el_class
207 self._setClassLookup(lookup)
208 root = self.XML(xml_str)
209 self.assertTrue(el_class.TRUE)
210
212 el_class = self._buildElementClass()
213 el_class.VAL = None
214 def lookup(doc, el):
215 if el_class.VAL is None:
216 el_class.VAL = el[0].get('a1')
217 return el_class
218 self._setClassLookup(lookup)
219 root = self.XML(xml_str)
220 self.assertNotEqual(None, el_class.VAL)
221 self.assertEqual(root[0].get('a1'), el_class.VAL)
222
224 el_class = self._buildElementClass()
225 default = str(id(el_class))
226 el_class.VAL = None
227 def lookup(doc, el):
228 if el_class.VAL is None:
229 el_class.VAL = el[0].get('unknownattribute', default)
230 return el_class
231 self._setClassLookup(lookup)
232 root = self.XML(xml_str)
233 self.assertEqual(default, el_class.VAL)
234
236 el_class = self._buildElementClass()
237 el_class.CHILD_TAGS = None
238 def lookup(doc, el):
239 if el_class.CHILD_TAGS is None:
240 el_class.CHILD_TAGS = [ c.tag for c in el.getchildren() ]
241 return el_class
242 self._setClassLookup(lookup)
243 root = self.XML(xml_str)
244 child_tags = root.CHILD_TAGS
245 self.assertNotEqual(None, child_tags)
246 self.assertEqual([ c.tag for c in root.getchildren() ],
247 child_tags)
248
250 el_class = self._buildElementClass()
251 el_class.CHILD_TAGS = None
252 def lookup(doc, el):
253 if el_class.CHILD_TAGS is None:
254 el_class.CHILD_TAGS = [ c.tag for c in el ]
255 return el_class
256 self._setClassLookup(lookup)
257 root = self.XML(xml_str)
258 child_tags = root.CHILD_TAGS
259 self.assertNotEqual(None, child_tags)
260 self.assertEqual([ c.tag for c in root.getchildren() ],
261 child_tags)
262
264 el_class = self._buildElementClass()
265 el_class.CHILD_TAGS = None
266 def lookup(doc, el):
267 if el_class.CHILD_TAGS is None:
268 el_class.CHILD_TAGS = [ c.tag for c in el.iterchildren() ]
269 return el_class
270 self._setClassLookup(lookup)
271 root = self.XML(xml_str)
272 child_tags = root.CHILD_TAGS
273 self.assertNotEqual(None, child_tags)
274 self.assertEqual([ c.tag for c in root.getchildren() ],
275 child_tags)
276
278 el_class = self._buildElementClass()
279 el_class.CHILD_TAGS = None
280 def lookup(doc, el):
281 if not el_class.CHILD_TAGS:
282 el_class.CHILD_TAGS = [
283 c.tag for c in el.iterchildren(tag='{objectified}c2') ]
284 return el_class
285 self._setClassLookup(lookup)
286
287 root = self.XML(xml_str)
288 child_tags = root.CHILD_TAGS
289 self.assertNotEqual(None, child_tags)
290 self.assertEqual([], child_tags)
291
292 c1 = root[0]
293 child_tags = root.CHILD_TAGS
294 self.assertNotEqual(None, child_tags)
295 self.assertNotEqual([], child_tags)
296 self.assertEqual(
297 [ c.tag for c in root[0].iterchildren(tag='{objectified}c2') ],
298 child_tags)
299
301 el_class = self._buildElementClass()
302 el_class.PARENT = None
303 def lookup(doc, el):
304 if el_class.PARENT is None:
305 el_class.PARENT = el[0].getparent().tag
306 return el_class
307 self._setClassLookup(lookup)
308 root = self.XML(xml_str)
309 self.assertEqual(root.tag, root.PARENT)
310
312 el_class = self._buildElementClass()
313 el_class.NEXT = None
314 def lookup(doc, el):
315 if el_class.NEXT is None:
316 el_class.NEXT = el[0][1].getnext().tag
317 return el_class
318 self._setClassLookup(lookup)
319 root = self.XML(xml_str)
320 self.assertNotEqual(None, el_class.NEXT)
321 self.assertEqual(root[0][1].getnext().tag, el_class.NEXT)
322
324 el_class = self._buildElementClass()
325 el_class.PREV = None
326 def lookup(doc, el):
327 if el_class.PREV is None:
328 el_class.PREV = el[0][1].getprevious().tag
329 return el_class
330 self._setClassLookup(lookup)
331 root = self.XML(xml_str)
332 self.assertNotEqual(None, el_class.PREV)
333 self.assertEqual(root[0][1].getprevious().tag, el_class.PREV)
334
338
339 self._setClassLookup(return_none)
340 el = self.XML('<a><!-- hello world --></a>')
341 self.assertEqual(el[0].tag, self.etree.Comment)
342 self.assertEqual(el[0].text, " hello world ")
343
344
346 suite = unittest.TestSuite()
347 suite.addTests([unittest.makeSuite(PyClassLookupTestCase)])
348 return suite
349
350 if __name__ == '__main__':
351 print('to test use test.py %s' % __file__)
352