XSLTools

Annotated XSLTools/XMLTable.py

567:83425ff09945
2007-02-28 paulb [project @ 2007-02-28 23:44:13 by paulb] Added WebStack as a build dependency so that the examples are generated.
paulb@202 1
#!/usr/bin/env python
paulb@202 2
paulb@202 3
"A list of tuples to XML document converter."
paulb@202 4
paulb@202 5
import libxml2dom
paulb@202 6
from UserDict import UserDict
paulb@202 7
paulb@202 8
class OrderedDict(UserDict):
paulb@202 9
paulb@202 10
    "A dictionary with keys in the order in which they were given."
paulb@202 11
paulb@202 12
    def __init__(self, *args):
paulb@202 13
        UserDict.__init__(self, *args)
paulb@202 14
        self._keys = self.data.keys()
paulb@202 15
paulb@202 16
    def __setitem__(self, key, value):
paulb@202 17
        UserDict.__setitem__(self, key, value)
paulb@202 18
        if key not in self._keys:
paulb@202 19
            self._keys.append(key)
paulb@202 20
paulb@202 21
    def __delitem__(self, key):
paulb@202 22
        UserDict.__delitem__(self, key)
paulb@202 23
        del self._keys[key]
paulb@202 24
paulb@202 25
    def keys(self):
paulb@202 26
        return self._keys
paulb@202 27
paulb@202 28
    def items(self):
paulb@202 29
        l = []
paulb@202 30
        for key in self._keys:
paulb@202 31
            l.append((key, self.data[key]))
paulb@202 32
        return l
paulb@202 33
paulb@202 34
    def values(self):
paulb@202 35
        return [value for key, value in self.items()]
paulb@202 36
paulb@202 37
class Converter:
paulb@202 38
    def __init__(self, ns=None, prefix="", doc=None, root=None):
paulb@202 39
        self.ns = ns
paulb@202 40
        self.prefix = prefix
paulb@202 41
        if doc is not None:
paulb@202 42
            self.doc = doc
paulb@202 43
        else:
paulb@202 44
            self.doc = libxml2dom.createDocument(ns, prefix+"table", None)
paulb@202 45
        if root is not None:
paulb@202 46
            self.root = root
paulb@202 47
        else:
paulb@202 48
            self.root = self.doc.xpath("*")[0]
paulb@202 49
paulb@214 50
        # Remember the last row element.
paulb@214 51
paulb@214 52
        self.last_row_element = None
paulb@214 53
paulb@202 54
    def add_rows(self, rows):
paulb@202 55
        for row in rows:
paulb@202 56
            self.add_row(row)
paulb@202 57
paulb@202 58
    def add_row(self, row, index=-1, row_element_name="row", use_key_as_element_name=0):
paulb@214 59
        self.last_row_element = self.doc.createElementNS(self.ns, self.prefix+row_element_name)
paulb@202 60
        if index == -1:
paulb@214 61
            self.root.appendChild(self.last_row_element)
paulb@202 62
        else:
paulb@214 63
            self.root.insertBefore(self.last_row_element, self.root.xpath("*[%s]" % (index + 1))[0])
paulb@202 64
paulb@202 65
        # Permit dictionaries.
paulb@202 66
paulb@202 67
        if hasattr(row, "items"):
paulb@202 68
            for name, value in row.items():
paulb@202 69
                if use_key_as_element_name:
paulb@202 70
                    column_element = self.doc.createElementNS(self.ns, self.prefix+unicode(name))
paulb@202 71
                else:
paulb@202 72
                    column_element = self.doc.createElementNS(self.ns, self.prefix+"column")
paulb@202 73
                    column_element.setAttributeNS(self.ns, self.prefix+"name", unicode(name))
paulb@214 74
                self.last_row_element.appendChild(column_element)
paulb@202 75
                text = self.doc.createTextNode(unicode(value))
paulb@202 76
                column_element.appendChild(text)
paulb@202 77
paulb@202 78
        # As well as sequences.
paulb@202 79
paulb@202 80
        else:
paulb@202 81
            for column in row:
paulb@202 82
                column_element = self.doc.createElementNS(self.ns, self.prefix+"column")
paulb@214 83
                self.last_row_element.appendChild(column_element)
paulb@202 84
                text = self.doc.createTextNode(unicode(column))
paulb@202 85
                column_element.appendChild(text)
paulb@202 86
paulb@214 87
    def last_row(self):
paulb@214 88
        if self.last_row_element is not None:
paulb@214 89
            return Converter(self.ns, self.prefix, self.doc, self.last_row_element)
paulb@214 90
        else:
paulb@214 91
            return None
paulb@214 92
paulb@202 93
if __name__ == "__main__":
paulb@202 94
    from rdflib.TripleStore import TripleStore
paulb@202 95
    import sys
paulb@202 96
    s = TripleStore()
paulb@202 97
    s.load(sys.argv[1])
paulb@202 98
    converter = Converter()
paulb@202 99
    converter.add_rows(s.triples((None, None, None)))
paulb@202 100
    libxml2dom.toStream(converter.doc, sys.stdout)
paulb@202 101
paulb@202 102
# vim: tabstop=4 expandtab shiftwidth=4