Search code examples
pythonturbogears2genshi

Block tags in turbogears/genshi (py:match)?


Ok, I'm coming from Django, so please excuse me if what I write doesn't make sense. I'm trying to "override" a portion of my master template in turbogears using genshi. So far I've only tried the py:match directive with no success:

master template:

<div id="menu">
    <div class="menu-items" py:match="topmenu" py:attrs="select('@*')">
        ${select('*')}
    </div>
</div>

child template:

<topmenu> <span> HELLO! </span> </topmenu>

This renders <span> HELLO! </span> outside of the menu div. What am I doing wrong?


Solution

  • Genshi py:match is a bit harsh to understand. The TurboGears2 documentation explains the concept quite well: "given an XPath expression, it finds and replaces every element in the template that matches the expression – with the content of the element containing the py:match."

    This means that actually the element that has the py:match replaces the one that doesn't have it. So if you want to put the menu inside the master from the child template you should invert the two:

    MASTER:

    <body py:match="body" py:attrs="select('@*')">
        <topmenu id="menu-items"></topmenu>
    </body>
    

    CHILD:

    <body>
        <div py:match="topmenu" py:attrs="select('@*')"><span>item1</span></div>
    </body>
    

    Using py:match is often more complex than what you need, I suggest you to take a look at the header and footer implementation inside the quickstart template, they use an easier way to manage reusable template parts.

    For the menu specific case you can also take a look at tgext.menu it makes quite easy to handle menus and navbars inside turbogears applications.