diff options
Diffstat (limited to 'sync/src')
-rw-r--r-- | sync/src/Makefile.am | 2 | ||||
-rw-r--r-- | sync/src/sync_evo2_item.c | 2 | ||||
-rw-r--r-- | sync/src/sync_evo2_item.h | 4 | ||||
-rw-r--r-- | sync/src/sync_file_item.c | 1 | ||||
-rw-r--r-- | sync/src/sync_file_item.h | 4 | ||||
-rw-r--r-- | sync/src/sync_group.c | 13 | ||||
-rw-r--r-- | sync/src/sync_main.c | 108 | ||||
-rw-r--r-- | sync/src/sync_syncml_item.c | 248 | ||||
-rw-r--r-- | sync/src/sync_syncml_item.h | 22 |
9 files changed, 367 insertions, 37 deletions
diff --git a/sync/src/Makefile.am b/sync/src/Makefile.am index 1682416..80a4ba5 100644 --- a/sync/src/Makefile.am +++ b/sync/src/Makefile.am @@ -5,7 +5,7 @@ bin_PROGRAMS = sync sync_SOURCES = sync_main.c sync.h sync_group.c sync_group.h sync_item.c \ sync_item.h sync_evo2_item.c sync_evo2_item.h sync_file_item.c \ - sync_file_item.h + sync_file_item.h sync_syncml_item.c sync_syncml_item.h sync_LDADD = $(SYNC_LIBS) diff --git a/sync/src/sync_evo2_item.c b/sync/src/sync_evo2_item.c index 69a0c65..19666b9 100644 --- a/sync/src/sync_evo2_item.c +++ b/sync/src/sync_evo2_item.c @@ -2,7 +2,7 @@ #include <opensync/opensync.h> #include <glib.h> #include <string.h> -#include "sync.h" +#include "sync_group.h" #include "sync_item.h" #include "sync_evo2_item.h" diff --git a/sync/src/sync_evo2_item.h b/sync/src/sync_evo2_item.h index 9717aae..3c446d9 100644 --- a/sync/src/sync_evo2_item.h +++ b/sync/src/sync_evo2_item.h @@ -1,6 +1,6 @@ -#ifndef SYNC_EVO2_H -#define SYNC_EVO2_H +#ifndef SYNC_EVO2_ITEM_H +#define SYNC_EVO2_ITEM_H #include <glib.h> #include "sync_item.h" diff --git a/sync/src/sync_file_item.c b/sync/src/sync_file_item.c index 9e4ce0b..132c4de 100644 --- a/sync/src/sync_file_item.c +++ b/sync/src/sync_file_item.c @@ -2,7 +2,6 @@ #include <opensync/opensync.h> #include <glib.h> #include <string.h> -#include "sync.h" #include "sync_item.h" #include "sync_group.h" #include "sync_file_item.h" diff --git a/sync/src/sync_file_item.h b/sync/src/sync_file_item.h index b1ae516..20c8bdf 100644 --- a/sync/src/sync_file_item.h +++ b/sync/src/sync_file_item.h @@ -1,6 +1,6 @@ -#ifndef SYNC_FILE_H -#define SYNC_FILE_H +#ifndef SYNC_FILE_ITEM_H +#define SYNC_FILE_ITEM_H #include <glib.h> #include "sync_item.h" diff --git a/sync/src/sync_group.c b/sync/src/sync_group.c index f9aa6f6..b5771c5 100644 --- a/sync/src/sync_group.c +++ b/sync/src/sync_group.c @@ -10,7 +10,7 @@ G_DEFINE_TYPE (SyncGroup, sync_group, G_TYPE_OBJECT); #define GROUP_PRIVATE(o) \ (G_TYPE_INSTANCE_GET_PRIVATE ((o), SYNC_TYPE_GROUP, SyncGroupPrivate)) -/*#define DEBUG*/ +#define DEBUG typedef struct _SyncGroupPrivate SyncGroupPrivate; @@ -730,7 +730,7 @@ sync_group_start (SyncGroup *group) g_warning ("Error while initializing syncengine: %s", osync_error_print (&error)); osync_error_free (&error); - sync_group_free_engine (group); +/* sync_group_free_engine (group);*/ return FALSE; } @@ -759,13 +759,18 @@ sync_group_resolve_conflict (SyncGroup *group, SyncGroupConflictRes res) } switch (res) { + case ABORT: + sync_group_abort (group); + break; case USE_ITEM1: case USE_ITEM2: - case ABORT: case IGNORE: - default: osengine_mapping_ignore_conflict ( priv->engine, priv->mapping); + break; + default: + g_warning ("Invalid conflict resolution code"); + return; } priv->mapping = NULL; diff --git a/sync/src/sync_main.c b/sync/src/sync_main.c index 85ca89c..c5d4278 100644 --- a/sync/src/sync_main.c +++ b/sync/src/sync_main.c @@ -14,6 +14,7 @@ #include "sync_item.h" #include "sync_evo2_item.h" #include "sync_file_item.h" +#include "sync_syncml_item.h" #if 0 static gboolean sync_clean_backup (SyncData *data) @@ -231,13 +232,13 @@ sync_failed_cb (SyncGroup *group, SyncData *data) g_source_remove (data->animate_id); } -static gboolean +gboolean sync_activate_cursor_item_cb (GtkIconView *iconview, SyncData *data) { return FALSE; } -static void +void sync_item_activated_cb (GtkIconView *iconview, GtkTreePath *arg1, SyncData *data) { @@ -282,6 +283,8 @@ sync_item_activated_cb (GtkIconView *iconview, GtkTreePath *arg1, data->xml, "sync_image_notebook"); gtk_notebook_set_current_page ( GTK_NOTEBOOK (widget), IMAGE_TAB_PREPARE); + widget = glade_xml_get_widget (data->xml, "cancel_button"); + gtk_widget_set_sensitive (widget, TRUE); widget = glade_xml_get_widget (data->xml, "main_notebook"); gtk_notebook_set_current_page (GTK_NOTEBOOK (widget), TAB_SYNC); data->animate_id = g_timeout_add ( @@ -289,7 +292,7 @@ sync_item_activated_cb (GtkIconView *iconview, GtkTreePath *arg1, } } -static void +void sync_sync_button_cb (GtkWidget *source, SyncData *data) { GtkWidget *widget = glade_xml_get_widget (data->xml, "main_iconview"); @@ -302,13 +305,79 @@ sync_sync_button_cb (GtkWidget *source, SyncData *data) } } -static void +void +sync_abort_cb (GtkWidget *source, SyncData *data) +{ + GtkWidget *widget = glade_xml_get_widget (data->xml, "cancel_button"); + gtk_widget_set_sensitive (widget, FALSE); + sync_group_abort (data->group); +} + +void +sync_conflict_resolve_cb (GtkWidget *source, SyncData *data) +{ + GtkWidget *widget; + SyncGroupConflictRes res = IGNORE; + + if (strcmp (gtk_widget_get_name (source), "abort_button") == 0) { + widget = glade_xml_get_widget (data->xml, "cancel_button"); + gtk_widget_set_sensitive (widget, FALSE); + res = ABORT; + } else if (strcmp (gtk_widget_get_name (source), "ignore_button") == 0) + res = IGNORE; + else if (strcmp (gtk_widget_get_name (source), "use_local_button") == 0) + res = USE_ITEM1; + else if (strcmp (gtk_widget_get_name (source), "use_ext_button") == 0) + res = USE_ITEM2; + + sync_group_resolve_conflict (data->group, res); + widget = glade_xml_get_widget (data->xml, "main_notebook"); + gtk_notebook_set_current_page (GTK_NOTEBOOK (widget), TAB_SYNC); +} + +void sync_chooser_cb (GtkWidget *source, SyncData *data) { GtkWidget *widget = glade_xml_get_widget (data->xml, "main_notebook"); gtk_notebook_set_current_page (GTK_NOTEBOOK (widget), TAB_CHOOSE); } +/* From Dates */ +static void +dates_autoconnect (const gchar *handler_name, GObject *object, + const gchar *signal_name, const gchar *signal_data, + GObject *connect_object, gboolean after, + gpointer user_data) +{ + static GModule *symbols = NULL; + GCallback func; + GCallback *pfunc = &func; + + if (!symbols) { + symbols = g_module_open(NULL, 0); + } + + if (!g_module_symbol (symbols, handler_name, (gpointer *)pfunc)) { + g_warning ("Handler '%s' not found.", handler_name); + return; + } + + if (connect_object) { + if (after) + g_signal_connect_object (object, signal_name, + func, connect_object, G_CONNECT_AFTER); + else + g_signal_connect_object (object, signal_name, + func, connect_object, 0); + } else { + if (after) + g_signal_connect_after(object, signal_name, + func, user_data); + else + g_signal_connect(object, signal_name, func, user_data); + } +} + int main (int argc, char **argv) { @@ -369,6 +438,13 @@ main (int argc, char **argv) 0, COL_NAME, "Test", COL_PIXBUF, data.backup_icon, -1); g_free (temp_path); + preset_item = g_object_ref (sync_syncml_item_new ("Mobical", + "http://www.mobical.net/sync/server", CONTACTS, + "guest", "guest", "con")); + g_hash_table_insert (data.sync_items, "Mobical", preset_item); + gtk_list_store_insert_with_values (GTK_LIST_STORE (data.model), &iter, + 0, COL_NAME, "Mobical", COL_PIXBUF, data.network_icon, -1); + /* TODO: Insert saved items */ /* TODO: Avahi detection of local sync servers */ /* TODO: Bluetooth scanning? */ @@ -381,28 +457,8 @@ main (int argc, char **argv) gtk_tree_path_free (path); - widget = glade_xml_get_widget (data.xml, "quit_menuitem"); - g_signal_connect (G_OBJECT (widget), "activate", - G_CALLBACK (gtk_main_quit), NULL); - widget = glade_xml_get_widget (data.xml, "main_window"); - g_signal_connect (G_OBJECT (widget), "destroy", - G_CALLBACK (gtk_main_quit), NULL); - widget = glade_xml_get_widget (data.xml, "main_iconview"); - g_signal_connect (G_OBJECT (widget), "activate-cursor-item", - G_CALLBACK (sync_activate_cursor_item_cb), &data); - g_signal_connect (G_OBJECT (widget), "item-activated", - G_CALLBACK (sync_item_activated_cb), &data); - widget = glade_xml_get_widget (data.xml, "sync_button"); - g_signal_connect (G_OBJECT (widget), "clicked", - G_CALLBACK (sync_sync_button_cb), &data); - - widget = glade_xml_get_widget (data.xml, "success_close_button"); - g_signal_connect (G_OBJECT (widget), "clicked", - G_CALLBACK (sync_chooser_cb), &data); - - widget = glade_xml_get_widget (data.xml, "error_close_button"); - g_signal_connect (G_OBJECT (widget), "clicked", - G_CALLBACK (sync_chooser_cb), &data); + /* Connect signals */ + glade_xml_signal_autoconnect_full (data.xml, dates_autoconnect, &data); /* Connect SyncGroup signals */ g_signal_connect (G_OBJECT (data.group), "started", diff --git a/sync/src/sync_syncml_item.c b/sync/src/sync_syncml_item.c new file mode 100644 index 0000000..00a9b56 --- /dev/null +++ b/sync/src/sync_syncml_item.c @@ -0,0 +1,248 @@ + +#include <opensync/opensync.h> +#include <glib.h> +#include <gconf/gconf-client.h> +#include <string.h> +#include "sync_group.h" +#include "sync_item.h" +#include "sync_syncml_item.h" + +#define SYNCML_PLUGIN "syncml-client" +#define SYNCML_CONFIG "<config>" \ + "<gconf-uri>%s</gconf-uri>" \ + "<object-type>%s</object-type>" \ + "<sync-source-name>%s</sync-source-name>" \ + "</config>" + +#define GCONF_ROOT "/apps/libsync/" + +typedef struct { + const gchar *key; + const gchar *value; +} SyncGConfSchema; + +/* NOTE: See the GConf schema that ships with the syncml client api */ +static const SyncGConfSchema syncml_config[] = { + { "/spds/syncml/begin", "0" }, + { "/spds/syncml/checkConn", "1" }, + { "/spds/syncml/deviceId", "localhost" }, + { "/spds/syncml/end", "0" }, + { "/spds/syncml/firstTimeSyncMode", "two-way" }, + { "/spds/syncml/password", "guest" }, + { "/spds/syncml/proxyHost", "" }, + { "/spds/syncml/proxyPort", "" }, + { "/spds/syncml/responseTimeout", "180" }, + { "/spds/syncml/serverName", "" }, + { "/spds/syncml/syncUrl", "" }, + { "/spds/syncml/useProxy", "" }, + { "/spds/syncml/username", "guest" }, + + { "/spds/sources/cal/dir", "/tmp/libsync" }, + { "/spds/sources/cal/last", "0" }, + { "/spds/sources/cal/name", "cal" }, + { "/spds/sources/cal/sync", "two-way" }, + { "/spds/sources/cal/syncModes", "none,slow,two-way" }, + { "/spds/sources/cal/type", "text/x-vcalendar" }, + { "/spds/sources/cal/uri", "cal" }, + + { "/spds/sources/card/dir", "/tmp/libsync" }, + { "/spds/sources/card/last", "0" }, + { "/spds/sources/card/name", "card" }, + { "/spds/sources/card/sync", "two-way" }, + { "/spds/sources/card/syncModes", "none,slow,two-way" }, + { "/spds/sources/card/type", "text/x-vcard" }, + { "/spds/sources/card/uri", "con" }, + + { "/spds/sources/note/dir", "/tmp/libsync" }, + { "/spds/sources/note/last", "0" }, + { "/spds/sources/note/name", "note" }, + { "/spds/sources/note/sync", "two-way" }, + { "/spds/sources/note/syncModes", "none,slow,two-way" }, + { "/spds/sources/note/type", "text/plain" }, + { "/spds/sources/note/uri", "note" }, + + { "/spds/sources/task/dir", "/tmp/libsync" }, + { "/spds/sources/task/last", "0" }, + { "/spds/sources/task/name", "task" }, + { "/spds/sources/task/sync", "two-way" }, + { "/spds/sources/task/syncModes", "none,slow,two-way" }, + { "/spds/sources/task/type", "text/x-vcalendar" }, + { "/spds/sources/task/uri", "task" }, + + { NULL } +}; + +#define NAME_KEY "/spds/syncml/serverName" +#define ADR_KEY "/spds/syncml/syncUrl" +#define USER_KEY "/spds/syncml/username" +#define PASS_KEY "/spds/syncml/password" +#define DIR_KEY "%s/spds/sources/%s/uri" + +typedef struct { + SyncSyncMLType type; + gchar *username; + gchar *password; + gchar *dir; +} SyncSyncMLItemData; + +static const char * +sync_syncml_type_to_type_string (SyncSyncMLType type) +{ + switch (type) { + case CONTACTS: return "contact"; + case EVENTS: return "event"; + case TODO: return "todo"; + case NOTE: return "note"; + default: + g_warning ("Invalid type!"); + return NULL; + } +} + +static const char * +sync_syncml_type_to_source_string (SyncSyncMLType type) +{ + switch (type) { + case CONTACTS: return "card"; + case EVENTS: return "cal"; + case TODO: return "task"; + case NOTE: return "note"; + default: + g_warning ("Invalid type!"); + return NULL; + } +} + +static OSyncMember * +sync_syncml_item_get_member (SyncItem *item) +{ + OSyncMember *member; + OSyncError *error = NULL; + OSyncConfigurationTypes type = NO_CONFIGURATION; + SyncGroup *group; + OSyncGroup *os_group; + + /* Setup SyncML sync member */ + group = sync_item_get_group (item); + os_group = sync_group_get_osync_group (group); + member = osync_member_new (os_group); + if (!osync_member_instance_plugin (member, SYNCML_PLUGIN, &error)) { + g_warning ("Error instancing SyncML client plug-in: %s", + osync_error_print (&error)); + osync_error_free (&error); + return NULL; + } + if (!osync_member_need_config (member, &type, &error)) { + g_warning ("Error reading plug-in config requirements: %s", + osync_error_print (&error)); + osync_error_free (&error); + return NULL; + } + if (type == NO_CONFIGURATION) { + g_warning ("SyncML client plug-in reports no need for " + "configuration"); + } else { + gint i; + SyncSyncMLItemData *data; + gchar *xml_config, *gconf_root, *gconf_path; + OSyncFormatEnv *env; + GConfClient *client = gconf_client_get_default (); + + data = (SyncSyncMLItemData *)sync_item_get_data (item); + + /* Configure OpenSync conf */ + gconf_root = g_strconcat (GCONF_ROOT, + sync_item_get_name (item), NULL); + + xml_config = g_strdup_printf (SYNCML_CONFIG, gconf_root, + sync_syncml_type_to_type_string (data->type), + sync_syncml_type_to_source_string (data->type)); + osync_member_set_config ( + member, xml_config, strlen (xml_config)); + g_free (xml_config); + + /* Configure funambol syncml client GConf keys */ + for (i = 0; syncml_config[i].key; i++) { + gconf_path = g_strconcat ( + gconf_root, syncml_config[i].key, NULL); + + gconf_client_set_string (client, + gconf_path, syncml_config[i].value, NULL); + g_free (gconf_path); + } + + gconf_path = g_strconcat (gconf_root, NAME_KEY, NULL); + gconf_client_set_string (client, gconf_path, + sync_item_get_name (item), NULL); + g_free (gconf_path); + + gconf_path = g_strconcat (gconf_root, ADR_KEY, NULL); + gconf_client_set_string (client, gconf_path, + sync_item_get_adr (item), NULL); + g_free (gconf_path); + + gconf_path = g_strconcat (gconf_root, USER_KEY, NULL); + gconf_client_set_string (client, gconf_path, data->username, + NULL); + g_free (gconf_path); + + gconf_path = g_strconcat (gconf_root, PASS_KEY, NULL); + gconf_client_set_string (client, gconf_path, data->password, + NULL); + g_free (gconf_path); + + gconf_path = g_strdup_printf (DIR_KEY, gconf_root, + sync_syncml_type_to_source_string (data->type)); + gconf_client_set_string (client, gconf_path, data->dir, NULL); + g_free (gconf_path); + + g_free (gconf_root); + + /* Filter out unwanted objects */ + env = osync_conv_env_new (osync_group_get_env (os_group)); + for (i = 0; i < osync_conv_num_objtypes (env); i++) { + const gchar *type = osync_objtype_get_name ( + osync_conv_nth_objtype (env, i)); + + if (strcmp (type, sync_syncml_type_to_type_string ( + data->type)) == 0) + continue; + + osync_group_set_objtype_enabled (os_group, type, 0); + } + } + + return member; +} + +static void +sync_syncml_free_data (SyncSyncMLItemData *data) +{ + g_free (data->username); + g_free (data->password); + if (data->dir) g_free (data->dir); + g_free (data); +} + +SyncItem * +sync_syncml_item_new (const gchar *name, const gchar *address, + SyncSyncMLType type, const gchar *username, + const gchar *password, const gchar *dir) +{ + SyncItem *item; + SyncSyncMLItemData *data; + + item = sync_item_new (name, address, sync_syncml_item_get_member); + + data = g_new0 (SyncSyncMLItemData, 1); + data->type = type; + data->username = username ? g_strdup (username) : g_strdup (""); + data->password = password ? g_strdup (password) : g_strdup (""); + data->dir = dir ? g_strdup (dir) : NULL; + + sync_item_set_data (item, data); + sync_item_set_data_free_func (item, + (SyncItemDataFreeFunc)sync_syncml_free_data); + + return item; +} diff --git a/sync/src/sync_syncml_item.h b/sync/src/sync_syncml_item.h new file mode 100644 index 0000000..541c342 --- /dev/null +++ b/sync/src/sync_syncml_item.h @@ -0,0 +1,22 @@ + +#ifndef SYNC_SYNCML_ITEM_H +#define SYNC_SYNCML_ITEM_H + +#include <glib.h> +#include "sync_item.h" + +typedef enum { + CONTACTS, + EVENTS, + TODO, + NOTE, +} SyncSyncMLType; + +SyncItem * sync_syncml_item_new (const gchar *name, + const gchar *address, + SyncSyncMLType type, + const gchar *username, + const gchar *password, + const gchar *dir); + +#endif |