source: main/waeup.sirp/trunk/src/waeup/sirp/meta.py @ 7893

Last change on this file since 7893 was 7653, checked in by Henrik Bettermann, 13 years ago

Log user management. If possible use full sentences in log messages. Use the imperative form when process is going to be started and the passive form when the process is finished.

  • Property svn:keywords set to Id
File size: 4.5 KB
Line 
1## $Id: meta.py 7653 2012-02-15 11:03:57Z henrik $
2##
3## Copyright (C) 2011 Uli Fouquet & Henrik Bettermann
4## This program is free software; you can redistribute it and/or modify
5## it under the terms of the GNU General Public License as published by
6## the Free Software Foundation; either version 2 of the License, or
7## (at your option) any later version.
8##
9## This program is distributed in the hope that it will be useful,
10## but WITHOUT ANY WARRANTY; without even the implied warranty of
11## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12## GNU General Public License for more details.
13##
14## You should have received a copy of the GNU General Public License
15## along with this program; if not, write to the Free Software
16## Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17##
18"""Grokkers for SIRP components.
19
20Stuff in here is mainly taken from grok.meta, with some modifications
21to provide a possibility to update catalogs in a running site. This is
22to solve the very common problem of already running sites for which
23the software changes and adds catalogs. These catalogs will not be
24automatically added in a running site.
25
26With the following Grokker and the upgrade helper class we can fire
27IObjectUpgradedEvents for any existing site and all catalogs
28registered will be really created.
29
30Please note that yet these catalogs are not filled automatically! That
31means the catalogs will exist but are empty in the beginning.
32
33We might solve this second problem by firing extra events like some
34ICatalogUpdatedEvent (which still do not exist) or similar.
35"""
36import grok
37import martian
38from grok import components
39from grok.meta import IndexesSetupSubscriber
40from martian.error import GrokError
41from zope import component
42from waeup.sirp.interfaces import IObjectUpgradeEvent
43
44class IndexesGrokker(martian.InstanceGrokker):
45    """Grokker for Grok index bundles."""
46    martian.component(components.IndexesClass)
47
48    def grok(self, name, factory, module_info, config, **kw):
49        site = grok.site.bind().get(factory)
50        context = grok.context.bind().get(factory, module_info.getModule())
51        catalog_name = grok.name.bind().get(factory)
52
53        if site is None:
54            raise GrokError("No site specified for grok.Indexes "
55                            "subclass in module %r. "
56                            "Use grok.site() to specify."
57                            % module_info.getModule(),
58                            factory)
59        indexes = getattr(factory, '__grok_indexes__', None)
60        if indexes is None:
61            return False
62
63        subscriber = SIRPIndexesUpgradeSubscriber(
64            catalog_name, indexes, context, module_info)
65        subscribed = (site, IObjectUpgradeEvent)
66        config.action(
67            discriminator=None,
68            callable=component.provideHandler,
69            args=(subscriber, subscribed),
70            )
71        return True
72
73
74class SIRPIndexesUpgradeSubscriber(IndexesSetupSubscriber):
75    """Helper that sets up indexes when their Grok site is upgraded.
76
77    Each `grok.Indexes` class serves as an assertion that, whenever an
78    instance of its `grok.site()` is upgraded, the given list of
79    indexes should be generated if not already created as well.  But a
80    long period of time could elapse between when the application
81    starts (and its indexes are grokked), and the moment, maybe days
82    or weeks later, when a new instance of that `grok.Site` is
83    created.  Hence this `IndexesSetupSubscriber`: it can be
84    instantiated at grokking time with the index information, and then
85    registered with the Component Architecture as an event that should
86    be fired later, whenever the right kind of `grok.Site` is
87    instantiated.  At that point its `__call__` method is kicked off
88    and it makes sure the index catalogs get created properly.
89
90    """
91    def __call__(self, site, event):
92        site.logger.info('Create catalog `%s` if not installed yet.'  % (
93                self.catalog_name,))
94        # make sure we have an intids
95        self._createIntIds(site)
96        # get the catalog
97        catalog = self._createCatalog(site)
98        # now install indexes
99        for name, index in self.indexes.items():
100            try:
101                site.logger.info('Create index `%s` in catalog.' % name)
102                index.setup(catalog, name, self.context, self.module_info)
103                site.logger.info('Index created.')
104            except KeyError: #, DuplicationError:
105                site.logger.info('Index `%s` already in catalog.' % name)
106                pass
107        site.logger.info('Catalog `%s` ready.' % self.catalog_name)
Note: See TracBrowser for help on using the repository browser.