Hello fellow Pyramid users,

I'm currently in the process of writing a web application proof-of-concept 
using Pyramid 1.4 + MongoDB, which is starting to morph into a something 
resembling a 'web application framework on top of Pyramid' more than just a 
'web application using Pyramid'. As a result, I find myself re-defining and 
extending some of the core Pyramid functionality, which up to now was 
relatively painless (one of the nicest features of Pyramid IMO, it's not 
very opinionated). Today I hit a strange corner case though, which I 
haven't been able to workaround the way I'd like to.

Some background: instead of setting up routes from Python code, I'm using 
JSON hyper-schema to automatically generate routes from my resource 
schema's. The routes are embedded in the hyper-schema 'link' relations, as 
URI templates very much like what pyramid.config.Configurator.add_route 
uses. Because the routes for each resource are completely embedded into 
their schema, and are also used to generate link relations from resource 
instance attributes, the route URI templates use resource attribute names 
and hence may be ambiguous when used in functions referring different 
resource classes. Example: I have an 'account' resource with a 'self' 
relation defined by a route '{name}', and a 'projects' relation defined by 
a route '{name}/projects'. At the same time I have a 'project' resource 
that has a 'self' relation defined by a route '{account}/projects/{name}'. 
In other words: the 'name' variable refers to an account name in the first 
2 URI templates, but to a project name in the last one. 

For reasons not relevant for this discussion I don't want to change the 
route URI template definitions, and I don't want to embed additional 
information in the resource schema's to disambiguate URI template 
variables. Somehow, I want to be able to include an URI template variable 
mapping where the view callable is declared using the view_config 
decorator, so I can lookup which entries in the request matchdict 
correspond with which attributes of my resource classes. So I tried to 
create my own view_config decorator that extends pyramid.view.view_config, 
looking somewhat like this:

import pyramid.view
class view_config(pyramid.view.view_config):
  def __init__(self, matchdict_attributes, **kwargs):
    super(view_config, self).__init__(**kwargs)
    self.matchdict_attributes = matchdict_attributes
  def __call__(self, wrapped):
    f = super(view_config, self).__call__(wrapped)
    m = self.matchdict_attributes
    def wrapped_f(*args):
      return f(*args, matchdict_attributes=m)
    return wrapped_f

 


The basic idea is that I simply want to add an extra initialisation 
parameter to my view_config decorator, which is passed to the wrapped 
method when it is called.

For some reason when I use this decorator, the view callable is not found 
by the route scan anymore. I don't get any syntax errors or runtime errors, 
it's just that the any view callables declared with this decorator appear 
to be ignored. Suspecting a problem in my decorator, I reduced it to the 
following:

class view_config(pyramid.view.view_config):
  def __init__(self, **kwargs):
    super(view_config, self).__init__(**kwargs)

  def __call__(self, wrapped):
    return super(view_config, self).__call__(wrapped)


This decorator basically does nothing but directly wrap the Pyramid 
view_config decorator, but even using this decorator, my view callables are 
ignored by Pyramid.

So I removed the __call__ method altogether, and declaring my view 
callables with that decorator everything works. So it seems something is 
going on in pyramid.view.view_config.__call__ which breaks the 
configuration scan for view callables if you override the __call__ method 
of the standard view_config decorator.

I looked up the source code of the pyramid.view.view_config.__call__ 
decorator method and pasted it verbatim in my derived decorator class, and 
that works as well. I can't get it to work without duplicating any Pyramid 
framework code though.

Looking at the pyramid.view.view_config.__call__ code, there's a few things 
I don't really follow, some venusian callback stuff that uses the module 
name, but nothing directly indicating why I cannot override the method in 
my own class without breaking route scanning...

Does anyone know what's going on here? What am I missing?

Thanks and regards, Wouter Bijlsma

-- 
You received this message because you are subscribed to the Google Groups 
"pylons-discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to pylons-discuss+unsubscr...@googlegroups.com.
To post to this group, send email to pylons-discuss@googlegroups.com.
Visit this group at http://groups.google.com/group/pylons-discuss.
For more options, visit https://groups.google.com/groups/opt_out.


Reply via email to