[Zope-dev] Q: Specialists, Racks, and ZCatalogs?

Steve Alexander steve@cat-box.net
Sat, 03 Feb 2001 20:25:33 +0000


Michael Bernstein wrote:

>
> Thanks, Steve. I'll try this a little later today. What are
> your thoughts on placing this in the Specialist's 'Plug-ins'
> tab vs. the Rack's?

A Specialist manages objects that play a particular role in your application.
You will usually have one Specialist for each role in your application; try
listing all the roles, and what they do, and that's a good start for thinking
about what specialists you need.

A Rack manages the storage for a particular class of objects.
Therefore, you will have different racks for different classes
of object. You will also have different racks for different
ways of storing the same class of object.

For example, let's say I have a Specialist "GoPlayers", which manages
objects that represent people who play the board-game Go with other people.

I have two implementation classes: AmateurGoPlayer and ProfessionalGoPlayer.
Objects of these classes have exactly the same interface to the rest of the application.
However, the implementation of some of the methods varies.

So, I'll need two racks in my GoPlayers specialist: one for 
AmateurGoPlayers and one for ProfessionalGoPlayers.

Let's complicate things by saying that I have the records for some 
ProfessionalGoPlayers in a relational database, but the rest of the 
ProfessionalGoPlayers are stored in the ZODB. All the AmateurGoPlayers 
are stored in the ZODB.

So, I need three Racks altogether:

   AmateurGoPlayers (stored in ZODB)
   ProGoPlayers_zodb (stored in ZODB)
   ProGoPlayers_rdbms (from legacy rdbms)

I'm indexing all the players that are stored in the ZODB using a 
ZCatalog called Catalog, in the GoPlayers specialist.

Now, when I want to answer a query such as "return all go players called 
'bill'", I need to do the following:

* create a PythonScript in GoPlayers called list_players_by_name(name)
* implement this method as follows:
   - query the ZCatalog for players who have that name
   - query the RDBMS using an SQL query for players who have that name
   - return the union of the results of both queries

In this scenario, I'd put the SkinScript to catalog AmateurGoPlayers in 
the AmateurGoPlayers rack, and likewise for the ProGoPlayers_zodb rack.

I'm not indexing the players from the rdbms in a ZCatalog because, in 
this example, other systems external to Zope can independently update 
the RDBMS.
If this wasn't the case, and the all changes to data in the RDBMS go 
through Zope, then I could put one set of cataloging skinscript as a 
data-plugin in the Specialist, and make the list_players_by_name(name) 
method just return the results from a ZCatalog search.

The rest of my application uses the interface provided by the 
Specialist, and can remain ignorant of where a particular GoPlayer's 
records are stored.

Note that the specialist provides exactly the methods that the rest of 
the application requires; ideally no more, and no fewer.

Beware when returning results from a ZCatalog query that you are only 
returning Catalog Brains -- simple objects that record the meta-data 
archived when the original object was cataloged. Where speed of 
execution is not an issue, you should return a list of actual GoPlayer 
objects rather than a list of CatalogBrains.
An alternative is to return a list of string ids.
Often, a better plan is to determine exactly what information is needed 
by the part of your application that requires the 
list_players_by_name(name) method call; then provide exactly that 
information.

--
Steve Alexander
Software Engineer
Cat-Box limited
http://www.cat-box.net