===================== Site view, life cycle ===================== ... or, making the view a site manager is a good idea after all, but let's see what dangers are lurking in the dark. Checking if the view finishes its lifetime ------------------------------------------ It is important that the view does not stay on after the request. This would cause them to continue listening to events. We need a few imports first. >>> from kss.core.azaxview import SiteView >>> from zope.interface import Interface, implements >>> from zope.component import adapter >>> from zope.lifecycleevent import ObjectModifiedEvent >>> from zope.event import notify >>> from zope.app.publication.interfaces import IEndRequestEvent >>> try: ... from Products.Five.testbrowser import Browser ... except ImportError: ... from zope.testbrowser.browser import Browser First, let's create a funky view that has two methods, one failing and one succeeding, and a habit to choke on any events. >>> class FunkyView(SiteView): ... def IAmGood(self): ... 'XXX' ... return self.render() ... def IAmBad(self): ... 'XXX' ... raise Exception, 'Generic badness' ... @adapter(Interface) ... def _eventRedispatcher(self, event): ... SiteView._eventRedispatcher(self, event) ... if not IEndRequestEvent.providedBy(event): ... raise Exception, 'Too late event %r' % event >>> import kss.core.tests >>> kss.core.tests.FunkyView = FunkyView We provide this view as a browser page. We care to register it properly, otherwise we would miss some Five acquisition woodoo. (XXX Note that this must be adjusted to run on Zope3.) >>> try: ... import Products.Five ... except ImportError: ... # probably zope 3, not supported ... raise 'Zope3 not supported in this test' ... else: ... from Products.Five.zcml import load_string, load_config >>> load_string(''' ... ... ... ... ... ''') Create a test browser now, so we can finally start. >>> browser = Browser() Let's call up the good request. >>> browser.open(self.folder.absolute_url() + '/@@funky_view/IAmGood') Now, if we happen to send an event... nothing happens, since the render() method has taken care of unregistering the event as a SiteView. >>> notify(ObjectModifiedEvent(None)) But it is also important, that even in case the render method does not run (it gives an error since we raised an exception, this is all right). We would already get an error during this, thanks to the RequestEvent that arrives. >>> browser = browser.open('http://nohost/@@funky_view/IAmBad') Traceback (most recent call last): ... HTTPError: HTTP Error 500: Internal Server Error And even if we send a new event, it must not get to the redispatcher of the view. >>> notify(ObjectModifiedEvent(None))