Search code examples
pythonbottle

bottle templating


I recently got into bottlepy and this is pretty much my first experience with a template engine.(Prior I would simply make what I needed in traditional PHP)

My question is this, let's say I have a base layout(A simple HTML/CSS layout), and, for example; a login box on the side. How do I keep the login box dynamically up to date without having to pass values to it on every route?

Take this for example:

from bottle import route,template

@route('/')
def main():

    return template("content.tpl") #rebase from layout.tpl

layout.tpl:

<html>
    <head>
        <title>{{title}}</title>
    </head>
    <body>
        %include
        <div id='sidebar'><!-- login box --></div>
    </body>
</html>

I guess my main question here is how do I make sure the login box runs without having to insert the variables for it at every single page


Solution

  • I'm not familiar with bottle, but for other templating engine this sort of thing is done via inheritance.

    For example,

    Imagine you have a base template called content.tpl that looks something like what you have for your layout.tpl:

    <html>
        <head>
            <title>{{title}}</title>
        </head>
        <body>
            <div id='sidebar'>%% section "sidebar" %%</div>
            <div id='content'>%% section "content" %%</div>
        </body>
    </html>
    

    Note that this is pseudocode - the stuff marked out by %% ... %% is made up & doesn't correspond to any particular templating engine (AFAIK).

    For your login page, you would have another template file called login.tpl:

    %% extends "content.tpl" %%
    
    %% start section "sidebar" %%
        <!-- whatever you put here will be rendered -->
        <!-- in the "sidebar" section of the parent -->
    %% end section "sidebar" %%
    
    %% start section "content" %%
        <!-- whatever you put here will be rendered -->
        <!-- in the "content" section of the parent -->
    
        <form> ... </form>
    %% end section "content" %%
    

    Then, in your route for your login page, you would do something like this:

    `return template("login.tpl")`
    

    This will cause the template engine to load login.tpl, fill in the values it has, and then load the content.tpl and stick the stuff it put together for the "sidebar" and "content" sections into the appropriate spots.

    There is another mechanism for composing a page from multiple templates: including a file. This would be similar to the example above, exception your login page would look something like this:

    <html>
        <head>
            <title>{{title}}</title>
        </head>
        <body>
            <div id='sidebar'>%% include "sidebar.tpl" %%</div>
            <div id='content'>%% include "content.tpl" %%</div>
        </body>
    </html>
    

    The main differences between them are:

    1. when you're inheriting, you don't have repeat everything on every page - stuff that's constant for all pages can be inherited from the parent layout.

    2. when you're inheriting, you can also include stuff from multiple templates into one. For example, imagine that you have templates that inherit like this "main.tpl" -> "template1.tpl" -> "template2.tpl". It is possible in some template engines to set it up so that each template can add to a section, so that the contents can be a composite of the whole family of templates.

    Of course, it is possible to use a mix of these techniques as well.