[Telepathy] How to handle a lost closed signal

Simon McVittie simon.mcvittie at collabora.co.uk
Fri Sep 27 06:01:59 PDT 2013


On 27/09/13 13:12, Tiago Katcipis wrote:
> I'm reading the telepathy specification and i have a doubt that i was
> unable to find a answer until now, when a channel is created you start
> to create a proxy to the new channel, but then the closed
> (http://telepathy.freedesktop.org/spec/Channel.html#Signal:Closed)
> signal is emitted, but before you can catch it since you are still on
> the process of creating a proxy to it, how you handle this kind of race
> condition on DBus objects?

Just detecting it isn't such a problem: when setting up the proxy, you
call a D-Bus method that all objects of that interface must implement
(Properties.GetAll for the relevant interface, usually) and that do not
fail under any normal circumstances (again, GetAll is ideal). If that
fails, you know the object already went away :-)

The next problem is that because it has already gone away, maybe you've
already lost some of the information you need. That's harder, but we've
developed several ways to solve it.

When we announce a new channel, we announce its "immutable properties"
immediately:

  - target handle (= contact or room you're talking to)
  - type of channel
  - initiator
  - etc.

which is enough to log a missed call, even if you never saw the actual
D-Bus object in an "alive" state.

Another technique is to have the object persist in a "dead" state until
a client acknowledges it. Call1 channels (our modern API for VoIP calls)
don't close until a client calls the Close() D-Bus method, even if the
call has actually already terminated. With hindsight, all Telepathy
channels (e.g. Text and tubes) should have always worked like this -
it's too late to do that in Telepathy 0.x, but I'm considering it for
Telepathy 1.0.

If you need multiple cooperating clients (which many APIs don't, but
it's a lot of the point of Telepathy) then another technique is to have
a policy by which multiple cooperating clients can agree when it's OK to
close/delete the object. For instance, Telepathy clients use the
ChannelDispatcher (Mission Control) as a coordination point, and agree
that it is incorrect to close a channel until Mission Control has given
it to a (single!) suitable Handler. Clients that implement Observer,
like telepathy-logger, can delay that point while they do whatever
sync-up they need to, because Mission Control will wait for them before
it proceeds.

> One way is to have a well know bus-name and object-path that notifies
> about the channel being closed, but then it seems to be useless to have
> the signal on the created object since you are obligated to monitor the
> signal on the well know object to avoid losing the signal of the
> recently created object.

We do this too (e.g. Channel.Closed duplicates Connection.ChannelClosed,
Account.Removed duplicates AccountManager.AccountRemoved). It isn't the
most elegant thing in the world, but it's necessary if you want state
recovery and change notification, which are two of our design principles:

* state recovery: if you miss signals, you can catch up on the current
  state by calling a method or getting a property, although you might
  miss old state transitions (e.g. you can get the list of channels,
  even if you missed NewChannels and ChannelClosed signals)

* change notification: if there's a GetThings method or a readable
  property, then there should be a way to keep up with its current
  value by watching signals, to avoid having to poll

Regards,
    S



More information about the telepathy mailing list