Thanks ted, I'm attaching an updated version to reflect most of your comments. I have a few questions/clarifications though.. but I've update the doc (attached) with your comments. I think most of my clarifications are beyond the scope of this particular meeting though.

  I don't see how this turns into an argument for subclassing UserCollections all over the place.
Well, I was partially trying to capture the spirit of what people said when I mentioned, "For example, ZaoBao needs a place to store a feed URL" and the reaction was "Well you can always subclass ItemCollection, that's how you do that"

Personally I'm not a fan of subclassing, per se either, but I think its close - perhaps "Mixing in" (stamping) - this is what I do today to mix "calendar data" in with a collection - I go and stamp the itemcollection (at runtime) with a calendar data class, and then attach calendar data to that. I can do that to any arbitrary ItemCollection right now, which is particularly nice. Then I can access itemCollection.calendarColor.

But perhaps if ZaoBao knows at declaration time that it will be managing things like the url for a feed, it might as well just subclass. *shrug*

What is the use case for distinguishing a SpecialCollection from a UserCollection?
Well some of my previous thinking is old-sk00l. These are all smart collections backed by queries, I should just be able to mark an item as "deleted" to make it appear in Trash collection, or mark a message as "outgoing". That makes far more sense then having to say "Put this Item in the Trash ItemCollection"

However, we need to distinguish 'specialness' for some other practical matters in the view. For instance:
  • You need specific icons for particular folders - the trash needs to look like a trashcan, and so forth.
  • You need specialized add/delete for most of these folders - for instance, trash.add() should not blindly add. It should instead set a "deleted" attribute on an item, that makes it appear in the trash.
  • When you view the Sent folder, you'd probably want to see the the recipients, rather than the sender, in the summary view column for "who".
  • In the Junk Mail folder, you wouldn't want the client checking the messages there for Junk.
Some of this might just be represented with metadata on the itemcollection (i.e. the "icon" attribute or the "sentness" attribute on a folder) but it would sure be nice if there was a consistent way to represent this metadata at least for basic application behavior, and I think that's why I was going for a subkind. I don't know - I'm not sure how strongly I feel on this one.
I think that subclassing to add metadata is a bad idea.  One of the things that we wanted to do in Chandler was to allow individual items to have ad-hoc attributes added to them.  From what I understand, this was one of the motivating factors for the choice of Python.
But we can't do that today - the Kind declares a schema for an item. If you attach an ad-hoc attribute to an item, the repository doesn't recognize that attribute so it doesn't persist. Unless there are plans to change that, you still need Kinds to indicate new attributes on Items. If there are plans, please let me know! :)

(And in fact, if there are plans to allow ad-hoc attributes, that really changes MY world view on the repository...)
   If that's the case, then it seems to me that requiring people to subclass in order to add meta-data is a step in the opposite direction.   Suppose two parcels want to add some of he same metadata to a Collection?    Now we have that nasty multiple inheritance stuff to deal with.   These collections are just items.   We should use whatever mechanism we are going to use for ad-hoc item attributes to solve this problem.
Well, ad-hoc item attributes have the same problem as the two parcels with the same metadata problem.. there is always possibility for conflicts. As Guido would say, "we are all consenting adults here" and we shouldn't be defining overlapping attributes, metadata, or what have you :)

Alec

Title: ItemCollection decisions

ItemCollection decisions

Date: 6/30/2005
Attending: Katie, John, Ted, Morgen, Grant, Philippe, Alec

This meeting was to discuss open issues regarding ItemCollection. The following diagram gives a visual representation for how the Sidebar intersects facets to show the user a resulting collection.

All Tasks Mail Calendar
All|
In|
OutV
Home----------->Calendar & Home
Work

Issues and Questions

The following specific questions were brought to the table.

  1. How does a view know what "collection" to use for additions or removals, when views typically deal with "filtered" versions of existing item collections?
  2. How to store metainformation in an item collection? Examples include color, sharing data, ZaoBao URL, etc

1. Adding/removing from collections

The Problem: When a view (i.e. the calendar view) needs to create or remove an item, how does it know what collection to add or remove it from? Views typically deal with ephemeral collections of items which are filtered versions of real collections.

For example, if a user has clicked the "Home" collection in the sidebar and the "Calendar" filter button in the toolbar, then it is dealing with a collection that is an intersection of all items in the Home collection that are also CalendarEvents. If a new item is created, how does it know to add that item to the "Home" collection, and not this ephemeral "Home and Calendar" collection?

The question of "how" has two facets:

1.1. How does the Calendar view get back to the "Home" collection from the "Home and Calendar" collection?

i.e. how does it find the "context" of the add?

Decision

The sidebar will notify the view about what collection should be used for add/delete, as a part of the SetContents event. Currently, the SetContents event passes along just the ephemeral collection in the "items" parameter to the event. Now, the real collection will also be passed along as another parameter.

Reasoning

It was decided that the "add" is really a user-level event that the user sees as add or removal from whatever is displayed in the sidebar. The user doesn't think about the add/delete only within the context of the ephemeral collection. So really, the add or delete is an action at the level of the view, not the collection. This means it is the responsibility of the UI that is managing the view's contents (i.e. its the Sidebar's responsibility because it tells the calendar view what data to deal with)

1.2. Given the context (i.e. the "real collection") of the add/delete, What does the calendar actually do with this context to indicate that the add should happen?

Decision

The view will call the add() or remove() method on the "real" collection. For example, realcollection.add(newItem).

Reasoning

There was some discussion about what makes an item a member of a collection, and membership is usually determined by some particular facet of an item. That facet could be represented by an attribute that matches a rule. In fact, that facet could be any arbitrary facet that matches a query, attached to a collection.

For instance the "label" attribute might be set to "Home" and if there was a rule on the "Home" collection saying that all items with the label "Home"

So that brings us back to the question, do we explicitly add an item to an itemcollection, or do we do something like set an attribute?

The choices end up being:

  • collection.add(item)
  • item.label=collectionName (or any other variation where you're setting an attribute on "item")

The problem is, that there may be any one of a number of properties of an item that make it a member of a collection. The sidebar, which "manages" these collections seemed like one candidate because it kind of "owns" its ItemCollection. But ultimately, this isn't a function of the view, this is really a function of the original collection.

Furthermore, even if we were to use item.label=... or some other convention, if that convention changed we'd have to update all the users of that convention.

Since it seems to be the responsibility of a collection to know what makes an item a member, then it should also have responsibility for the add/remove operations, by performing the respective modification to that item. The obvious way to do this is with an add and remove method on the collection, and let the collection handle the messy details of the actual add or delete.

3. When using attributes to denote collection membership, how should that attribute be used?

If some collections do determine membership by some simply query, like "All items whose label is pink" what convention should we use? What is the name and type of that attribute?

Decision

Ted and John and Alec will hash this one out. It looks like the choices right now are:

  • A string: item.label = collection.name? John prefers this for readability of the label, but it leaves open issues like:
    • What happens if an item is a member of multiple collections?
    • What happens when the target collection goes away?
    • What happens when the name of the collection changes
  • A bidirectional attribute pointing directly to the collection: item.collections.append(collection)? (like itemCollectionInclusions) Alec likes this because it leaves much of the lifetime management to the repository.
  • A list of uuids of itemcollections - maybe this is the same as bidirectional refs? Ted talked about this but I wasn't sure if it was the same

4. User level collections vs. other collections

What exactly is an "ItemCollection" in the context of the user's view of his/her data? There was some discussion of logically separating a user's collections (e.g. "Home") and the ephemeral collections (e.g. "CalendarEvents in Home")

Decision

Much of this comes down to implementation details. Alec and Katie saw a need for this, whereas John thought that when it comes to implementation, there won't be any need to make the distinction.

Katie and Alec imagined cases where a user might be presented with a list of his/her collections, and that you wouldn't want that list to include the ephemeral collections

Discussion

Perhaps the notion of UserCollection as a subclass of something called Collection would make sense? Kind queries could find them, and perhaps that is one place we could store color data, especially if UserCollection is more or less a special case of the just-subclass-collection to get meta information? Sort of Collection is to Item as UserCollection is to ContentItem?

Alec's proposal

  • class Collection: the unit by which most items are collected together in an Item-based list. The most basic unit that can be treated like a set, queried against, and so forth. When seen in the wild, these collections are likely a subclass such as FilteredCollection()
  • class UserCollection(Collection): a collection, as presented to the user. This may be the place for add/remove? These collections would be the ones that exist in the sidebar, and perhaps could contain some user-facing data like color. In many ways, UserCollection is just one case of the meta-data argument for subclassing item collections.
  • class SpecialCollection(UserCollection): the base class for "All" "In" "Out" and so forth. Has dummy implementations of add()/remove() that either throw exceptions or do nothing. Has a string with an internal name of the specialness of the collection, such as "all", "in", "out" and so forth. This one is still up for debate, and is really beyond the scope of the meeting.

5. How and where will itemcollection metadata be stored?

Information about the item collection such as its color, label, etc, needs a home.

Decision

No real firm decision on this yet. But most were in favor of a system that hung the data off the collection somewhere, rather than in some global place. When the ZaoBao case of needing to store a URL with a collection was mentioned, everyone immediately said "Subclass ItemCollection!" So it seems like that might be the way to go.

That said, I wonder if we'll just want to subclass item collection for items that live in the sidebar for things like color. See Alec's proposal in section on User Collections vs. other collections.

Another variation of subclassing is "mixing in" or "stamping" an itemcollection with a class that can contain useful metadata. The difference is that it happens at runtime and any particular code can do it.

6. Special Collections - how to handle their special behavior, like All, In, Out, etc?

They may have special rules about how items are added, and so forth.

Decision

No real decision just yet, the issues haven't been flushed out. May be beyond the scope of this meeting

Discussion

This is when Alec floated his idea of subclassing - see the section on User-level collections vs. other collections.

There are two situations in which you need the 'specialness' of a collection:

  1. When you need to add/remove items from a special collection: In a traditional application, deleting something moves it to a trash folder. This is implemented by physically removing it from one folder and moving it to another. In the world of chandler, collections like Trash are really special collections backed by queries. Instead of "moving it to the trash" you want to just mark it as deleted, (i.e. item.deleted = True)and let the Trash query pick that up.
  2. When the view needs to make special presentation decisions based on the specialness of a particular folder. In this case, the folder has already been 'found' so you don't need to hunt down the Trash folder. Instead, the view is trying to make decisions about how to display a folder

    7. How will queries work on collections?

    For instance, if the calendar wants to query all items in a collection, within a given date range?

    Decision

    Queries are just predicates applied to a Collection or Set. The FilteredCollection class will be used to apply predicates to members of a set:
    c = UserCollection(...)
    fc = FilteredCollection(c, "i.startDate < '3/3/2005 03:15'")

    8. How will the autogeneration of recurring items happen?

    We need a mechanism so that if you query a collection on a given date range, the appropriate recurring items are created.

    Decision

    Ted is trying to make a pluggable system so that when a given attribute (or is it Kind?) is searched, a callback mechanism can be triggered to allow the creation of the items before the query actually runs, so the query finds them.


    U-ALECF-T41\alecf
    Last modified: Fri Jul 1 10:36:37 PDT 2005
    _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
    
    Open Source Applications Foundation "Dev" mailing list
    http://lists.osafoundation.org/mailman/listinfo/dev
    

Reply via email to