[Erp5-report] r38666 nicolas.dumazet - in /erp5/trunk/products: ERP5/ ERP5Type/Dynamic/ ERP...

nobody at svn.erp5.org nobody at svn.erp5.org
Mon Sep 27 15:34:08 CEST 2010


Author: nicolas.dumazet
Date: Mon Sep 27 15:34:07 2010
New Revision: 38666

URL: http://svn.erp5.org?rev=38666&view=rev
Log:
Clean up code related to Dynamic modules invalidation:
* add CacheCookieMixin to ERP5Site and use its methods
  instead of manually using ZODBCookie's
* rename resetDynamicDocuments to synchronizeDynamicModules
  to clarify its role.
* use "force" instead of "slave" and document the meaning
  more clearly
* put all cookie-related code inside synchronizeDynamicModules

Modified:
    erp5/trunk/products/ERP5/ERP5Site.py
    erp5/trunk/products/ERP5Type/Dynamic/portaltypeclass.py
    erp5/trunk/products/ERP5Type/Tool/TypesTool.py
    erp5/trunk/products/ERP5Type/patches/getSite.py

Modified: erp5/trunk/products/ERP5/ERP5Site.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5/ERP5Site.py?rev=38666&r1=38665&r2=38666&view=diff
==============================================================================
--- erp5/trunk/products/ERP5/ERP5Site.py [utf8] (original)
+++ erp5/trunk/products/ERP5/ERP5Site.py [utf8] Mon Sep 27 15:34:07 2010
@@ -29,7 +29,7 @@ from Acquisition import aq_base
 from Products.ERP5Type import allowClassTool
 from Products.ERP5Type.Accessor.Constant import PropertyGetter as ConstantGetter
 from Products.ERP5Type.Cache import caching_instance_method
-from Products.ERP5Type.Cache import CachingMethod
+from Products.ERP5Type.Cache import CachingMethod, CacheCookieMixin
 from Products.ERP5Type.ERP5Type import ERP5TypeInformation
 from Products.ERP5.Document.BusinessTemplate import BusinessTemplate
 from Products.ERP5Type.Log import log as unrestrictedLog
@@ -178,7 +178,7 @@ class ReferCheckerBeforeTraverseHook:
             'request : "%s"' % http_url)
         response.unauthorized()
 
-class ERP5Site(FolderMixIn, CMFSite):
+class ERP5Site(FolderMixIn, CMFSite, CacheCookieMixin):
   """
   The *only* function this class should have is to help in the setup
   of a new ERP5.  It should not assist in the functionality at all.

Modified: erp5/trunk/products/ERP5Type/Dynamic/portaltypeclass.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/Dynamic/portaltypeclass.py?rev=38666&r1=38665&r2=38666&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/Dynamic/portaltypeclass.py [utf8] (original)
+++ erp5/trunk/products/ERP5Type/Dynamic/portaltypeclass.py [utf8] Mon Sep 27 15:34:07 2010
@@ -9,10 +9,10 @@ from types import ModuleType
 from Products.ERP5Type.patches.getSite import getSite
 from Products.ERP5Type.Globals import InitializeClass
 from Products.ERP5Type.Utils import setDefaultClassProperties
-from Products.ERP5Type.Cache import ZODBCookie
 
 from Products.ERP5Type import document_class_registry, mixin_class_registry
 
+from ExtensionClass import Base as ExtensionBase
 from zLOG import LOG, ERROR, BLATHER
 
 def _import_class(classpath):
@@ -167,17 +167,35 @@ def initializeDynamicModules():
                                                    temp_portal_type_loader)
 
 
-from ExtensionClass import Base as ExtensionBase
-def resetDynamicDocuments(context, slave=False):
+last_sync = 0
+def synchronizeDynamicModules(context, force=False):
   """
   Allow resetting all classes to ghost state, most likely done after
   adding and removing mixins on the fly
 
-  Nodes just trying to catch up with state of classes without wanting
-  to invalidate them globally should set slave=True.
+  Most of the time, this reset is only hypothetic:
+  * with force=False, the reset is only done if another node resetted
+    the classes since the last reset on this node.
+  * with force=True, forcefully reset the classes on the current node
+    and send out an invalidation to other nodes
   """
   LOG("ERP5Type.Dynamic", 0, "Resetting dynamic classes")
   return # XXX disabled for now
+
+  portal = context.getPortalObject()
+
+  global last_sync
+  if force:
+    # hard invalidation to force sync between nodes
+    portal.newCacheCookie('dynamic_classes')
+    last_sync = portal.getCacheCookie('dynamic_classes')
+  else:
+    cookie = portal.getCacheCookie('dynamic_classes')
+    if cookie == last_sync:
+      # up to date, nothing to do
+      return
+    last_sync = cookie
+
   import erp5.portal_type
   for class_name, klass in inspect.getmembers(erp5.portal_type, inspect.isclass):
     ghostbase = getattr(klass, '__ghostbase__', None)
@@ -188,12 +206,3 @@ def resetDynamicDocuments(context, slave
       klass.__bases__ = ghostbase
       type(ExtensionBase).__init__(klass, klass)
 
-
-  if not slave:
-    # hard invalidation to force sync between nodes
-    portal = context.getPortalObject()
-    cookie = getattr(portal, '_dynamic_class_cookie', None)
-    if cookie is not None:
-      cookie.value += 1
-    else:
-      portal._dynamic_class_cookie = ZODBCookie()

Modified: erp5/trunk/products/ERP5Type/Tool/TypesTool.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/Tool/TypesTool.py?rev=38666&r1=38665&r2=38666&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/Tool/TypesTool.py [utf8] (original)
+++ erp5/trunk/products/ERP5Type/Tool/TypesTool.py [utf8] Mon Sep 27 15:34:07 2010
@@ -29,6 +29,7 @@ from Products.ERP5Type.ERP5Type import E
 from Products.ERP5Type.UnrestrictedMethod import UnrestrictedMethod
 from zLOG import LOG, WARNING, PANIC
 from Products.ERP5Type.interfaces import ITypeProvider, ITypesTool
+from Products.ERP5Type.Dynamic.portaltypeclass import synchronizeDynamicModules
 
 
 class ComposedObjectIds(object):
@@ -244,8 +245,7 @@ class TypesTool(TypeProvider):
                             'resetDynamicDocuments')
   def resetDynamicDocuments(self):
     """Resets all dynamic documents: force reloading erp.* classes"""
-    from Products.ERP5Type.Dynamic.portaltypeclass import resetDynamicDocuments
-    resetDynamicDocuments(self)
+    synchronizeDynamicModules(self, force=True)
 
   security.declareProtected(Permissions.AddPortalContent,
                             'manage_addTypeInformation')

Modified: erp5/trunk/products/ERP5Type/patches/getSite.py
URL: http://svn.erp5.org/erp5/trunk/products/ERP5Type/patches/getSite.py?rev=38666&r1=38665&r2=38666&view=diff
==============================================================================
--- erp5/trunk/products/ERP5Type/patches/getSite.py [utf8] (original)
+++ erp5/trunk/products/ERP5Type/patches/getSite.py [utf8] Mon Sep 27 15:34:07 2010
@@ -1,3 +1,4 @@
+from Products.ERP5Type.Dynamic.portaltypeclass import synchronizeDynamicModules
 from Products.ERP5Type import Globals
 module_name = 'zope.site.hooks'
 try:
@@ -37,13 +38,5 @@ hooks.getSite = getSite
 last_cookie_value = None
 def setSite(site=None):
   _setSite(site)
-  cookie = getattr(site, '_dynamic_class_cookie', None)
-  if cookie is not None:
-    global last_cookie_value
-    if cookie.value != last_cookie_value:
-      # some other node changed a portal type
-      # reload locally the dynamic classes
-      from Products.ERP5Type.Dynamic.portaltypeclass import resetDynamicDocuments
-      resetDynamicDocuments(site, slave=True)
-      last_cookie_value = cookie.value
+  synchronizeDynamicModules(site)
 hooks.setSite = setSite




More information about the Erp5-report mailing list