[Dev] notifications about the collection itself

Andi Vajda vajda at osafoundation.org
Fri Sep 9 21:27:32 PDT 2005


> Maybe we should get rid collection notifications and use monitors instead 
> since notification don't do what we need -- what do you think?

I think collection notifications fill a specific need and monitors another 
more general need.

  - Ted and you invented collection notifications because you wanted to know
    whenever an item belonging to a collection changed and you wanted code to
    react to these changes when the system was ready - asynchronously, for
    example when idle.
    Collection notifications are sent out when polling for changes.

  - Monitors are more general, are synchronous and don't depend on the UI. A
    monitor method is told about an attribute value change synchronously,
    immediately after it occurred. No polling is necessary. Monitors are
    dispatched by operation - 'set', 'remove', 'schema' at the moment - and by
    attribute name.

Both devices have drawbacks:

  - Misusing or abusing collection notifications is going to cause us to create
    more collections than needed and is going to create unmet expectations as
    these are sent out from the UI only, asynchronously. UI-less unit tests,
    for example will not have them.

  - On the other hand, abusing monitors is going to slow down the system as all
    monitors for a given (op, attributeName) tuple are invoked for every change
    to an attribute's value.

I think both devices serve a purpose and should be used sparingly as they are 
both hard to debug and trace. Monitors fire sometimes when you least expect 
it and can be recursive. Collection notifications will sometimes not fire, 
also when you least expect it.
Yet, both patterns, allow for some pretty convenient and powerful constructs, 
so, in a word, buyer beware, use the right tool for the right task.

Now, to Alec's question. If I understood it right, Alec was asking to be told 
when the color of a colored collection changed, not when the color of an item 
in that collection changed, something quite different. Unless that collection 
- an item itself - belongs to a collection too, no collection notification is 
going to fire for that change. It seems that a simple monitor would be very 
well suited for this task.

Yet another way to do solve Alec's problem is instead of defining a 'color'
attribute on a collection item - I've argued many times in the past that it 
didn't belong there - one could use a mixin kind defining that attribute 
along with a mixin class with relevant code to react to changes to that 
'color' attribute in an onValueChanged() hook method. This approach is by far 
the most efficient from an execution path standpoint.
It also seems that PJE's annotation API would make this trivial to implement 
from a developer's point of view.

Andi..

>
> John
>
> Andi Vajda wrote:
>
>> 
>>> John/Ted -
>>> So right now the way notifications work is if any items in a collection
>>> get modified/etc, then a notification goes out to subscribers.
>>> 
>>> In the case of color, I'm actually interested in getting notified when
>>> the 'color' attribute on the collection itself, not a member of the
>>> collection, is changed. I can change it via a menu right now, but the
>>> calendar code doesn't know the color changed, so it doesn't know to
>>> redraw.
>>> 
>>> what would you guys think about making notifications fire for both the
>>> collection items, as well as changes to the collection itself?
>> 
>> 
>> Don't use notifications for that, use a monitor.
>> For example:
>>
>>    class AlecsItem(Item):
>>
>>       def aColorChangedSomewhere(self, op, item, attribute):
>>
>>          if op == 'set' and isCollection(item) and attribute == 'color':
>>              print 'gosh, a colored collection changed to', item.color
>> 
>> Attach the monitor:
>>
>>    Monitors.attach(alecsItemInstance, 'aColorChangedSomewhere', 'set', 
>> 'color')
>> 
>> Et voila. Monitors are persistent so you only need to set this up once.
>> Collection notifications, as implemented today, are a UI-only device fired 
>> from the wx event loop's OnIdle() method. They are asynchronous and rather 
>> heavy as they are broadcast all subscribers of a set, indiscriminately.
>> 
>> Monitors are synchronous and broadcast only to items monitoring the given 
>> op/attribute combination.
>> 
>> Andi..
>
>


More information about the Dev mailing list