Re: [Evolution-hackers] How to use the Camel library to access email service




Hi!,

您好吗?

I found Milan reply interesting but did not really hack on this,
您见不见了?

Cheers
Pierre-Yves 

Milan Crha <mcrha redhat com> writes:

On Tue, 2014-08-19 at 16:34 +0800, Chunyang Xu wrote:
Hi all!

I want to adding email as storage supporting for a GNOME app, named
"bijiben". With this feature users can read & save notes to their
email box (a folder like "Notes"). But I do not how to use the Camel
library to access email folders. I have two question:

1. How to authenticate user with gnome-online-accounts? I can get 
user
name, IMAP server address etc via gnome-online-accounts.

2. How to operate email like files and folders, i.e, how to download 
/
update / upload files between email service and local? Is it possible
to sync a local folder to a email folder like "INBOX"?




        Hi,
the evolution-data-server (its evolution-source-registry D-Bus 
service) provides a list of configured sources, which can be 
calendars, address books, mail accounts and so on. Many things are 
referenced by source (ESource) uids (e_source_get_uid()) in the code. 
More about ESource-s can be found here [1][2].

These are used also by Camel [3][4]. Even the Wiki pages are a little 
bit outdated, the principle is still the same. You should provide your 
own descendant of CamelSession, which holds list of configured mail 
accounts (added by camel_session_add_service(), got by 
camel_session_ref_service()). The service can be either CamelStore or 
CamelTransport descendant. The CamelStore provides you with a list of 
CamelFolder-s and so on. The CamelService lets you connect to the 
server.

I guess the simplest way is to borrow Evolution's implementation of 
CamelSession, the EMailSession [5], and build on top of it - at least 
as a starter. If your mail account is configured through GOA and you 
have evolution-data-server compiled with GOA module, then the account 
will be automatically available for you. Getting the account's ESource 
(and its uid) is a little bit tricky. You should let the users pick 
which account to use, rather than guess which of the 5 different GOA 
configured mail accounts to use. Supposing you know the uid of the 
chosen mail account you can do something like this:

   #include <libemail-engine/libemail-engine.h>

   ...

  EMailSession *session;
   ESourceRegistry *registry;
   CamelService *service;
   CamelStore *store;
   CamelFolder *folder;
   GError *error = NULL;

   registry = e_source_registry_new_sync (cancellable, &error);
   if (!registry) {
      // do something with 'error' and free it
      return;
   }

   session = e_mail_session_new (registry);
   g_object_unref (registry);

   service = camel_session_ref_service (CAMEL_SESSION (session), uid);
   if (!service) {
      g_warning ("Cannot open service '%s'", uid);
      g_object_unref (session);
      return;
   }

   if (!CAMEL_IS_STORE (service)) {
      g_warning ("Cannot open service '%s'", uid);
      g_object_unref (service);
      g_object_unref (session);
      return;
   }

   store = CAMEL_STORE (service);

   if (!camel_service_connect_sync (service, cancellable, &error)) {
      // do something with 'error' and free it
      g_object_unref (service);
      g_object_unref (session);
      return;
   }

   folder = camel_store_get_folder_sync (store, "INBOX/sub-folder", 0, cancellable, &error);
   // alternatively for Inbox itself:
   // folder = camel_store_get_inbox_folder_sync (store, cancellable, &error);

   if (!folder) {
      // do something with 'error' and free it
      g_object_unref (service);
      g_object_unref (session);
      return;
   }

   // to get up-to-date folder content
   if (!camel_folder_synchronize_sync (folder, 0, cancellable, &error) ||
       !camel_folder_refresh_info_sync (folder, cancellable, &error)) {
      // do something with 'error' and free it
      g_object_unref (service);
      g_object_unref (session);
      return;
   }

   // do something with the 'folder' [6]

   g_object_unref (service);
   g_object_unref (session);

Note I used "sync" versions of the functions only for its simplicity, 
you might run the code in a dedicated thread or use "async" functions, 
to not get your UI/main thread blocked by a remote call. Also note 
that connecting to the service each time you want to manipulate folder 
content is not efficient, the network I/O or large folder update can 
take significant amount of time.

        Hope it helps,
        Milan

[1] https://wiki.gnome.org/Apps/Evolution/ESourceFileFormat
[2] https://wiki.gnome.org/Apps/Evolution/ESourceMigrationGuide
[3] http://developer.gnome.org/camel/unstable
[4] https://wiki.gnome.org/Apps/Evolution/Camel
[5] https://git.gnome.org/browse/evolution/tree/libemail-engine/e-mail-session.h
[6] https://developer.gnome.org/camel/unstable/CamelFolder.html


_______________________________________________
evolution-hackers mailing list
evolution-hackers gnome org
To change your list options or unsubscribe, visit ...
https://mail.gnome.org/mailman/listinfo/evolution-hackers



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]