Getting a hang of Zope's Grok

Grok from Wikipedia : For example, to say that you "know" Lisp is simply to assert that you can code in it if necessary — but to say you "grok" LISP is to claim that you have deeply entered the world-view and spirit of the language, with the implication that it has transformed your view of programming.

Getting started with Django or, for that matter, Rails, will typically involve creating a model. This is likely to be just a relational table. The framework will create a form with the option to insert, edit and delete the records. We have a working application in a matter of minutes.

The tutorial of Grok ( as a surprise. It starts with views and templates instead. Persistence of data magically happens behind the scenes using ZODB. The tutorial exposes us to the basic usage of Zope Page Templates and its relationship to the Python code. We get a flavour of Grok quickly though building a working application takes more effort.

Comparing with the MVC paradigm, we seem to be able to relate to the idea of models and views but controllers seem to be missing - The url's seem to point to model objects in the grok application views. It brings up the interesting issue when trying different frameworks. While it may take just a few lines of code to implement some concept, it can be hard in the beginning to find what those lines are or where they go. So, the chances are that the first framework we learn will seem much easier and more 'natural' than the rest!

While Grok makes it easier to build Zope3 applications, understanding of the Zope concepts is needed. Zope seems sufficiently different that it is not surprising to come across a site like the following -

ZopeInAnger is meant to help you develop Zope programs without necessarily understanding the full API (as if that were possible for mere mortals)...”

The geeky humour makes sure that I do not give up.

While Grok's tutorial was fine, several user contributed example applications had issues with the current versions. The issues were minor, but they can be intimidating when one is just getting started.


As the main conceptually different factor from other major frameworks is the persistence mechanism,

The persistence model of Grok/Zope3 can be thought of as a database consisting of containers and persistent objects. A container can be thought of as a python dictionary with key value pairs, much like gdbm or Berkeley DB. The value in this case is any python object that can be pickled. The key is used for navigating through the objects. While ZODB is normally used by Zope applications, it is possible to replace ZODB with a relational database and an object relational mapper, e.g. SQLAlchemy.

A persistent object is defined by a class which inherits from grok.Model. Consider a simple example of LFY application which stores articles. A code fragment may look like:

class LFY(grok.Application, grok.Container):

def add_object(self, name, article):
self[name] = article

class Ariticle(grok.Model):

title = ''
content = ''

If we want to be able to create a form dynamically for the model, we need to do a little more effort. We need to define the object in a zope interface with specification of the schema data types. We then implement the interface in the model. The code fragment for the interface would be

class IArticle(interface.Interface):

title = schema.TextLine(title=u"Title")
content = schema.TextLine(title=u"Content")
The model will now be:

class Ariticle(grok.Model):

title = ''
content = ''
Suppose each article can have comments. We can model the comments as a python dictionary. However, suppose the number of comments can be very large, we can then use a container for storing the comment objects.

In case the data needs to be stored in a relational database and ZODB is not an option. Grok provides an option to use an object relational mapper, e.g. SQLAlchemy.

For completeness, it is worth noting that it is possible to use ZODB with Django!


As expected, it is easy to create the add and edit forms. The code and the visual elements are well separated thanks to Zope Page Templates(ZPT), which encourage clean separation of content, graphic design, and program code. ZPT standards are TAL (Template Attribute Language), TALES (TAL Expression Syntax) and METAL (Macro Expansion TAL). Here is an example illustrating the display of all articles, with each row clickable:

<p>Available Articles:</p>
<li tal:repeat="key python:context.keys()">

<a tal:attributes="href python:view.url(key)" tal:content="python:key">Article Name</a>


One can guess that the name of the article, which is the key for storing articles in the container, is displayed on each line. The key replaces the sample text 'Article Name' in the template. Clicking on a name would call a url as determined by a python method.

The syntax is pure xml and fits well into html. This is in contrast to some template engines which tend to use some special characters, e.g. curly brackets to differentiate the template code from html code (

Whether not using xml in a template engine makes it easier is questionable since the template language and html have to be in the same file.. However, if both html and template engine were replaced by something like YAML, it would definitely be a step forward in ease of coding and understanding.

For learning more about Grok, I would recommend exploring the following tutorial, but after going through the official Grok tutorial mentioned in the beginning.

It is worth learning alternate frameworks like Grok even if one does not use them, simply because it can help one grok the framework that one uses!