aboutsummaryrefslogtreecommitdiffstats
path: root/mail
diff options
context:
space:
mode:
Diffstat (limited to 'mail')
-rw-r--r--mail/ChangeLog23
-rw-r--r--mail/em-folder-browser.c7
-rw-r--r--mail/evolution-mail.schemas.in28
-rw-r--r--mail/mail-component.c229
-rw-r--r--mail/mail-component.h1
-rw-r--r--mail/mail-config.c44
-rw-r--r--mail/mail-config.h2
-rw-r--r--mail/mail-mt.c44
-rw-r--r--mail/mail-mt.h1
-rw-r--r--mail/mail-ops.c17
-rw-r--r--mail/mail-send-recv.c5
11 files changed, 391 insertions, 10 deletions
diff --git a/mail/ChangeLog b/mail/ChangeLog
index 5228a70f7e..6e488e1ee7 100644
--- a/mail/ChangeLog
+++ b/mail/ChangeLog
@@ -1,3 +1,26 @@
+2007-12-17 Srinivasa Ragavan <sragavan@novell.com>
+
+ ** Non-intrusive errror reporting and basic logging support.
+
+ * em-folder-browser.c: (emfb_help_debug): Invoke the debug menu.
+ * evolution-mail.schemas.in: Schema for error timeout and level.
+ * mail-component.c: (mail_component_init), (render_pixbuf),
+ (render_level), (render_date), (append_logs), (spin_value_changed),
+ (mail_component_show_logger): Handle the lifecycle of the logger.
+ * mail-component.h: Api to show the logger.
+ * mail-config.c: (gconf_error_time_changed),
+ (gconf_error_level_changed), (mail_config_init),
+ (mail_config_get_error_timeout), (mail_config_get_error_level): Load
+ and get the error time and level.
+ * mail-config.h:
+ * mail-mt.c: (mail_msg_set_cancelable), (mail_msg_new),
+ (end_event_callback), (mail_msg_free), (mail_msg_check_error),
+ (operation_cancel), (do_op_status): Revamp the error handling.
+ * mail-mt.h:
+ * mail-ops.c: (send_queue_send), (mail_send_queue): Handle the send/receive
+ case of error reporting separately.
+ * mail-send-recv.c: (free_send_info), (mail_send):
+
2007-12-15 Matthew Barnes <mbarnes@redhat.com>
* em-folder-tree-model.c (emft_model_unread_count_changed),
diff --git a/mail/em-folder-browser.c b/mail/em-folder-browser.c
index 83193f42e8..e3e35ab3c0 100644
--- a/mail/em-folder-browser.c
+++ b/mail/em-folder-browser.c
@@ -1550,6 +1550,12 @@ emfb_focus_search(BonoboUIComponent *uid, void *data, const char *path)
}
static void
+emfb_help_debug (BonoboUIComponent *uid, void *data, const char *path)
+{
+ mail_component_show_logger ((GtkWidget *) data);
+}
+
+static void
emfb_tools_vfolders(BonoboUIComponent *uid, void *data, const char *path)
{
/* FIXME: rename/refactor this */
@@ -1583,6 +1589,7 @@ static BonoboUIVerb emfb_verbs[] = {
BONOBO_UI_UNSAFE_VERB ("FolderRefresh", emfb_folder_refresh),
BONOBO_UI_UNSAFE_VERB ("FolderRename", emfb_folder_rename),
BONOBO_UI_UNSAFE_VERB ("FolderCreate", emfb_folder_create),
+ BONOBO_UI_UNSAFE_VERB ("HelpDebug", emfb_help_debug),
BONOBO_UI_UNSAFE_VERB ("MailPost", emfb_mail_post),
BONOBO_UI_UNSAFE_VERB ("MailStop", emfb_mail_stop),
diff --git a/mail/evolution-mail.schemas.in b/mail/evolution-mail.schemas.in
index ffba439eb9..d4fc65a618 100644
--- a/mail/evolution-mail.schemas.in
+++ b/mail/evolution-mail.schemas.in
@@ -918,6 +918,34 @@
</locale>
</schema>
+ <schema>
+ <key>/schemas/apps/evolution/mail/display/error_timeout</key>
+ <applyto>/apps/evolution/mail/display/error_timeout</applyto>
+ <owner>evolution-mail</owner>
+ <type>int</type>
+ <default>60</default>
+ <locale name="C">
+ <short>Amount of time in seconds the error should be showed on the status bar.</short>
+ <long>
+ Amount of time in seconds the error should be showed on the status bar.
+ </long>
+ </locale>
+ </schema>
+ <schema>
+ <key>/schemas/apps/evolution/mail/display/error_level</key>
+ <applyto>/apps/evolution/mail/display/error_level</applyto>
+ <owner>evolution-mail</owner>
+ <type>int</type>
+ <default>0</default>
+ <locale name="C">
+ <short>Level beyond which it should the message should be logged.</short>
+ <long> This can have three possible values. 0 for errors. 1 for warnings.
+ 2 for debug messages.
+ </long>
+ </locale>
+ </schema>
+
+
<!-- Labels and Colours -->
<schema>
diff --git a/mail/mail-component.c b/mail/mail-component.c
index 9c2fd80524..b8ff1c2df9 100644
--- a/mail/mail-component.c
+++ b/mail/mail-component.c
@@ -46,10 +46,12 @@
#include "em-folder-selection.h"
#include "em-folder-utils.h"
#include "em-migrate.h"
+#include "e-util/e-icon-factory.h"
#include "misc/e-info-label.h"
#include "e-util/e-error.h"
#include "e-util/e-util-private.h"
+#include "e-util/e-logger.h"
#include "em-search-context.h"
#include "mail-config.h"
@@ -139,6 +141,7 @@ struct _MailComponentPrivate {
char *context_path; /* current path for right-click menu */
CamelStore *local_store;
+ ELogger *logger;
EComponentView *component_view;
};
@@ -481,6 +484,7 @@ impl_finalize (GObject *object)
g_free (priv->context_path);
g_mutex_free(priv->lock);
+ g_object_unref (priv->logger);
g_free (priv);
(* G_OBJECT_CLASS (parent_class)->finalize) (object);
@@ -1205,8 +1209,10 @@ mail_component_init (MailComponent *component)
abort ();
priv->model = em_folder_tree_model_new (priv->base_directory);
-
+ priv->logger = e_logger_create ("mail");
priv->activity_handler = e_activity_handler_new ();
+ e_activity_handler_set_logger (priv->activity_handler, priv->logger);
+ e_activity_handler_set_error_flush_time (priv->activity_handler, mail_config_get_error_timeout ()*1000);
mail_session_init (priv->base_directory);
@@ -1495,4 +1501,225 @@ mail_indicate_new_mail (gboolean have_new_mail)
e_component_view_set_button_icon (mc->priv->component_view, icon);
}
+struct _log_data {
+ int level;
+ char *key;
+ char *text;
+ char *icon;
+ GdkPixbuf *pbuf;
+} ldata [] = {
+ { E_LOG_ERROR, N_("Error"), N_("Errors"), "stock_dialog-error" },
+ { E_LOG_WARNINGS, N_("Warning"), N_("Warnings and Errors"), "stock_dialog-warning" },
+ { E_LOG_DEBUG, N_("Debug"), N_("Error, Warnings and Debug messages"), "stock_dialog-info" }
+};
+
+enum
+{
+ COL_LEVEL = 0,
+ COL_TIME,
+ COL_DATA
+};
+
+static void
+render_pixbuf (GtkTreeViewColumn *column, GtkCellRenderer *renderer,
+ GtkTreeModel *model, GtkTreeIter *iter, gpointer user_data)
+{
+ static gboolean initialised = FALSE;
+ gint level;
+ int i;
+
+ if (!initialised) {
+ for (i=E_LOG_ERROR; i<=E_LOG_DEBUG; i++) {
+ ldata[i].pbuf = e_icon_factory_get_icon (ldata[i].icon, E_ICON_SIZE_MENU);
+ }
+ initialised = TRUE;
+ }
+
+ gtk_tree_model_get (model, iter, COL_LEVEL, &level, -1);
+ g_object_set (renderer, "pixbuf", ldata[level].pbuf, "visible", TRUE, NULL);
+}
+
+static void
+render_level (GtkTreeViewColumn *column, GtkCellRenderer *renderer,
+ GtkTreeModel *model, GtkTreeIter *iter, gpointer user_data)
+{
+ gint level;
+
+ gtk_tree_model_get (model, iter, COL_LEVEL, &level, -1);
+ g_object_set (renderer, "text", ldata[level].key, NULL);
+}
+
+static void
+render_date (GtkTreeViewColumn *column, GtkCellRenderer *renderer,
+ GtkTreeModel *model, GtkTreeIter *iter, gpointer user_data)
+{
+ time_t t;
+ char sdt[100]; /* Should be sufficient? */
+
+ gtk_tree_model_get (model, iter, COL_TIME, &t, -1);
+ strftime (sdt, 100, "%x %X", localtime (&t));
+ g_object_set (renderer, "text", sdt, NULL);
+}
+
+
+
+static void
+append_logs (const char *txt, GtkListStore *store)
+{
+ char **str;
+
+ str = g_strsplit (txt, ":", 3);
+ if (str[0] && str[1] && str[2]) {
+ int level;
+ time_t time;
+ char *data;
+ GtkTreeIter iter;
+
+ level = atoi (str[0]);
+ time = atol (str[1]);
+ data = strrchr (str[2], '\n');
+ *data = 0;
+ data = str[2];
+
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter,
+ COL_LEVEL, level,
+ COL_TIME, time,
+ COL_DATA, data,
+ -1);
+ } else
+ printf("Unable to decode error log: %s\n", txt);
+
+ g_strfreev (str);
+
+
+}
+
+static void
+spin_value_changed (GtkSpinButton *b, gpointer data)
+{
+ int value = gtk_spin_button_get_value_as_int (b);
+ GConfClient *client = mail_config_get_gconf_client ();
+
+ gconf_client_set_int (client, "/apps/evolution/mail/display/error_timeout", value, NULL);
+}
+
+void
+mail_component_show_logger (gpointer top)
+{
+ MailComponent *mc = mail_component_peek ();
+ GtkWidget *window, *hbox, *vbox, *spin, *label, *combo, *scrolled;
+ ELogger *logger = mc->priv->logger;
+ int i;
+ GtkListStore *store;
+ GtkCellRenderer *renderer;
+ GtkTreeView *treeview;
+ GtkTreeViewColumn *column;
+
+ window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
+ gtk_window_set_transient_for ((GtkWindow *) window, (GtkWindow *) gtk_widget_get_toplevel ((GtkWidget *) top));
+ gtk_container_set_border_width ((GtkContainer *) window, 6);
+
+ gtk_window_set_title ((GtkWindow *) window, _("Debug Logs"));
+ vbox = gtk_vbox_new (FALSE, 6);
+ hbox = gtk_hbox_new (FALSE, 6);
+ gtk_container_add ((GtkContainer *) window, vbox);
+ label = gtk_label_new_with_mnemonic (_("Show _errors in the status bar for"));
+ gtk_box_pack_start ((GtkBox *) hbox, label, FALSE, FALSE, 6);
+ spin = gtk_spin_button_new_with_range(1.0, 60.0, 1.0);
+ gtk_spin_button_set_value ((GtkSpinButton *) spin, (double) mail_config_get_error_timeout ());
+ g_signal_connect (spin, "value-changed", G_CALLBACK (spin_value_changed), NULL);
+ gtk_label_set_mnemonic_widget ((GtkLabel *) label, spin);
+ gtk_box_pack_start ((GtkBox *) hbox, spin, FALSE, FALSE, 6);
+ label = gtk_label_new_with_mnemonic (_("seconds."));
+ gtk_box_pack_start ((GtkBox *) hbox, label, FALSE, FALSE, 6);
+ gtk_box_pack_start ((GtkBox *) vbox, hbox, FALSE, FALSE, 6);
+
+ combo = gtk_combo_box_new_text ();
+ for (i = E_LOG_ERROR; i <=E_LOG_DEBUG; i++)
+ gtk_combo_box_append_text (GTK_COMBO_BOX (combo), ldata[i].text);
+ gtk_combo_box_set_active ((GtkComboBox *) combo, mail_config_get_error_level ());
+
+ hbox = gtk_hbox_new (FALSE, 6);
+ label = gtk_label_new_with_mnemonic (_("Log Messages:"));
+ gtk_label_set_mnemonic_widget ((GtkLabel *) label, combo);
+ gtk_box_pack_start ((GtkBox *) hbox, label, FALSE, FALSE, 6);
+ gtk_box_pack_start ((GtkBox *) hbox, combo, FALSE, FALSE, 6);
+ gtk_box_pack_start ((GtkBox *) vbox, hbox, FALSE, FALSE, 6);
+
+ store = gtk_list_store_new(3, G_TYPE_INT, G_TYPE_LONG, G_TYPE_STRING);
+ e_logger_get_logs (logger, (ELogFunction) append_logs, store);
+ if (0)
+ {
+ GtkTreeIter iter;
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter,
+ COL_LEVEL, 0,
+ COL_TIME, "21/12/07 10:55 PM",
+ COL_DATA, "Error Refreshing Folder",
+ -1);
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter,
+ COL_LEVEL, 1,
+ COL_TIME, "21/12/07 10:55 PM",
+ COL_DATA, "Error refreshing folder",
+ -1);
+ gtk_list_store_append(store, &iter);
+ gtk_list_store_set(store, &iter,
+ COL_LEVEL, 2,
+ COL_TIME, "21/12/07 10:55 PM",
+ COL_DATA, "Error refreshing folder",
+ -1);
+ }
+ gtk_tree_sortable_set_sort_column_id(GTK_TREE_SORTABLE (store),
+ COL_TIME, GTK_SORT_DESCENDING);
+
+
+ treeview = (GtkTreeView *)gtk_tree_view_new();
+ gtk_tree_view_set_rules_hint ((GtkTreeView *) treeview, TRUE);
+ gtk_tree_view_set_reorderable(GTK_TREE_VIEW(treeview), FALSE);
+ gtk_tree_view_set_model(treeview, GTK_TREE_MODEL (store));
+ gtk_tree_view_set_search_column(treeview, COL_DATA);
+ gtk_tree_view_set_headers_visible(treeview, TRUE);
+
+ column = gtk_tree_view_column_new ();
+ gtk_tree_view_append_column ((GtkTreeView *) treeview, column);
+ renderer = gtk_cell_renderer_pixbuf_new ();
+ gtk_tree_view_column_pack_start (column, renderer, FALSE);
+ gtk_tree_view_column_set_cell_data_func (column, renderer, render_pixbuf, NULL, NULL);
+
+
+ column = gtk_tree_view_column_new ();
+ gtk_tree_view_append_column ((GtkTreeView *) treeview, column);
+ renderer = gtk_cell_renderer_text_new ();
+ gtk_tree_view_column_pack_start (column, renderer, FALSE);
+ gtk_tree_view_column_set_title (column, _("Log Level"));
+ gtk_tree_view_column_set_cell_data_func (column, renderer, render_level, NULL, NULL);
+
+
+ column = gtk_tree_view_column_new ();
+ gtk_tree_view_append_column ((GtkTreeView *) treeview, column);
+ renderer = gtk_cell_renderer_text_new ();
+ gtk_tree_view_column_set_title (column, _("Time"));
+ gtk_tree_view_column_pack_start (column, renderer, FALSE);
+ gtk_tree_view_column_set_cell_data_func (column, renderer, render_date, NULL, NULL);
+
+
+ renderer = gtk_cell_renderer_text_new ();
+ gtk_tree_view_insert_column_with_attributes(treeview,
+ -1, _("Messages"),
+ renderer, "text", COL_DATA,
+ NULL);
+
+ scrolled = gtk_scrolled_window_new (NULL, NULL);
+ gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled),
+ GTK_POLICY_AUTOMATIC, GTK_POLICY_AUTOMATIC);
+ gtk_scrolled_window_set_shadow_type (GTK_SCROLLED_WINDOW (scrolled), GTK_SHADOW_IN);
+
+ gtk_container_add (GTK_CONTAINER (scrolled), (GtkWidget *) treeview);
+
+ gtk_box_pack_start ((GtkBox *) vbox, (GtkWidget *) scrolled, TRUE, TRUE, 6);
+ gtk_widget_show_all (window);
+}
+
BONOBO_TYPE_FUNC_FULL (MailComponent, GNOME_Evolution_MailComponent, PARENT_TYPE, mail_component)
diff --git a/mail/mail-component.h b/mail/mail-component.h
index e5c5a29e6f..b2d96d1761 100644
--- a/mail/mail-component.h
+++ b/mail/mail-component.h
@@ -101,5 +101,6 @@ const char *mail_component_get_folder_uri(MailComponent *mc, enum _mail_componen
int status_check (GNOME_Evolution_ShellState shell_state);
void mail_indicate_new_mail (gboolean have_new_mail);
+void mail_component_show_logger (gpointer);
#endif /* _MAIL_COMPONENT_H_ */
diff --git a/mail/mail-config.c b/mail/mail-config.c
index f10ac3e868..a59128b9f1 100644
--- a/mail/mail-config.c
+++ b/mail/mail-config.c
@@ -112,6 +112,10 @@ typedef struct {
gint mlimit_size;
guint magic_spacebar_notify_id;
gboolean magic_spacebar;
+ guint error_time;
+ guint error_notify_id;
+ guint error_level;
+ guint error_level_id;
GPtrArray *mime_types;
guint mime_types_notify_id;
@@ -340,6 +344,20 @@ gconf_address_count_changed (GConfClient *client, guint cnxn_id,
}
static void
+gconf_error_time_changed (GConfClient *client, guint cnxn_id,
+ GConfEntry *entry, gpointer user_data)
+{
+ config->error_time = gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/error_timeout", NULL);
+}
+
+static void
+gconf_error_level_changed (GConfClient *client, guint cnxn_id,
+ GConfEntry *entry, gpointer user_data)
+{
+ config->error_level = gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/error_level", NULL);
+}
+
+static void
gconf_address_compress_changed (GConfClient *client, guint cnxn_id,
GConfEntry *entry, gpointer user_data)
{
@@ -403,6 +421,11 @@ mail_config_init (void)
gconf_address_compress_changed, NULL, NULL, NULL);
config->font_notify_id = gconf_client_notify_add (config->gconf, "/apps/evolution/mail/display/address_count",
gconf_address_count_changed, NULL, NULL, NULL);
+ config->error_notify_id = gconf_client_notify_add (config->gconf, "/apps/evolution/mail/display/error_timeout",
+ gconf_error_time_changed, NULL, NULL, NULL);
+ config->error_level_id = gconf_client_notify_add (config->gconf, "/apps/evolution/mail/display/error_level",
+ gconf_error_level_changed, NULL, NULL, NULL);
+
config->mlimit_notify_id = gconf_client_notify_add (config->gconf, "/apps/evolution/mail/display/force_message_limit",
gconf_mlimit_changed, NULL, NULL, NULL);
config->mlimit_size_notify_id = gconf_client_notify_add (config->gconf, "/apps/evolution/mail/display/message_text_part_limit",
@@ -432,6 +455,9 @@ mail_config_init (void)
config_cache_mime_types ();
config->address_compress = gconf_client_get_bool (config->gconf, "/apps/evolution/mail/display/address_compress", NULL);
config->address_count = gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/address_count", NULL);
+ config->error_time = gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/error_timeout", NULL);
+ config->error_level= gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/error_level", NULL);
+
config->mlimit = gconf_client_get_bool (config->gconf, "/apps/evolution/mail/display/force_message_limit", NULL);
config->mlimit_size = gconf_client_get_int (config->gconf, "/apps/evolution/mail/display/message_text_part_limit", NULL);
config->magic_spacebar = gconf_client_get_bool (config->gconf, "/apps/evolution/mail/display/magic_spacebar", NULL);
@@ -576,6 +602,24 @@ mail_config_get_address_count (void)
return config->address_count;
}
+guint
+mail_config_get_error_timeout (void)
+{
+ if (!config)
+ mail_config_init ();
+
+ return config->error_time;
+}
+
+guint
+mail_config_get_error_level (void)
+{
+ if (!config)
+ mail_config_init ();
+
+ return config->error_level;
+}
+
int
mail_config_get_message_limit (void)
{
diff --git a/mail/mail-config.h b/mail/mail-config.h
index 698cb74399..3d159fe7e1 100644
--- a/mail/mail-config.h
+++ b/mail/mail-config.h
@@ -162,6 +162,8 @@ void mail_config_uri_deleted (GCompareFunc uri_cmp, const char *uri);
/* static utility functions */
char *mail_config_folder_to_cachename (struct _CamelFolder *folder, const char *prefix);
char *mail_config_folder_to_safe_url (struct _CamelFolder *folder);
+guint mail_config_get_error_timeout (void);
+guint mail_config_get_error_level (void);
GType evolution_mail_config_get_type (void);
diff --git a/mail/mail-mt.c b/mail/mail-mt.c
index 9572d3cd3f..af5dfd741d 100644
--- a/mail/mail-mt.c
+++ b/mail/mail-mt.c
@@ -67,6 +67,8 @@ struct _mail_msg_priv {
int activity_state; /* sigh sigh sigh, we need to keep track of the state external to the
pointer itself for locking/race conditions */
int activity_id;
+ GtkWidget *error;
+ gboolean cancelable;
};
static GdkPixbuf *progress_icon = NULL;
@@ -88,6 +90,11 @@ MailAsyncEvent *mail_async_event;
static void mail_msg_destroy(EThread *e, EMsg *msg, void *data);
+void mail_msg_set_cancelable (struct _mail_msg *msg, gboolean status)
+{
+ msg->priv->cancelable = status;
+}
+
void *mail_msg_new(mail_msg_op_t *ops, EMsgPort *reply_port, size_t size)
{
struct _mail_msg *msg;
@@ -129,6 +136,7 @@ void *mail_msg_new(mail_msg_op_t *ops, EMsgPort *reply_port, size_t size)
msg->cancel = camel_operation_new(mail_operation_status, GINT_TO_POINTER(msg->seq));
camel_exception_init(&msg->ex);
msg->priv = g_malloc0(sizeof(*msg->priv));
+ msg->priv->cancelable = TRUE;
g_hash_table_insert(mail_msg_active_table, GINT_TO_POINTER(msg->seq), msg);
@@ -144,12 +152,18 @@ void *mail_msg_new(mail_msg_op_t *ops, EMsgPort *reply_port, size_t size)
}
-static void end_event_callback (CamelObject *o, void *event_data, void *data)
+static void end_event_callback (CamelObject *o, void *event_data, void *error)
{
EActivityHandler *activity_handler = mail_component_peek_activity_handler (mail_component_peek ());
guint activity_id = GPOINTER_TO_INT (event_data);
- e_activity_handler_operation_finished (activity_handler, activity_id);
+ if (!error) {
+ e_activity_handler_operation_finished (activity_handler, activity_id);
+ } else {
+ d(printf("Yahooooo, we got it nonintrusively\n"));
+ e_activity_handler_operation_set_error (activity_handler, activity_id, error);
+
+ }
}
@@ -181,6 +195,7 @@ void mail_msg_free(void *msg)
{
struct _mail_msg *m = msg;
int activity_id;
+ GtkWidget *error = NULL;
#ifdef MALLOC_CHECK
checkmem(m);
@@ -212,11 +227,18 @@ void mail_msg_free(void *msg)
return;
} else {
activity_id = m->priv->activity_id;
+ error = m->priv->error;
+ if (error && !activity_id) {
+ e_activity_handler_make_error (mail_component_peek_activity_handler (mail_component_peek ()), "mail",
+ g_object_get_data ((GObject *) error, "primary"), error);
+ printf("Making error\n");
+ }
+
}
MAIL_MT_UNLOCK(mail_msg_lock);
- if (m->cancel) {
+ if (m->cancel && m->cancel != -1) {
camel_operation_mute(m->cancel);
camel_operation_unref(m->cancel);
}
@@ -228,7 +250,7 @@ void mail_msg_free(void *msg)
if (activity_id != 0)
mail_async_event_emit(mail_async_event, MAIL_ASYNC_GUI, (MailAsyncFunc) end_event_callback,
- NULL, GINT_TO_POINTER (activity_id), NULL);
+ NULL, GINT_TO_POINTER (activity_id), error);
}
/* hash table of ops->dialogue of active errors */
@@ -286,7 +308,10 @@ void mail_msg_check_error(void *msg)
g_hash_table_insert(active_errors, m->ops, gd);
g_signal_connect(gd, "response", G_CALLBACK(error_response), m->ops);
g_signal_connect(gd, "destroy", G_CALLBACK(error_destroy), m->ops);
- gtk_widget_show((GtkWidget *)gd);
+ if (m->priv->cancelable)
+ m->priv->error = gd;
+ else
+ gtk_widget_show((GtkWidget *)gd);
}
void mail_msg_cancel(unsigned int msgid)
@@ -927,6 +952,12 @@ void mail_disable_stop(void)
MAIL_MT_UNLOCK(status_lock);
}
+static void
+operation_cancel (CamelOperation *p)
+{
+ camel_operation_cancel (p);
+}
+
/* ******************************************************************************** */
struct _op_status_msg {
@@ -995,8 +1026,7 @@ static void do_op_status(struct _mail_msg *mm)
what = g_strdup("");
}
-
- data->activity_id = e_activity_handler_operation_started (activity_handler, "evolution-mail", progress_icon, what, TRUE);
+ data->activity_id = e_activity_handler_cancelable_operation_started (activity_handler, "evolution-mail", progress_icon, what, TRUE, operation_cancel, msg->cancel);
g_free (what);
MAIL_MT_LOCK (mail_msg_lock);
diff --git a/mail/mail-mt.h b/mail/mail-mt.h
index 61a8aedf50..a508b87d46 100644
--- a/mail/mail-mt.h
+++ b/mail/mail-mt.h
@@ -64,6 +64,7 @@ int mail_msg_active(unsigned int msgid);
void *mail_cancel_hook_add(GDestroyNotify func, void *data);
void mail_cancel_hook_remove(void *handle);
void mail_cancel_all(void);
+void mail_msg_set_cancelable (struct _mail_msg *msg, gboolean status);
/* request a string/password */
char *mail_get_password (CamelService *service, const char *prompt,
diff --git a/mail/mail-ops.c b/mail/mail-ops.c
index 6d02a3108d..46a781f9ac 100644
--- a/mail/mail-ops.c
+++ b/mail/mail-ops.c
@@ -724,6 +724,11 @@ send_queue_send(struct _mail_msg *mm)
if (m->cancel)
camel_operation_register (m->cancel);
+ else
+ camel_operation_register (mm->cancel);
+
+ if (!m->cancel)
+ camel_operation_start (NULL, _("Sending message"));
camel_exception_init (&ex);
@@ -734,6 +739,8 @@ send_queue_send(struct _mail_msg *mm)
int pc = (100 * i) / send_uids->len;
report_status (m, CAMEL_FILTER_STATUS_START, pc, _("Sending message %d of %d"), i+1, send_uids->len);
+ if (!m->cancel)
+ camel_operation_progress (NULL, (i+1) * 100 / send_uids->len);
mail_send_message (m->queue, send_uids->pdata[i], m->destination, m->driver, &ex);
if (camel_exception_is_set (&ex)) {
@@ -779,9 +786,15 @@ send_queue_send(struct _mail_msg *mm)
camel_folder_sync (sent_folder, FALSE, &ex);
camel_exception_clear (&ex);
}
+
+ if (!m->cancel)
+ camel_operation_end (NULL);
if (m->cancel)
camel_operation_unregister (m->cancel);
+ else
+ camel_operation_unregister (mm->cancel);
+
}
static void
@@ -830,6 +843,10 @@ mail_send_queue(CamelFolder *queue, const char *destination,
if (cancel) {
m->cancel = cancel;
camel_operation_ref(cancel);
+ camel_operation_unref (((struct _mail_msg *) m)->cancel);
+ mail_msg_set_cancelable ((struct _mail_msg *)m, FALSE);
+
+ ((struct _mail_msg *) m)->cancel = NULL;
}
m->status = status;
m->status_data = status_data;
diff --git a/mail/mail-send-recv.c b/mail/mail-send-recv.c
index 9ed205087b..9c20da4634 100644
--- a/mail/mail-send-recv.c
+++ b/mail/mail-send-recv.c
@@ -149,7 +149,8 @@ static void
free_send_info(struct _send_info *info)
{
g_free(info->uri);
- camel_operation_unref(info->cancel);
+ if (info->cancel)
+ camel_operation_unref(info->cancel);
if (info->timeout_id != 0)
g_source_remove(info->timeout_id);
g_free(info->what);
@@ -1187,7 +1188,7 @@ mail_send (void)
info->status_label = NULL;
info->uri = g_strdup (transport->url);
info->keep = FALSE;
- info->cancel = camel_operation_new (operation_status, info);
+ info->cancel = NULL;
info->cancel_button = NULL;
info->data = data;
info->state = SEND_ACTIVE;