[Checkins] SVN: grok/trunk/src/grok/ Fix
https://launchpad.net/grok/+bug/83953:
Philipp von Weitershausen
philikon at philikon.de
Thu Feb 8 12:43:25 EST 2007
Log message for revision 72468:
Fix https://launchpad.net/grok/+bug/83953:
Custom grokkers should be registered only once.
Changed:
U grok/trunk/src/grok/grokker.py
A grok/trunk/src/grok/tests/grokker/onlyonce.py
A grok/trunk/src/grok/tests/grokker/onlyonce_fixture/
A grok/trunk/src/grok/tests/grokker/onlyonce_fixture/__init__.py
A grok/trunk/src/grok/tests/grokker/onlyonce_fixture/_meta.py
A grok/trunk/src/grok/tests/grokker/onlyonce_fixture/component.py
A grok/trunk/src/grok/tests/grokker/onlyonce_fixture/implementation.py
-=-
Modified: grok/trunk/src/grok/grokker.py
===================================================================
--- grok/trunk/src/grok/grokker.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/grokker.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -7,18 +7,24 @@
self.clear()
def clear(self):
- self._grokkers = []
+ self._grokkers = {}
# register the meta grokkers manually as we can't grok those
self.registerGrokker(ClassGrokkerGrokker())
self.registerGrokker(InstanceGrokkerGrokker())
self.registerGrokker(ModuleGrokkerGrokker())
-
+
def registerGrokker(self, grokker):
- self._grokkers.append(grokker)
+ # we're using a dictionary to make sure each type of grokker
+ # is registered only once (e.g. during meta-grok-time, and not again
+ # during grok-time).
+ key = grokker.__class__
+ if key in self._grokkers:
+ return
+ self._grokkers[key] = grokker
def _getGrokkersInOrder(self):
# sort grokkers by priority
- grokkers = sorted(self._grokkers,
+ grokkers = sorted(self._grokkers.values(),
key=lambda grokker: grokker.priority)
# we want to handle high priority first
grokkers.reverse()
@@ -26,7 +32,7 @@
def scan(self, module_info):
components = {}
- for grokker in self._grokkers:
+ for grokker in self._grokkers.values():
if isinstance(grokker, grok.ModuleGrokker):
continue
components[grokker.component_class] = []
@@ -34,9 +40,9 @@
grokkers = self._getGrokkersInOrder()
module = module_info.getModule()
for name in dir(module):
- obj = getattr(module, name)
if name.startswith('__grok_'):
continue
+ obj = getattr(module, name)
if not util.defined_locally(obj, module_info.dotted_name):
continue
# XXX find way to get rid of this inner loop by doing hash table
@@ -59,9 +65,9 @@
scanned_results.get(grok.LocalUtility, []) +
scanned_results.get(grok.Container, []))]
context = util.determine_module_context(module_info, possible_contexts)
-
+
templates = templatereg.TemplateRegistry()
-
+
# run through all grokkers registering found components in order
for grokker in self._getGrokkersInOrder():
# if we run into a ModuleGrokker, just do simple registration.
@@ -71,8 +77,9 @@
if isinstance(grokker, grok.ModuleGrokker):
grokker.register(context, module_info, templates)
continue
-
+
components = scanned_results.get(grokker.component_class, [])
+
for name, component in components:
# this is a base class as it ends with Base, skip
if type(component) is type:
@@ -100,7 +107,7 @@
class MetaGrokker(grok.ClassGrokker):
def register(self, context, name, factory, module_info, templates):
grokkerRegistry.registerGrokker(factory())
-
+
class ClassGrokkerGrokker(MetaGrokker):
component_class = grok.ClassGrokker
@@ -109,7 +116,7 @@
class ModuleGrokkerGrokker(MetaGrokker):
component_class = grok.ModuleGrokker
-
+
# the global grokker registry
grokkerRegistry = GrokkerRegistry()
Added: grok/trunk/src/grok/tests/grokker/onlyonce.py
===================================================================
--- grok/trunk/src/grok/tests/grokker/onlyonce.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/tests/grokker/onlyonce.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -0,0 +1,27 @@
+"""
+
+We define a grokker AlphaGrokker for a component called Alpha. We first need to
+grok the module defining the grokkers, in order to get them registered.
+
+Usually this would be triggered from a meta.zcml in a package, that would grok
+the module containing the grokkers (e.g. meta.py).
+
+We do it manually now::
+
+ >>> import grok
+ >>> grok.grok('grok.tests.grokker.onlyonce_fixture._meta')
+
+This _meta.py module then will be grokked again during 'normal' grok time. Grok
+will not re-register the grokkers as this could have unwanted side-effects. It
+will grok the components of course.
+
+NOTE: the module is called _meta to make sure it is grokked (although its
+grokker registration should be ignored) before the other files. The modules are
+picked up in alphabetical order.
+
+To simulate this, we grok the whole package::
+
+ >>> grok.grok('grok.tests.grokker.onlyonce_fixture')
+ alpha
+
+"""
Property changes on: grok/trunk/src/grok/tests/grokker/onlyonce.py
___________________________________________________________________
Name: svn:eol-style
+ native
Added: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/__init__.py
===================================================================
--- grok/trunk/src/grok/tests/grokker/onlyonce_fixture/__init__.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/tests/grokker/onlyonce_fixture/__init__.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -0,0 +1 @@
+# fixture package
\ No newline at end of file
Property changes on: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/__init__.py
___________________________________________________________________
Name: svn:eol-style
+ native
Added: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/_meta.py
===================================================================
--- grok/trunk/src/grok/tests/grokker/onlyonce_fixture/_meta.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/tests/grokker/onlyonce_fixture/_meta.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -0,0 +1,8 @@
+import grok
+from component import Alpha
+
+class AlphaGrokker(grok.ClassGrokker):
+ component_class = Alpha
+
+ def register(self, context, name, factory, module_info, templates):
+ print "alpha"
Property changes on: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/_meta.py
___________________________________________________________________
Name: svn:eol-style
+ native
Added: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/component.py
===================================================================
--- grok/trunk/src/grok/tests/grokker/onlyonce_fixture/component.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/tests/grokker/onlyonce_fixture/component.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -0,0 +1,4 @@
+import grok
+
+class Alpha(object):
+ grok.baseclass()
Property changes on: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/component.py
___________________________________________________________________
Name: svn:eol-style
+ native
Added: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/implementation.py
===================================================================
--- grok/trunk/src/grok/tests/grokker/onlyonce_fixture/implementation.py 2007-02-08 17:31:12 UTC (rev 72467)
+++ grok/trunk/src/grok/tests/grokker/onlyonce_fixture/implementation.py 2007-02-08 17:43:24 UTC (rev 72468)
@@ -0,0 +1,4 @@
+from component import Alpha
+
+class AlphaSub(Alpha):
+ pass
\ No newline at end of file
Property changes on: grok/trunk/src/grok/tests/grokker/onlyonce_fixture/implementation.py
___________________________________________________________________
Name: svn:eol-style
+ native
More information about the Checkins
mailing list