michael@d2m.at  |  +43 (664) 948-8084
You are here: Home Blog 2008 10 09 Grok-by-Example: Demosite

Grok-by-Example: Demosite

by Michael Haubenwallner last modified Jun 26, 2010 10:42 PM

This post is part of a series of postings about more or less basic Grok apps that are ported from other python web frameworks. Motivation is that you can look at the original source and the grok code side-by-side and deduce from both. Source is available from svn.zope.org/grokapps/gbesite/.

screenshot-gbesite.jpg

This "site application" shows how to install multiple Grok applications and make them available from a single Grok instance (using ZEO and Apache). A test instance is available at gbe.d2m.at.

Review

Now that you have a few working Grok apps (Grok-By-Example), how about serving them all together from a single Grok instance?

 

Setup multiple applications for your site

 

One possible setup is to create the site as a Grok app on its own. You just construct the basic app layout (or let grokproject do it for you or simply checkout the 'gbesite' application). I strongly recommend to run your development from inside a virtualenv:

    $ svn co svn://svn.zope.org/repos/main/grokapps/gbesite
    $ cd gbesite
    $ virtualenv --no-site-packages .
    $ source bin/activate
You then apply the necessary changes for a multi-app setup. Lets start with 'setup.py'. Add the package name of the apps you want to run to the 'install-requires' section:
    install_requires=[...
                      'gbeguestbook',
                      'gbe99bottles',
                      'gbewiki',
                      'gbepastebin',
                      ...
                     ],

Now checkout the packages from SVN to your 'gbesite' folder. If the packages where available from PyPI or another package repository you could just skip this and the next step, buildout would fetch and install the packages on the next run:

    svn co svn://svn.zope.org/repos/main/grokapps/gbeguestbook
    svn co svn://svn.zope.org/repos/main/grokapps/gbe99bottles
    svn co svn://svn.zope.org/repos/main/grokapps/gbewiki
    svn co svn://svn.zope.org/repos/main/grokapps/gbepastebin

In 'buildout.cfg' add the same packages to 'develop':

    [buildout]
    develop = . gbeguestbook gbe99bottles gbewiki gbepastebin
Run bootstrap (if you have not already) and buildout:
    $ bin/python bootstrap.py
    $ bin/buildout
That's all for now, lets move on to create the 'gbesite' app itself.
Create the 'site' application
You basically only need to change the 'app.py' template file. Lets assume you created the app by running "grokproject site", you already have a 'site' application class, with an Index view and the associated 'app_templates/index.pt' template file.

You now want to setup all available example apps automatically when creating an instance of the site application. Adding an event subscription handler for the 'site' class does just that:

    @grok.subscribe(site, grok.IObjectAddedEvent)
    def handle(obj, event):
        applications=(('gbeguestbook.app.Application','Guestbook'),
                      ('gbe99bottles.app.Song','Song'),
                      ('gbewiki.app.WikiPage','Wiki'),
                      ('gbepastebin.app.Application','Pastebin'),
                      )
        for application, name in applications:
            app = zope.component.getUtility(grok.interfaces.IApplication,
                                            name=application)
            try:
                obj[name] = app()
            except DuplicationError:
                pass

The 'applications' list defines the example apps and their instance names. Whenever you create a new instance of your 'site' class the example apps will be created with their fixed names inside it.

 

Make your site ready for public

 

If you want to serve your apps to the public, your site also should provide a 'robots.txt' file for the webcrawlers.

Add another grok.View to your application class and give it the name 'robots.txt':

    class Robots(grok.View):
        grok.name('robots.txt')

Then create another template file in 'app_templates/robots.pt'. The template could be empty or hold instructions following the robots exclusion standard.

Next create a virtual host to serve the site from behind Apache:

    <VirtualHost *>
    ServerName    your.server.name
    ...    
    RewriteEngine On
    RewriteRule ^/(.*)  http://127.0.0.1:8080/<site>/++vh++http:your.server.name:80/++/$1 [P,L]
    </VirtualHost>

(with <site> having the name of your public site instance). This should make your apps available at root level. Your 'app_templates/index.pt' template already holds links to all installed example apps and serves as default page for the Grok instance. If you need to access the 'admin' screens again point your browser to:

    http://localhost:8080/applications

 

Enable ZEO

 

Finally you want to debug the running site. Some of the example apps have no means to delete existing objects - but you can simply delete objects from the debugger too.

Debugging a running zope instance needs a change in the server setup: you create a ZEO server that holds the ZODB (Data.fs) and 2 ZEO clients that access their data from the ZEO server. One client ('zopectl') will serve the site application, the other client ('instance2') will be used for debugging.

You need to change 'buildout.cfg', add and modify parts:

    [buildout]
    ...
    parts = ... zodb server instance2

[zodb] recipe = zc.recipe.egg:script eggs = ZODB3 [server] recipe = zc.zodbrecipes:server zeo.conf = <zeo> address 8100 </zeo> <filestorage 1> path ${buildout:parts-directory}/data/ZEOData.fs </filestorage>

[zopectl] recipe = zc.zope3recipes:instance application = app address = 8080 zope.conf = devmode on <zodb> <zeoclient> server 8100 </zeoclient> </zodb> site-definition ${buildout:parts-directory}/app/site.zcml <accesslog> <logfile> path ${buildout:parts-directory}/zopectl/access.log </logfile> </accesslog> <eventlog> <logfile> formatter zope.exceptions.log.Formatter path STDOUT </logfile> </eventlog> [instance2] recipe = zc.zope3recipes:instance extends = zopectl address = 9080

 

Finally

 

Run buildout again, run the tests, start the server, start the client:

    $ bin/buildout
    $ bin/test
    $ bin/server start
    $ bin/zopectl fg
Setup apache:
    $ sudo a2ensite your-vhost-id
    $ sudo /etc/init.d/apache2 restart
Access the site admin screens, create a 'site' instance and use it:
    http://your.server.name/applications
Hope that gets you up and running in record time - creating the site application was done in an hour. As always writing the docs took a bit longer ;)

Comment

Posted by kedai at 2008-10-09 09:52:22
Thanks for this entry. Really helped put 2 and 2 together

Comment

Posted by erez at 2008-11-01 07:38:02
Thanks for the post, I have been having the same problems.
Filed under: , ,