[CMF-checkins] SVN: CMF/branches/2.1/C - changed the way skins are
set up, using __before_publishing_traverse__ instead of __of__
Yvo Schubbe
y.2007- at wcm-solutions.de
Sun Jun 17 10:08:33 EDT 2007
Log message for revision 76729:
- changed the way skins are set up, using __before_publishing_traverse__ instead of __of__
Changed:
U CMF/branches/2.1/CHANGES.txt
U CMF/branches/2.1/CMFCalendar/tests/test_Calendar.py
U CMF/branches/2.1/CMFCore/DynamicType.py
U CMF/branches/2.1/CMFCore/PortalObject.py
U CMF/branches/2.1/CMFCore/Skinnable.py
U CMF/branches/2.1/CMFCore/tests/test_SkinsTool.py
U CMF/branches/2.1/CMFDefault/tests/RegistrationTool.txt
-=-
Modified: CMF/branches/2.1/CHANGES.txt
===================================================================
--- CMF/branches/2.1/CHANGES.txt 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CHANGES.txt 2007-06-17 14:08:32 UTC (rev 76729)
@@ -11,6 +11,12 @@
Bug Fixes
+ - SkinnableObjectManager: Changed the way skins are set up.
+ Acquisition wrapping no longer triggers 'setupCurrentSkin'. This is now
+ done on publishing traversal after the BeforeTraverseEvent triggers
+ 'setSite'. This fix replaces a temporary hack introduced in 2.1.0-beta,
+ making sure ISkinsTool is looked up after setting the site.
+
- CMFCore.CMFBTreeFolder: CMFBTreeFolders could not be used as the
toplevel /Members container.
(http://www.zope.org/Collectors/CMF/441)
Modified: CMF/branches/2.1/CMFCalendar/tests/test_Calendar.py
===================================================================
--- CMF/branches/2.1/CMFCalendar/tests/test_Calendar.py 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFCalendar/tests/test_Calendar.py 2007-06-17 14:08:32 UTC (rev 76729)
@@ -109,6 +109,7 @@
def afterSetUp(self):
setSite(self.app.site)
+ self.app.site.setupCurrentSkin(self.app.REQUEST)
newSecurityManager(None, UnrestrictedUser('god', '', ['Manager'], ''))
# sessioning setup
Modified: CMF/branches/2.1/CMFCore/DynamicType.py
===================================================================
--- CMF/branches/2.1/CMFCore/DynamicType.py 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFCore/DynamicType.py 2007-06-17 14:08:32 UTC (rev 76729)
@@ -19,11 +19,10 @@
from AccessControl import ClassSecurityInfo
from Globals import InitializeClass
-
-from zope.app.publication.zopepublication import BeforeTraverseEvent
+from zope.app.publisher.browser import queryDefaultViewName
from zope.component import getUtility
+from zope.component import queryMultiAdapter
from zope.component import queryUtility
-from zope.event import notify
from zope.interface import implements
from interfaces import IDynamicType
@@ -31,8 +30,6 @@
from interfaces import IURLTool
from interfaces.Dynamic import DynamicType as z2IDynamicType
-from zope.component import queryMultiAdapter
-from zope.app.publisher.browser import queryDefaultViewName
class DynamicType:
@@ -89,7 +86,7 @@
else:
msg = 'Action "%s" not available for %s' % (
action_chain, '/'.join(self.getPhysicalPath()))
- raise ValueError(msg)
+ raise ValueError(msg)
# Support for dynamic icons
@@ -124,8 +121,6 @@
# XXX hack around a bug(?) in BeforeTraverse.MultiHook
REQUEST = arg2 or arg1
- notify(BeforeTraverseEvent(self, REQUEST))
-
if REQUEST['REQUEST_METHOD'] not in ('GET', 'POST'):
return
Modified: CMF/branches/2.1/CMFCore/PortalObject.py
===================================================================
--- CMF/branches/2.1/CMFCore/PortalObject.py 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFCore/PortalObject.py 2007-06-17 14:08:32 UTC (rev 76729)
@@ -21,7 +21,9 @@
from five.localsitemanager.registry import PersistentComponents
from Globals import InitializeClass
from Products.Five.component.interfaces import IObjectManagerSite
+from zope.app.publication.zopepublication import BeforeTraverseEvent
from zope.component.globalregistry import base
+from zope.event import notify
from zope.interface import implements
from interfaces import ISiteRoot
@@ -44,7 +46,6 @@
# Ensure certain attributes come from the correct base class.
__getattr__ = SkinnableObjectManager.__getattr__
- __of__ = SkinnableObjectManager.__of__
_checkId = SkinnableObjectManager._checkId
# Ensure all necessary permissions exist.
@@ -73,4 +74,16 @@
self._components.__parent__ = self
return self._components
+ def __before_publishing_traverse__(self, arg1, arg2=None):
+ """ Pre-traversal hook.
+ """
+ # XXX hack around a bug(?) in BeforeTraverse.MultiHook
+ REQUEST = arg2 or arg1
+
+ notify(BeforeTraverseEvent(self, REQUEST))
+ self.setupCurrentSkin(REQUEST)
+
+ super(PortalObjectBase,
+ self).__before_publishing_traverse__(arg1, arg2)
+
InitializeClass(PortalObjectBase)
Modified: CMF/branches/2.1/CMFCore/Skinnable.py
===================================================================
--- CMF/branches/2.1/CMFCore/Skinnable.py 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFCore/Skinnable.py 2007-06-17 14:08:32 UTC (rev 76729)
@@ -25,7 +25,6 @@
from AccessControl import ClassSecurityInfo
from Acquisition import aq_base
-from Acquisition import ImplicitAcquisitionWrapper
from Globals import InitializeClass
from OFS.ObjectManager import ObjectManager
from ZODB.POSException import ConflictError
@@ -47,7 +46,7 @@
except AttributeError:
superGetAttr = None
-_marker = [] # Create a new marker object.
+_MARKER = object() # Create a new marker object.
SKINDATA = {} # mapping thread-id -> (skinobj, skinname, ignore, resolve)
@@ -90,8 +89,8 @@
if not ignore.has_key(name):
if resolve.has_key(name):
return resolve[name]
- subob = getattr(ob, name, _marker)
- if subob is not _marker:
+ subob = getattr(ob, name, _MARKER)
+ if subob is not _MARKER:
# Return it in context of self, forgetting
# its location and acting as if it were located
# in self.
@@ -110,11 +109,6 @@
"""
skinob = None
sf = queryUtility(ISkinsTool)
- if sf is None:
- # XXX: Maybe we can set up the skin *after* the sm?
- # try again with self as explicit site
- sm = getSiteManager(self)
- sf = sm.queryUtility(ISkinsTool)
if sf is not None:
if name is not None:
@@ -130,16 +124,12 @@
def getSkinNameFromRequest(self, REQUEST=None):
'''Returns the skin name from the Request.'''
sf = queryUtility(ISkinsTool)
- if sf is None:
- # XXX: Maybe we can set up the skin *after* the sm?
- # try again with self as explicit site
- sm = getSiteManager(self)
- sf = sm.queryUtility(ISkinsTool)
+
if sf is not None:
return REQUEST.get(sf.getRequestVarname(), None)
security.declarePublic('changeSkin')
- def changeSkin(self, skinname):
+ def changeSkin(self, skinname, REQUEST=_MARKER):
'''Change the current skin.
Can be called manually, allowing the user to change
@@ -149,7 +139,11 @@
if skinobj is not None:
tid = get_ident()
SKINDATA[tid] = (skinobj, skinname, {}, {})
- REQUEST = getattr(self, 'REQUEST', None)
+ if REQUEST is _MARKER:
+ REQUEST = getattr(self, 'REQUEST', None)
+ warn("changeSkin should be called with 'REQUEST' as second "
+ "argument. The BBB code will be removed in CMF 2.3.",
+ DeprecationWarning, stacklevel=2)
if REQUEST is not None:
REQUEST._hold(SkinDataCleanup(tid))
@@ -177,15 +171,18 @@
del SKINDATA[tid]
security.declarePublic('setupCurrentSkin')
- def setupCurrentSkin(self, REQUEST=None):
+ def setupCurrentSkin(self, REQUEST=_MARKER):
'''
Sets up skindata so that __getattr__ can find it.
Can NOT be called manually to change skins in the middle of a
request! Use changeSkin for that.
'''
- if REQUEST is None:
+ if REQUEST is _MARKER:
REQUEST = getattr(self, 'REQUEST', None)
+ warn("setupCurrentSkin should be called with 'REQUEST' as "
+ "argument. The BBB code will be removed in CMF 2.3.",
+ DeprecationWarning, stacklevel=2)
if REQUEST is None:
# self is not fully wrapped at the moment. Don't
# change anything.
@@ -194,23 +191,14 @@
# Already set up for this request.
return
skinname = self.getSkinNameFromRequest(REQUEST)
- self.changeSkin(skinname)
-
- def __of__(self, parent):
- '''
- Sneakily sets up the portal skin then returns the wrapper
- that Acquisition.Implicit.__of__() would return.
- '''
- w_self = ImplicitAcquisitionWrapper(self, parent)
try:
- w_self.setupCurrentSkin()
+ self.changeSkin(skinname, REQUEST)
except ConflictError:
raise
except:
# This shouldn't happen, even if the requested skin
# does not exist.
logger.exception("Unable to setupCurrentSkin()")
- return w_self
def _checkId(self, id, allow_dup=0):
'''
Modified: CMF/branches/2.1/CMFCore/tests/test_SkinsTool.py
===================================================================
--- CMF/branches/2.1/CMFCore/tests/test_SkinsTool.py 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFCore/tests/test_SkinsTool.py 2007-06-17 14:08:32 UTC (rev 76729)
@@ -129,7 +129,7 @@
self.failUnless(som.getCurrentSkinName() == 'skinA')
# after a changeSkin the new skin name should be returned
- som.changeSkin('skinB')
+ som.changeSkin('skinB', som.REQUEST)
self.failUnless(som.getCurrentSkinName() == 'skinB')
Modified: CMF/branches/2.1/CMFDefault/tests/RegistrationTool.txt
===================================================================
--- CMF/branches/2.1/CMFDefault/tests/RegistrationTool.txt 2007-06-17 13:35:02 UTC (rev 76728)
+++ CMF/branches/2.1/CMFDefault/tests/RegistrationTool.txt 2007-06-17 14:08:32 UTC (rev 76729)
@@ -32,6 +32,7 @@
>>> from Products.CMFCore.interfaces import IMembershipTool
>>> from Products.MailHost.interfaces import IMailHost
>>> setSite(app.site)
+ >>> app.site.setupCurrentSkin(app.REQUEST)
>>> sm = getSiteManager()
>>> sm.registerUtility(MembershipTool(), IMembershipTool)
>>> sm.registerUtility(MailHost(), IMailHost)
More information about the CMF-checkins
mailing list