diff options
author | Not Zed <NotZed@Ximian.com> | 2005-05-24 17:39:24 +0800 |
---|---|---|
committer | Michael Zucci <zucchi@src.gnome.org> | 2005-05-24 17:39:24 +0800 |
commit | c33282a6549d7f7d64a27a9d14e6e99b114053b9 (patch) | |
tree | a1e58438c102e24de7a38cb86cce1896802f4df2 /plugins/mail-remote/evolution-mail-session.c | |
parent | 0822a01317ed088a14aa9268f1d086ff73cb423c (diff) | |
download | gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar.gz gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar.bz2 gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar.lz gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar.xz gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.tar.zst gsoc2013-evolution-c33282a6549d7f7d64a27a9d14e6e99b114053b9.zip |
Lots more work. Now implements a full listener interface. Filled out api.
2005-05-24 Not Zed <NotZed@Ximian.com>
* Lots more work. Now implements a full listener interface.
Filled out api.
svn path=/trunk/; revision=29406
Diffstat (limited to 'plugins/mail-remote/evolution-mail-session.c')
-rw-r--r-- | plugins/mail-remote/evolution-mail-session.c | 237 |
1 files changed, 196 insertions, 41 deletions
diff --git a/plugins/mail-remote/evolution-mail-session.c b/plugins/mail-remote/evolution-mail-session.c index 7f1e854f1a..6cdee95b2b 100644 --- a/plugins/mail-remote/evolution-mail-session.c +++ b/plugins/mail-remote/evolution-mail-session.c @@ -38,21 +38,26 @@ #include <camel/camel-session.h> -#define FACTORY_ID "OAFIID:GNOME_Evolution_Mail_Session_Factory:" BASE_VERSION -#define MAIL_SESSION_ID "OAFIID:GNOME_Evolution_Mail_Session:" BASE_VERSION - #define PARENT_TYPE bonobo_object_get_type () static BonoboObjectClass *parent_class = NULL; #define _PRIVATE(o) (g_type_instance_get_private ((GTypeInstance *)o, evolution_mail_session_get_type())) +struct _listener { + struct _listener *next; + struct _listener *prev; + + CORBA_long flags; + GNOME_Evolution_Mail_Listener listener; +}; + struct _EvolutionMailSessionPrivate { EAccountList *accounts; GList *stores; /* FIXME: locking */ - GSList *listeners; + EDList listeners; guint account_added; guint account_changed; @@ -83,6 +88,8 @@ impl_dispose (GObject *object) /* FIXME: Free accounts */ + /* FIXME: free listners */ + (* G_OBJECT_CLASS (parent_class)->dispose) (object); } @@ -129,7 +136,6 @@ impl_getStores(PortableServer_Servant _servant, seq->_length = len; seq->_maximum = len; seq->_buffer = GNOME_Evolution_Mail_StoreInfos_allocbuf(seq->_length); - CORBA_sequence_set_release(seq, TRUE); l = p->stores; @@ -146,14 +152,31 @@ impl_getStores(PortableServer_Servant _servant, static void impl_addListener(PortableServer_Servant _servant, const GNOME_Evolution_Mail_Listener listener, + CORBA_long flags, CORBA_Environment * ev) { EvolutionMailSession *ems = (EvolutionMailSession *)bonobo_object_from_servant(_servant); struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l; - printf("Adding listener to session\n"); + printf("Adding listener to session %p\n", listener); + l = g_malloc0(sizeof(*l)); + l->listener = CORBA_Object_duplicate(listener, ev); + l->flags = flags?flags:~0; - p->listeners = g_slist_append(p->listeners, CORBA_Object_duplicate(listener, ev)); + e_dlist_addtail(&p->listeners, (EDListNode *)l); +} + +static void +remove_listener(struct _listener *l) +{ + CORBA_Environment ev = { 0 }; + + CORBA_Object_release(l->listener, &ev); + if (ev._major != CORBA_NO_EXCEPTION) + CORBA_exception_free(&ev); + e_dlist_remove((EDListNode *)l); + g_free(l); } static void @@ -163,12 +186,20 @@ impl_removeListener(PortableServer_Servant _servant, { EvolutionMailSession *ems = (EvolutionMailSession *)bonobo_object_from_servant(_servant); struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l; printf("Removing listener from session\n"); - /* FIXME: need to use proper comparison function & free stuff, this works with orbit though */ - p->listeners = g_slist_remove(p->listeners, listener); - CORBA_Object_release(listener, ev); + l = (struct _listener *)p->listeners.head; + while (l->next) { + /* FIXME: need to use proper comparison function & free stuff, this works with orbit though */ + if (l->listener == listener) { + remove_listener(l); + break; + } + + l = l->next; + } } /* Initialization */ @@ -194,33 +225,50 @@ evolution_mail_session_class_init (EvolutionMailSessionClass *klass) } static void -ems_listener_event(EvolutionMailSession *ems, GNOME_Evolution_Mail_ChangeType how, EvolutionMailStore *store) +ems_set_changes(GNOME_Evolution_Mail_SessionChange *change, GNOME_Evolution_Mail_ChangeType how, EvolutionMailStore *store) { - struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); - GNOME_Evolution_Mail_SessionChange *change; - GSList *l; - - for (l=p->listeners;l;l=g_slist_next(l)) { - CORBA_Environment ev; - - change = GNOME_Evolution_Mail_SessionChange__alloc(); - change->type = how; - - change->stores._length = 1; - change->stores._maximum = 1; - change->stores._buffer = GNOME_Evolution_Mail_StoreInfos_allocbuf(change->stores._maximum); - CORBA_sequence_set_release(&change->stores, TRUE); - e_mail_storeinfo_set_store(&change->stores._buffer[0], store); - - GNOME_Evolution_Mail_Listener_sessionChanged(l->data, bonobo_object_corba_objref((BonoboObject *)ems), change, &ev); - if (ev._major != CORBA_NO_EXCEPTION) { - printf("listener.sessionChanged() failed: %s\n", ev._id); - /* TODO: if it fails, remove the listener? */ - CORBA_exception_free(&ev); - } else { - printf("listener.sessionChanged() successful\n"); - } + change->type = how; + change->stores._length = 1; + change->stores._maximum = 1; + change->stores._buffer = GNOME_Evolution_Mail_StoreInfos_allocbuf(change->stores._maximum); + CORBA_sequence_set_release(&change->stores, TRUE); + + e_mail_storeinfo_set_store(&change->stores._buffer[0], store); +} + +static void +ems_listener_session_event(EvolutionMailSession *ems, GNOME_Evolution_Mail_ChangeType how, EvolutionMailStore *store) +{ + GNOME_Evolution_Mail_SessionChanges *changes; + CORBA_long flags = 0; + + switch (how) { + case GNOME_Evolution_Mail_ADDED: + flags = GNOME_Evolution_Mail_Session_SESSION_ADDED; + break; + case GNOME_Evolution_Mail_CHANGED: + flags = GNOME_Evolution_Mail_Session_SESSION_CHANGED; + break; + case GNOME_Evolution_Mail_REMOVED: + flags = GNOME_Evolution_Mail_Session_SESSION_REMOVED; + break; } + + if ((evolution_mail_session_listening(ems) & flags) == 0) + return; + + /* NB: we only ever create 1 changetype at the moment */ + + changes = GNOME_Evolution_Mail_SessionChanges__alloc(); + changes->_maximum = 1; + changes->_length = 1; + changes->_buffer = GNOME_Evolution_Mail_SessionChanges_allocbuf(1); + CORBA_sequence_set_release(changes, TRUE); + ems_set_changes(&changes->_buffer[0], how, store); + + evolution_mail_session_session_changed(ems, changes); + + CORBA_free(changes); } static void @@ -234,7 +282,7 @@ ems_account_added(EAccountList *eal, EAccount *ea, EvolutionMailSession *ems) printf("Account added %s\n", ea->uid); store = evolution_mail_store_new(ems, ea); p->stores = g_list_append(p->stores, store); - ems_listener_event(ems, GNOME_Evolution_Mail_ADDED, store); + ems_listener_session_event(ems, GNOME_Evolution_Mail_ADDED, store); } } @@ -257,17 +305,17 @@ ems_account_changed(EAccountList *eal, EAccount *ea, EvolutionMailSession *ems) if (!ea->enabled) { printf("Account changed, now disabled %s\n", ea->uid); p->stores = g_list_remove(p->stores, store); - ems_listener_event(ems, GNOME_Evolution_Mail_REMOVED, store); + ems_listener_session_event(ems, GNOME_Evolution_Mail_REMOVED, store); g_object_unref(store); } else { printf("Account changed, dont know how %s\n", ea->uid); - ems_listener_event(ems, GNOME_Evolution_Mail_CHANGED, store); + ems_listener_session_event(ems, GNOME_Evolution_Mail_CHANGED, store); } } else if (ea->enabled && is_storage(ea)) { printf("Account changed, now added %s\n", ea->uid); store = evolution_mail_store_new(ems, ea); p->stores = g_list_append(p->stores, store); - ems_listener_event(ems, GNOME_Evolution_Mail_ADDED, store); + ems_listener_session_event(ems, GNOME_Evolution_Mail_ADDED, store); } } @@ -285,7 +333,7 @@ ems_account_removed(EAccountList *eal, EAccount *ea, EvolutionMailSession *ems) if (store->account == ea) { printf("Account removed %s\n", ea->uid); p->stores = g_list_remove(p->stores, store); - ems_listener_event(ems, GNOME_Evolution_Mail_REMOVED, store); + ems_listener_session_event(ems, GNOME_Evolution_Mail_REMOVED, store); g_object_unref(store); break; } @@ -299,7 +347,9 @@ evolution_mail_session_init (EvolutionMailSession *ems, EvolutionMailSessionClas struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); EIterator *iter; - /* FIXME: listen to changes */ + printf("EvolutionMailSession.init\n"); + + e_dlist_init(&p->listeners); /* local store first */ p->stores = g_list_append(p->stores, evolution_mail_store_new(ems, NULL)); @@ -328,4 +378,109 @@ evolution_mail_session_init (EvolutionMailSession *ems, EvolutionMailSessionClas ems->session = mail_component_peek_session(NULL); } +void +evolution_mail_session_session_changed(EvolutionMailSession *ems, GNOME_Evolution_Mail_SessionChanges *changes) +{ + struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l, *n; + CORBA_Environment ev; + + l=(struct _listener *)p->listeners.head; + n=l->next; + while (n) { + if (l->flags & (GNOME_Evolution_Mail_Session_SESSION_CHANGED|GNOME_Evolution_Mail_Session_SESSION_ADDED|GNOME_Evolution_Mail_Session_SESSION_REMOVED)) { + memset(&ev, 0, sizeof(ev)); + GNOME_Evolution_Mail_Listener_sessionChanged(l->listener, bonobo_object_corba_objref((BonoboObject *)ems), changes, &ev); + if (ev._major != CORBA_NO_EXCEPTION) { + printf("listener.sessionChanged() failed, removing listener: %s\n", ev._id); + CORBA_exception_free(&ev); + + remove_listener(l); + } else { + printf("listener.sessionChanged() successful\n"); + } + } + l = n; + n = n->next; + } +} + +void +evolution_mail_session_store_changed(EvolutionMailSession *ems, GNOME_Evolution_Mail_Store store, GNOME_Evolution_Mail_StoreChanges *changes) +{ + struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l, *n; + CORBA_Environment ev; + + l=(struct _listener *)p->listeners.head; + n=l->next; + while (n) { + if (l->flags & (GNOME_Evolution_Mail_Session_STORE_CHANGED|GNOME_Evolution_Mail_Session_STORE_ADDED|GNOME_Evolution_Mail_Session_STORE_REMOVED)) { + memset(&ev, 0, sizeof(ev)); + GNOME_Evolution_Mail_Listener_storeChanged(l->listener, bonobo_object_corba_objref((BonoboObject *)ems), + store, changes, &ev); + + if (ev._major != CORBA_NO_EXCEPTION) { + printf("listener.storeChanged() failed, removing listener: %s\n", ev._id); + CORBA_exception_free(&ev); + + remove_listener(l); + } else { + printf("listener.storeChanged() successful\n"); + } + } + l = n; + n = n->next; + } +} + +void +evolution_mail_session_folder_changed(EvolutionMailSession *ems, GNOME_Evolution_Mail_Store store, GNOME_Evolution_Mail_Folder folder, GNOME_Evolution_Mail_FolderChanges *changes) +{ + struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l, *n; + CORBA_Environment ev; + + l=(struct _listener *)p->listeners.head; + n=l->next; + while (n) { + if (l->flags & (GNOME_Evolution_Mail_Session_FOLDER_CHANGED|GNOME_Evolution_Mail_Session_FOLDER_ADDED|GNOME_Evolution_Mail_Session_FOLDER_REMOVED)) { + memset(&ev, 0, sizeof(ev)); + GNOME_Evolution_Mail_Listener_folderChanged(l->listener, bonobo_object_corba_objref((BonoboObject *)ems), + store, folder, changes, &ev); + + if (ev._major != CORBA_NO_EXCEPTION) { + printf("listener.folderChanged() failed, removing listener: %s\n", ev._id); + CORBA_exception_free(&ev); + remove_listener(l); + } else { + printf("listener.folderChanged() successful\n"); + } + } + l = n; + n = n->next; + } +} + +/** + * evolution_mail_session_listening: + * @ems: + * + * Check if anything is listening for events. Used to optimise the + * code so it doesn't generate events if it doesn't need to. + * + * Return value: + **/ +CORBA_long evolution_mail_session_listening(EvolutionMailSession *ems) +{ + struct _EvolutionMailSessionPrivate *p = _PRIVATE(ems); + struct _listener *l; + CORBA_long flags = 0; + + for (l=(struct _listener *)p->listeners.head;l->next;l=l->next) + flags |= l->flags; + + return flags; +} + BONOBO_TYPE_FUNC_FULL (EvolutionMailSession, GNOME_Evolution_Mail_Session, PARENT_TYPE, evolution_mail_session) |