f559c45d04459035e0cf054e17e1381a81088f2a
[sdc/sdc-distribution-client.git] /
1 from __future__ import absolute_import, division, unicode_literals
2
3 from genshi.core import QName
4 from genshi.core import START, END, XML_NAMESPACE, DOCTYPE, TEXT
5 from genshi.core import START_NS, END_NS, START_CDATA, END_CDATA, PI, COMMENT
6
7 from . import _base
8
9 from ..constants import voidElements, namespaces
10
11
12 class TreeWalker(_base.TreeWalker):
13     def __iter__(self):
14         # Buffer the events so we can pass in the following one
15         previous = None
16         for event in self.tree:
17             if previous is not None:
18                 for token in self.tokens(previous, event):
19                     yield token
20             previous = event
21
22         # Don't forget the final event!
23         if previous is not None:
24             for token in self.tokens(previous, None):
25                 yield token
26
27     def tokens(self, event, next):
28         kind, data, pos = event
29         if kind == START:
30             tag, attribs = data
31             name = tag.localname
32             namespace = tag.namespace
33             converted_attribs = {}
34             for k, v in attribs:
35                 if isinstance(k, QName):
36                     converted_attribs[(k.namespace, k.localname)] = v
37                 else:
38                     converted_attribs[(None, k)] = v
39
40             if namespace == namespaces["html"] and name in voidElements:
41                 for token in self.emptyTag(namespace, name, converted_attribs,
42                                            not next or next[0] != END
43                                            or next[1] != tag):
44                     yield token
45             else:
46                 yield self.startTag(namespace, name, converted_attribs)
47
48         elif kind == END:
49             name = data.localname
50             namespace = data.namespace
51             if name not in voidElements:
52                 yield self.endTag(namespace, name)
53
54         elif kind == COMMENT:
55             yield self.comment(data)
56
57         elif kind == TEXT:
58             for token in self.text(data):
59                 yield token
60
61         elif kind == DOCTYPE:
62             yield self.doctype(*data)
63
64         elif kind in (XML_NAMESPACE, DOCTYPE, START_NS, END_NS,
65                       START_CDATA, END_CDATA, PI):
66             pass
67
68         else:
69             yield self.unknown(kind)