1 # !/usr/local/bin/python
2 #
3 # Filename: test.py
4 # Copyright (c) Alex Shindich, 2000
5 # Author: Alex Shindich
6 # License: The author is making this software available on an "AS IS" basis.
7 # There are no warranties regarding this software. Use it at your own risk!
8 # Permission to use, copy, modify, and distribute this software and its
9 # documentation for any purpose and without fee is hereby granted without
10 # any restrictions.
11 #
12 # Purpose: This file contains unit tests for WeakRef extension module
13 # In order to run these tests, two unit test modules have to
14 # be installed in python module path: unittest.py and unittestgui.py
15 # These modules can be obtained at http://pyunit.sourceforge.net/
16
17 import unittest
18 import unittestgui
19 import sys
20 import weakref
21
22 class WeakRefTestCase(unittest.TestCase):
23 """A test case for the Weak Reference class"""
24
25 class Foo:
26 instanceCount = 0
27 def __init__(self):
28 WeakRefTestCase.Foo.instanceCount += 1
29 def __del__(self):
30 WeakRefTestCase.Foo.instanceCount -= 1
31
32 def setUp(self):
33 """"""
34 pass
35
36 def __createTestObjects (self, count):
37 """This method create a list of test objects."""
38
39 # Declare a list of types we want to test
40 factories = [lambda : 's', lambda : 1L, lambda : 20., lambda : WeakRefTestCase.Foo (),
41 lambda : None, lambda : 1, lambda : [], lambda : {}]
42 # Create a whole bunch of references
43 retList = []
44 for x in range (count):
45 for factory in factories:
46 # Create a new object
47 newObj = factory ()
48 # Add the object to the list
49 retList.append (newObj)
50
51 return retList
52
53 def __createWeakReferences (self, testObjects):
54 """This method create a list of weak references for every element in
the testObjects list."""
56
57 retList = []
58 for testObj in testObjects:
59 newWeakRef = weakref.new (testObj)
60 retList.append (newWeakRef)
61
62 return retList
63
64 def __copyFromWeakReferences (self, weakReferences):
65 """This method create a list of new references to the test objects
from the list of weak references."""
67
68 retList = []
69 for weakReference in weakReferences:
70 newRef = weakReference.newref ()
71 retList.append (newRef)
72
73 return retList
74
75 def check_Stress (self):
76 """This method conducts stress testing of the weak reference object."""
77
78 # Create test objects
79 testObjects = self.__createTestObjects (1000)
80 # Create a list of weak references
81 weakRefList = self.__createWeakReferences (testObjects)
82 # Copy the list from the weak references
83 copyOfTestObjects = self.__copyFromWeakReferences (weakRefList)
84 # Compare the lists
85 assert (testObjects == copyOfTestObjects)
86 # Delete the copy list
87 del copyOfTestObjects
88 # Delete half of the original test list
89 midPos = len (testObjects)/2
90 testObjects = testObjects[0:midPos]
91 # Iterate over the list of weak references and make sure that it returns new
92 # references for the first half of the list and None references for the weak
93 # references to Foo for the second half of the list
94 for index in range (len (weakRefList)):
95 # Create a new reference from the weak reference
96 newRef = weakRefList[index].newref ()
97 # Check to see if this is supposed to be a stale reference
98 if index < len (testObjects):
99 # This is a good reference
100 testRef = testObjects[index]
101 else:
102 # This is a stale reference
103 testRef = None
104 # Copare the object to the original object
105 assert (type(newRef) != type (WeakRefTestCase.Foo) or testRef == newRef)
106 assert (type(newRef) != type (WeakRefTestCase.Foo) or type(testRef) == type(newRef))
107
108 def check_None (self):
109 """This method makes sure that the weak reference implementation
returns None if the 'weak' object has been deleted."""
111
112 # Create an instance of the Foo class
113 f = WeakRefTestCase.Foo ()
114 # Create a weak reference
115 wr = weakref.new (f)
116 # Delete the test instance of Foo
117 del f
118 # Now create a new reference from the weak reference
119 f2 = wr.newref ()
120 # Make sure that the new reference is a None object
121 assert (type(None) == type (f2))
122 assert (None == f2)
123
124 def check_Idenity (self):
125 """This method makes sure that the weak reference implementation
does not violate Python identity rules."""
127
128 # Create an instance of the Foo class
129 f = WeakRefTestCase.Foo ()
130 # Create a weak reference
131 wr = weakref.new (f)
132 # Now create a new reference from the weak reference
133 f2 = wr.newref ()
134 # Make sure that f2 equals to f
135 assert (f == f2)
136 # Make sure that f2 is an instance of Foo
137 assert (isinstance (f2, type(f)))
138
139 def check_TestRefCount (self):
140 """This method makes sure that reference counting rules
have not been broken."""
142
143 # Save the number of Foo instances
144 instanceCount = WeakRefTestCase.Foo.instanceCount
145 # Create an instance of the Foo class
146 f = WeakRefTestCase.Foo ()
147 # Save the reference count
148 refCount = sys.getrefcount (f)
149 # Create a weak reference
150 wr = weakref.new (f)
151 # Make sure that the reference count has not changed
152 refCount == sys.getrefcount (f)
153 # Now create a new reference from the weak reference
154 f2 = wr.newref ()
155 # Make sure that the reference count was bumped by one
156 refCount == sys.getrefcount (f)-1
157 # Delete the original Foo reference
158 del f
159 # Make sure that the object count went down by one
160 refCount == sys.getrefcount (f2)
161 # Delete the second Foo reference
162 del f2
163 # Make sure that the original test instance of Foo got detroyed
164 assert (instanceCount == WeakRefTestCase.Foo.instanceCount)
165
166 def check_TestCmp (self):
167 """This method makes sure that comparison operator works
correctly."""
169
170 # Create an instance of the Foo class
171 f = WeakRefTestCase.Foo ()
172 # Create a weak reference
173 wr = weakref.new (f)
174 # Create another weak reference
175 awr = weakref.new (f)
176 # Make sure that the references are equal
177 assert (wr == awr)
178 # Create another instance of the Foo class
179 f2 = WeakRefTestCase.Foo ()
180 # Create a weak reference for f2
181 awr = weakref.new (f2)
182 # Make sure that the references are not equal
183 assert (wr != awr)
184
185 def check_TestHash (self):
186 """This method makes sure that hash function works
correctly."""
188
189 # Create an instance of the Foo class
190 f = WeakRefTestCase.Foo ()
191 # Create a weak reference
192 wr = weakref.new (f)
193 # Create another weak reference
194 awr = weakref.new (f)
195 # Make sure that hash numbers are the same
196 assert (hash(wr) == hash(awr))
197 # Create another instance of the Foo class
198 f2 = WeakRefTestCase.Foo ()
199 # Create a weak reference for f2
200 awr = weakref.new (f2)
201 # Make sure that the references are not equal
202 assert (hash(wr) != hash(awr))
203
204 def check_TestGetType (self):
205 """This method makes sure that gettype function works
correctly."""
207
208 # Create an instance of the Foo class
209 f = WeakRefTestCase.Foo ()
210 # Create a weak reference
211 wr = weakref.new (f)
212 # Create another weak reference
213 awr = weakref.new (f)
214 # Make sure that types are the same
215 assert (wr.gettype () == type (f))
216 assert (wr.gettype () == awr.gettype ())
217 # Delete the object
218 del f
219 # Make sure that types are None
220 assert (wr.gettype () == None)
221 assert (wr.gettype () == awr.gettype ())
222
223 def check_TestDict (self):
224 """This method makes sure that dictionary objects
work correctly with weak references."""
226
227 # Create test objects
228 testObjects = self.__createTestObjects (1000)
229 # Create a list of weak references
230 weakRefList = self.__createWeakReferences (testObjects)
231 # Create a dictionary of weak references from the list
232 weakRefDict = {}
233 for wr in weakRefList:
234 weakRefDict[wr] = wr
235 # Create another list of weak references
236 weakRefList2 = self.__createWeakReferences (testObjects)
237 # Make sure that map works properly
238 for wr in weakRefList2:
239 assert (weakRefDict[wr] == wr)
240
241 def suite():
242 return unittest.makeSuite(WeakRefTestCase, 'check')
243
244 if __name__ == '__main__':
245 unittestgui.main ('test.suite')