# HG changeset patch # User cmlenz # Date 1159816116 0 # Node ID 4b5b4653d41e93c5457ea7cbbe77854d22bf53d7 # Parent 8de2620504b9d2c1a4c4fa768e48e82a2347596d Some adjustments to make core data structures picklable (requires protocol 2). diff --git a/genshi/core.py b/genshi/core.py --- a/genshi/core.py +++ b/genshi/core.py @@ -22,6 +22,11 @@ class StreamEventKind(str): """A kind of event on an XML stream.""" + __slots__ = [] + _instances = {} + + def __new__(cls, val): + return cls._instances.setdefault(val, str.__new__(cls, val)) class Stream(object): @@ -503,6 +508,15 @@ return uri return object.__new__(cls, uri) + def __getnewargs__(self): + return (self.uri,) + + def __getstate__(self): + return self.uri + + def __setstate__(self, uri): + self.uri = uri + def __init__(self, uri): self.uri = unicode(uri) @@ -572,3 +586,6 @@ self = unicode.__new__(cls, qname) self.namespace, self.localname = None, unicode(qname) return self + + def __getnewargs__(self): + return (self.lstrip('{'),) diff --git a/genshi/tests/core.py b/genshi/tests/core.py --- a/genshi/tests/core.py +++ b/genshi/tests/core.py @@ -12,9 +12,12 @@ # history and logs, available at http://genshi.edgewall.org/log/. import doctest +import pickle +from StringIO import StringIO import unittest -from genshi.core import * +from genshi import core +from genshi.core import Markup, Namespace, QName, escape, unescape from genshi.input import XML, ParseError @@ -32,6 +35,14 @@ xml = XML('
  • Über uns
  • ') self.assertEqual('
  • Über uns
  • ', xml.render(encoding='ascii')) + def test_pickle(self): + xml = XML('
  • Foo
  • ') + buf = StringIO() + pickle.dump(xml, buf, 2) + buf.seek(0) + xml = pickle.load(buf) + self.assertEquals('
  • Foo
  • ', xml.render()) + class MarkupTestCase(unittest.TestCase): @@ -115,12 +126,48 @@ assert type(markup) is Markup self.assertEquals('foo', markup) + def test_pickle(self): + markup = Markup('foo') + buf = StringIO() + pickle.dump(markup, buf, 2) + buf.seek(0) + self.assertEquals('', repr(pickle.load(buf))) + + +class NamespaceTestCase(unittest.TestCase): + + def test_pickle(self): + ns = Namespace('http://www.example.org/namespace') + buf = StringIO() + pickle.dump(ns, buf, 2) + buf.seek(0) + unpickled = pickle.load(buf) + self.assertEquals('', + repr(unpickled)) + self.assertEquals('http://www.example.org/namespace', unpickled.uri) + + +class QNameTestCase(unittest.TestCase): + + def test_pickle(self): + qname = QName('http://www.example.org/namespace}elem') + buf = StringIO() + pickle.dump(qname, buf, 2) + buf.seek(0) + unpickled = pickle.load(buf) + self.assertEquals('{http://www.example.org/namespace}elem', unpickled) + self.assertEquals('http://www.example.org/namespace', + unpickled.namespace) + self.assertEquals('elem', unpickled.localname) + def suite(): suite = unittest.TestSuite() suite.addTest(unittest.makeSuite(StreamTestCase, 'test')) suite.addTest(unittest.makeSuite(MarkupTestCase, 'test')) - suite.addTest(doctest.DocTestSuite(Markup.__module__)) + suite.addTest(unittest.makeSuite(NamespaceTestCase, 'test')) + suite.addTest(unittest.makeSuite(QNameTestCase, 'test')) + suite.addTest(doctest.DocTestSuite(core)) return suite if __name__ == '__main__':