Bug 54010

Summary: Plugins should have async API to create accounts
Product: Telepathy Reporter: Xavier Claessens <xclaesse>
Component: mission-controlAssignee: Telepathy bugs list <telepathy-bugs>
Status: RESOLVED MOVED QA Contact: Telepathy bugs list <telepathy-bugs>
Severity: normal    
Priority: medium    
Version: unspecified   
Hardware: Other   
OS: All   
URL: http://cgit.collabora.com/git/user/xclaesse/telepathy-mission-control.git/log/?h=create_async
Whiteboard:
i915 platform: i915 features:

Description Xavier Claessens 2012-08-24 14:05:31 UTC
For Ubuntu Online Account plugin (libaccounts) we use the AgAccount's id as storage identifier (mcp_account_storage_get_identifier). However that id is know only hafter the AgAccount has been stored in permanent storage. This means that _create_account() is racy because we cannot tell MC to wait for the commit to be done before getting the account's identifier.
Comment 1 Xavier Claessens 2012-08-28 07:40:08 UTC
Forgot to attach my branch.
Comment 2 Simon McVittie 2012-08-28 09:26:36 UTC
From IRC discussion, I understand you were unsure about create_async vs. commit_async.

I feel as though if anything is async, committing ought to be async (intuitively, it's the thing that ought to take time and be failable).

On the other hand, for your usage in UOA, you can't return the object-path tail synchronously... so account creation can't usefully be sync either?

There is also the issue that UOA is currently the only thing overriding create() (true?), which makes create() rather useless. I wish we'd thought about this before merging create().

I'm tempted to merge a branch I'm working on (which combines McdStorage into McdPluginAccountManager) before this one, so that you don't have to write so much boilerplate...
Comment 3 Simon McVittie 2012-08-28 09:43:23 UTC
(I haven't reviewed in detail til we agree on an approach.)

The fallback chain through attempts to create accounts, asynchronously, seems rather undesirable: if you have, say, 5 plugins, then it takes 5 async round-trips (of which the first 4 are just "do you want to store this account?" "not really") before we actually do anything. Could we perhaps change it to be more like this?

    create() -> unique ID, a special constant not syntactically allowed
        in account names meaning "in progress" (maybe #define
        MCP_ACCOUNT_CREATION_IN_PROGRESS to "<in progress>"?),
        or NULL to decline

    complete_account_creation_async(), _finish() -> unique ID
        (should only be called if MCP_ACCOUNT_CREATION_IN_PROGRESS
        was returned)

Then we could do (pseudocode):

    foreach (storage_plugin)
      {
        id = storage_plugin.create(...)

        if (!tp_strdiff (id, MCP_ACCOUNT_CREATION_IN_PROGRESS))
          {
            storage_plugin.complete_account_creation_async(...,
                lambda id: raise error or actually create the account (id));
            break;
          }
        else if (id != NULL)
          {
            actually create the account (id);
            break;
          }
        /* else continue to next backend */
      }

    if (nobody took responsibility)
       raise error;

and even though you can't necessarily know what the account's ID is until you have actually done the "complete account creation" step, you can at least know whether this plugin is going to be the one to store the account or not. I'm assuming that plugins are at least intelligent enough to know what they can and can't store in a synchronous way?

I'm currently thinking about whether to take Bug #35896 as an excuse to write an actually helpful plugin API with a sensible data model. Perhaps we can discuss that on IRC later?
Comment 4 Xavier Claessens 2012-08-28 10:10:51 UTC
(In reply to comment #2)
> I feel as though if anything is async, committing ought to be async
> (intuitively, it's the thing that ought to take time and be failable).

Yep, even independently to this bug, I think commit_async() is a good thing.

> On the other hand, for your usage in UOA, you can't return the object-path tail
> synchronously... so account creation can't usefully be sync either?

Actually in my case I can. The problem I have is the identifier returned by tp_account_get_storage_identifier() is known only after the account has been stored. So if CreateAccount returns too early and client gets the storage identifier it will be 0 instead of a real identifier.

I didn't though about this when writing the patch above, but actually just making commit_async() and make sure CreateAccount does not return before commit_async is done is enough to fix my case.

> There is also the issue that UOA is currently the only thing overriding
> create() (true?), which makes create() rather useless. I wish we'd thought
> about this before merging create().

With RH ignoring what Canonical does, I think they'll soon come with the same kid of storage in GOA.

> I'm tempted to merge a branch I'm working on (which combines McdStorage into
> McdPluginAccountManager) before this one, so that you don't have to write so
> much boilerplate...

Oh yes please do!
Comment 5 GitLab Migration User 2019-12-03 20:12:31 UTC
-- GitLab Migration Automatic Message --

This bug has been migrated to freedesktop.org's GitLab instance and has been closed from further activity.

You can subscribe and participate further through the new bug through this link to our GitLab instance: https://gitlab.freedesktop.org/telepathy/telepathy-mission-control/issues/65.

Use of freedesktop.org services, including Bugzilla, is subject to our Code of Conduct. How we collect and use information is described in our Privacy Policy.