[Erp5-report] r14005 - in /erp5/trunk/products/ERP5Type: ./ tests/
nobody at svn.erp5.org
nobody at svn.erp5.org
Fri Apr 6 15:08:02 CEST 2007
Author: yo
Date: Fri Apr 6 15:08:00 2007
New Revision: 14005
URL: http://svn.erp5.org?rev=14005&view=rev
Log:
Define isTempDocument to specify if an object is a temporary object or persistent object, rather than using a hack. Remove hasattr in TempDocumentConstructor. Write a test for _aq_dynamic with a temporary object. Remove an unused test. Make it safe to call _aq_dynamic with a temporary object.
Modified:
erp5/trunk/products/ERP5Type/Base.py
erp5/trunk/products/ERP5Type/Utils.py
erp5/trunk/products/ERP5Type/tests/testERP5Type.py
Modified: erp5/trunk/products/ERP5Type/Base.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/Base.py?rev=14005&r1=14004&r2=14005&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/Base.py (original)
+++ erp5/trunk/products/ERP5Type/Base.py Fri Apr 6 15:08:00 2007
@@ -407,6 +407,7 @@
isPredicate = 0 #
isTemplate = 0 #
isDocument = 0 #
+ isTempDocument = 0 # If set to 0, instances are temporary.
# Dynamic method acquisition system (code generation)
aq_method_generated = {}
@@ -490,6 +491,13 @@
# Proceed with property generation
klass = self.__class__
+ if self.isTempObject():
+ # If self is a temporary object, generate methods for the base
+ # document class rather than for the temporary document class.
+ # Otherwise, instances of the base document class would fail
+ # in calling such methods, because they are not instances of
+ # the temporary document class.
+ klass = klass.__bases__[0]
generated = 0 # Prevent infinite loops
# Generate class methods
@@ -2114,13 +2122,9 @@
security.declarePublic('isTempObject')
def isTempObject(self):
- """
- Tells if an object is temporary or not
-
- Implementation is based on the fact that reindexObject method is overloaded
- for all TempObjects with the same dummy method
- """
- return self.reindexObject.im_func is self._temp_reindexObject.im_func
+ """Return true if self is an instance of a temporary document class.
+ """
+ return getattr(self.__class__, 'isTempDocument', 0)
# Workflow Related Method
security.declarePublic('getWorkflowStateItemList')
@@ -2916,6 +2920,7 @@
we shoud used TempBase
"""
isIndexable = 0
+ isTempDocument = 1
# Declarative security
security = ClassSecurityInfo()
Modified: erp5/trunk/products/ERP5Type/Utils.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/Utils.py?rev=14005&r1=14004&r2=14005&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/Utils.py (original)
+++ erp5/trunk/products/ERP5Type/Utils.py Fri Apr 6 15:08:00 2007
@@ -350,6 +350,7 @@
def __init__(self, klass):
# Create a new class to set permissions specific to temporary objects.
class TempDocument(klass):
+ isTempDocument = 1
pass
# Replace some attributes.
@@ -369,7 +370,8 @@
o = self.klass(id)
if kw:
o.__of__(folder)._edit(force_update=1, **kw)
- if hasattr(folder, 'isTempObject') and folder.isTempObject():
+ isTempObject = getattr(folder, 'isTempObject', None)
+ if isTempObject is not None and isTempObject():
folder._setObject(id, o)# Temp Object in Temp Object should use containment
return id # return id to be compatible with CMF constructInstance
else: # Temp Object in Persistent Object should use acquisition
Modified: erp5/trunk/products/ERP5Type/tests/testERP5Type.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/tests/testERP5Type.py?rev=14005&r1=14004&r2=14005&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/tests/testERP5Type.py (original)
+++ erp5/trunk/products/ERP5Type/tests/testERP5Type.py Fri Apr 6 15:08:00 2007
@@ -209,19 +209,8 @@
self.failUnless(business_template.getTitle()==test_string)
# Test Dynamic Code Generation
- def test_01_AqDynamic(self):
- portal = self.getPortal()
- #module = portal.person
- from Products.ERP5Type.Base import initializeClassDynamicProperties
- from Products.ERP5Type.Base import initializePortalTypeDynamicProperties
- from Products.ERP5Type.Base import Base
- from Products.ERP5Type import Document
- initializeClassDynamicProperties(portal, Base)
- # Base class should now have a state method
- # self.failUnless(hasattr(Base, 'getFirstName'))
- # This test is now useless since methods are portal type based
-
- def test_02_AqDynamic(self):
+ def test_02_AqDynamic(self, quiet=quiet, run=run_all_test):
+ if not run: return
portal = self.getPortal()
module = self.getPersonModule()
person = module.newContent(id='1', portal_type='Person')
@@ -1273,6 +1262,72 @@
checked_permission="View"),
[doo.getTitle(), bar.getTitle(), ])
+ def test_25_AqDynamicWithTempObject(self, quiet=quiet, run=run_all_test):
+ """Check if _aq_dynamic works correctly, regardless of whether
+ it is first called for a temporary object or a persistent object.
+
+ This test is based on the fact that a portal type is shared between
+ a temporary document and a persistent document, and if a class for
+ the temporary document is used for generating new methods, calling
+ such methods from a persistent object may fail, because such a
+ persistent object is not an instance of the temporary document class.
+ """
+ if not run: return
+ portal = self.getPortal()
+
+ # Clear out all generated methods.
+ _aq_reset()
+
+ # Create a new temporary person object.
+ from Products.ERP5Type.Document import newTempPerson
+ o = newTempPerson(portal, 'temp_person_1')
+ self.failUnless(o.isTempObject())
+
+ # This should generate a workflow method.
+ self.assertEquals(o.getValidationState(), 'draft')
+ o.validate()
+ self.assertEquals(o.getValidationState(), 'validated')
+
+ # Create a new persistent person object.
+ person_module = portal.person_module
+ person_id = 'person_1'
+ if person_id in person_module.objectIds():
+ person_module.manage_delObjects([person_id])
+ o = person_module.newContent(id=person_id, portal_type='Person')
+ self.failIf(o.isTempObject())
+
+ # This should call methods generated above for the temporary object.
+ self.assertEquals(o.getValidationState(), 'draft')
+ o.validate()
+ self.assertEquals(o.getValidationState(), 'validated')
+
+ # Paranoia: test the reverse snenario as well, although this
+ # should succeed anyway.
+
+ # Create a new persistent person object.
+ person_id = 'person_2'
+ if person_id in person_module.objectIds():
+ person_module.manage_delObjects([person_id])
+ o = person_module.newContent(id=person_id, portal_type='Person')
+ self.failIf(o.isTempObject())
+
+ # Clear out all generated methods.
+ _aq_reset()
+
+ # This should generate workflow methods.
+ self.assertEquals(o.getValidationState(), 'draft')
+ o.validate()
+ self.assertEquals(o.getValidationState(), 'validated')
+
+ # Create a new temporary person object.
+ o = newTempPerson(portal, 'temp_person_2')
+ self.failUnless(o.isTempObject())
+
+ # This should call methods generated for the persistent object.
+ self.assertEquals(o.getValidationState(), 'draft')
+ o.validate()
+ self.assertEquals(o.getValidationState(), 'validated')
+
if __name__ == '__main__':
framework()
else:
More information about the Erp5-report
mailing list