Writing Zope Products
Last month, we continued our discussion of the Zope web development environment by installing and examining Zope products. As we saw, each product is actually a Python object module that can be instantiated one or more times on a Zope server. Hundreds of products are available for Zope, ranging from a small and lightweight fortune-teller to the large and impressive content management framework (CMF).
Many Zope administrators are content to install and use the products that they can download from the Web. And indeed, there are enough products to satisfy most basic sites; whatever you cannot do with an existing product is often simple enough to create in DTML, Zope's Dynamic Template Markup Language (described in the February 2002 issue of LJ).
But as easy and straightforward as it may be to do many tasks in DTML, it is neither as complete nor as flexible as Python. And while the addition of PythonScripts (and PerlScripts!) in Zope has certainly reduced the need to write products for many medium-sized tasks, most Zope hackers eventually find themselves writing a product of some sort.
This month, we look at how to build a simple Zope product that we can then integrate into our site. As you will see, it is quite easy to create a Zope product that integrates well into the rest of this environment.
At its core, a Zope product is a Python module. The product (as we saw last month) is installed into the lib/python/Products directory under the main Zope directory. Zope looks for products when it is started (or restarted), which means that you must start or restart Zope after installing a new product.
We can instantiate an installed product as many times as we like, placing each instance somewhere in the web hierarchy. Each instance has a unique “id” attribute that both uniquely identifies it within a folder and allows us to invoke methods on the object.
If this already sounds confusing, remember that the URL /foo/bar normally means that a web server should retrieve the file “bar” within the directory “foo”. But in Zope, the URL foo/bar means that the system should invoke the method “bar” on the object “foo”. In other words, foo/bar gets turned into foo.bar. And when we say “the object foo”, we really mean to say, “the object whose ID is foo”. Setting the ID is essential if we are going to invoke methods on our object successfully.
We also will need to define a meta_type for our product. The meta_type name is the text string that will appear in the Add pull-down list of Zope products in the upper-right corner of the /manage screen. In general, you can name the meta_type the same as your class or perhaps something a bit easier to understand. Remember that items in the Add menu are displayed in ASCII order, which means that capital “Z” comes before lowercase “a”.
To create our own product, we need to do the following:
Define a class in its own module and install it in lib/python/Products.
Define an __init__ method in which we assign the “id” instance variable a value.
Define one or more methods whose return value is a text string containing HTML.
Define a meta_type class variable, which sets the meta_type for all instances of our product.
This turns out to be surprisingly simple to do, as you can see in Listing 1, which defines helloworld.py, a simple Zope product that you can install and almost instantiate in your site. (We'll soon see how to get around these limitations.)
Listing 1. helloworld.py, a Simple Zope Product
There are several important items to notice in our helloworld class. For starters, the class and its methods contain documentation strings. It's always a good idea to write docstrings, and Python's inclusion of such a feature is a rare and refreshing reminder that programmers can and should include documentation along with the source code. Zope enforces this restriction by mandating that classes and methods must include docstrings if you want them to be used in the system.
Our class also defines two methods, __init__ and index_html. The __init__ method is invoked automatically by Zope when it creates an instance of our object and typically is used to initialize instance variables and define other behaviors that will be needed later on. In this particular case, __init__ defines a single instance variable (self.id) that allows our object to keep track of its identity. As you might expect, __init__ is not meant to be invoked from the outside world, but rather from within Zope itself.
The index_html method, by contrast, is designed to be invoked via a URL. If we place an instance of “helloworld” in the root (/) directory of our Zope server, we can invoke the index_html method on it with a URL of /helloworld/index_html. But index_html is special; like the index.html file on many Apache servers, it is invoked by default if no other method is named explicitly.
Finally, notice that index_html returns HTML to its caller. It does not return a status code or anything other than the HTML.
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Sponsored by AMD
Built-in forensics, incident response, and security with Red Hat Enterprise Linux 6
Every security policy provides guidance and requirements for ensuring adequate protection of information and data, as well as high-level technical and administrative security requirements for a system in a given environment. Traditionally, providing security for a system focuses on the confidentiality of the information on it. However, protecting the data integrity and system and data availability is just as important. For example, when processing United States intelligence information, there are three attributes that require protection: confidentiality, integrity, and availability.
Learn more about catching the bad guy in this free white paper.
Sponsored by DLT Solutions
| Designing Electronics with Linux | May 22, 2013 |
| Dynamic DNS—an Object Lesson in Problem Solving | May 21, 2013 |
| Using Salt Stack and Vagrant for Drupal Development | May 20, 2013 |
| Making Linux and Android Get Along (It's Not as Hard as It Sounds) | May 16, 2013 |
| Drupal Is a Framework: Why Everyone Needs to Understand This | May 15, 2013 |
| Home, My Backup Data Center | May 13, 2013 |
- New Products
- Linux Systems Administrator
- Senior Perl Developer
- Technical Support Rep
- UX Designer
- Web & UI Developer (JavaScript & j Query)
- Designing Electronics with Linux
- Dynamic DNS—an Object Lesson in Problem Solving
- Making Linux and Android Get Along (It's Not as Hard as It Sounds)
- Using Salt Stack and Vagrant for Drupal Development
- Reply to comment | Linux Journal
6 hours 22 min ago - Nice article, thanks for the
17 hours 2 min ago - I once had a better way I
22 hours 48 min ago - Not only you I too assumed
23 hours 6 min ago - another very interesting
1 day 59 min ago - Reply to comment | Linux Journal
1 day 2 hours ago - Reply to comment | Linux Journal
1 day 9 hours ago - Reply to comment | Linux Journal
1 day 10 hours ago - Favorite (and easily brute-forced) pw's
1 day 11 hours ago - Have you tried Boxen? It's a
1 day 17 hours ago
Enter to Win an Adafruit Pi Cobbler Breakout Kit for Raspberry Pi

It's Raspberry Pi month at Linux Journal. Each week in May, Adafruit will be giving away a Pi-related prize to a lucky, randomly drawn LJ reader. Winners will be announced weekly.
Fill out the fields below to enter to win this week's prize-- a Pi Cobbler Breakout Kit for Raspberry Pi.
Congratulations to our winners so far:
- 5-8-13, Pi Starter Pack: Jack Davis
- 5-15-13, Pi Model B 512MB RAM: Patrick Dunn
- 5-21-13, Prototyping Pi Plate Kit: Philip Kirby
- Next winner announced on 5-27-13!
Featured Jobs
| Linux Systems Administrator | Houston and Austin, Texas | Host Gator |
| Senior Perl Developer | Austin, Texas | Host Gator |
| Technical Support Rep | Houston and Austin, Texas | Host Gator |
| UX Designer | Austin, Texas | Host Gator |
| Web & UI Developer (JavaScript & j Query) | Austin, Texas | Host Gator |
Free Webinar: Hadoop
How to Build an Optimal Hadoop Cluster to Store and Maintain Unlimited Amounts of Data Using Microservers
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Some of key questions to be discussed are:
- What is the “typical” Hadoop cluster and what should be installed on the different machine types?
- Why should you consider the typical workload patterns when making your hardware decisions?
- Are all microservers created equal for Hadoop deployments?
- How do I plan for expansion if I require more compute, memory, storage or networking?




Comments
Re: At the Forge: Writing Zope Products
Very nice article!
Greate list of the ready for use Zope products can be found on content management software info