4.6 Building Applications with Page Modules

Implementing an application as a monolithic program is fine for small applications. As the application grows the startup time becomes an issue, as does maintenance. Albatross provides a set of classes that allow you to implement each page in a separate Python module. In this section we will convert the popview application to this type of application.

Converting a monolithic application to a page module application is usually fairly simple. First we must turn each page object into a page module. When we used page objects, the class that implemented each page was identified by the name class member. With page modules the name of the module identifies the page that it processes.

The complete sample program is contained in the samples/popview4 directory. Use the install.py script to install the sample.

cd samples/popview4
python install.py

The LoginPage class becomes login.py.

import poplib

def page_process(ctx):
    if ctx.req_equals('login'):
        if ctx.locals.username and ctx.locals.passwd:
            try:
                ctx.open_mbox()
                ctx.add_session_vars('username', 'passwd')
            except poplib.error_proto:
                return
            ctx.set_page('list')

def page_display(ctx):
    ctx.run_template('login.html')

The ListPage class becomes list.py.

def page_process(ctx):
    if ctx.req_equals('msgnum'):
        ctx.set_page('detail')

def page_display(ctx):
    ctx.open_mbox()
    ctx.run_template('list.html')

And the DetailPage class becomes detail.py.

def page_process(ctx):
    if ctx.req_equals('list'):
        ctx.set_page('list')

def page_display(ctx):
    ctx.open_mbox()
    ctx.read_msg()
    ctx.run_template('detail.html')

When using page modules we do not need to register each page module. When Albatross needs to locate the code for a page it simply imports the module. So the entire popview.py program now looks like this:

#!/usr/bin/python
from albatross import ModularSessionApp, SessionAppContext
from albatross.cgiapp import Request
import popviewlib

class AppContext(SessionAppContext):

    def open_mbox(self):
        if hasattr(self.locals, 'mbox'):
            return
        self.locals.mbox = popviewlib.Mbox(self.locals.username, self.locals.passwd)

    def read_msg(self):
        if hasattr(self.locals, 'msg'):
            return
        self.locals.msg = self.locals.mbox[int(self.locals.msgnum) - 1]
        self.locals.msg.read_body()

class App(ModularSessionApp):

    def __init__(self):
        ModularSessionApp.__init__(self,
                                   base_url = 'popview.py',
                                   module_path = '.',
                                   template_path = '.',
                                   start_page = 'login',
                                   secret = '-=-secret-=-',
                                   session_appid = 'popview4')

    def create_context(self):
        return AppContext(self)

app = App()

if __name__ == '__main__':
    app.run(Request())