[Twisted-web] Right way to implement layout objects with Nevow?

Leif K-Brooks eurleif at gmail.com
Fri Jul 29 21:24:25 MDT 2005


For the Nevow-based application I'm coding, I want to have a
standardized layout with a header and footer. The layout needs to be
implemented as an object, so that a new one can be swapped in without
having to change the code.

A simplified version of the code I'm using looks like this:


class Layout(rend.Fragment):
    docFactory = loaders.xmlstr('''
<html xmlns:nevow="http://nevow.com/ns/nevow/0.1">
<head>
<title>Foo</title>
</head>
<body>
<p>Header...</p>
<nevow:invisible nevow:data="body" nevow:render="data"/>
<p>Footer...</p>
</body>
</html>
''')
    def data_body(self, context, data):
        return self.original

class Resource(rend.Page):
    docFactory = loaders.xmlstr('''
<html  xmlns:nevow="http://nevow.com/ns/nevow/0.1" nevow:render="withLayout">
<body nevow:pattern="body">
<p>Hello, world!</p>
</body>
</html>
''')
    def render_withLayout(self, context, data):
        return Layout(inevow.IQ(context).onePattern('body').children)


This works fine for a simple static page like the one in the example,
but if I add nevow:render="foo" to an element in the page, it gets
looked up as as Layout.render_foo instead of as Resource.render_foo.

I can fix that by making Resource.render_withLayout call flatten() on
the page's body, but that causes Deferred data to stop working. Is
there a better approach?



More information about the Twisted-web mailing list