From: Hans Petter Jansson Date: Thu, 27 Nov 2003 02:30:10 +0000 (+0000) Subject: Support absolute URI. (e_source_update_from_xml_node): Ditto. X-Git-Tag: upstream/3.7.4~9681 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=1d59cdfe5446128f083d557e922c7c5d3df49185;p=platform%2Fupstream%2Fevolution-data-server.git Support absolute URI. (e_source_update_from_xml_node): Ditto. 2003-11-26 Hans Petter Jansson * libedataserver/e-source.c (impl_finalize): Support absolute URI. (e_source_update_from_xml_node): Ditto. (e_source_get_uri): Ditto. (dump_common_to_xml_node): Implement for parameters common to dependent and standalone ESources. (e_source_dump_to_xml_node): Use dump_common_to_xml_node (). (e_source_to_standalone_xml): Implement. (e_source_new_from_standalone_xml): Implement. 2003-11-26 Hans Petter Jansson * idl/Evolution-DataServer-Calendar.idl (getCal): Take source XML instead of URI. * libecal/client-test.c (create_client): Adapt to API changes. (main): Ditto. * libecal/e-cal.c (fetch_corba_cal): Move to ESource. (e_cal_new): Take ESource. (e_cal_new_from_uri): Implement convenience call that takes URI. * libedata-cal/e-cal-backend.c (e_cal_backend_set_property): Implement PROP_SOURCE. (e_cal_backend_get_property): Same. (e_cal_backend_class_init): Same. (e_cal_backend_get_source): Same. * libedata-cal/e-data-cal-factory.c (impl_CalFactory_getCal): Take source XML and construct an ESource. Init backend with that. 2003-11-26 Hans Petter Jansson * backends/file/e-book-backend-file.c (e_book_backend_file_load_uri): Rename to e_book_backend_file_load_source () and take an ESource instead of an URI. (e_book_backend_file_dispose): Don't free URI anymore. (e_book_backend_file_class_init): load_uri -> load_source. (e_book_backend_file_init): Don't init URI anymore. * backends/ldap/e-book-backend-ldap.c (e_book_backend_ldap_load_uri): Rename to e_book_backend_ldap_load_uri () and take an ESource instead of an URI. (e_book_backend_ldap_dispose): Don't free URI anymore. (e_book_backend_ldap_class_init): load_uri -> load_source. * backends/vcf/e-book-backend-vcf.c (e_book_backend_vcf_load_uri): Rename to e_book_backend_vcf_load_source () and take an ESource instead of an URI. (e_book_backend_vcf_dispose): Don't free URI anymore. (e_book_backend_vcf_class_init): load_uri -> load_source. (e_book_backend_vcf_init): Don't init URI anymore. * idl/Evolution-DataServer-Addressbook.idl (getBook): In parameter "uri" renamed to "source". Takes standalone source XML. * libebook/e-book.c (fetch_corba_book): Implement, taking ESource. (e_book_load_source): Implement. (e_book_load_uri): Create a source based on the URI and use e_book_load_source () to load that. * libedata-book/e-book-backend.c (e_book_backend_load_uri): Renamed to e_book_backend_load_source () and takes ESource instead of URI. (e_book_backend_get_uri): Renamed to e_book_backend_get_source () and returns ESource instead of URI. (e_book_backend_open): Use e_book_backend_load_source (). (e_book_backend_init): Don't init URI anymore. (e_book_backend_dispose): Don't free URI anymore. * libedata-book/e-data-book-factory.c (backend_last_client_gone_cb): Get URI from backend's ESource. (impl_GNOME_Evolution_Addressbook_BookFactory_getBook): Take standalone source XML, construct an ESource, and fetch a backend with that. * libedata-book/e-data-book.c (e_data_book_get_uri): Renamed to e_data_book_get_source () and return ESource. (e_data_book_construct): Take ESource instead of URI. (e_data_book_new): Take ESource instead of URI. (e_data_book_dispose): Don't free URI. Instead, unref ESource. --- diff --git a/ChangeLog b/ChangeLog index 9c45f40..45e9afd 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,14 @@ +2003-11-26 Hans Petter Jansson + + * libedataserver/e-source.c (impl_finalize): Support absolute URI. + (e_source_update_from_xml_node): Ditto. + (e_source_get_uri): Ditto. + (dump_common_to_xml_node): Implement for parameters common to + dependent and standalone ESources. + (e_source_dump_to_xml_node): Use dump_common_to_xml_node (). + (e_source_to_standalone_xml): Implement. + (e_source_new_from_standalone_xml): Implement. + 2003-11-26 Rodney Dawes * Makefile.am: remove \ on last line of LIBDB_FILES diff --git a/addressbook/ChangeLog b/addressbook/ChangeLog index dedc609..a58345b 100644 --- a/addressbook/ChangeLog +++ b/addressbook/ChangeLog @@ -1,3 +1,53 @@ +2003-11-26 Hans Petter Jansson + + * backends/file/e-book-backend-file.c (e_book_backend_file_load_uri): + Rename to e_book_backend_file_load_source () and take an ESource + instead of an URI. + (e_book_backend_file_dispose): Don't free URI anymore. + (e_book_backend_file_class_init): load_uri -> load_source. + (e_book_backend_file_init): Don't init URI anymore. + + * backends/ldap/e-book-backend-ldap.c (e_book_backend_ldap_load_uri): + Rename to e_book_backend_ldap_load_uri () and take an ESource instead + of an URI. + (e_book_backend_ldap_dispose): Don't free URI anymore. + (e_book_backend_ldap_class_init): load_uri -> load_source. + + * backends/vcf/e-book-backend-vcf.c (e_book_backend_vcf_load_uri): + Rename to e_book_backend_vcf_load_source () and take an ESource + instead of an URI. + (e_book_backend_vcf_dispose): Don't free URI anymore. + (e_book_backend_vcf_class_init): load_uri -> load_source. + (e_book_backend_vcf_init): Don't init URI anymore. + + * idl/Evolution-DataServer-Addressbook.idl (getBook): In parameter + "uri" renamed to "source". Takes standalone source XML. + + * libebook/e-book.c (fetch_corba_book): Implement, taking ESource. + (e_book_load_source): Implement. + (e_book_load_uri): Create a source based on the URI and use + e_book_load_source () to load that. + + * libedata-book/e-book-backend.c (e_book_backend_load_uri): Renamed + to e_book_backend_load_source () and takes ESource instead of URI. + (e_book_backend_get_uri): Renamed to e_book_backend_get_source () + and returns ESource instead of URI. + (e_book_backend_open): Use e_book_backend_load_source (). + (e_book_backend_init): Don't init URI anymore. + (e_book_backend_dispose): Don't free URI anymore. + + * libedata-book/e-data-book-factory.c (backend_last_client_gone_cb): + Get URI from backend's ESource. + (impl_GNOME_Evolution_Addressbook_BookFactory_getBook): Take + standalone source XML, construct an ESource, and fetch a backend + with that. + + * libedata-book/e-data-book.c (e_data_book_get_uri): Renamed to + e_data_book_get_source () and return ESource. + (e_data_book_construct): Take ESource instead of URI. + (e_data_book_new): Take ESource instead of URI. + (e_data_book_dispose): Don't free URI. Instead, unref ESource. + 2003-11-25 Chris Toshok * tests/ebook/test-self.c: new file/test, print out the current diff --git a/addressbook/backends/file/e-book-backend-file.c b/addressbook/backends/file/e-book-backend-file.c index 622dbb1..775f841 100644 --- a/addressbook/backends/file/e-book-backend-file.c +++ b/addressbook/backends/file/e-book-backend-file.c @@ -43,7 +43,6 @@ static EBookBackendSyncClass *e_book_backend_file_parent_class; struct _EBookBackendFilePrivate { - char *uri; char *dirname; char *filename; char *summary_filename; @@ -838,9 +837,9 @@ e_book_backend_file_maybe_upgrade_db (EBookBackendFile *bf) #include static GNOME_Evolution_Addressbook_CallStatus -e_book_backend_file_load_uri (EBookBackend *backend, - const char *uri, - gboolean only_if_exists) +e_book_backend_file_load_source (EBookBackend *backend, + ESource *source, + gboolean only_if_exists) { EBookBackendFile *bf = E_BOOK_BACKEND_FILE (backend); char *dirname, *filename; @@ -849,12 +848,13 @@ e_book_backend_file_load_uri (EBookBackend *backend, DB *db; time_t db_mtime; struct stat sb; + gchar *uri; - g_free(bf->priv->uri); - bf->priv->uri = g_strdup (uri); + uri = e_source_get_uri (source); dirname = e_book_backend_file_extract_path_from_uri (uri); filename = g_build_filename (dirname, "addressbook.db", NULL); + g_free (uri); db_error = e_db3_utils_maybe_recover (filename); if (db_error != 0) @@ -1069,7 +1069,6 @@ e_book_backend_file_dispose (GObject *object) if (bf->priv) { if (bf->priv->summary) g_object_unref(bf->priv->summary); - g_free (bf->priv->uri); g_free (bf->priv->filename); g_free (bf->priv->dirname); g_free (bf->priv->summary_filename); @@ -1094,7 +1093,7 @@ e_book_backend_file_class_init (EBookBackendFileClass *klass) backend_class = E_BOOK_BACKEND_CLASS (klass); /* Set the virtual methods. */ - backend_class->load_uri = e_book_backend_file_load_uri; + backend_class->load_source = e_book_backend_file_load_source; backend_class->get_static_capabilities = e_book_backend_file_get_static_capabilities; backend_class->start_book_view = e_book_backend_file_start_book_view; backend_class->stop_book_view = e_book_backend_file_stop_book_view; @@ -1119,7 +1118,6 @@ e_book_backend_file_init (EBookBackendFile *backend) EBookBackendFilePrivate *priv; priv = g_new0 (EBookBackendFilePrivate, 1); - priv->uri = NULL; backend->priv = priv; } diff --git a/addressbook/backends/ldap/e-book-backend-ldap.c b/addressbook/backends/ldap/e-book-backend-ldap.c index 718fdcf..165b2af 100644 --- a/addressbook/backends/ldap/e-book-backend-ldap.c +++ b/addressbook/backends/ldap/e-book-backend-ldap.c @@ -81,7 +81,6 @@ typedef struct LDAPOp LDAPOp; struct _EBookBackendLDAPPrivate { - char *uri; gboolean connected; gchar *ldap_host; /* the hostname of the server */ @@ -3037,9 +3036,9 @@ e_book_backend_ldap_get_supported_auth_methods (EBookBackend *backend, } static GNOME_Evolution_Addressbook_CallStatus -e_book_backend_ldap_load_uri (EBookBackend *backend, - const char *uri, - gboolean only_if_exists) +e_book_backend_ldap_load_source (EBookBackend *backend, + ESource *source, + gboolean only_if_exists) { EBookBackendLDAP *bl = E_BOOK_BACKEND_LDAP (backend); LDAPURLDesc *lud; @@ -3048,13 +3047,18 @@ e_book_backend_ldap_load_uri (EBookBackend *backend, int i; int limit = 100; int timeout = 60; /* 1 minute */ + gchar *uri; g_assert (bl->priv->connected == FALSE); + uri = e_source_get_uri (source); + attributes = g_strsplit (uri, ";", 0); - if (attributes[0] == NULL) + if (attributes[0] == NULL) { + g_free (uri); return FALSE; + } for (i = 1; attributes[i]; i++) { char *equals; @@ -3098,9 +3102,9 @@ e_book_backend_ldap_load_uri (EBookBackend *backend, ldap_error = ldap_url_parse ((char*)attributes[0], &lud); g_strfreev (attributes); + g_free (uri); + if (ldap_error == LDAP_SUCCESS) { - g_free(bl->priv->uri); - bl->priv->uri = g_strdup (uri); bl->priv->ldap_host = g_strdup(lud->lud_host); bl->priv->ldap_port = lud->lud_port; /* if a port wasn't specified, default to LDAP_PORT */ @@ -3191,8 +3195,6 @@ e_book_backend_ldap_dispose (GObject *object) g_list_free (bl->priv->supported_auth_methods); } - g_free (bl->priv->uri); - g_free (bl->priv); bl->priv = NULL; } @@ -3215,7 +3217,7 @@ e_book_backend_ldap_class_init (EBookBackendLDAPClass *klass) parent_class = E_BOOK_BACKEND_CLASS (klass); /* Set the virtual methods. */ - parent_class->load_uri = e_book_backend_ldap_load_uri; + parent_class->load_source = e_book_backend_ldap_load_source; parent_class->get_static_capabilities = e_book_backend_ldap_get_static_capabilities; parent_class->create_contact = e_book_backend_ldap_create_contact; diff --git a/addressbook/backends/vcf/e-book-backend-vcf.c b/addressbook/backends/vcf/e-book-backend-vcf.c index 902e3ba..3d7822c 100644 --- a/addressbook/backends/vcf/e-book-backend-vcf.c +++ b/addressbook/backends/vcf/e-book-backend-vcf.c @@ -34,7 +34,6 @@ typedef struct _EBookBackendVCFBookView EBookBackendVCFBookView; typedef struct _EBookBackendVCFSearchContext EBookBackendVCFSearchContext; struct _EBookBackendVCFPrivate { - char *uri; char *filename; GMutex *mutex; GHashTable *contacts; @@ -471,17 +470,17 @@ e_book_backend_vcf_get_supported_fields (EBookBackendSync *backend, #include static GNOME_Evolution_Addressbook_CallStatus -e_book_backend_vcf_load_uri (EBookBackend *backend, - const char *uri, - gboolean only_if_exists) +e_book_backend_vcf_load_source (EBookBackend *backend, + ESource *source, + gboolean only_if_exists) { EBookBackendVCF *bvcf = E_BOOK_BACKEND_VCF (backend); char *dirname; gboolean writable = FALSE; + gchar *uri; int fd; - g_free(bvcf->priv->uri); - bvcf->priv->uri = g_strdup (uri); + uri = e_source_get_uri (source); dirname = e_book_backend_vcf_extract_path_from_uri (uri); bvcf->priv->filename = g_build_filename (dirname, "addressbook.vcf", NULL); @@ -516,6 +515,7 @@ e_book_backend_vcf_load_uri (EBookBackend *backend, if (fd == -1) { g_warning ("Failed to open addressbook at uri `%s'", uri); g_warning ("error == %s", strerror(errno)); + g_free (uri); return GNOME_Evolution_Addressbook_OtherError; } @@ -524,6 +524,7 @@ e_book_backend_vcf_load_uri (EBookBackend *backend, e_book_backend_set_is_loaded (backend, TRUE); e_book_backend_set_is_writable (backend, writable); + g_free (uri); return GNOME_Evolution_Addressbook_Success; } @@ -591,7 +592,6 @@ e_book_backend_vcf_dispose (GObject *object) g_hash_table_destroy (bvcf->priv->contacts); - g_free (bvcf->priv->uri); g_free (bvcf->priv->filename); g_mutex_unlock (bvcf->priv->mutex); @@ -618,7 +618,7 @@ e_book_backend_vcf_class_init (EBookBackendVCFClass *klass) backend_class = E_BOOK_BACKEND_CLASS (klass); /* Set the virtual methods. */ - backend_class->load_uri = e_book_backend_vcf_load_uri; + backend_class->load_source = e_book_backend_vcf_load_source; backend_class->get_static_capabilities = e_book_backend_vcf_get_static_capabilities; backend_class->start_book_view = e_book_backend_vcf_start_book_view; backend_class->stop_book_view = e_book_backend_vcf_stop_book_view; @@ -641,7 +641,6 @@ e_book_backend_vcf_init (EBookBackendVCF *backend) EBookBackendVCFPrivate *priv; priv = g_new0 (EBookBackendVCFPrivate, 1); - priv->uri = NULL; priv->mutex = g_mutex_new(); backend->priv = priv; diff --git a/addressbook/idl/Evolution-DataServer-Addressbook.idl b/addressbook/idl/Evolution-DataServer-Addressbook.idl index 193d124..dd62b07 100644 --- a/addressbook/idl/Evolution-DataServer-Addressbook.idl +++ b/addressbook/idl/Evolution-DataServer-Addressbook.idl @@ -179,7 +179,7 @@ module Addressbook { interface BookFactory : Bonobo::Unknown { exception ProtocolNotSupported {}; - Book getBook (in string uri, in BookListener listener) + Book getBook (in string source, in BookListener listener) raises (ProtocolNotSupported); }; }; diff --git a/addressbook/libebook/e-book.c b/addressbook/libebook/e-book.c index 51e3f46..6be424b 100644 --- a/addressbook/libebook/e-book.c +++ b/addressbook/libebook/e-book.c @@ -1615,25 +1615,29 @@ activate_factories_for_uri (EBook *book, const char *uri) return factories; } -gboolean -e_book_load_uri (EBook *book, - const char *uri, - gboolean only_if_exists, - GError **error) +static gboolean +fetch_corba_book (EBook *book, + ESource *source, + gboolean only_if_exists, + GError **error) { + GNOME_Evolution_Addressbook_Book corba_book = CORBA_OBJECT_NIL; + gchar *uri; + gchar *source_xml; GList *factories; GList *l; gboolean rv = FALSE; - GNOME_Evolution_Addressbook_Book corba_book = CORBA_OBJECT_NIL; - - e_return_error_if_fail (book && E_IS_BOOK (book), E_BOOK_ERROR_INVALID_ARG); - e_return_error_if_fail (uri, E_BOOK_ERROR_INVALID_ARG); - /* XXX this needs to happen while holding the book's lock i would think... */ - e_return_error_if_fail (book->priv->load_state == E_BOOK_URI_NOT_LOADED, E_BOOK_ERROR_URI_ALREADY_LOADED); + uri = e_source_get_uri (source); + if (!uri) { + g_set_error (error, E_BOOK_ERROR, E_BOOK_ERROR_OTHER_ERROR, + _("e_book_load_uri: Invalid source.")); + return FALSE; + } /* try to find a list of factories that can handle the protocol */ - if (! (factories = activate_factories_for_uri (book, uri))) { + factories = activate_factories_for_uri (book, uri); + if (!factories) { g_set_error (error, E_BOOK_ERROR, E_BOOK_ERROR_PROTOCOL_NOT_SUPPORTED, _("e_book_load_uri: no factories available for uri `%s'"), uri); return FALSE; @@ -1656,7 +1660,9 @@ e_book_load_uri (EBook *book, G_CALLBACK (e_book_handle_response), book); g_free (book->priv->uri); - book->priv->uri = g_strdup (uri); + book->priv->uri = uri; + + source_xml = e_source_to_standalone_xml (source); for (l = factories; l; l = l->next) { GNOME_Evolution_Addressbook_BookFactory factory = l->data; @@ -1670,7 +1676,7 @@ e_book_load_uri (EBook *book, CORBA_exception_init (&ev); - corba_book = GNOME_Evolution_Addressbook_BookFactory_getBook (factory, book->priv->uri, + corba_book = GNOME_Evolution_Addressbook_BookFactory_getBook (factory, source_xml, bonobo_object_corba_objref (BONOBO_OBJECT (book->priv->listener)), &ev); @@ -1715,6 +1721,8 @@ e_book_load_uri (EBook *book, } } + g_free (source_xml); + /* free up the factories */ for (l = factories; l; l = l->next) CORBA_Object_release ((CORBA_Object)l->data, NULL); @@ -1737,6 +1745,49 @@ e_book_load_uri (EBook *book, } gboolean +e_book_load_source (EBook *book, + ESource *source, + gboolean only_if_exists, + GError **error) +{ + e_return_error_if_fail (book && E_IS_BOOK (book), E_BOOK_ERROR_INVALID_ARG); + e_return_error_if_fail (source && E_IS_SOURCE (source), E_BOOK_ERROR_INVALID_ARG); + + /* XXX this needs to happen while holding the book's lock i would think... */ + e_return_error_if_fail (book->priv->load_state == E_BOOK_URI_NOT_LOADED, E_BOOK_ERROR_URI_ALREADY_LOADED); + + return fetch_corba_book (book, source, only_if_exists, error); +} + +gboolean +e_book_load_uri (EBook *book, + const char *uri, + gboolean only_if_exists, + GError **error) +{ + ESourceGroup *group; + ESource *source; + gboolean rv; + + e_return_error_if_fail (book && E_IS_BOOK (book), E_BOOK_ERROR_INVALID_ARG); + e_return_error_if_fail (uri, E_BOOK_ERROR_INVALID_ARG); + + /* XXX this needs to happen while holding the book's lock i would think... */ + e_return_error_if_fail (book->priv->load_state == E_BOOK_URI_NOT_LOADED, E_BOOK_ERROR_URI_ALREADY_LOADED); + + group = e_source_group_new ("", uri); + source = e_source_new ("", ""); + e_source_set_group (source, group); + + rv = e_book_load_source (book, source, only_if_exists, error); + + g_object_unref (source); + g_object_unref (group); + + return rv; +} + +gboolean e_book_load_local_addressbook (EBook *book, GError **error) { diff --git a/addressbook/libebook/e-book.h b/addressbook/libebook/e-book.h index 737d1f3..dc69728 100644 --- a/addressbook/libebook/e-book.h +++ b/addressbook/libebook/e-book.h @@ -14,6 +14,7 @@ #include #include +#include #include #include #include @@ -60,6 +61,11 @@ struct _EBookClass { EBook *e_book_new (void); /* loading arbitrary addressbooks */ +gboolean e_book_load_source (EBook *book, + ESource *source, + gboolean only_if_exists, + GError **error); + gboolean e_book_load_uri (EBook *book, const char *uri, gboolean only_if_exists, diff --git a/addressbook/libedata-book/e-book-backend.c b/addressbook/libedata-book/e-book-backend.c index 71855ff..2073472 100644 --- a/addressbook/libedata-book/e-book-backend.c +++ b/addressbook/libedata-book/e-book-backend.c @@ -18,7 +18,7 @@ struct _EBookBackendPrivate { GMutex *clients_mutex; GList *clients; - char *uri; + ESource *source; gboolean loaded, writable, removed; GMutex *views_mutex; @@ -42,40 +42,42 @@ e_book_backend_construct (EBookBackend *backend) } GNOME_Evolution_Addressbook_CallStatus -e_book_backend_load_uri (EBookBackend *backend, - const char *uri, - gboolean only_if_exists) +e_book_backend_load_source (EBookBackend *backend, + ESource *source, + gboolean only_if_exists) { GNOME_Evolution_Addressbook_CallStatus status; g_return_val_if_fail (E_IS_BOOK_BACKEND (backend), FALSE); - g_return_val_if_fail (uri, FALSE); + g_return_val_if_fail (source, FALSE); g_return_val_if_fail (backend->priv->loaded == FALSE, FALSE); - g_assert (E_BOOK_BACKEND_GET_CLASS (backend)->load_uri); + g_assert (E_BOOK_BACKEND_GET_CLASS (backend)->load_source); - status = (* E_BOOK_BACKEND_GET_CLASS (backend)->load_uri) (backend, uri, only_if_exists); + status = (* E_BOOK_BACKEND_GET_CLASS (backend)->load_source) (backend, source, only_if_exists); - if (status == GNOME_Evolution_Addressbook_Success) - backend->priv->uri = g_strdup (uri); + if (status == GNOME_Evolution_Addressbook_Success) { + g_object_ref (source); + backend->priv->source = source; + } return status; } /** - * e_book_backend_get_uri: + * e_book_backend_get_source: * @backend: An addressbook backend. * - * Queries the URI that an addressbook backend is serving. + * Queries the source that an addressbook backend is serving. * - * Return value: URI for the backend. + * Return value: ESource for the backend. **/ -const char * -e_book_backend_get_uri (EBookBackend *backend) +ESource * +e_book_backend_get_source (EBookBackend *backend) { g_return_val_if_fail (E_IS_BOOK_BACKEND (backend), NULL); - return backend->priv->uri; + return backend->priv->source; } void @@ -95,7 +97,7 @@ e_book_backend_open (EBookBackend *backend, e_data_book_report_writable (book, backend->priv->writable); } else { GNOME_Evolution_Addressbook_CallStatus status = - e_book_backend_load_uri (backend, e_data_book_get_uri (book), only_if_exists); + e_book_backend_load_source (backend, e_data_book_get_source (book), only_if_exists); e_data_book_respond_open (book, status); @@ -583,7 +585,6 @@ e_book_backend_init (EBookBackend *backend) EBookBackendPrivate *priv; priv = g_new0 (EBookBackendPrivate, 1); - priv->uri = NULL; priv->clients = NULL; priv->views = e_list_new((EListCopyFunc) g_object_ref, (EListFreeFunc) g_object_unref, NULL); priv->open_mutex = g_mutex_new (); @@ -603,9 +604,6 @@ e_book_backend_dispose (GObject *object) if (backend->priv) { g_list_free (backend->priv->clients); - if (backend->priv->uri) - g_free (backend->priv->uri); - if (backend->priv->views) { g_object_unref (backend->priv->views); backend->priv->views = NULL; diff --git a/addressbook/libedata-book/e-book-backend.h b/addressbook/libedata-book/e-book-backend.h index adb01a2..47e79bb 100644 --- a/addressbook/libedata-book/e-book-backend.h +++ b/addressbook/libedata-book/e-book-backend.h @@ -47,7 +47,7 @@ struct _EBookBackendClass { GObjectClass parent_class; /* Virtual methods */ - GNOME_Evolution_Addressbook_CallStatus (*load_uri) (EBookBackend *backend, const char *uri, gboolean only_if_exists); + GNOME_Evolution_Addressbook_CallStatus (*load_source) (EBookBackend *backend, ESource *source, gboolean only_if_exists); void (*remove) (EBookBackend *backend, EDataBook *book); char *(*get_static_capabilities) (EBookBackend *backend); @@ -80,10 +80,10 @@ typedef EBookBackend * (*EBookBackendFactoryFn) (void); gboolean e_book_backend_construct (EBookBackend *backend); GNOME_Evolution_Addressbook_CallStatus - e_book_backend_load_uri (EBookBackend *backend, - const char *uri, - gboolean only_if_exists); -const char *e_book_backend_get_uri (EBookBackend *backend); + e_book_backend_load_source (EBookBackend *backend, + ESource *source, + gboolean only_if_exists); +ESource *e_book_backend_get_source (EBookBackend *backend); gboolean e_book_backend_add_client (EBookBackend *backend, EDataBook *book); diff --git a/addressbook/libedata-book/e-data-book-factory.c b/addressbook/libedata-book/e-data-book-factory.c index 42b8ef2..9ca65e3 100644 --- a/addressbook/libedata-book/e-data-book-factory.c +++ b/addressbook/libedata-book/e-data-book-factory.c @@ -153,13 +153,19 @@ static void backend_last_client_gone_cb (EBookBackend *backend, gpointer data) { EDataBookFactory *factory; - const char *uri; + ESource *source; + gchar *uri; factory = E_DATA_BOOK_FACTORY (data); /* Remove the backend from the active server map */ - uri = e_book_backend_get_uri (backend); + source = e_book_backend_get_source (backend); + if (source) + uri = e_source_get_uri (source); + else + uri = NULL; + if (uri) { gpointer orig_key; gboolean result; @@ -185,6 +191,8 @@ backend_last_client_gone_cb (EBookBackend *backend, gpointer data) /* Notify upstream if there are no more backends */ g_signal_emit (G_OBJECT (factory), factory_signals[LAST_BOOK_GONE], 0); } + + g_free (uri); } @@ -244,16 +252,36 @@ e_data_book_factory_launch_backend (EDataBookFactory *factory, static GNOME_Evolution_Addressbook_Book impl_GNOME_Evolution_Addressbook_BookFactory_getBook (PortableServer_Servant servant, - const CORBA_char *uri, + const CORBA_char *source_xml, const GNOME_Evolution_Addressbook_BookListener listener, CORBA_Environment *ev) { EDataBookFactory *factory = E_DATA_BOOK_FACTORY (bonobo_object (servant)); + GNOME_Evolution_Addressbook_Book corba_book; EBookBackend *backend; EDataBook *book; + ESource *source; + gchar *uri; printf ("impl_GNOME_Evolution_Addressbook_BookFactory_getBook\n"); + source = e_source_new_from_standalone_xml (source_xml); + if (!source) { + CORBA_exception_set (ev, CORBA_USER_EXCEPTION, + ex_GNOME_Evolution_Addressbook_BookFactory_ProtocolNotSupported, + NULL); + return CORBA_OBJECT_NIL; + } + + uri = e_source_get_uri (source); + if (!uri) { + g_object_unref (source); + CORBA_exception_set (ev, CORBA_USER_EXCEPTION, + ex_GNOME_Evolution_Addressbook_BookFactory_ProtocolNotSupported, + NULL); + return CORBA_OBJECT_NIL; + } + /* Look up the backend and create one if needed */ g_mutex_lock (factory->priv->map_mutex); @@ -271,12 +299,15 @@ impl_GNOME_Evolution_Addressbook_BookFactory_getBook (PortableServer_Servant g_mutex_unlock (factory->priv->map_mutex); + g_free (uri); return CORBA_OBJECT_NIL; } backend = e_data_book_factory_launch_backend (factory, backend_factory, listener, uri); } + g_free (uri); + if (backend) { GNOME_Evolution_Addressbook_BookListener listener_copy; @@ -284,11 +315,11 @@ impl_GNOME_Evolution_Addressbook_BookFactory_getBook (PortableServer_Servant g_mutex_unlock (factory->priv->map_mutex); - book = e_data_book_new (backend, uri, listener); + book = e_data_book_new (backend, source, listener); e_book_backend_add_client (backend, book); - return bonobo_object_corba_objref (BONOBO_OBJECT (book)); + corba_book = bonobo_object_corba_objref (BONOBO_OBJECT (book)); } else { /* probably need a more descriptive exception here */ @@ -297,8 +328,11 @@ impl_GNOME_Evolution_Addressbook_BookFactory_getBook (PortableServer_Servant NULL); g_mutex_unlock (factory->priv->map_mutex); - return CORBA_OBJECT_NIL; + corba_book = CORBA_OBJECT_NIL; } + + g_object_unref (source); + return corba_book; } static void diff --git a/addressbook/libedata-book/e-data-book.c b/addressbook/libedata-book/e-data-book.c index d1789ae..1114d48 100644 --- a/addressbook/libedata-book/e-data-book.c +++ b/addressbook/libedata-book/e-data-book.c @@ -25,7 +25,7 @@ POA_GNOME_Evolution_Addressbook_Book__vepv e_data_book_vepv; struct _EDataBookPrivate { EBookBackend *backend; GNOME_Evolution_Addressbook_BookListener listener; - char *uri; + ESource *source; }; static void @@ -247,10 +247,10 @@ e_data_book_get_listener (EDataBook *book) return book->priv->listener; } -const char* -e_data_book_get_uri (EDataBook *book) +ESource * +e_data_book_get_source (EDataBook *book) { - return book->priv->uri; + return book->priv->source; } /** @@ -660,13 +660,14 @@ e_data_book_report_writable (EDataBook *book, static void e_data_book_construct (EDataBook *book, EBookBackend *backend, - const char *uri, + ESource *source, GNOME_Evolution_Addressbook_BookListener listener) { EDataBookPrivate *priv; CORBA_Environment ev; g_return_if_fail (book != NULL); + g_return_if_fail (source != NULL); priv = book->priv; @@ -681,9 +682,10 @@ e_data_book_construct (EDataBook *book, CORBA_exception_free (&ev); - priv->backend = backend; - priv->uri = g_strdup (uri); + g_object_ref (source); + priv->backend = backend; + priv->source = source; } /** @@ -691,7 +693,7 @@ e_data_book_construct (EDataBook *book, */ EDataBook * e_data_book_new (EBookBackend *backend, - const char *uri, + ESource *source, GNOME_Evolution_Addressbook_BookListener listener) { EDataBook *book; @@ -701,7 +703,7 @@ e_data_book_new (EBookBackend *backend, "poa", bonobo_poa_get_threaded (ORBIT_THREAD_HINT_PER_REQUEST, NULL), NULL); - e_data_book_construct (book, backend, uri, listener); + e_data_book_construct (book, backend, source, listener); g_free (caps); @@ -724,7 +726,7 @@ e_data_book_dispose (GObject *object) CORBA_exception_free (&ev); - g_free (book->priv->uri); + g_object_unref (book->priv->source); g_free (book->priv); book->priv = NULL; } diff --git a/addressbook/libedata-book/e-data-book.h b/addressbook/libedata-book/e-data-book.h index e7f41d5..a3a73fc 100644 --- a/addressbook/libedata-book/e-data-book.h +++ b/addressbook/libedata-book/e-data-book.h @@ -14,6 +14,7 @@ #include #include +#include #include #include @@ -46,11 +47,11 @@ struct _EDataBookClass { EDataBook *e_data_book_new (EBookBackend *backend, - const char *uri, + ESource *source, GNOME_Evolution_Addressbook_BookListener listener); GNOME_Evolution_Addressbook_BookListener e_data_book_get_listener (EDataBook *book); EBookBackend *e_data_book_get_backend (EDataBook *book); -const char *e_data_book_get_uri (EDataBook *book); +ESource *e_data_book_get_source (EDataBook *book); void e_data_book_respond_open (EDataBook *book, GNOME_Evolution_Addressbook_CallStatus status); diff --git a/calendar/ChangeLog b/calendar/ChangeLog index 3af7525..e880041 100644 --- a/calendar/ChangeLog +++ b/calendar/ChangeLog @@ -1,3 +1,24 @@ +2003-11-26 Hans Petter Jansson + + * idl/Evolution-DataServer-Calendar.idl (getCal): Take source XML + instead of URI. + + * libecal/client-test.c (create_client): Adapt to API changes. + (main): Ditto. + + * libecal/e-cal.c (fetch_corba_cal): Move to ESource. + (e_cal_new): Take ESource. + (e_cal_new_from_uri): Implement convenience call that takes URI. + + * libedata-cal/e-cal-backend.c (e_cal_backend_set_property): + Implement PROP_SOURCE. + (e_cal_backend_get_property): Same. + (e_cal_backend_class_init): Same. + (e_cal_backend_get_source): Same. + + * libedata-cal/e-data-cal-factory.c (impl_CalFactory_getCal): Take + source XML and construct an ESource. Init backend with that. + 2003-11-25 Rodrigo Moya * backends/groupwise/e-gw-message.[ch]: new files to contain utility diff --git a/calendar/backends/file/e-cal-backend-file.c b/calendar/backends/file/e-cal-backend-file.c index 19fcce0..8327f78 100644 --- a/calendar/backends/file/e-cal-backend-file.c +++ b/calendar/backends/file/e-cal-backend-file.c @@ -587,7 +587,7 @@ get_uri_string_for_gnome_vfs (ECalBackend *backend) priv = cbfile->priv; master_uri = e_cal_backend_get_uri (backend); - + /* FIXME Check the error conditions a little more elegantly here */ if (g_strrstr ("tasks.ics", master_uri) || g_strrstr ("calendar.ics", master_uri)) { g_warning (G_STRLOC ": Existing file name %s", master_uri); diff --git a/calendar/idl/Evolution-DataServer-Calendar.idl b/calendar/idl/Evolution-DataServer-Calendar.idl index 42ddf62..76a010f 100644 --- a/calendar/idl/Evolution-DataServer-Calendar.idl +++ b/calendar/idl/Evolution-DataServer-Calendar.idl @@ -265,7 +265,7 @@ module Calendar { exception InvalidURI {}; exception UnsupportedMethod {}; - Cal getCal (in string uri, in CalObjType type, in CalListener listener) + Cal getCal (in string source, in CalObjType type, in CalListener listener) raises (NilListener, InvalidURI, UnsupportedMethod); }; }; diff --git a/calendar/libecal/client-test.c b/calendar/libecal/client-test.c index a7a5c5e..ef3019f 100644 --- a/calendar/libecal/client-test.c +++ b/calendar/libecal/client-test.c @@ -138,12 +138,12 @@ client_destroy_cb (gpointer data, GObject *object) /* Creates a calendar client and tries to load the specified URI into it */ static void -create_client (ECal **client, const char *uri, CalObjType type, gboolean only_if_exists) +create_client (ECal **client, const gchar *uri, CalObjType type, gboolean only_if_exists) { ECalView *query; GError *error = NULL; - *client = e_cal_new (uri, type); + *client = e_cal_new_from_uri (uri, type); if (!*client) { g_message (G_STRLOC ": could not create the client"); exit (1); @@ -152,6 +152,7 @@ create_client (ECal **client, const char *uri, CalObjType type, gboolean only_if g_object_weak_ref (G_OBJECT (*client), client_destroy_cb, NULL); cl_printf (*client, "Calendar loading `%s'...\n", uri); + if (!e_cal_open (*client, only_if_exists, &error)) { cl_printf (*client, "Load/create %s\n", error->message); exit (1); @@ -175,6 +176,7 @@ create_client (ECal **client, const char *uri, CalObjType type, gboolean only_if e_cal_view_start (query); g_idle_add (list_uids, *client); + } int @@ -191,8 +193,10 @@ main (int argc, char **argv) exit (1); } - create_client (&client1, "file:///home/gnome24-evolution-new-calendar/evolution/local/Calendar", - CALOBJ_TYPE_EVENT, FALSE); +#if 0 + source = e_source_new ("test-source", "file:///home/gnome24-evolution-new-calendar/evolution/local/Calendar"); +#endif + create_client (&client1, "file:///home/hpj/.evolution/calendar/local/OnThisComputer/Pakk", CALOBJ_TYPE_EVENT, FALSE); // create_client (&client2, "file:///tmp/tasks", TRUE); bonobo_main (); diff --git a/calendar/libecal/e-cal.c b/calendar/libecal/e-cal.c index eafb934..49b5b18 100644 --- a/calendar/libecal/e-cal.c +++ b/calendar/libecal/e-cal.c @@ -1196,45 +1196,58 @@ e_cal_get_type (void) static gboolean -fetch_corba_cal (ECal *ecal, const char *str_uri, CalObjType type) +fetch_corba_cal (ECal *ecal, ESource *source, CalObjType type) { ECalPrivate *priv; GList *f; CORBA_Environment ev; + gchar *source_xml; + gchar *str_uri; + gboolean result = FALSE; priv = ecal->priv; g_return_val_if_fail (priv->load_state == E_CAL_LOAD_NOT_LOADED, FALSE); g_assert (priv->uri == NULL); + g_return_val_if_fail (source != NULL, FALSE); - g_return_val_if_fail (str_uri != NULL, FALSE); + str_uri = e_source_get_uri (source); + if (!str_uri) + return FALSE; - if (!get_factories (str_uri, &priv->factories)) + if (!get_factories (str_uri, &priv->factories)) { + g_free (str_uri); return FALSE; + } priv->uri = g_strdup (str_uri); priv->type = type; + source_xml = e_source_to_standalone_xml (source); + for (f = priv->factories; f; f = f->next) { GNOME_Evolution_Calendar_Cal cal; CORBA_exception_init (&ev); - cal = GNOME_Evolution_Calendar_CalFactory_getCal (f->data, priv->uri, priv->type, + cal = GNOME_Evolution_Calendar_CalFactory_getCal (f->data, source_xml, priv->type, BONOBO_OBJREF (priv->listener), &ev); if (BONOBO_EX (&ev)) continue; priv->cal = cal; - return TRUE; + result = TRUE; + break; } - return FALSE; + g_free (str_uri); + g_free (source_xml); + return result; } /** * e_cal_new: - * @uri: + * @source: * @type: * * Creates a new calendar ecal. It should be initialized by calling @@ -1244,13 +1257,13 @@ fetch_corba_cal (ECal *ecal, const char *str_uri, CalObjType type) * not be constructed because it could not contact the calendar server. **/ ECal * -e_cal_new (const char *uri, CalObjType type) +e_cal_new (ESource *source, CalObjType type) { ECal *ecal; ecal = g_object_new (E_TYPE_CAL, NULL); - if (!fetch_corba_cal (ecal, uri, type)) { + if (!fetch_corba_cal (ecal, source, type)) { g_object_unref (ecal); return NULL; @@ -1260,6 +1273,36 @@ e_cal_new (const char *uri, CalObjType type) } /** + * e_cal_new_from_uri: + * @uri: + * @type: + * + * Creates a new calendar ecal. It should be initialized by calling + * e_cal_open(). + * + * Return value: A newly-created calendar ecal, or NULL if the ecal could + * not be constructed because it could not contact the calendar server. + **/ +ECal * +e_cal_new_from_uri (const gchar *uri, CalObjType type) +{ + ESourceGroup *group; + ESource *source; + ECal *cal; + + group = e_source_group_new ("", uri); + source = e_source_new ("", ""); + e_source_set_group (source, group); + + cal = e_cal_new (source, type); + + g_object_unref (source); + g_object_unref (group); + + return cal; +} + +/** * e_cal_set_auth_func * @ecal: A calendar ecal. * @func: The authentication function diff --git a/calendar/libecal/e-cal.h b/calendar/libecal/e-cal.h index 8fb12dd..17682b9 100644 --- a/calendar/libecal/e-cal.h +++ b/calendar/libecal/e-cal.h @@ -22,6 +22,7 @@ #define E_CAL_H #include +#include #include #include #include @@ -93,7 +94,8 @@ GType e_cal_open_status_enum_get_type (void); GType e_cal_set_mode_status_enum_get_type (void); GType cal_mode_enum_get_type (void); -ECal *e_cal_new (const char *uri, CalObjType type); +ECal *e_cal_new (ESource *source, CalObjType type); +ECal *e_cal_new_from_uri (const gchar *uri, CalObjType type); void e_cal_set_auth_func (ECal *ecal, ECalAuthFunc func, gpointer data); diff --git a/calendar/libedata-cal/e-cal-backend.c b/calendar/libedata-cal/e-cal-backend.c index 6886aa6..89287d3 100644 --- a/calendar/libedata-cal/e-cal-backend.c +++ b/calendar/libedata-cal/e-cal-backend.c @@ -42,7 +42,10 @@ typedef struct { /* Private part of the CalBackend structure */ struct _ECalBackendPrivate { - /* The uri for this backend */ + /* The source for this backend */ + ESource *source; + + /* URI, from source. This is cached, since we return const. */ char *uri; /* The kind of components for this backend */ @@ -70,6 +73,7 @@ struct _ECalBackendPrivate { /* Property IDs */ enum props { PROP_0, + PROP_SOURCE, PROP_URI, PROP_KIND }; @@ -136,9 +140,31 @@ e_cal_backend_set_property (GObject *object, guint property_id, const GValue *va priv = backend->priv; switch (property_id) { + case PROP_SOURCE: + { + ESource *new_source; + + new_source = g_value_get_object (value); + if (new_source) + g_object_ref (new_source); + + if (priv->source) + g_object_unref (priv->source); + + priv->source = new_source; + + /* Cache the URI */ + if (new_source) { + g_free (priv->uri); + priv->uri = e_source_get_uri (priv->source); + } + } + break; case PROP_URI: - g_free (priv->uri); - priv->uri = g_value_dup_string (value); + if (!priv->source) { + g_free (priv->uri); + priv->uri = g_value_dup_string (value); + } break; case PROP_KIND: priv->kind = g_value_get_ulong (value); @@ -159,6 +185,9 @@ e_cal_backend_get_property (GObject *object, guint property_id, GValue *value, G priv = backend->priv; switch (property_id) { + case PROP_SOURCE: + g_value_set_object (value, e_cal_backend_get_source (backend)); + break; case PROP_URI: g_value_set_string (value, e_cal_backend_get_uri (backend)); break; @@ -185,6 +214,11 @@ e_cal_backend_class_init (ECalBackendClass *class) object_class->get_property = e_cal_backend_get_property; object_class->finalize = e_cal_backend_finalize; + g_object_class_install_property (object_class, PROP_SOURCE, + g_param_spec_object ("source", NULL, NULL, E_TYPE_SOURCE, + G_PARAM_READABLE | G_PARAM_WRITABLE + | G_PARAM_CONSTRUCT_ONLY)); + g_object_class_install_property (object_class, PROP_URI, g_param_spec_string ("uri", NULL, NULL, "", G_PARAM_READABLE | G_PARAM_WRITABLE @@ -323,6 +357,19 @@ e_cal_backend_finalize (GObject *object) +ESource * +e_cal_backend_get_source (ECalBackend *backend) +{ + ECalBackendPrivate *priv; + + g_return_val_if_fail (backend != NULL, NULL); + g_return_val_if_fail (E_IS_CAL_BACKEND (backend), NULL); + + priv = backend->priv; + + return priv->source; +} + /** * e_cal_backend_get_uri: * @backend: A calendar backend. diff --git a/calendar/libedata-cal/e-cal-backend.h b/calendar/libedata-cal/e-cal-backend.h index acaa82f..80ede5e 100644 --- a/calendar/libedata-cal/e-cal-backend.h +++ b/calendar/libedata-cal/e-cal-backend.h @@ -25,6 +25,7 @@ #define E_CAL_BACKEND_H #include +#include #include #include #include @@ -110,6 +111,7 @@ struct _ECalBackendClass { GType e_cal_backend_get_type (void); +ESource *e_cal_backend_get_source (ECalBackend *backend); const char *e_cal_backend_get_uri (ECalBackend *backend); icalcomponent_kind e_cal_backend_get_kind (ECalBackend *backend); diff --git a/calendar/libedata-cal/e-data-cal-factory.c b/calendar/libedata-cal/e-data-cal-factory.c index 31d8907..596b344 100644 --- a/calendar/libedata-cal/e-data-cal-factory.c +++ b/calendar/libedata-cal/e-data-cal-factory.c @@ -24,6 +24,7 @@ #include #include #include +#include #include "e-cal-backend.h" #include "e-data-cal.h" #include "e-data-cal-factory.h" @@ -148,7 +149,7 @@ backend_last_client_gone_cb (ECalBackend *backend, gpointer data) static GNOME_Evolution_Calendar_Cal impl_CalFactory_getCal (PortableServer_Servant servant, - const CORBA_char *str_uri, + const CORBA_char *source_xml, const GNOME_Evolution_Calendar_CalObjType type, const GNOME_Evolution_Calendar_CalListener listener, CORBA_Environment *ev) @@ -160,14 +161,34 @@ impl_CalFactory_getCal (PortableServer_Servant servant, CORBA_Environment ev2; GNOME_Evolution_Calendar_CalListener listener_copy; GType backend_type; + ESource *source; + char *str_uri; EUri *uri; char *uri_string; factory = E_DATA_CAL_FACTORY (bonobo_object_from_servant (servant)); priv = factory->priv; + source = e_source_new_from_standalone_xml (source_xml); + if (!source) { + bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); + + return CORBA_OBJECT_NIL; + } + + /* Get the URI so we can extract the protocol */ + str_uri = e_source_get_uri (source); + if (!str_uri) { + g_object_unref (source); + bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); + + return CORBA_OBJECT_NIL; + } + /* Parse the uri */ uri = e_uri_new (str_uri); + g_free (str_uri); + if (!uri) { bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_InvalidURI); @@ -199,7 +220,7 @@ impl_CalFactory_getCal (PortableServer_Servant servant, backend = lookup_backend (factory, uri_string); if (!backend) { /* There was no existing backend, create a new one */ - backend = g_object_new (backend_type, "uri", uri_string, "kind", calobjtype_to_icalkind (type), NULL); + backend = g_object_new (backend_type, "source", source, "kind", calobjtype_to_icalkind (type), NULL); if (!backend) { g_warning (G_STRLOC ": could not instantiate backend"); bonobo_exception_set (ev, ex_GNOME_Evolution_Calendar_CalFactory_UnsupportedMethod); @@ -228,6 +249,7 @@ impl_CalFactory_getCal (PortableServer_Servant servant, cleanup: e_uri_free (uri); g_free (uri_string); + g_object_unref (source); return CORBA_Object_duplicate (BONOBO_OBJREF (cal), ev); } @@ -373,7 +395,7 @@ e_data_cal_factory_register_storage (EDataCalFactory *factory, const char *iid) return TRUE; case Bonobo_ACTIVATION_REG_NOT_LISTED: - g_warning (G_STRLOC ": cannot register the calendar factory (not listed)"); + g_warning (G_STRLOC ": cannot register the calendar factory %s (not listed)", tmp_iid); break; case Bonobo_ACTIVATION_REG_ALREADY_ACTIVE: diff --git a/libedataserver/e-source.c b/libedataserver/e-source.c index c27ff27..090b930 100644 --- a/libedataserver/e-source.c +++ b/libedataserver/e-source.c @@ -46,6 +46,7 @@ struct _ESourcePrivate { char *uid; char *name; char *relative_uri; + char *absolute_uri; gboolean has_color; guint32 color; @@ -83,6 +84,7 @@ impl_finalize (GObject *object) g_free (priv->uid); g_free (priv->name); g_free (priv->relative_uri); + g_free (priv->absolute_uri); g_free (priv); (* G_OBJECT_CLASS (parent_class)->finalize) (object); @@ -213,15 +215,17 @@ e_source_update_from_xml_node (ESource *source, { xmlChar *name; xmlChar *relative_uri; + xmlChar *absolute_uri; xmlChar *color_string; gboolean retval; gboolean changed = FALSE; name = xmlGetProp (node, "name"); relative_uri = xmlGetProp (node, "relative_uri"); + absolute_uri = xmlGetProp (node, "uri"); color_string = xmlGetProp (node, "color"); - if (name == NULL || relative_uri == NULL) { + if (name == NULL || (relative_uri == NULL && absolute_uri == NULL)) { retval = FALSE; goto done; } @@ -239,6 +243,12 @@ e_source_update_from_xml_node (ESource *source, changed = TRUE; } + if (absolute_uri != NULL) { + g_free (source->priv->absolute_uri); + source->priv->absolute_uri = g_strdup (absolute_uri); + changed = TRUE; + } + if (color_string == NULL) { if (source->priv->has_color) { source->priv->has_color = FALSE; @@ -268,6 +278,8 @@ e_source_update_from_xml_node (ESource *source, xmlFree (name); if (relative_uri != NULL) xmlFree (relative_uri); + if (absolute_uri != NULL) + xmlFree (absolute_uri); if (color_string != NULL) xmlFree (color_string); @@ -443,8 +455,12 @@ e_source_get_uri (ESource *source) g_return_val_if_fail (E_IS_SOURCE (source), NULL); - if (source->priv->group == NULL) + if (source->priv->group == NULL) { + if (source->priv->absolute_uri != NULL) + return g_strdup (source->priv->absolute_uri); + return NULL; + } base_uri_str = e_source_group_peek_base_uri (source->priv->group); @@ -461,16 +477,18 @@ e_source_get_uri (ESource *source) } -void -e_source_dump_to_xml_node (ESource *source, - xmlNodePtr parent_node) +static xmlNodePtr +dump_common_to_xml_node (ESource *source, + xmlNodePtr parent_node) { gboolean has_color; guint32 color; - xmlNodePtr node = xmlNewChild (parent_node, NULL, "source", NULL); - - g_return_if_fail (E_IS_SOURCE (source)); + xmlNodePtr node; + if (parent_node) + node = xmlNewChild (parent_node, NULL, "source", NULL); + else + node = xmlNewNode (NULL, "source"); xmlSetProp (node, "uid", e_source_peek_uid (source)); xmlSetProp (node, "name", e_source_peek_name (source)); @@ -482,4 +500,72 @@ e_source_dump_to_xml_node (ESource *source, xmlSetProp (node, "color", color_string); g_free (color_string); } + + return node; +} + + +void +e_source_dump_to_xml_node (ESource *source, + xmlNodePtr parent_node) +{ + g_return_if_fail (E_IS_SOURCE (source)); + + dump_common_to_xml_node (source, parent_node); +} + + +char * +e_source_to_standalone_xml (ESource *source) +{ + xmlDocPtr doc; + xmlNodePtr node; + xmlChar *xml_buffer; + char *returned_buffer; + int xml_buffer_size; + gchar *uri; + + g_return_val_if_fail (E_IS_SOURCE (source), NULL); + g_return_val_if_fail (source->priv->group != NULL, NULL); + + doc = xmlNewDoc ("1.0"); + node = dump_common_to_xml_node (source, NULL); + + xmlDocSetRootElement (doc, node); + + uri = e_source_get_uri (source); + xmlSetProp (node, "uri", uri); + g_free (uri); + + xmlDocDumpMemory (doc, &xml_buffer, &xml_buffer_size); + xmlFreeDoc (doc); + + returned_buffer = g_malloc (xml_buffer_size + 1); + memcpy (returned_buffer, xml_buffer, xml_buffer_size); + returned_buffer [xml_buffer_size] = '\0'; + xmlFree (xml_buffer); + + return returned_buffer; +} + + +ESource * +e_source_new_from_standalone_xml (const char *xml) +{ + xmlDocPtr doc; + xmlNodePtr root; + ESource *source; + + doc = xmlParseDoc ((char *) xml); + if (doc == NULL) + return NULL; + + root = doc->children; + if (strcmp (root->name, "source") != 0) + return NULL; + + source = e_source_new_from_xml_node (root); + xmlFreeDoc (doc); + + return source; } diff --git a/libedataserver/e-source.h b/libedataserver/e-source.h index 6060b8b..87afbef 100644 --- a/libedataserver/e-source.h +++ b/libedataserver/e-source.h @@ -58,6 +58,7 @@ GType e_source_get_type (void); ESource *e_source_new (const char *name, const char *relative_uri); ESource *e_source_new_from_xml_node (xmlNodePtr node); +ESource *e_source_new_from_standalone_xml (const char *xml); gboolean e_source_update_from_xml_node (ESource *source, xmlNodePtr node, @@ -86,6 +87,7 @@ char *e_source_get_uri (ESource *source); void e_source_dump_to_xml_node (ESource *source, xmlNodePtr parent_node); +char *e_source_to_standalone_xml (ESource *source); #endif /* _E_SOURCE_H_ */