[Zope3-dev] Florent's O-R blog entry

Martijn Faassen faassen at infrae.com
Wed Aug 24 11:28:54 EDT 2005


Paul Winkler wrote:
> Martijn Faassen wrote:
> 
>>Missing powerful query concepts
>>-------------------------------
>>
>>Certain powerful query concepts like joins, available in a relational
>>setting, are missing. I've already run into a scenario where I wanted to
>> someting like this: given a bunch of version objects with field 'id',
>>where multiple objects can have the same 'id' to indicate they're
>>versions of the same object, I want all objects where field
>>'workflow_state' is 'PUBLISHED' unless there is another object with the
>>same id that have workflow_state 'NEW', in which case I want that one'.
>>
>>I think joins would be a way to solve it, though I haven't figured out
>>the details, nor how to implement them efficiently on top of the
>>catalog. This kind of thing is where a relational database makes life a
>>lot simpler.
> 
> 
> I used to have the same complaints in Zope 2, but so far I've been happy
> with Dieter's AdvancedQuery product.  See
> http://www.dieter.handshake.de/pyprojects/zope/AdvancedQuery.html
> It might be worth a look while thinking about what to implement for zope 3.
> 
> Here's Dieter's example from that page:
> 
> from Products.AdvancedQuery import Eq, Between, Le
> 
> # search for objects below 'a/b/c' with ids between 'a' and 'z~'
> query = Eq('path','a/b/c') & Between('id', 'a', 'z~')

Something very similar to this I can also do with the layer I built on 
top of Zope 3's catalog. It wasn't hard to write at all, which speaks 
for the clean design of the Zope 3 catalog.

> # evaluate and sort descending by 'modified' and ascending by 'Creator'
> context.Catalog.evalAdvancedQuery(query, (('modified','desc'), 'Creator',))

This is interesting and my layer cannot do this yet.

> # search 'News' not yet archived and 'File's not yet expired.
> now = context.ZopeTime()
> query = Eq('portal_type', 'News') & ~ Le('ArchivalDate', now)
>         | Eq('portal_type', 'File') & ~ Le('expires', now)
> context.Catalog.evalAdvancedQuery(query)

In your example you haven't done a join as I describe above, unless I 
miss something. The essential part is that I want an object with state 
'PUBLISHED' unless there is another object where field 'ID' is the same 
as this object that is with state 'NEW'. The join is in the 'ID' 
matching part.

Regards,

Martijn


More information about the Zope3-dev mailing list