[RFC] First draft of the new async client API to interact with Akonadi
Needs ReviewPublic

Authored by dvratil on Jun 2 2019, 2:15 PM.

Details

Reviewers
kde-pim
Summary

This is a first draft of the new API that I'm putting up so everyone
can express their opinions and ideas for improvements. I have
experimentally ported most parts of Akonadi Core library to it and I was
able to run and use Kontact with it, but I want to settle on the API first
before porting the rest.

The purpose of this API is to not remove/obsolete the existing Job-based
API, but to provide an alternative that we can slowly port the codebase
to, but as of now the Job-based API is actually used as the internal
implementation of the new API, so it is not going away any time soon.

This change introduces a factory-like interface that has methods for
various operations (createItem, deleteItem, etc.) that take arguments
for the operation and return a KAsync::Job. KAsync allows chaining
and nesting of jobs (somewhat like the std::future continuation from
Concurrency TS).

The interface has one real implementation called StorageInterface, which
provides integration with the real Akonadi Server, currently wrapping
the good old Akonadi Jobs. When the API matures enough we can flip this
around and have full implementation of the protocol in the
StorageInterface and the Akonadi Jobs simply as wrappers for the async
jobs (and then eventually deprecating the old Job API, but that's for a
very distant future).

The major advantage of this new API is that the interface can be
reimplemented to talk to a mock Akonadi server, either by using a
MockStorageInterface (to be written), or by implementing a custom one
from scratch - this allows users to have complex tests without having to
start a real Akonadi server, as well as making it much easier to prepare
the initial state and conditions for the test.

However, the interface and its implementations are not meant to be used
directly: the "storage.h" file contains a free functions in the
Akonadi namespace that internally only call the corresponding methods on
the interface: this makes it possible to simply swap the default
interface implementation (the one that talks to the real Akonadi server)
for a mock one in a single place and make it apply to all client code
without the code being aware of this.

Currently the Interface is missing abstraction for the Monitor which as
of now interacts with the Server by directly creating and receiving raw
Akonadi Protocol messages - I don't have a good clean solution for this
yet without polluting the Interface with API that is otherwise internal
to the Monitor.

Diff Detail

Repository
R165 Akonadi
Lint
No Linters Available
Unit
No Unit Test Coverage
Build Status
Buildable 12342
Build 12360: arc lint + arc unit
dvratil created this revision.Jun 2 2019, 2:15 PM
Restricted Application added a project: KDE PIM. · View Herald TranscriptJun 2 2019, 2:15 PM
dvratil requested review of this revision.Jun 2 2019, 2:15 PM
dvratil added inline comments.Jun 2 2019, 2:18 PM
src/core/jobs/tagmodifyjob.cpp
54

This method never got implemented, apparently, I'm the first one to use it :-)

src/core/session.h
69

The old API works with a raw pointer to Session, so to allow for the new API to use a QSharedPointer, QEnableSharedFromThis is used to avoid breaking the existing API and code.