* [PATCH 0/5] Rewrite mbox and raw show formats @ 2012-03-03 5:20 Austin Clements 2012-03-03 5:20 ` [PATCH 1/5] show: Allow formatters to return errors Austin Clements ` (6 more replies) 0 siblings, 7 replies; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch The show (rewrite) must go on. These are the last two formats in notmuch show proper; the only remaining format is the reply format. One of the ultimate goals of the show rewrite is to make raw actually work (and probably to split it into two different formats). This series does not do that; it just ports the existing raw format. I plan to make the new raw formats once the rewrite is done. ^ permalink raw reply [flat|nested] 23+ messages in thread
* [PATCH 1/5] show: Allow formatters to return errors 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements @ 2012-03-03 5:20 ` Austin Clements 2012-03-03 5:20 ` [PATCH 2/5] show: Move format_message_mbox with the other new-style formats Austin Clements ` (5 subsequent siblings) 6 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch Formatter errors are propagated to the exit status of notmuch show. This isn't used by the JSON or text formatters, but it will be useful for the raw format, which is pickier. --- notmuch-client.h | 6 ++-- notmuch-show.c | 69 +++++++++++++++++++++++++++++++++++------------------ 2 files changed, 48 insertions(+), 27 deletions(-) diff --git a/notmuch-client.h b/notmuch-client.h index f4a62cc..a220fe4 100644 --- a/notmuch-client.h +++ b/notmuch-client.h @@ -67,9 +67,9 @@ struct notmuch_show_params; typedef struct notmuch_show_format { const char *message_set_start; - void (*part) (const void *ctx, - struct mime_node *node, int indent, - const struct notmuch_show_params *params); + notmuch_status_t (*part) (const void *ctx, + struct mime_node *node, int indent, + const struct notmuch_show_params *params); const char *message_start; void (*message) (const void *ctx, notmuch_message_t *message, diff --git a/notmuch-show.c b/notmuch-show.c index 6a171a4..648f468 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -23,7 +23,7 @@ static void format_headers_message_part_text (GMimeMessage *message); -static void +static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -34,7 +34,7 @@ static const notmuch_show_format_t format_text = { .message_set_end = "" }; -static void +static notmuch_status_t format_part_json_entry (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -562,7 +562,7 @@ format_part_content_raw (GMimeObject *part) g_object_unref(stream_stdout); } -static void +static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params) { @@ -650,6 +650,8 @@ format_part_text (const void *ctx, mime_node_t *node, printf ("\fbody}\n"); printf ("\f%s}\n", part_type); + + return NOTMUCH_STATUS_SUCCESS; } static void @@ -751,14 +753,16 @@ format_part_json (const void *ctx, mime_node_t *node, notmuch_bool_t first) printf ("%s}", terminator); } -static void +static notmuch_status_t format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), unused (const notmuch_show_params_t *params)) { format_part_json (ctx, node, TRUE); + + return NOTMUCH_STATUS_SUCCESS; } -static void +static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, notmuch_message_t *message, @@ -768,14 +772,18 @@ show_message (void *ctx, if (format->part) { void *local = talloc_new (ctx); mime_node_t *root, *part; + notmuch_status_t status; - if (mime_node_open (local, message, params->cryptoctx, params->decrypt, - &root) == NOTMUCH_STATUS_SUCCESS && - (part = mime_node_seek_dfs (root, (params->part < 0 ? - 0 : params->part)))) - format->part (local, part, indent, params); + status = mime_node_open (local, message, params->cryptoctx, + params->decrypt, &root); + if (status) + goto DONE; + part = mime_node_seek_dfs (root, (params->part < 0 ? 0 : params->part)); + if (part) + status = format->part (local, part, indent, params); + DONE: talloc_free (local); - return; + return status; } if (params->part <= 0) { @@ -799,9 +807,11 @@ show_message (void *ctx, fputs (format->message_end, stdout); } + + return NOTMUCH_STATUS_SUCCESS; } -static void +static notmuch_status_t show_messages (void *ctx, const notmuch_show_format_t *format, notmuch_messages_t *messages, @@ -812,6 +822,7 @@ show_messages (void *ctx, notmuch_bool_t match; int first_set = 1; int next_indent; + notmuch_status_t status, res = NOTMUCH_STATUS_SUCCESS; fputs (format->message_set_start, stdout); @@ -832,17 +843,22 @@ show_messages (void *ctx, next_indent = indent; if (match || params->entire_thread) { - show_message (ctx, format, message, indent, params); + status = show_message (ctx, format, message, indent, params); + if (status && !res) + res = status; next_indent = indent + 1; - fputs (format->message_set_sep, stdout); + if (!status) + fputs (format->message_set_sep, stdout); } - show_messages (ctx, - format, - notmuch_message_get_replies (message), - next_indent, - params); + status = show_messages (ctx, + format, + notmuch_message_get_replies (message), + next_indent, + params); + if (status && !res) + res = status; notmuch_message_destroy (message); @@ -850,6 +866,8 @@ show_messages (void *ctx, } fputs (format->message_set_end, stdout); + + return res; } /* Formatted output of single message */ @@ -914,13 +932,13 @@ do_show_single (void *ctx, fclose (file); + return 0; + } else { - show_message (ctx, format, message, 0, params); + return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; } - - return 0; } /* Formatted output of threads */ @@ -934,6 +952,7 @@ do_show (void *ctx, notmuch_thread_t *thread; notmuch_messages_t *messages; int first_toplevel = 1; + notmuch_status_t status, res = NOTMUCH_STATUS_SUCCESS; fputs (format->message_set_start, stdout); @@ -953,7 +972,9 @@ do_show (void *ctx, fputs (format->message_set_sep, stdout); first_toplevel = 0; - show_messages (ctx, format, messages, 0, params); + status = show_messages (ctx, format, messages, 0, params); + if (status && !res) + res = status; notmuch_thread_destroy (thread); @@ -961,7 +982,7 @@ do_show (void *ctx, fputs (format->message_set_end, stdout); - return 0; + return res != NOTMUCH_STATUS_SUCCESS; } enum { -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH 2/5] show: Move format_message_mbox with the other new-style formats 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements 2012-03-03 5:20 ` [PATCH 1/5] show: Allow formatters to return errors Austin Clements @ 2012-03-03 5:20 ` Austin Clements 2012-03-03 5:20 ` [PATCH 3/5] show: Convert mbox format to new self-recursive style Austin Clements ` (4 subsequent siblings) 6 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch Just code motion. --- notmuch-show.c | 100 ++++++++++++++++++++++++++++---------------------------- 1 files changed, 50 insertions(+), 50 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 648f468..b3a4550 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -219,56 +219,6 @@ _is_from_line (const char *line) return 0; } -/* Print a message in "mboxrd" format as documented, for example, - * here: - * - * http://qmail.org/qmail-manual-html/man5/mbox.html - */ -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)) -{ - const char *filename; - FILE *file; - const char *from; - - time_t date; - struct tm date_gmtime; - char date_asctime[26]; - - char *line = NULL; - size_t line_size; - ssize_t line_len; - - filename = notmuch_message_get_filename (message); - file = fopen (filename, "r"); - if (file == NULL) { - fprintf (stderr, "Failed to open %s: %s\n", - filename, strerror (errno)); - return; - } - - from = notmuch_message_get_header (message, "from"); - from = _extract_email_address (ctx, from); - - date = notmuch_message_get_date (message); - gmtime_r (&date, &date_gmtime); - asctime_r (&date_gmtime, date_asctime); - - printf ("From %s %s", from, date_asctime); - - while ((line_len = getline (&line, &line_size, file)) != -1 ) { - if (_is_from_line (line)) - putchar ('>'); - printf ("%s", line); - } - - printf ("\n"); - - fclose (file); -} - static void format_headers_message_part_text (GMimeMessage *message) { @@ -762,6 +712,56 @@ format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } +/* Print a message in "mboxrd" format as documented, for example, + * here: + * + * http://qmail.org/qmail-manual-html/man5/mbox.html + */ +static void +format_message_mbox (const void *ctx, + notmuch_message_t *message, + unused (int indent)) +{ + const char *filename; + FILE *file; + const char *from; + + time_t date; + struct tm date_gmtime; + char date_asctime[26]; + + char *line = NULL; + size_t line_size; + ssize_t line_len; + + filename = notmuch_message_get_filename (message); + file = fopen (filename, "r"); + if (file == NULL) { + fprintf (stderr, "Failed to open %s: %s\n", + filename, strerror (errno)); + return; + } + + from = notmuch_message_get_header (message, "from"); + from = _extract_email_address (ctx, from); + + date = notmuch_message_get_date (message); + gmtime_r (&date, &date_gmtime); + asctime_r (&date_gmtime, date_asctime); + + printf ("From %s %s", from, date_asctime); + + while ((line_len = getline (&line, &line_size, file)) != -1 ) { + if (_is_from_line (line)) + putchar ('>'); + printf ("%s", line); + } + + printf ("\n"); + + fclose (file); +} + static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH 3/5] show: Convert mbox format to new self-recursive style 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements 2012-03-03 5:20 ` [PATCH 1/5] show: Allow formatters to return errors Austin Clements 2012-03-03 5:20 ` [PATCH 2/5] show: Move format_message_mbox with the other new-style formats Austin Clements @ 2012-03-03 5:20 ` Austin Clements 2012-03-03 5:20 ` [PATCH 4/5] show: Move format_part_content_raw with the other new-style formats Austin Clements ` (3 subsequent siblings) 6 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch Given the lack of recursion, this is pretty easy. --- notmuch-show.c | 40 ++++++++++++++++++---------------------- 1 files changed, 18 insertions(+), 22 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index b3a4550..72c141e 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -45,25 +45,15 @@ static const notmuch_show_format_t format_json = { .message_set_end = "]" }; -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)); +static notmuch_status_t +format_part_mbox (const void *ctx, mime_node_t *node, + int indent, const notmuch_show_params_t *params); static const notmuch_show_format_t format_mbox = { - "", NULL, - "", format_message_mbox, - "", NULL, NULL, "", - "", - NULL, - NULL, - NULL, - NULL, - NULL, - "", - "", - "", "", - "" + .message_set_start = "", + .part = format_part_mbox, + .message_set_sep = "", + .message_set_end = "" }; static void @@ -717,11 +707,12 @@ format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), * * http://qmail.org/qmail-manual-html/man5/mbox.html */ -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)) +static notmuch_status_t +format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), + unused (const notmuch_show_params_t *params)) { + notmuch_message_t *message = node->envelope_file; + const char *filename; FILE *file; const char *from; @@ -734,12 +725,15 @@ format_message_mbox (const void *ctx, size_t line_size; ssize_t line_len; + if (!message) + INTERNAL_ERROR ("format_part_mbox requires a root part"); + filename = notmuch_message_get_filename (message); file = fopen (filename, "r"); if (file == NULL) { fprintf (stderr, "Failed to open %s: %s\n", filename, strerror (errno)); - return; + return NOTMUCH_STATUS_FILE_ERROR; } from = notmuch_message_get_header (message, "from"); @@ -760,6 +754,8 @@ format_message_mbox (const void *ctx, printf ("\n"); fclose (file); + + return NOTMUCH_STATUS_SUCCESS; } static notmuch_status_t -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH 4/5] show: Move format_part_content_raw with the other new-style formats 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements ` (2 preceding siblings ...) 2012-03-03 5:20 ` [PATCH 3/5] show: Convert mbox format to new self-recursive style Austin Clements @ 2012-03-03 5:20 ` Austin Clements 2012-03-03 5:20 ` [PATCH 5/5] show: Convert raw format to the new self-recursive style Austin Clements ` (2 subsequent siblings) 6 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch Just code motion. --- notmuch-show.c | 54 +++++++++++++++++++++++++++--------------------------- 1 files changed, 27 insertions(+), 27 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 72c141e..6f6052c 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -475,33 +475,6 @@ format_part_sigstatus_json (mime_node_t *node) } #endif -static void -format_part_content_raw (GMimeObject *part) -{ - if (! GMIME_IS_PART (part)) - return; - - GMimeStream *stream_stdout; - GMimeStream *stream_filter = NULL; - GMimeDataWrapper *wrapper; - - stream_stdout = g_mime_stream_file_new (stdout); - g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); - - stream_filter = g_mime_stream_filter_new (stream_stdout); - - wrapper = g_mime_part_get_content_object (GMIME_PART (part)); - - if (wrapper && stream_filter) - g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); - - if (stream_filter) - g_object_unref (stream_filter); - - if (stream_stdout) - g_object_unref(stream_stdout); -} - static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params) @@ -758,6 +731,33 @@ format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } +static void +format_part_content_raw (GMimeObject *part) +{ + if (! GMIME_IS_PART (part)) + return; + + GMimeStream *stream_stdout; + GMimeStream *stream_filter = NULL; + GMimeDataWrapper *wrapper; + + stream_stdout = g_mime_stream_file_new (stdout); + g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); + + stream_filter = g_mime_stream_filter_new (stream_stdout); + + wrapper = g_mime_part_get_content_object (GMIME_PART (part)); + + if (wrapper && stream_filter) + g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + + if (stream_filter) + g_object_unref (stream_filter); + + if (stream_stdout) + g_object_unref(stream_stdout); +} + static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH 5/5] show: Convert raw format to the new self-recursive style 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements ` (3 preceding siblings ...) 2012-03-03 5:20 ` [PATCH 4/5] show: Move format_part_content_raw with the other new-style formats Austin Clements @ 2012-03-03 5:20 ` Austin Clements 2012-03-03 22:05 ` Jameson Graef Rollins 2012-03-03 8:18 ` [PATCH 0/5] Rewrite mbox and raw show formats Tomi Ollila 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements 6 siblings, 1 reply; 23+ messages in thread From: Austin Clements @ 2012-03-03 5:20 UTC (permalink / raw) To: notmuch This is fully compatible for root and leaf parts, but drops support for interior parts. Showing interior parts in raw has always been braindead broken, so I don't think anyone will miss this. Tests have been updated to reflect this. The diff looks complicated, but the change is simple. We delete format_headers_message_part_text, since it's no longer needed; move the special-case code for --part=0 that used to be in do_show_single to format_part_raw; and re-indent the code for formatting leaf parts in format_part_raw. --- notmuch-show.c | 165 ++++++++++++++++++++++---------------------------------- test/multipart | 51 ++++-------------- 2 files changed, 76 insertions(+), 140 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 6f6052c..9c2f890 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -20,9 +20,6 @@ #include "notmuch-client.h" -static void -format_headers_message_part_text (GMimeMessage *message); - static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -56,23 +53,16 @@ static const notmuch_show_format_t format_mbox = { .message_set_end = "" }; -static void -format_part_content_raw (GMimeObject *part); +static notmuch_status_t +format_part_raw (unused (const void *ctx), mime_node_t *node, + unused (int indent), + unused (const notmuch_show_params_t *params)); static const notmuch_show_format_t format_raw = { - "", NULL, - "", NULL, - "", NULL, format_headers_message_part_text, "\n", - "", - NULL, - NULL, - NULL, - format_part_content_raw, - NULL, - "", - "", - "", "", - "" + .message_set_start = "", + .part = format_part_raw, + .message_set_sep = "", + .message_set_end = "" }; static const char * @@ -210,27 +200,6 @@ _is_from_line (const char *line) } static void -format_headers_message_part_text (GMimeMessage *message) -{ - InternetAddressList *recipients; - const char *recipients_string; - - printf ("Subject: %s\n", g_mime_message_get_subject (message)); - printf ("From: %s\n", g_mime_message_get_sender (message)); - recipients = g_mime_message_get_recipients (message, GMIME_RECIPIENT_TYPE_TO); - recipients_string = internet_address_list_to_string (recipients, 0); - if (recipients_string) - printf ("To: %s\n", - recipients_string); - recipients = g_mime_message_get_recipients (message, GMIME_RECIPIENT_TYPE_CC); - recipients_string = internet_address_list_to_string (recipients, 0); - if (recipients_string) - printf ("Cc: %s\n", - recipients_string); - printf ("Date: %s\n", g_mime_message_get_date_as_string (message)); -} - -static void format_headers_json (const void *ctx, GMimeMessage *message) { void *local = talloc_new (ctx); @@ -731,31 +700,70 @@ format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } -static void -format_part_content_raw (GMimeObject *part) +static notmuch_status_t +format_part_raw (unused (const void *ctx), mime_node_t *node, + unused (int indent), + unused (const notmuch_show_params_t *params)) { - if (! GMIME_IS_PART (part)) - return; + if (node->envelope_file) { + const char *filename; + FILE *file; + size_t size; + char buf[4096]; - GMimeStream *stream_stdout; - GMimeStream *stream_filter = NULL; - GMimeDataWrapper *wrapper; + filename = notmuch_message_get_filename (node->envelope_file); + if (filename == NULL) { + fprintf (stderr, "Error: Cannot get message filename.\n"); + return NOTMUCH_STATUS_FILE_ERROR; + } - stream_stdout = g_mime_stream_file_new (stdout); - g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); + file = fopen (filename, "r"); + if (file == NULL) { + fprintf (stderr, "Error: Cannot open file %s: %s\n", filename, strerror (errno)); + return NOTMUCH_STATUS_FILE_ERROR; + } - stream_filter = g_mime_stream_filter_new (stream_stdout); + while (!feof (file)) { + size = fread (buf, 1, sizeof (buf), file); + if (ferror (file)) { + fprintf (stderr, "Error: Read failed from %s\n", filename); + fclose (file); + return NOTMUCH_STATUS_FILE_ERROR; + } - wrapper = g_mime_part_get_content_object (GMIME_PART (part)); + if (fwrite (buf, size, 1, stdout) != 1) { + fprintf (stderr, "Error: Write failed\n"); + fclose (file); + return NOTMUCH_STATUS_FILE_ERROR; + } + } - if (wrapper && stream_filter) - g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + fclose (file); + } else if (GMIME_IS_PART (node->part)) { + GMimeStream *stream_stdout; + GMimeStream *stream_filter = NULL; + GMimeDataWrapper *wrapper; - if (stream_filter) - g_object_unref (stream_filter); + stream_stdout = g_mime_stream_file_new (stdout); + g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); - if (stream_stdout) - g_object_unref(stream_stdout); + stream_filter = g_mime_stream_filter_new (stream_stdout); + + wrapper = g_mime_part_get_content_object (GMIME_PART (node->part)); + + if (wrapper && stream_filter) + g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + + if (stream_filter) + g_object_unref (stream_filter); + + if (stream_stdout) + g_object_unref(stream_stdout); + } else { + fprintf (stderr, "Error: Raw only supports root and leaf parts\n"); + return NOTMUCH_STATUS_FILE_ERROR; + } + return NOTMUCH_STATUS_SUCCESS; } static notmuch_status_t @@ -891,50 +899,7 @@ do_show_single (void *ctx, notmuch_message_set_flag (message, NOTMUCH_MESSAGE_FLAG_MATCH, 1); - /* Special case for --format=raw of full single message, just cat out file */ - if (params->raw && 0 == params->part) { - - const char *filename; - FILE *file; - size_t size; - char buf[4096]; - - filename = notmuch_message_get_filename (message); - if (filename == NULL) { - fprintf (stderr, "Error: Cannot message filename.\n"); - return 1; - } - - file = fopen (filename, "r"); - if (file == NULL) { - fprintf (stderr, "Error: Cannot open file %s: %s\n", filename, strerror (errno)); - return 1; - } - - while (!feof (file)) { - size = fread (buf, 1, sizeof (buf), file); - if (ferror (file)) { - fprintf (stderr, "Error: Read failed from %s\n", filename); - fclose (file); - return 1; - } - - if (fwrite (buf, size, 1, stdout) != 1) { - fprintf (stderr, "Error: Write failed\n"); - fclose (file); - return 1; - } - } - - fclose (file); - - return 0; - - } else { - - return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; - - } + return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; } /* Formatted output of threads */ diff --git a/test/multipart b/test/multipart index a3036b4..cb16b43 100755 --- a/test/multipart +++ b/test/multipart @@ -448,59 +448,30 @@ notmuch show --format=raw --part=0 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUT test_expect_equal_file OUTPUT "${MAIL_DIR}"/multipart test_begin_subtest "--format=raw --part=1, message body" -notmuch show --format=raw --part=1 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT -# output should *not* include newline -echo >>OUTPUT +notmuch show --format=raw --part=1 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT cat <<EOF >EXPECTED -Subject: html message -From: Carl Worth <cworth@cworth.org> -To: cworth@cworth.org -Date: Fri, 05 Jan 2001 15:42:57 +0000 - -<p>This is an embedded message, with a multipart/alternative part.</p> -This is an embedded message, with a multipart/alternative part. -This is a text attachment. -And this message is signed. - --Carl ------BEGIN PGP SIGNATURE----- -Version: GnuPG v1.4.11 (GNU/Linux) - -iEYEARECAAYFAk3SA/gACgkQ6JDdNq8qSWj0sACghqVJEQJUs3yV8zbTzhgnSIcD -W6cAmQE4dcYrx/LPLtYLZm1jsGauE5hE -=zkga ------END PGP SIGNATURE----- +Error: Raw only supports root and leaf parts EOF test_expect_equal_file OUTPUT EXPECTED test_begin_subtest "--format=raw --part=2, multipart/mixed" -notmuch show --format=raw --part=2 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT +notmuch show --format=raw --part=2 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT cat <<EOF >EXPECTED -Subject: html message -From: Carl Worth <cworth@cworth.org> -To: cworth@cworth.org -Date: Fri, 05 Jan 2001 15:42:57 +0000 - -<p>This is an embedded message, with a multipart/alternative part.</p> -This is an embedded message, with a multipart/alternative part. -This is a text attachment. -And this message is signed. - --Carl +Error: Raw only supports root and leaf parts EOF test_expect_equal_file OUTPUT EXPECTED test_begin_subtest "--format=raw --part=3, rfc822 part" -test_subtest_known_broken - -notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT -test_expect_equal_file OUTPUT embedded_message +notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT +cat <<EOF >EXPECTED +Error: Raw only supports root and leaf parts +EOF +test_expect_equal_file OUTPUT EXPECTED test_begin_subtest "--format=raw --part=4, rfc822's html part" -notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT +notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT cat <<EOF >EXPECTED -<p>This is an embedded message, with a multipart/alternative part.</p> -This is an embedded message, with a multipart/alternative part. +Error: Raw only supports root and leaf parts EOF test_expect_equal_file OUTPUT EXPECTED -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* Re: [PATCH 5/5] show: Convert raw format to the new self-recursive style 2012-03-03 5:20 ` [PATCH 5/5] show: Convert raw format to the new self-recursive style Austin Clements @ 2012-03-03 22:05 ` Jameson Graef Rollins 2012-03-06 18:43 ` Austin Clements 0 siblings, 1 reply; 23+ messages in thread From: Jameson Graef Rollins @ 2012-03-03 22:05 UTC (permalink / raw) To: Austin Clements, notmuch [-- Attachment #1: Type: text/plain, Size: 3667 bytes --] Hey, Austin. As always, thank you so much for your hard work on this rewrite. It looks like things are definitely moving the right direction. I haven't done a full review of this patch set, and I've been pretty out of the loop on this stuff recently, but I do notice that there are some changes to the tests that don't look right to me. On Sat, 3 Mar 2012 00:20:25 -0500, Austin Clements <amdragon@MIT.EDU> wrote: > This is fully compatible for root and leaf parts, but drops support > for interior parts. Showing interior parts in raw has always been > braindead broken, so I don't think anyone will miss this. Tests have > been updated to reflect this. I think I'm confused about this "drop support for interior parts". What constitutes an "interior part"? Aren't all parts interior? It looks From the patch that maybe you're referring specifically to rfc822 parts? I can understand not supporting output of multipart parts in raw; it's unclear what a "raw" multipart even is. But I think we do need to support common-sense handling of rfc822 parts, even if it requires special casing. These following two test modifications illustrate the issue: > test_begin_subtest "--format=raw --part=3, rfc822 part" > -test_subtest_known_broken > - > -notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT > -test_expect_equal_file OUTPUT embedded_message > +notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT > +cat <<EOF >EXPECTED > +Error: Raw only supports root and leaf parts > +EOF > +test_expect_equal_file OUTPUT EXPECTED I pretty strongly think that this test needs to remain how it was. If someone forwards me a message as a rfc822 part I should be able to retrieve the full forwarded message directly, by e.g. redirecting it to a file and recreating the original message exactly intact. That's why I constructed this test the way I did originally, and left it known_broken. If we can't support this now that's fine, but I still think this test describes an important needed functionality that we should strive to support at some point. Maybe it needs an entirely new output formatter, or some special casing, but I still think it's reasonable to expect that we should support this. > test_begin_subtest "--format=raw --part=4, rfc822's html part" > -notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT > +notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT > cat <<EOF >EXPECTED > -<p>This is an embedded message, with a multipart/alternative part.</p> > -This is an embedded message, with a multipart/alternative part. > +Error: Raw only supports root and leaf parts > EOF > test_expect_equal_file OUTPUT EXPECTED Maybe this is ultimately a limitation of what we can expect the raw formatter to do, but isn't this a leaf part? As with whole rfc822 parts, I also expect that we should be able to retrieve interior leaf parts of rfc822 message parts. So I think I would prefer that this test just move to test_subtest_known_broken until a better way to handle this is figured out. Without looking into the details of your whole show rewrite, I'm guessing that we just can't reasonably expect the raw formatter to handle rfc822 parts the way we need. Is that correct? Is there some other formatter that might be better suited for this? Like I say, I think it's ok if we have to have some special casing for this particular type of part. But either way I think we should try to support handling rfc822 parts in a useful way. jamie. [-- Attachment #2: Type: application/pgp-signature, Size: 835 bytes --] ^ permalink raw reply [flat|nested] 23+ messages in thread
* Re: [PATCH 5/5] show: Convert raw format to the new self-recursive style 2012-03-03 22:05 ` Jameson Graef Rollins @ 2012-03-06 18:43 ` Austin Clements 0 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:43 UTC (permalink / raw) To: Jameson Graef Rollins; +Cc: notmuch TL;DR: I had a MIMEpiphany and I'm sending a new version of this series that I think will address your concerns. Quoth Jameson Graef Rollins on Mar 03 at 2:05 pm: > Hey, Austin. As always, thank you so much for your hard work on this > rewrite. It looks like things are definitely moving the right > direction. > > I haven't done a full review of this patch set, and I've been pretty out > of the loop on this stuff recently, but I do notice that there are some > changes to the tests that don't look right to me. > > On Sat, 3 Mar 2012 00:20:25 -0500, Austin Clements <amdragon@MIT.EDU> wrote: > > This is fully compatible for root and leaf parts, but drops support > > for interior parts. Showing interior parts in raw has always been > > braindead broken, so I don't think anyone will miss this. Tests have > > been updated to reflect this. > > I think I'm confused about this "drop support for interior parts". What > constitutes an "interior part"? Aren't all parts interior? It looks > From the patch that maybe you're referring specifically to rfc822 parts? Interior parts are any part that isn't a root part (the whole message) or a leaf part. I had originally planned to simply deprecate raw in favor of two new formats: "body", which outputted just bodies with transfer decoding (which, for rfc822 parts, would include the attached message headers, but not the envelope headers) and "source", which outputted full parts with headers. I had been thinking that "source" would be necessary for fetching the entire message and "body" for fetching attachments and other leaf parts, but then it dawned on me that even trivial messages have two parts already: part 0 is an rfc822 part representing the whole message and part 1 is the body. Hence, modulo specialty uses like crypto, "body" was already sufficient for both uses *and* compatible with "raw" for root and leaf parts. I've updated my series to reflect this. Raw now works for any part. > > test_begin_subtest "--format=raw --part=4, rfc822's html part" > > -notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT > > +notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >&OUTPUT > > cat <<EOF >EXPECTED > > -<p>This is an embedded message, with a multipart/alternative part.</p> > > -This is an embedded message, with a multipart/alternative part. > > +Error: Raw only supports root and leaf parts > > EOF > > test_expect_equal_file OUTPUT EXPECTED > > Maybe this is ultimately a limitation of what we can expect the raw > formatter to do, but isn't this a leaf part? Actually that was a typo in the test name. Part 4 is a multipart, not a leaf part. The new series includes a patch for this. ^ permalink raw reply [flat|nested] 23+ messages in thread
* Re: [PATCH 0/5] Rewrite mbox and raw show formats 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements ` (4 preceding siblings ...) 2012-03-03 5:20 ` [PATCH 5/5] show: Convert raw format to the new self-recursive style Austin Clements @ 2012-03-03 8:18 ` Tomi Ollila 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements 6 siblings, 0 replies; 23+ messages in thread From: Tomi Ollila @ 2012-03-03 8:18 UTC (permalink / raw) To: Austin Clements, notmuch On Sat, 3 Mar 2012 00:20:20 -0500, Austin Clements <amdragon@MIT.EDU> wrote: > The show (rewrite) must go on. These are the last two formats in > notmuch show proper; the only remaining format is the reply format. > > One of the ultimate goals of the show rewrite is to make raw actually > work (and probably to split it into two different formats). This > series does not do that; it just ports the existing raw format. I > plan to make the new raw formats once the rewrite is done. The whole patch series LGTM. On somewhat related note: should there be NOTMUCH_STATUS_FAILURE (= 1) in enum _notmuch_status (indicating unspecified failure). This would make lines like return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; look better (or were/are all of these failures due to memory exhaustion) ? Tomi ^ permalink raw reply [flat|nested] 23+ messages in thread
* [PATCH v2 0/8] Rewrite mbox and raw show formats 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements ` (5 preceding siblings ...) 2012-03-03 8:18 ` [PATCH 0/5] Rewrite mbox and raw show formats Tomi Ollila @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 1/8] test: Fix typo in test description Austin Clements ` (9 more replies) 6 siblings, 10 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch v2 makes the new raw format support interior, as well as root and leaf parts. Patches 1, 2, and 8 are new but simple. Patches 3 through 6 have not changed. Patch 7 has obviously changed quite a bit. ^ permalink raw reply [flat|nested] 23+ messages in thread
* [PATCH v2 1/8] test: Fix typo in test description 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 2/8] test: Fix malformed multipart message Austin Clements ` (8 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Part 4 is a multipart, not an html part. --- test/multipart | 2 +- 1 files changed, 1 insertions(+), 1 deletions(-) diff --git a/test/multipart b/test/multipart index a3036b4..d36a65d 100755 --- a/test/multipart +++ b/test/multipart @@ -496,7 +496,7 @@ test_subtest_known_broken notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT test_expect_equal_file OUTPUT embedded_message -test_begin_subtest "--format=raw --part=4, rfc822's html part" +test_begin_subtest "--format=raw --part=4, rfc822's multipart" notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT cat <<EOF >EXPECTED <p>This is an embedded message, with a multipart/alternative part.</p> -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 2/8] test: Fix malformed multipart message 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements 2012-03-06 18:48 ` [PATCH v2 1/8] test: Fix typo in test description Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 3/8] show: Allow formatters to return errors Austin Clements ` (7 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Previously, there was only one CRLF between the terminating boundary of the embedded multipart/alternative and the boundary of the containing multipart. However, according the RFC 1341, 7.2.1: The boundary must be followed immediately either by another CRLF and the header fields for the next part, or by two CRLFs, in which case there are no header fields for the next part and The CRLF preceding the encapsulation line is considered part of the boundary so that it is possible to have a part that does not end with a CRLF (line break). Thus, there must be *two* CRLFs between these boundaries: one that ends the terminating boundary and one that begins the enclosing boundary. While GMime accepted the message we had before, it could not produce such a message. --- test/multipart | 1 + 1 files changed, 1 insertions(+), 0 deletions(-) diff --git a/test/multipart b/test/multipart index d36a65d..475c6a2 100755 --- a/test/multipart +++ b/test/multipart @@ -46,6 +46,7 @@ Content-Disposition: inline EOF cat embedded_message >> ${MAIL_DIR}/multipart cat <<EOF >> ${MAIL_DIR}/multipart + --=-=-= Content-Disposition: attachment; filename=attachment -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 3/8] show: Allow formatters to return errors 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements 2012-03-06 18:48 ` [PATCH v2 1/8] test: Fix typo in test description Austin Clements 2012-03-06 18:48 ` [PATCH v2 2/8] test: Fix malformed multipart message Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 21:22 ` Mark Walters 2012-03-06 18:48 ` [PATCH v2 4/8] show: Move format_message_mbox with the other new-style formats Austin Clements ` (6 subsequent siblings) 9 siblings, 1 reply; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Formatter errors are propagated to the exit status of notmuch show. This isn't used by the JSON or text formatters, but it will be useful for the raw format, which is pickier. --- notmuch-client.h | 6 ++-- notmuch-show.c | 71 +++++++++++++++++++++++++++++++++++------------------- 2 files changed, 49 insertions(+), 28 deletions(-) diff --git a/notmuch-client.h b/notmuch-client.h index f4a62cc..a220fe4 100644 --- a/notmuch-client.h +++ b/notmuch-client.h @@ -67,9 +67,9 @@ struct notmuch_show_params; typedef struct notmuch_show_format { const char *message_set_start; - void (*part) (const void *ctx, - struct mime_node *node, int indent, - const struct notmuch_show_params *params); + notmuch_status_t (*part) (const void *ctx, + struct mime_node *node, int indent, + const struct notmuch_show_params *params); const char *message_start; void (*message) (const void *ctx, notmuch_message_t *message, diff --git a/notmuch-show.c b/notmuch-show.c index 6a171a4..648f468 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -23,7 +23,7 @@ static void format_headers_message_part_text (GMimeMessage *message); -static void +static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -34,7 +34,7 @@ static const notmuch_show_format_t format_text = { .message_set_end = "" }; -static void +static notmuch_status_t format_part_json_entry (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -562,7 +562,7 @@ format_part_content_raw (GMimeObject *part) g_object_unref(stream_stdout); } -static void +static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params) { @@ -650,6 +650,8 @@ format_part_text (const void *ctx, mime_node_t *node, printf ("\fbody}\n"); printf ("\f%s}\n", part_type); + + return NOTMUCH_STATUS_SUCCESS; } static void @@ -751,14 +753,16 @@ format_part_json (const void *ctx, mime_node_t *node, notmuch_bool_t first) printf ("%s}", terminator); } -static void +static notmuch_status_t format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), unused (const notmuch_show_params_t *params)) { format_part_json (ctx, node, TRUE); + + return NOTMUCH_STATUS_SUCCESS; } -static void +static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, notmuch_message_t *message, @@ -768,14 +772,18 @@ show_message (void *ctx, if (format->part) { void *local = talloc_new (ctx); mime_node_t *root, *part; - - if (mime_node_open (local, message, params->cryptoctx, params->decrypt, - &root) == NOTMUCH_STATUS_SUCCESS && - (part = mime_node_seek_dfs (root, (params->part < 0 ? - 0 : params->part)))) - format->part (local, part, indent, params); + notmuch_status_t status; + + status = mime_node_open (local, message, params->cryptoctx, + params->decrypt, &root); + if (status) + goto DONE; + part = mime_node_seek_dfs (root, (params->part < 0 ? 0 : params->part)); + if (part) + status = format->part (local, part, indent, params); + DONE: talloc_free (local); - return; + return status; } if (params->part <= 0) { @@ -799,9 +807,11 @@ show_message (void *ctx, fputs (format->message_end, stdout); } + + return NOTMUCH_STATUS_SUCCESS; } -static void +static notmuch_status_t show_messages (void *ctx, const notmuch_show_format_t *format, notmuch_messages_t *messages, @@ -812,6 +822,7 @@ show_messages (void *ctx, notmuch_bool_t match; int first_set = 1; int next_indent; + notmuch_status_t status, res = NOTMUCH_STATUS_SUCCESS; fputs (format->message_set_start, stdout); @@ -832,17 +843,22 @@ show_messages (void *ctx, next_indent = indent; if (match || params->entire_thread) { - show_message (ctx, format, message, indent, params); + status = show_message (ctx, format, message, indent, params); + if (status && !res) + res = status; next_indent = indent + 1; - fputs (format->message_set_sep, stdout); + if (!status) + fputs (format->message_set_sep, stdout); } - show_messages (ctx, - format, - notmuch_message_get_replies (message), - next_indent, - params); + status = show_messages (ctx, + format, + notmuch_message_get_replies (message), + next_indent, + params); + if (status && !res) + res = status; notmuch_message_destroy (message); @@ -850,6 +866,8 @@ show_messages (void *ctx, } fputs (format->message_set_end, stdout); + + return res; } /* Formatted output of single message */ @@ -914,13 +932,13 @@ do_show_single (void *ctx, fclose (file); + return 0; + } else { - show_message (ctx, format, message, 0, params); + return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; } - - return 0; } /* Formatted output of threads */ @@ -934,6 +952,7 @@ do_show (void *ctx, notmuch_thread_t *thread; notmuch_messages_t *messages; int first_toplevel = 1; + notmuch_status_t status, res = NOTMUCH_STATUS_SUCCESS; fputs (format->message_set_start, stdout); @@ -953,7 +972,9 @@ do_show (void *ctx, fputs (format->message_set_sep, stdout); first_toplevel = 0; - show_messages (ctx, format, messages, 0, params); + status = show_messages (ctx, format, messages, 0, params); + if (status && !res) + res = status; notmuch_thread_destroy (thread); @@ -961,7 +982,7 @@ do_show (void *ctx, fputs (format->message_set_end, stdout); - return 0; + return res != NOTMUCH_STATUS_SUCCESS; } enum { -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* Re: [PATCH v2 3/8] show: Allow formatters to return errors 2012-03-06 18:48 ` [PATCH v2 3/8] show: Allow formatters to return errors Austin Clements @ 2012-03-06 21:22 ` Mark Walters 2012-03-07 20:18 ` Tomi Ollila 2012-03-11 23:34 ` Austin Clements 0 siblings, 2 replies; 23+ messages in thread From: Mark Walters @ 2012-03-06 21:22 UTC (permalink / raw) To: Austin Clements, notmuch On Tue, 6 Mar 2012 18:48:39 +0000, Austin Clements <amdragon@MIT.EDU> wrote: > Formatter errors are propagated to the exit status of notmuch show. > > This isn't used by the JSON or text formatters, but it will be useful > for the raw format, which is pickier. I am not very familiar with this part of the code but the whole series looks fine to me. My only minor comment is that I like Tom's suggestion (in id:"m2399qrtat.fsf@guru.guru-group.fi") of having NOTMUCH_STATUS_FAILURE (= 1) to make the error handling look cleaner. Alternatively (or possibly as well) the functions do_show and do_show_messages could pass the actual error back up to notmuch_show_command and then that function could convert return 0/1 as appropriate. As usual I am quite happy to be overruled! Best wishes Mark ^ permalink raw reply [flat|nested] 23+ messages in thread
* Re: [PATCH v2 3/8] show: Allow formatters to return errors 2012-03-06 21:22 ` Mark Walters @ 2012-03-07 20:18 ` Tomi Ollila 2012-03-11 23:34 ` Austin Clements 1 sibling, 0 replies; 23+ messages in thread From: Tomi Ollila @ 2012-03-07 20:18 UTC (permalink / raw) To: Mark Walters, Austin Clements, notmuch On Tue, 06 Mar 2012 21:22:55 +0000, Mark Walters <markwalters1009@gmail.com> wrote: > On Tue, 6 Mar 2012 18:48:39 +0000, Austin Clements <amdragon@MIT.EDU> wrote: > > Formatter errors are propagated to the exit status of notmuch show. > > > > This isn't used by the JSON or text formatters, but it will be useful > > for the raw format, which is pickier. > > I am not very familiar with this part of the code but the whole series > looks fine to me. Looks good to me too. > > My only minor comment is that I like Tom's suggestion (in > id:"m2399qrtat.fsf@guru.guru-group.fi") of having NOTMUCH_STATUS_FAILURE > (= 1) to make the error handling look cleaner. Alternatively (or > possibly as well) the functions do_show and do_show_messages could pass > the actual error back up to notmuch_show_command and then that function > could convert return 0/1 as appropriate. > > As usual I am quite happy to be overruled! As usual I no longer know why I suggested that in the first place (at least in the context of these patches ;D) > Best wishes > > Mark Tomi ^ permalink raw reply [flat|nested] 23+ messages in thread
* Re: [PATCH v2 3/8] show: Allow formatters to return errors 2012-03-06 21:22 ` Mark Walters 2012-03-07 20:18 ` Tomi Ollila @ 2012-03-11 23:34 ` Austin Clements 1 sibling, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-11 23:34 UTC (permalink / raw) To: Mark Walters, notmuch On Tue, 06 Mar 2012 21:22:55 +0000, Mark Walters <markwalters1009@gmail.com> wrote: > On Tue, 6 Mar 2012 18:48:39 +0000, Austin Clements <amdragon@MIT.EDU> wrote: > > Formatter errors are propagated to the exit status of notmuch show. > > > > This isn't used by the JSON or text formatters, but it will be useful > > for the raw format, which is pickier. > > I am not very familiar with this part of the code but the whole series > looks fine to me. > > My only minor comment is that I like Tom's suggestion (in > id:"m2399qrtat.fsf@guru.guru-group.fi") of having NOTMUCH_STATUS_FAILURE > (= 1) to make the error handling look cleaner. Alternatively (or We could introduce a generic failure, though it couldn't be equal to 1 without breaking binary compatibility. I'm not sure a generic failure would make things much better, though; as far as I can tell, error handling in C is doomed to ugliness. > possibly as well) the functions do_show and do_show_messages could pass > the actual error back up to notmuch_show_command and then that function > could convert return 0/1 as appropriate. I would be happy to be convinced either way. It's the way it is because I didn't bother changing it and because I think it's reasonable to think of do_show and do_show_messages as extensions of notmuch_show_command. > As usual I am quite happy to be overruled! > > Best wishes > > Mark > ^ permalink raw reply [flat|nested] 23+ messages in thread
* [PATCH v2 4/8] show: Move format_message_mbox with the other new-style formats 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (2 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 3/8] show: Allow formatters to return errors Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 5/8] show: Convert mbox format to new self-recursive style Austin Clements ` (5 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Just code motion. --- notmuch-show.c | 100 ++++++++++++++++++++++++++++---------------------------- 1 files changed, 50 insertions(+), 50 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 648f468..b3a4550 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -219,56 +219,6 @@ _is_from_line (const char *line) return 0; } -/* Print a message in "mboxrd" format as documented, for example, - * here: - * - * http://qmail.org/qmail-manual-html/man5/mbox.html - */ -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)) -{ - const char *filename; - FILE *file; - const char *from; - - time_t date; - struct tm date_gmtime; - char date_asctime[26]; - - char *line = NULL; - size_t line_size; - ssize_t line_len; - - filename = notmuch_message_get_filename (message); - file = fopen (filename, "r"); - if (file == NULL) { - fprintf (stderr, "Failed to open %s: %s\n", - filename, strerror (errno)); - return; - } - - from = notmuch_message_get_header (message, "from"); - from = _extract_email_address (ctx, from); - - date = notmuch_message_get_date (message); - gmtime_r (&date, &date_gmtime); - asctime_r (&date_gmtime, date_asctime); - - printf ("From %s %s", from, date_asctime); - - while ((line_len = getline (&line, &line_size, file)) != -1 ) { - if (_is_from_line (line)) - putchar ('>'); - printf ("%s", line); - } - - printf ("\n"); - - fclose (file); -} - static void format_headers_message_part_text (GMimeMessage *message) { @@ -762,6 +712,56 @@ format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } +/* Print a message in "mboxrd" format as documented, for example, + * here: + * + * http://qmail.org/qmail-manual-html/man5/mbox.html + */ +static void +format_message_mbox (const void *ctx, + notmuch_message_t *message, + unused (int indent)) +{ + const char *filename; + FILE *file; + const char *from; + + time_t date; + struct tm date_gmtime; + char date_asctime[26]; + + char *line = NULL; + size_t line_size; + ssize_t line_len; + + filename = notmuch_message_get_filename (message); + file = fopen (filename, "r"); + if (file == NULL) { + fprintf (stderr, "Failed to open %s: %s\n", + filename, strerror (errno)); + return; + } + + from = notmuch_message_get_header (message, "from"); + from = _extract_email_address (ctx, from); + + date = notmuch_message_get_date (message); + gmtime_r (&date, &date_gmtime); + asctime_r (&date_gmtime, date_asctime); + + printf ("From %s %s", from, date_asctime); + + while ((line_len = getline (&line, &line_size, file)) != -1 ) { + if (_is_from_line (line)) + putchar ('>'); + printf ("%s", line); + } + + printf ("\n"); + + fclose (file); +} + static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 5/8] show: Convert mbox format to new self-recursive style 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (3 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 4/8] show: Move format_message_mbox with the other new-style formats Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 6/8] show: Move format_part_content_raw with the other new-style formats Austin Clements ` (4 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Given the lack of recursion, this is pretty easy. --- notmuch-show.c | 40 ++++++++++++++++++---------------------- 1 files changed, 18 insertions(+), 22 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index b3a4550..72c141e 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -45,25 +45,15 @@ static const notmuch_show_format_t format_json = { .message_set_end = "]" }; -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)); +static notmuch_status_t +format_part_mbox (const void *ctx, mime_node_t *node, + int indent, const notmuch_show_params_t *params); static const notmuch_show_format_t format_mbox = { - "", NULL, - "", format_message_mbox, - "", NULL, NULL, "", - "", - NULL, - NULL, - NULL, - NULL, - NULL, - "", - "", - "", "", - "" + .message_set_start = "", + .part = format_part_mbox, + .message_set_sep = "", + .message_set_end = "" }; static void @@ -717,11 +707,12 @@ format_part_json_entry (const void *ctx, mime_node_t *node, unused (int indent), * * http://qmail.org/qmail-manual-html/man5/mbox.html */ -static void -format_message_mbox (const void *ctx, - notmuch_message_t *message, - unused (int indent)) +static notmuch_status_t +format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), + unused (const notmuch_show_params_t *params)) { + notmuch_message_t *message = node->envelope_file; + const char *filename; FILE *file; const char *from; @@ -734,12 +725,15 @@ format_message_mbox (const void *ctx, size_t line_size; ssize_t line_len; + if (!message) + INTERNAL_ERROR ("format_part_mbox requires a root part"); + filename = notmuch_message_get_filename (message); file = fopen (filename, "r"); if (file == NULL) { fprintf (stderr, "Failed to open %s: %s\n", filename, strerror (errno)); - return; + return NOTMUCH_STATUS_FILE_ERROR; } from = notmuch_message_get_header (message, "from"); @@ -760,6 +754,8 @@ format_message_mbox (const void *ctx, printf ("\n"); fclose (file); + + return NOTMUCH_STATUS_SUCCESS; } static notmuch_status_t -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 6/8] show: Move format_part_content_raw with the other new-style formats 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (4 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 5/8] show: Convert mbox format to new self-recursive style Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 7/8] show: Convert raw format to the new self-recursive style, properly support interior parts Austin Clements ` (3 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch Just code motion. --- notmuch-show.c | 54 +++++++++++++++++++++++++++--------------------------- 1 files changed, 27 insertions(+), 27 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 72c141e..6f6052c 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -475,33 +475,6 @@ format_part_sigstatus_json (mime_node_t *node) } #endif -static void -format_part_content_raw (GMimeObject *part) -{ - if (! GMIME_IS_PART (part)) - return; - - GMimeStream *stream_stdout; - GMimeStream *stream_filter = NULL; - GMimeDataWrapper *wrapper; - - stream_stdout = g_mime_stream_file_new (stdout); - g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); - - stream_filter = g_mime_stream_filter_new (stream_stdout); - - wrapper = g_mime_part_get_content_object (GMIME_PART (part)); - - if (wrapper && stream_filter) - g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); - - if (stream_filter) - g_object_unref (stream_filter); - - if (stream_stdout) - g_object_unref(stream_stdout); -} - static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params) @@ -758,6 +731,33 @@ format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } +static void +format_part_content_raw (GMimeObject *part) +{ + if (! GMIME_IS_PART (part)) + return; + + GMimeStream *stream_stdout; + GMimeStream *stream_filter = NULL; + GMimeDataWrapper *wrapper; + + stream_stdout = g_mime_stream_file_new (stdout); + g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); + + stream_filter = g_mime_stream_filter_new (stream_stdout); + + wrapper = g_mime_part_get_content_object (GMIME_PART (part)); + + if (wrapper && stream_filter) + g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + + if (stream_filter) + g_object_unref (stream_filter); + + if (stream_stdout) + g_object_unref(stream_stdout); +} + static notmuch_status_t show_message (void *ctx, const notmuch_show_format_t *format, -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 7/8] show: Convert raw format to the new self-recursive style, properly support interior parts 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (5 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 6/8] show: Move format_part_content_raw with the other new-style formats Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 8/8] man: Update raw format documentation Austin Clements ` (2 subsequent siblings) 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch This is fully compatible for root and leaf parts, but now has proper support for interior parts. This requires some design decisions that were guided by what I would want if I were to save a part. Specifically: - Leaf parts are printed without headers and with transfer decoding. This is what makes sense for saving attachments. (Furthermore, the transfer decoding is necessary since, without the headers, the caller would not be able to interpret non-transfer-decoded output.) - Message parts are printed with their message headers, but without enclosing part headers. This is what makes sense for saving a message as a whole (which is a message part) and for saving attached messages. This is symmetric for whole messages and for attached messages, though we special-case the whole message for performance reasons (and corner-case correctness reasons: given malformed input, GMime may not be able to reproduce it from the parsed representation). - Multipart parts are printed with their headers and all child parts. It's not clear what the best thing to do for multipart is, but this was the most natural to implement and can be justified because such parts can't be interpreted without their headers. As an added benefit, we can move the special-case code for part 0 into the raw formatter. --- notmuch-show.c | 159 ++++++++++++++++++++++++-------------------------------- test/multipart | 74 +++++++++++++++++--------- 2 files changed, 116 insertions(+), 117 deletions(-) diff --git a/notmuch-show.c b/notmuch-show.c index 6f6052c..8ed6896 100644 --- a/notmuch-show.c +++ b/notmuch-show.c @@ -20,9 +20,6 @@ #include "notmuch-client.h" -static void -format_headers_message_part_text (GMimeMessage *message); - static notmuch_status_t format_part_text (const void *ctx, mime_node_t *node, int indent, const notmuch_show_params_t *params); @@ -56,23 +53,16 @@ static const notmuch_show_format_t format_mbox = { .message_set_end = "" }; -static void -format_part_content_raw (GMimeObject *part); +static notmuch_status_t +format_part_raw (unused (const void *ctx), mime_node_t *node, + unused (int indent), + unused (const notmuch_show_params_t *params)); static const notmuch_show_format_t format_raw = { - "", NULL, - "", NULL, - "", NULL, format_headers_message_part_text, "\n", - "", - NULL, - NULL, - NULL, - format_part_content_raw, - NULL, - "", - "", - "", "", - "" + .message_set_start = "", + .part = format_part_raw, + .message_set_sep = "", + .message_set_end = "" }; static const char * @@ -210,27 +200,6 @@ _is_from_line (const char *line) } static void -format_headers_message_part_text (GMimeMessage *message) -{ - InternetAddressList *recipients; - const char *recipients_string; - - printf ("Subject: %s\n", g_mime_message_get_subject (message)); - printf ("From: %s\n", g_mime_message_get_sender (message)); - recipients = g_mime_message_get_recipients (message, GMIME_RECIPIENT_TYPE_TO); - recipients_string = internet_address_list_to_string (recipients, 0); - if (recipients_string) - printf ("To: %s\n", - recipients_string); - recipients = g_mime_message_get_recipients (message, GMIME_RECIPIENT_TYPE_CC); - recipients_string = internet_address_list_to_string (recipients, 0); - if (recipients_string) - printf ("Cc: %s\n", - recipients_string); - printf ("Date: %s\n", g_mime_message_get_date_as_string (message)); -} - -static void format_headers_json (const void *ctx, GMimeMessage *message) { void *local = talloc_new (ctx); @@ -731,31 +700,82 @@ format_part_mbox (const void *ctx, mime_node_t *node, unused (int indent), return NOTMUCH_STATUS_SUCCESS; } -static void -format_part_content_raw (GMimeObject *part) +static notmuch_status_t +format_part_raw (unused (const void *ctx), mime_node_t *node, + unused (int indent), + unused (const notmuch_show_params_t *params)) { - if (! GMIME_IS_PART (part)) - return; + if (node->envelope_file) { + /* Special case the entire message to avoid MIME parsing. */ + const char *filename; + FILE *file; + size_t size; + char buf[4096]; + + filename = notmuch_message_get_filename (node->envelope_file); + if (filename == NULL) { + fprintf (stderr, "Error: Cannot get message filename.\n"); + return NOTMUCH_STATUS_FILE_ERROR; + } + + file = fopen (filename, "r"); + if (file == NULL) { + fprintf (stderr, "Error: Cannot open file %s: %s\n", filename, strerror (errno)); + return NOTMUCH_STATUS_FILE_ERROR; + } + + while (!feof (file)) { + size = fread (buf, 1, sizeof (buf), file); + if (ferror (file)) { + fprintf (stderr, "Error: Read failed from %s\n", filename); + fclose (file); + return NOTMUCH_STATUS_FILE_ERROR; + } + + if (fwrite (buf, size, 1, stdout) != 1) { + fprintf (stderr, "Error: Write failed\n"); + fclose (file); + return NOTMUCH_STATUS_FILE_ERROR; + } + } + + fclose (file); + return NOTMUCH_STATUS_SUCCESS; + } GMimeStream *stream_stdout; GMimeStream *stream_filter = NULL; - GMimeDataWrapper *wrapper; stream_stdout = g_mime_stream_file_new (stdout); g_mime_stream_file_set_owner (GMIME_STREAM_FILE (stream_stdout), FALSE); stream_filter = g_mime_stream_filter_new (stream_stdout); - wrapper = g_mime_part_get_content_object (GMIME_PART (part)); + if (GMIME_IS_PART (node->part)) { + /* For leaf parts, we emit only the transfer-decoded + * body. */ + GMimeDataWrapper *wrapper; + wrapper = g_mime_part_get_content_object (GMIME_PART (node->part)); - if (wrapper && stream_filter) - g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + if (wrapper && stream_filter) + g_mime_data_wrapper_write_to_stream (wrapper, stream_filter); + } else { + /* Write out the whole part. For message parts (the root + * part and embedded message parts), this will be the + * message including its headers (but not the + * encapsulating part's headers). For multipart parts, + * this will include the headers. */ + if (stream_filter) + g_mime_object_write_to_stream (node->part, stream_filter); + } if (stream_filter) g_object_unref (stream_filter); if (stream_stdout) g_object_unref(stream_stdout); + + return NOTMUCH_STATUS_SUCCESS; } static notmuch_status_t @@ -891,50 +911,7 @@ do_show_single (void *ctx, notmuch_message_set_flag (message, NOTMUCH_MESSAGE_FLAG_MATCH, 1); - /* Special case for --format=raw of full single message, just cat out file */ - if (params->raw && 0 == params->part) { - - const char *filename; - FILE *file; - size_t size; - char buf[4096]; - - filename = notmuch_message_get_filename (message); - if (filename == NULL) { - fprintf (stderr, "Error: Cannot message filename.\n"); - return 1; - } - - file = fopen (filename, "r"); - if (file == NULL) { - fprintf (stderr, "Error: Cannot open file %s: %s\n", filename, strerror (errno)); - return 1; - } - - while (!feof (file)) { - size = fread (buf, 1, sizeof (buf), file); - if (ferror (file)) { - fprintf (stderr, "Error: Read failed from %s\n", filename); - fclose (file); - return 1; - } - - if (fwrite (buf, size, 1, stdout) != 1) { - fprintf (stderr, "Error: Write failed\n"); - fclose (file); - return 1; - } - } - - fclose (file); - - return 0; - - } else { - - return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; - - } + return show_message (ctx, format, message, 0, params) != NOTMUCH_STATUS_SUCCESS; } /* Formatted output of threads */ diff --git a/test/multipart b/test/multipart index 475c6a2..c1a5702 100755 --- a/test/multipart +++ b/test/multipart @@ -450,58 +450,80 @@ test_expect_equal_file OUTPUT "${MAIL_DIR}"/multipart test_begin_subtest "--format=raw --part=1, message body" notmuch show --format=raw --part=1 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT -# output should *not* include newline -echo >>OUTPUT -cat <<EOF >EXPECTED -Subject: html message -From: Carl Worth <cworth@cworth.org> -To: cworth@cworth.org -Date: Fri, 05 Jan 2001 15:42:57 +0000 - -<p>This is an embedded message, with a multipart/alternative part.</p> -This is an embedded message, with a multipart/alternative part. -This is a text attachment. -And this message is signed. - --Carl ------BEGIN PGP SIGNATURE----- -Version: GnuPG v1.4.11 (GNU/Linux) - -iEYEARECAAYFAk3SA/gACgkQ6JDdNq8qSWj0sACghqVJEQJUs3yV8zbTzhgnSIcD -W6cAmQE4dcYrx/LPLtYLZm1jsGauE5hE -=zkga ------END PGP SIGNATURE----- -EOF -test_expect_equal_file OUTPUT EXPECTED +test_expect_equal_file OUTPUT "${MAIL_DIR}"/multipart test_begin_subtest "--format=raw --part=2, multipart/mixed" notmuch show --format=raw --part=2 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT cat <<EOF >EXPECTED -Subject: html message +Content-Type: multipart/mixed; boundary="=-=-=" + +--=-=-= +Content-Type: message/rfc822 +Content-Disposition: inline + From: Carl Worth <cworth@cworth.org> To: cworth@cworth.org +Subject: html message Date: Fri, 05 Jan 2001 15:42:57 +0000 +User-Agent: Notmuch/0.5 (http://notmuchmail.org) Emacs/23.3.1 (i486-pc-linux-gnu) +Message-ID: <87liy5ap01.fsf@yoom.home.cworth.org> +MIME-Version: 1.0 +Content-Type: multipart/alternative; boundary="==-=-==" + +--==-=-== +Content-Type: text/html <p>This is an embedded message, with a multipart/alternative part.</p> + +--==-=-== +Content-Type: text/plain + This is an embedded message, with a multipart/alternative part. + +--==-=-==-- + +--=-=-= +Content-Disposition: attachment; filename=attachment + This is a text attachment. + +--=-=-= + And this message is signed. -Carl + +--=-=-=-- EOF test_expect_equal_file OUTPUT EXPECTED test_begin_subtest "--format=raw --part=3, rfc822 part" -test_subtest_known_broken - notmuch show --format=raw --part=3 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT test_expect_equal_file OUTPUT embedded_message test_begin_subtest "--format=raw --part=4, rfc822's multipart" notmuch show --format=raw --part=4 'id:87liy5ap00.fsf@yoom.home.cworth.org' >OUTPUT cat <<EOF >EXPECTED +From: Carl Worth <cworth@cworth.org> +To: cworth@cworth.org +Subject: html message +Date: Fri, 05 Jan 2001 15:42:57 +0000 +User-Agent: Notmuch/0.5 (http://notmuchmail.org) Emacs/23.3.1 (i486-pc-linux-gnu) +Message-ID: <87liy5ap01.fsf@yoom.home.cworth.org> +MIME-Version: 1.0 +Content-Type: multipart/alternative; boundary="==-=-==" + +--==-=-== +Content-Type: text/html + <p>This is an embedded message, with a multipart/alternative part.</p> + +--==-=-== +Content-Type: text/plain + This is an embedded message, with a multipart/alternative part. + +--==-=-==-- EOF test_expect_equal_file OUTPUT EXPECTED -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* [PATCH v2 8/8] man: Update raw format documentation 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (6 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 7/8] show: Convert raw format to the new self-recursive style, properly support interior parts Austin Clements @ 2012-03-06 18:48 ` Austin Clements 2012-03-09 3:25 ` [PATCH v2 0/8] Rewrite mbox and raw show formats Adam Wolfe Gordon 2012-03-18 12:51 ` David Bremner 9 siblings, 0 replies; 23+ messages in thread From: Austin Clements @ 2012-03-06 18:48 UTC (permalink / raw) To: notmuch --- man/man1/notmuch-show.1 | 13 +++++++++---- 1 files changed, 9 insertions(+), 4 deletions(-) diff --git a/man/man1/notmuch-show.1 b/man/man1/notmuch-show.1 index 4c5db94..9506367 100644 --- a/man/man1/notmuch-show.1 +++ b/man/man1/notmuch-show.1 @@ -84,12 +84,17 @@ http://homepage.ntlworld.com/jonathan.deboynepollard/FGA/mail-mbox-formats.html .TP 4 .BR raw " (default for a single part, see \-\-part)" -For a message, the original, raw content of the email message is -output. Consumers of this format should expect to implement MIME -decoding and similar functions. +For a message or an attached message part, the original, raw content +of the email message is output. Consumers of this format should expect +to implement MIME decoding and similar functions. For a single part (\-\-part) the raw part content is output after -performing any necessary MIME decoding. +performing any necessary MIME decoding. Note that messages with a +simple body still have two parts: part 0 is the whole message and part +1 is the body. + +For a multipart part, the part headers and body (including all child +parts) is output. The raw format must only be used with search terms matching single message. -- 1.7.7.3 ^ permalink raw reply related [flat|nested] 23+ messages in thread
* Re: [PATCH v2 0/8] Rewrite mbox and raw show formats 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (7 preceding siblings ...) 2012-03-06 18:48 ` [PATCH v2 8/8] man: Update raw format documentation Austin Clements @ 2012-03-09 3:25 ` Adam Wolfe Gordon 2012-03-18 12:51 ` David Bremner 9 siblings, 0 replies; 23+ messages in thread From: Adam Wolfe Gordon @ 2012-03-09 3:25 UTC (permalink / raw) To: Austin Clements; +Cc: notmuch On Tue, Mar 6, 2012 at 11:48, Austin Clements <amdragon@mit.edu> wrote: > v2 makes the new raw format support interior, as well as root and leaf > parts. > > Patches 1, 2, and 8 are new but simple. Patches 3 through 6 have not > changed. Patch 7 has obviously changed quite a bit. The whole series looks good to me. ^ permalink raw reply [flat|nested] 23+ messages in thread
* Re: [PATCH v2 0/8] Rewrite mbox and raw show formats 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements ` (8 preceding siblings ...) 2012-03-09 3:25 ` [PATCH v2 0/8] Rewrite mbox and raw show formats Adam Wolfe Gordon @ 2012-03-18 12:51 ` David Bremner 9 siblings, 0 replies; 23+ messages in thread From: David Bremner @ 2012-03-18 12:51 UTC (permalink / raw) To: Austin Clements, notmuch On Tue, 6 Mar 2012 18:48:36 +0000, Austin Clements <amdragon@MIT.EDU> wrote: > v2 makes the new raw format support interior, as well as root and leaf > parts. > > Patches 1, 2, and 8 are new but simple. Patches 3 through 6 have not > changed. Patch 7 has obviously changed quite a bit. Pushed, d ^ permalink raw reply [flat|nested] 23+ messages in thread
end of thread, other threads:[~2012-03-18 12:51 UTC | newest] Thread overview: 23+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2012-03-03 5:20 [PATCH 0/5] Rewrite mbox and raw show formats Austin Clements 2012-03-03 5:20 ` [PATCH 1/5] show: Allow formatters to return errors Austin Clements 2012-03-03 5:20 ` [PATCH 2/5] show: Move format_message_mbox with the other new-style formats Austin Clements 2012-03-03 5:20 ` [PATCH 3/5] show: Convert mbox format to new self-recursive style Austin Clements 2012-03-03 5:20 ` [PATCH 4/5] show: Move format_part_content_raw with the other new-style formats Austin Clements 2012-03-03 5:20 ` [PATCH 5/5] show: Convert raw format to the new self-recursive style Austin Clements 2012-03-03 22:05 ` Jameson Graef Rollins 2012-03-06 18:43 ` Austin Clements 2012-03-03 8:18 ` [PATCH 0/5] Rewrite mbox and raw show formats Tomi Ollila 2012-03-06 18:48 ` [PATCH v2 0/8] " Austin Clements 2012-03-06 18:48 ` [PATCH v2 1/8] test: Fix typo in test description Austin Clements 2012-03-06 18:48 ` [PATCH v2 2/8] test: Fix malformed multipart message Austin Clements 2012-03-06 18:48 ` [PATCH v2 3/8] show: Allow formatters to return errors Austin Clements 2012-03-06 21:22 ` Mark Walters 2012-03-07 20:18 ` Tomi Ollila 2012-03-11 23:34 ` Austin Clements 2012-03-06 18:48 ` [PATCH v2 4/8] show: Move format_message_mbox with the other new-style formats Austin Clements 2012-03-06 18:48 ` [PATCH v2 5/8] show: Convert mbox format to new self-recursive style Austin Clements 2012-03-06 18:48 ` [PATCH v2 6/8] show: Move format_part_content_raw with the other new-style formats Austin Clements 2012-03-06 18:48 ` [PATCH v2 7/8] show: Convert raw format to the new self-recursive style, properly support interior parts Austin Clements 2012-03-06 18:48 ` [PATCH v2 8/8] man: Update raw format documentation Austin Clements 2012-03-09 3:25 ` [PATCH v2 0/8] Rewrite mbox and raw show formats Adam Wolfe Gordon 2012-03-18 12:51 ` David Bremner
Code repositories for project(s) associated with this public inbox https://yhetil.org/notmuch.git/ This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).