pastebin - collaborative debugging

pastebin is a collaborative debugging tool allowing you to share and modify code snippets while chatting on IRC, IM or a message board.

This site is developed to XHTML and CSS2 W3C standards. If you see this paragraph, your browser does not support those standards and you need to upgrade. Visit WaSP for a variety of options.

Python pastebin - collaborative debugging tool View Help


Posted by Eduardo Padoan on Mon 18 Feb 02:44
report abuse | download | new post

  1. import unittest
  2. from copy import copy
  3.  
  4.  
  5. class Proto(object):
  6.     """ A prototype object.
  7.    """
  8.  
  9.     def __init__(self, wrapped=None, proto=None):
  10.         self._wrapped = wrapped
  11.         self.proto = proto
  12.         self._protos = [proto] # +/- like __mro__
  13.  
  14.         try:
  15.             # instantialize the state of the clone
  16.             self.init(self)
  17.         except AttributeError:
  18.             pass
  19.  
  20.     def __getattr__(self, name):
  21.         #### diferential inheritance ####
  22.         # __getattr__ is only called
  23.         # when the attribute is not found
  24.         try:
  25.             value = getattr(self._wrapped, name)
  26.         except AttributeError:
  27.             for proto in self._protos:
  28.                 try:
  29.                     value = getattr(proto, name)
  30.                     break
  31.                 except AttributeError:
  32.                     continue
  33.             else:
  34.                 raise AttributeError('Object %r have no %s attribute.'
  35.                                      % (self, name))
  36.         return value
  37.  
  38.     def __repr__(self):
  39.         return '<object %r>' % self._wrapped
  40.  
  41.     @property
  42.     def protos(self):
  43.         for proto in self._protos:
  44.             if proto is not None:
  45.                 yield proto
  46.                 # ask the protos for its protos...
  47.                 for super_proto in proto.protos:
  48.                     if super_proto is not None:
  49.                         yield super_proto
  50.  
  51.     def clone(self):
  52.         """ Create a new object, based on this one.
  53.        """
  54.         wrapped = self._wrapped
  55.         try:
  56.             # if the object is immutable,
  57.             # no problem sharing it
  58.             hash(wrapped)
  59.             return Proto(wrapped, self)
  60.         except TypeError:
  61.             return Proto(copy(wrapped), self)
  62.  
  63.     def append_proto(self, proto):
  64.         self._protos.append(proto)
  65.  
  66.     def prepend_proto(self, proto):
  67.         self._protos.insert(0, proto)
  68.  
  69.     def remove_proto(self, proto):
  70.         self._protos.remove(proto)
  71.  
  72.  
  73. class TestProto(unittest.TestCase):
  74.  
  75.     def test_wraps(self):
  76.         obj = Proto('hello')
  77.         self.assertFalse(obj.isupper())
  78.         self.assertTrue(obj.islower())
  79.         self.assertTrue(obj.isalpha())
  80.         c1 = obj.clone()
  81.         self.assertFalse(c1.isdigit())
  82.         self.assertFalse(c1.isspace())
  83.         self.assertEqual(c1.title(), 'Hello')
  84.         self.assertRaises(AttributeError, getattr, c1, 'append')
  85.  
  86.     def test_clone_and_protos(self):
  87.         obj = Proto(42)
  88.         self.assertEqual(repr(obj), '<object 42>')
  89.         self.assertEqual(None, obj.proto)
  90.         clone = obj.clone()
  91.         proto_a = clone.proto
  92.         proto_b = list(clone.protos).pop()
  93.         self.assertEqual(proto_a, proto_b)
  94.         self.assertNotEqual(obj.proto, proto_a)
  95.         self.assertNotEqual(obj.proto, proto_b)
  96.         self.assertEqual(list(clone.protos), [obj])
  97.  
  98.         c2 = clone.clone()
  99.         c3 = c2.clone()
  100.         c4 = c3.clone()
  101.         self.assertEqual(list(c2.protos), [clone, obj])
  102.         self.assertEqual(list(c3.protos), [c2, clone, obj])
  103.         self.assertEqual(list(c4.protos), [c3, c2, clone, obj])
  104.  
  105.     def test_init(self):
  106.         Movie = Proto("Movie")
  107.         def init(self):
  108.             self.cast = []
  109.         Movie.init = init
  110.         some_movie = Movie.clone()
  111.         self.assertEqual(some_movie.cast, [])
  112.         some_movie.cast.append('Some Actor')
  113.         another_movie  = Movie.clone()
  114.         self.assertEqual(another_movie.cast, [])
  115.         self.assertNotEqual(another_movie.cast, some_movie.cast)
  116.  
  117.     def test_inheritance(self):
  118.         obj = Proto('foo')
  119.         obj.bar = 'baz'
  120.         c1 = obj.clone()
  121.         self.assertEqual(obj.bar, c1.bar)
  122.         self.assertEqual(c1.bar, 'baz')
  123.         obj.baz = 'foo'
  124.         self.assertEqual(obj.baz, c1.baz)
  125.         self.assertEqual(c1.baz, 'foo')
  126.         obj.quux = 'foobar'
  127.         self.assertEqual(obj.quux, c1.quux)
  128.         self.assertEqual(c1.quux, 'foobar')
  129.  
  130.         c2 = c1.clone()
  131.         c3 = c2.clone()
  132.  
  133.         self.assertEqual(obj.bar, c2.bar)
  134.         self.assertEqual(c2.bar, 'baz')
  135.         self.assertEqual(obj.quux, c2.quux)
  136.         self.assertEqual(c2.quux, 'foobar')
  137.  
  138.         self.assertEqual(obj.bar, c3.bar)
  139.         self.assertEqual(c3.bar, 'baz')
  140.         self.assertEqual(obj.quux, c3.quux)
  141.         self.assertEqual(c3.quux, 'foobar')
  142.  
  143.         self.assertEqual(c2.bar, c3.bar)
  144.         self.assertEqual(c1.bar, c2.bar)
  145.         self.assertEqual(c1.bar, c3.bar)
  146.  
  147.         self.assertEqual(c2.quux, c3.quux)
  148.         self.assertEqual(c1.quux, c2.quux)
  149.         self.assertEqual(c1.quux, c3.quux)
  150.  
  151.         obj.bar = 42
  152.         self.assertEqual(obj.bar, c3.bar)
  153.         self.assertEqual(c3.bar, 42)
  154.  
  155.         obj2 = Proto('bar')
  156.         c3.prepend_proto(obj2)
  157.         obj2.baz = 'hello'
  158.         self.assertEqual(c3.bar, 42)
  159.         self.assertEqual(c3.baz, 'hello')
  160.  
  161.         obj3 = Proto('baz')
  162.         c3.append_proto(obj3)
  163.         obj3.quuuux = 'quuuux'
  164.         obj3.bar = 'quuuux'
  165.         self.assertEqual(c3.bar, 42)
  166.         self.assertEqual(c3.baz, 'hello')
  167.         self.assertEqual(c3.quuuux, 'quuuux')
  168.  
  169.         c3.remove_proto(obj3)
  170.         self.assertRaises(AttributeError, getattr, obj3, 'quuux')
  171.  
  172.  
  173. if __name__ == '__main__':
  174.     unittest.main()

Submit a correction or amendment below (click here to make a fresh posting)
After submitting an amendment, you'll be able to view the differences between the old and new posts easily.

Syntax highlighting:

To highlight particular lines, prefix each line with @@


Remember me so that I can delete my post