From f6f072dc7257c84124c678d43a39913c6004cef2 Mon Sep 17 00:00:00 2001 From: Ricardo Mones Date: Fri, 18 Nov 2011 19:36:55 +0000 Subject: [PATCH] 2011-11-18 [mones] 3.7.10cvs87 * src/compose.c * src/procheader.c * src/procheader.h Fixes bug #2509, "manually added headers are lost unless mail is sent inmediately" --- ChangeLog | 8 ++++ PATCHSETS | 1 + configure.ac | 2 +- src/compose.c | 105 +++++++++++++++++++++++++++++++++++++++++++++++ src/procheader.c | 48 ++++++++++++++++++++++ src/procheader.h | 8 +++- 6 files changed, 170 insertions(+), 2 deletions(-) diff --git a/ChangeLog b/ChangeLog index d1588a6fa..98e0f846c 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,11 @@ +2011-11-18 [mones] 3.7.10cvs87 + + * src/compose.c + * src/procheader.c + * src/procheader.h + Fixes bug #2509, "manually added headers are lost unless + mail is sent inmediately" + 2011-11-17 [pawel] 3.7.10cvs86 * src/mimeview.c diff --git a/PATCHSETS b/PATCHSETS index 13ddf1286..3bb699cf5 100644 --- a/PATCHSETS +++ b/PATCHSETS @@ -4290,3 +4290,4 @@ ( cvs diff -u -r 1.654.2.4364 -r 1.654.2.4365 configure.ac; ) > 3.7.10cvs84.patchset ( cvs diff -u -r 1.382.2.593 -r 1.382.2.594 src/compose.c; ) > 3.7.10cvs85.patchset ( cvs diff -u -r 1.83.2.180 -r 1.83.2.181 src/mimeview.c; ) > 3.7.10cvs86.patchset +( cvs diff -u -r 1.382.2.594 -r 1.382.2.595 src/compose.c; cvs diff -u -r 1.47.2.54 -r 1.47.2.55 src/procheader.c; cvs diff -u -r 1.11.2.12 -r 1.11.2.13 src/procheader.h; ) > 3.7.10cvs87.patchset diff --git a/configure.ac b/configure.ac index f8c08da60..9d5485fbc 100644 --- a/configure.ac +++ b/configure.ac @@ -12,7 +12,7 @@ MINOR_VERSION=7 MICRO_VERSION=10 INTERFACE_AGE=0 BINARY_AGE=0 -EXTRA_VERSION=86 +EXTRA_VERSION=87 EXTRA_RELEASE= EXTRA_GTK2_VERSION= diff --git a/src/compose.c b/src/compose.c index 45a8bceac..8d31b1653 100644 --- a/src/compose.c +++ b/src/compose.c @@ -220,6 +220,9 @@ static MailField compose_entries_set (Compose *compose, ComposeEntryType to_type); static gint compose_parse_header (Compose *compose, MsgInfo *msginfo); +static gint compose_parse_manual_headers (Compose *compose, + MsgInfo *msginfo, + HeaderEntry *entries); static gchar *compose_parse_references (const gchar *ref, const gchar *msgid); @@ -291,6 +294,7 @@ static gint compose_queue_sub (Compose *compose, static int compose_add_attachments (Compose *compose, MimeInfo *parent); static gchar *compose_get_header (Compose *compose); +static gchar *compose_get_manual_headers_info (Compose *compose); static void compose_convert_header (Compose *compose, gchar *dest, @@ -2125,6 +2129,7 @@ Compose *compose_reedit(MsgInfo *msginfo, gboolean batch) MsgInfo *replyinfo = NULL, *fwdinfo = NULL; gboolean autowrap = prefs_common.autowrap; gboolean autoindent = prefs_common.auto_indent; + HeaderEntry *manual_headers = NULL; cm_return_val_if_fail(msginfo != NULL, NULL); cm_return_val_if_fail(msginfo->folder != NULL, NULL); @@ -2231,6 +2236,15 @@ Compose *compose_reedit(MsgInfo *msginfo, gboolean batch) } g_strfreev(tokens); } + /* Get manual headers */ + if (!procheader_get_header_from_msginfo(msginfo, queueheader_buf, sizeof(queueheader_buf), "X-Claws-Manual-Headers:")) { + gchar *listmh = g_strdup(&queueheader_buf[strlen("X-Claws-Manual-Headers:")]); + if (*listmh != '\0') { + debug_print("Got manual headers: %s\n", listmh); + manual_headers = procheader_entries_from_str(listmh); + } + g_free(listmh); + } } else { account = msginfo->folder->folder->account; } @@ -2339,6 +2353,16 @@ Compose *compose_reedit(MsgInfo *msginfo, gboolean batch) G_CALLBACK(compose_changed_cb), compose); + if (manual_headers != NULL) { + if (compose_parse_manual_headers(compose, msginfo, manual_headers) < 0) { + procheader_entries_free(manual_headers); + compose->updating = FALSE; + compose_destroy(compose); + return NULL; + } + procheader_entries_free(manual_headers); + } + gtk_widget_grab_focus(compose->text); if (prefs_common.auto_exteditor) { @@ -2879,6 +2903,33 @@ static gint compose_parse_header(Compose *compose, MsgInfo *msginfo) return 0; } +static gint compose_parse_manual_headers(Compose *compose, MsgInfo *msginfo, HeaderEntry *entries) +{ + FILE *fp; + HeaderEntry *he; + + cm_return_val_if_fail(msginfo != NULL, -1); + + if ((fp = procmsg_open_message(msginfo)) == NULL) return -1; + procheader_get_header_fields(fp, entries); + fclose(fp); + + he = entries; + while (he != NULL && he->name != NULL) { + GtkTreeIter iter; + GtkListStore *model = NULL; + + debug_print("Adding manual header: %s with value %s\n", he->name, he->body); + model = GTK_LIST_STORE(gtk_combo_box_get_model(GTK_COMBO_BOX(compose->header_last->combo))); + COMBOBOX_ADD(model, he->name, COMPOSE_TO); + gtk_combo_box_set_active_iter(GTK_COMBO_BOX(compose->header_last->combo), &iter); + gtk_entry_set_text(GTK_ENTRY(compose->header_last->entry), he->body); + ++he; + } + + return 0; +} + static gchar *compose_parse_references(const gchar *ref, const gchar *msgid) { GSList *ref_id_list, *cur; @@ -6106,6 +6157,55 @@ static void compose_add_headerfield_from_headerlist(Compose *compose, return; } +static gchar *compose_get_manual_headers_info(Compose *compose) +{ + GString *sh_header = g_string_new(" "); + GSList *list; + gchar *std_headers[] = {"To:", "Cc:", "Bcc:", "Newsgroups:", "Reply-To:", "Followup-To:", NULL}; + + for (list = compose->header_list; list; list = list->next) { + ComposeHeaderEntry *headerentry; + gchar *tmp; + gchar *headername; + gchar *headername_wcolon; + const gchar *headername_trans; + gchar **string; + gboolean standard_header = FALSE; + + headerentry = ((ComposeHeaderEntry *)list->data); + + tmp = g_strdup(gtk_entry_get_text(GTK_ENTRY(gtk_bin_get_child(GTK_BIN((headerentry->combo)))))); + g_strstrip(tmp); + if (*tmp == '\0' || strchr(tmp, ' ') != NULL || strchr(tmp, '\r') != NULL || strchr(tmp, '\n') != NULL) { + g_free(tmp); + continue; + } + + if (!strstr(tmp, ":")) { + headername_wcolon = g_strconcat(tmp, ":", NULL); + headername = g_strdup(tmp); + } else { + headername_wcolon = g_strdup(tmp); + headername = g_strdup(strtok(tmp, ":")); + } + g_free(tmp); + + string = std_headers; + while (*string != NULL) { + headername_trans = prefs_common_translated_header_name(*string); + if (!strcmp(headername_trans, headername_wcolon)) + standard_header = TRUE; + string++; + } + if (!standard_header && !IS_IN_CUSTOM_HEADER(headername)) + g_string_append_printf(sh_header, "%s ", headername); + g_free(headername); + g_free(headername_wcolon); + } + g_string_truncate(sh_header, strlen(sh_header->str) - 1); /* remove last space */ + return g_string_free(sh_header, FALSE); +} + static gchar *compose_get_header(Compose *compose) { gchar buf[BUFFSIZE]; @@ -9412,6 +9512,7 @@ gboolean compose_draft (gpointer data, guint action) Compose *compose = (Compose *)data; FolderItem *draft; gchar *tmp; + gchar *sheaders; gint msgnum; MsgFlags flag = {0, 0}; static gboolean lock = FALSE; @@ -9492,6 +9593,10 @@ gboolean compose_draft (gpointer data, guint action) err |= (fprintf(fp, "X-Claws-Auto-Wrapping:%d\n", compose->autowrap) < 0); err |= (fprintf(fp, "X-Claws-Auto-Indent:%d\n", compose->autoindent) < 0); + sheaders = compose_get_manual_headers_info(compose); + err |= (fprintf(fp, "X-Claws-Manual-Headers:%s\n", sheaders) < 0); + g_free(sheaders); + /* end of headers */ err |= (fprintf(fp, "X-Claws-End-Special-Headers: 1\n") < 0); diff --git a/src/procheader.c b/src/procheader.c index 9c12ddede..370539012 100644 --- a/src/procheader.c +++ b/src/procheader.c @@ -1033,3 +1033,51 @@ gint procheader_get_header_from_msginfo(MsgInfo *msginfo, gchar *buf, gint len, return 0; } + +HeaderEntry *procheader_entries_from_str(const gchar *str) +{ + HeaderEntry *entries = NULL, *he; + int numh = 0, i = 0; + gchar **names = NULL; + gchar *s = str; + + if (s == NULL) { + return NULL; + } + while (*s != '\0') { + if (*s == ' ') ++numh; + ++s; + } + if (numh == 0) { + return NULL; + } + entries = g_new0(HeaderEntry, numh + 1); /* room for last NULL */ + s = str; + ++s; /* skip first space */ + names = g_strsplit(s, " ", numh); + he = entries; + while (names[i]) { + he->name = g_strdup_printf("%s:", names[i]); + he->body = NULL; + he->unfold = FALSE; + ++i, ++he; + } + he->name = NULL; + g_strfreev(names); + return entries; +} + +void procheader_entries_free (HeaderEntry *entries) +{ + if (entries != NULL) { + HeaderEntry *he = entries; + while (he->name != NULL) { + g_free(he->name); + if (he->body != NULL) + g_free(he->body); + ++he; + } + g_free(entries); + } +} + diff --git a/src/procheader.h b/src/procheader.h index dc4d16352..743752a50 100644 --- a/src/procheader.h +++ b/src/procheader.h @@ -89,5 +89,11 @@ Header * procheader_parse_header (gchar * buf); gboolean procheader_headername_equal (char * hdr1, char * hdr2); void procheader_header_free (Header * header); -gint procheader_get_header_from_msginfo(MsgInfo *msginfo, gchar *buf, gint len,gchar *header); +gint procheader_get_header_from_msginfo (MsgInfo *msginfo, + gchar *buf, + gint len, + gchar *header); + +HeaderEntry *procheader_entries_from_str(const gchar *str); +void procheader_entries_free (HeaderEntry *entries); #endif /* __PROCHEADER_H__ */ -- 2.25.1