A tuple can be modeled as a (database) row, with columns having either a NULL (undefined) or a non-NULL value. The relational database analogy is incomplete, but helpful for some issues and leads to readily expressible operations that are well understood and easily implemented. It requires that tuples are 'flat', i.e., only have a single level of attributes. In this model, a tuple describes properties of a contact URI. (A contact URI can have multiple descriptions if it indeed has multiple disjoint properties.) Most columns can have either a single value or a set of values. Examples: URL | AOR | media | activity | mobility ------------------------------------------------------ u1 | u | audio,video | active | mobile u2 | u | audio | NULL | mobile,fixed u3 | u | audio,video | NULL | mobile,fixed There are two kinds of rows: - elementary rows Elementary rows have the property that there is a communication service that satisfies all row attributes. In the example, u1 can be elementary: there is a (at least one) communication service that speaks audio and video, is active and mobile. - composite rows A composite row represents the properties of a number of elementary rows. It is not required that instances with all permutations of attributes actually exist. In the example, u3 represents a composite. There may be no communication endpoint that satisfies the criteria 'audio' and 'mobile'. There will however, be one from the following list both audio and video mobile both audio and video fixed just audio mobile just video mobile just audio fixed just video fixed One cannot necessarily tell by looking at the row whether a row is elementary or composite. For example, u1 could be either: it could be the composite of an audio-only and a video-only device or a device that can do both. * Composition (merging) rules for merging tuples Two or more rows can be composed (merged) into a single row; we denote the operation as '#'. The rules for merging attributes may depend on the attribute. A few simple rules always hold: - NULL # NULL = NULL - NULL # a = a (may not be right - could be argued that it should be NULL) - a # a = a For non-NULL enumerated values, there are two choices: - set union: a # b = a,b - undefined: a # b = NULL if a != b For ordered values (integers, time values, ordered properties such as on/off-hook), composition could be - undefined: as above - maximum: a # b = max(a,b) - range: a # b = [a,b] - enumeration (union): a # b = a,b With union, the semantics is "You will be able to get one of these attribute values (and may be able to select a specific one with caller preferences" The others provide the semantics of "You will be able to get something that's at least as good as advertised." URIs cannot be sensibly composited like that, so we define a different rule: Rows can only be merged if they either have the same contact URI (often, a device URI) or the same AOR. If they have the same AOR, the composite row assumes the AOR. Note that there can be multiple compositing operations, so that the row count may or may not decrease after all composing is done. Only the 'undefine' operation maintains the elementary property of the composited row, but the row becomes less specific, i.e, the recipient knows less about the tuple. Merging is, except for trivial cases, a non-reversible operation. Once two rows have been merged, information has been lost and the operation cannot be undone to recreate the original rows. * Grouping ('pivoting') Grouping is a special kind of compositing, where one parameter is selected as the grouping indicator. Compositors and watchers can perform grouping. Rows are sorted by that parameter values and all rows with an equal parameter value for the grouping column are merged, as above. For example, if we have the rows media mobility placetype privacy category --------------------------------------------- a,v fixed home private away a mobile NULL public meeting t mobile NULL private meeting (Here, a=audio, v=video, t=text) we can group them by media as media mobility placetype privacy category -------------------------------------------------------- a fix,mob home private away,meeting v fixed home private,public away t mobile NULL private meeting The composition rule 'union' was used for all attributes. Grouping is also possible for set-valued values; this is left as an exercise to the reader. (Here, we'd have an uninteresting result, with the same rows, a,v v t). NB: Grouping is not restricted to media. Any column could theoretically be used for grouping, although columns that have enumerated values are probably most useful in practice. I don't think that grouping by last activity, say, is particularly useful. One could also group by functions of one or more columns. For example, a transformation could combine multiple attribute values into one, such as 'in-transit' and 'meeting' into 'interruptible', while all others are 'non-interruptible'. * Filtering Watchers and compositors can filter rows. This is equivalent to an SQL SELECT operation, where the output is another table. Filters have two consequences: they select a subset of rows and a subset of columns. In SQL, as SQL column selection is expressed as, for example, SELECT c1,c2 FROM table A row selection is expressed as in the examples below: SELECT * FROM table WHERE c1=v1 AND c2=v2 SELECT c1,c2+c3 FROM table WHERE c1 > c2 Generally, the column list can be an enumeration of columns or can generate new columns, e.g., the sum of multiple columns or some other transformation. For presence tuples, we won't consider such transformations at compositors. They are potentially useful for watchers. Views are essentially automatic SELECTs that limit the columns that are visible to a particular user. * Rendering The watcher does not have to know the detailed view in order to render a table row. It only has to know the meaning and data definition of columns. Since these definitions are prescribed and standardized, there is no particular issue here. * Open issues (1) Is it useful to label each *attribute* or each tuple as composed? (I suspect that labeling attributes doesn't help much, since a single composed attribute renders the whole row non-elementary.) (2) Are the composition rules general enough or too general? (3) It would be possible to have a different description format that explicitly enumerates all the valid combinations within each tuple, avoiding the loss of information incurred by composition. However, it seems that (making up a syntax) u1 voice meeting voice vacation is no more expressive, yet more complicated than: u1 voice meeting u1 voice vacation * Related work Composition is similar to the centroid operation in the old whois++ proposal (RFC 1835), although RFC 1835 only considers enumeration of all values.