From: Ethan Glasser-Camp <[email protected]>

This introduces (and uses) the mailstore parameter to the
notmuch_message_file_open API, and passes this through wherever it
will be needed. This requires touching a lot of places just to change
one API. We end up adding it to the notmuch_database_t struct because
it is needed for notmuch_database_upgrade.

This doesn't touch the Python bindings, which require a certain amount
of effort. (Therefore, the Python tests will be broken until the next commit.)

Signed-off-by: Ethan Glasser-Camp <ethan at betacantrips.com>
---
 lib/Makefile.local     |    1 +
 lib/database-private.h |    1 +
 lib/database.cc        |   10 +++++---
 lib/mailstore.c        |   59 ++++++++++++++++++++++++++++++++++++++++++++++++
 lib/message-file.c     |   10 +++++---
 lib/message.cc         |   11 +++++---
 lib/notmuch-private.h  |    7 ++++-
 lib/notmuch.h          |   21 ++++++++++++++--
 lib/thread.cc          |   24 +++++++++++--------
 notmuch-client.h       |    6 +++++
 notmuch-config.c       |   12 +++++++++
 notmuch-count.c        |    3 +-
 notmuch-dump.c         |    3 +-
 notmuch-new.c          |    8 +++++-
 notmuch-reply.c        |   45 ++++++++++++++++++++++++------------
 notmuch-restore.c      |    3 +-
 notmuch-search.c       |    3 +-
 notmuch-show.c         |   56 ++++++++++++++++++++++++++++++---------------
 notmuch-tag.c          |    3 +-
 test/symbol-test.cc    |    3 +-
 20 files changed, 220 insertions(+), 69 deletions(-)
 create mode 100644 lib/mailstore.c

diff --git a/lib/Makefile.local b/lib/Makefile.local
index 54c4dea..461e5cd 100644
--- a/lib/Makefile.local
+++ b/lib/Makefile.local
@@ -51,6 +51,7 @@ libnotmuch_c_srcs =           \
        $(dir)/filenames.c      \
        $(dir)/string-list.c    \
        $(dir)/libsha1.c        \
+       $(dir)/mailstore.c      \
        $(dir)/message-file.c   \
        $(dir)/messages.c       \
        $(dir)/sha1.c           \
diff --git a/lib/database-private.h b/lib/database-private.h
index 88532d5..1cb8c43 100644
--- a/lib/database-private.h
+++ b/lib/database-private.h
@@ -39,6 +39,7 @@
 struct _notmuch_database {
     notmuch_bool_t exception_reported;

+    notmuch_mailstore_t *mailstore;
     char *path;

     notmuch_bool_t needs_upgrade;
diff --git a/lib/database.cc b/lib/database.cc
index c928d02..e3c8095 100644
--- a/lib/database.cc
+++ b/lib/database.cc
@@ -521,7 +521,7 @@ parse_references (void *ctx,
 }

 notmuch_database_t *
-notmuch_database_create (const char *path)
+notmuch_database_create (notmuch_mailstore_t *mailstore, const char *path)
 {
     notmuch_database_t *notmuch = NULL;
     char *notmuch_path = NULL;
@@ -556,7 +556,7 @@ notmuch_database_create (const char *path)
        goto DONE;
     }

-    notmuch = notmuch_database_open (path,
+    notmuch = notmuch_database_open (mailstore, path,
                                     NOTMUCH_DATABASE_MODE_READ_WRITE);
     notmuch_database_upgrade (notmuch, NULL, NULL);

@@ -579,7 +579,8 @@ _notmuch_database_ensure_writable (notmuch_database_t 
*notmuch)
 }

 notmuch_database_t *
-notmuch_database_open (const char *path,
+notmuch_database_open (notmuch_mailstore_t *mailstore,
+                      const char *path,
                       notmuch_database_mode_t mode)
 {
     void *local = talloc_new (NULL);
@@ -619,6 +620,7 @@ notmuch_database_open (const char *path,
     notmuch = talloc_zero (NULL, notmuch_database_t);
     notmuch->exception_reported = FALSE;
     notmuch->path = talloc_strdup (notmuch, path);
+    notmuch->mailstore = mailstore;

     if (notmuch->path[strlen (notmuch->path) - 1] == '/')
        notmuch->path[strlen (notmuch->path) - 1] = '\0';
@@ -1636,7 +1638,7 @@ notmuch_database_add_message (notmuch_database_t *notmuch,
     if (ret)
        return ret;

-    message_file = notmuch_message_file_open (filename);
+    message_file = notmuch_message_file_open (notmuch->mailstore, filename);
     if (message_file == NULL)
        return NOTMUCH_STATUS_FILE_ERROR;

diff --git a/lib/mailstore.c b/lib/mailstore.c
new file mode 100644
index 0000000..290da70
--- /dev/null
+++ b/lib/mailstore.c
@@ -0,0 +1,59 @@
+/* mailstore.c - mail storage backends
+ *
+ * Copyright ? 2009 Carl Worth
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see http://www.gnu.org/licenses/ .
+ */
+
+#include <stdio.h>
+
+#include "notmuch-private.h"
+
+typedef struct _notmuch_mailstore {
+    FILE *(*open) (struct _notmuch_mailstore *mailstore, const char *filename);
+} _notmuch_mailstore;
+
+static FILE *
+_maildir_open_function (unused (notmuch_mailstore_t *mailstore),
+                       const char *filename)
+{
+    return fopen (filename, "r");
+}
+
+/* A mailstore is defined as:
+ *
+ * - A function used to "open" a mail message. This takes the
+ *   "filename" for the file and should return a FILE *.
+ *
+ * - TODO: A way to scan for new messages?
+ *
+ * - TODO: A "constructor"?
+ */
+_notmuch_mailstore
+notmuch_mailstore_maildir = { _maildir_open_function };
+
+_notmuch_mailstore *
+notmuch_mailstore_get_by_name (const char *name)
+{
+    if (strcmp (name, "maildir") == 0)
+       return &notmuch_mailstore_maildir;
+
+    return NULL;
+}
+
+FILE *
+notmuch_mailstore_open (notmuch_mailstore_t *mailstore, const char *filename)
+{
+    return mailstore->open (mailstore, filename);
+}
diff --git a/lib/message-file.c b/lib/message-file.c
index 915aba8..61f4d04 100644
--- a/lib/message-file.c
+++ b/lib/message-file.c
@@ -94,7 +94,8 @@ _notmuch_message_file_destructor (notmuch_message_file_t 
*message)
 /* Create a new notmuch_message_file_t for 'filename' with 'ctx' as
  * the talloc owner. */
 notmuch_message_file_t *
-_notmuch_message_file_open_ctx (void *ctx, const char *filename)
+_notmuch_message_file_open_ctx (void *ctx, notmuch_mailstore_t *mailstore,
+                               const char *filename)
 {
     notmuch_message_file_t *message;

@@ -104,7 +105,7 @@ _notmuch_message_file_open_ctx (void *ctx, const char 
*filename)

     talloc_set_destructor (message, _notmuch_message_file_destructor);

-    message->file = fopen (filename, "r");
+    message->file = notmuch_mailstore_open (mailstore, filename);
     if (message->file == NULL)
        goto FAIL;

@@ -126,9 +127,10 @@ _notmuch_message_file_open_ctx (void *ctx, const char 
*filename)
 }

 notmuch_message_file_t *
-notmuch_message_file_open (const char *filename)
+notmuch_message_file_open (notmuch_mailstore_t *mailstore,
+                          const char *filename)
 {
-    return _notmuch_message_file_open_ctx (NULL, filename);
+    return _notmuch_message_file_open_ctx (NULL, mailstore, filename);
 }

 void
diff --git a/lib/message.cc b/lib/message.cc
index 0075425..762a18f 100644
--- a/lib/message.cc
+++ b/lib/message.cc
@@ -395,7 +395,8 @@ notmuch_message_get_message_id (notmuch_message_t *message)
 }

 static void
-_notmuch_message_ensure_message_file (notmuch_message_t *message)
+_notmuch_message_ensure_message_file (notmuch_mailstore_t *mailstore,
+                                     notmuch_message_t *message)
 {
     const char *filename;

@@ -406,11 +407,13 @@ _notmuch_message_ensure_message_file (notmuch_message_t 
*message)
     if (unlikely (filename == NULL))
        return;

-    message->message_file = _notmuch_message_file_open_ctx (message, filename);
+    message->message_file = _notmuch_message_file_open_ctx (message, mailstore,
+                                                           filename);
 }

 const char *
-notmuch_message_get_header (notmuch_message_t *message, const char *header)
+notmuch_message_get_header (notmuch_mailstore_t *mailstore,
+                           notmuch_message_t *message, const char *header)
 {
     std::string value;

@@ -427,7 +430,7 @@ notmuch_message_get_header (notmuch_message_t *message, 
const char *header)
        return talloc_strdup (message, value.c_str ());

     /* Otherwise fall back to parsing the file */
-    _notmuch_message_ensure_message_file (message);
+    _notmuch_message_ensure_message_file (mailstore, message);
     if (message->message_file == NULL)
        return NULL;

diff --git a/lib/notmuch-private.h b/lib/notmuch-private.h
index 7bf153e..0f01437 100644
--- a/lib/notmuch-private.h
+++ b/lib/notmuch-private.h
@@ -331,11 +331,14 @@ typedef struct _notmuch_message_file 
notmuch_message_file_t;
  * Returns NULL if any error occurs.
  */
 notmuch_message_file_t *
-notmuch_message_file_open (const char *filename);
+notmuch_message_file_open (notmuch_mailstore_t *mailstore,
+                          const char *filename);

 /* Like notmuch_message_file_open but with 'ctx' as the talloc owner. */
 notmuch_message_file_t *
-_notmuch_message_file_open_ctx (void *ctx, const char *filename);
+_notmuch_message_file_open_ctx (void *ctx,
+                               notmuch_mailstore_t *mailstore,
+                               const char *filename);

 /* Close a notmuch message previously opened with notmuch_message_open. */
 void
diff --git a/lib/notmuch.h b/lib/notmuch.h
index 7929fe7..7ebe034 100644
--- a/lib/notmuch.h
+++ b/lib/notmuch.h
@@ -123,6 +123,7 @@ typedef struct _notmuch_message notmuch_message_t;
 typedef struct _notmuch_tags notmuch_tags_t;
 typedef struct _notmuch_directory notmuch_directory_t;
 typedef struct _notmuch_filenames notmuch_filenames_t;
+typedef struct _notmuch_mailstore notmuch_mailstore_t;

 /* Create a new, empty notmuch database located at 'path'.
  *
@@ -144,7 +145,7 @@ typedef struct _notmuch_filenames notmuch_filenames_t;
  * an error message on stderr).
  */
 notmuch_database_t *
-notmuch_database_create (const char *path);
+notmuch_database_create (notmuch_mailstore_t *mailstore, const char *path);

 typedef enum {
     NOTMUCH_DATABASE_MODE_READ_ONLY = 0,
@@ -172,7 +173,8 @@ typedef enum {
  * an error message on stderr).
  */
 notmuch_database_t *
-notmuch_database_open (const char *path,
+notmuch_database_open (notmuch_mailstore_t *mailstore,
+                      const char *path,
                       notmuch_database_mode_t mode);

 /* Close the given notmuch database, freeing all associated
@@ -409,6 +411,18 @@ notmuch_database_find_message_by_filename 
(notmuch_database_t *notmuch,
 notmuch_tags_t *
 notmuch_database_get_all_tags (notmuch_database_t *db);

+/* Return a mail storage backend based on the given name.
+ *
+ * Storage backends are required in order to manipulate message files.
+ */
+notmuch_mailstore_t *
+notmuch_mailstore_get_by_name (const char *name);
+
+/* Get an input stream for a filename.
+ */
+FILE *
+notmuch_mailstore_open (notmuch_mailstore_t *mailstore, const char *filename);
+
 /* Create a new query for 'database'.
  *
  * Here, 'database' should be an open database, (see
@@ -929,7 +943,8 @@ notmuch_message_get_date  (notmuch_message_t *message);
  * header line matching 'header'. Returns NULL if any error occurs.
  */
 const char *
-notmuch_message_get_header (notmuch_message_t *message, const char *header);
+notmuch_message_get_header (notmuch_mailstore_t *mailstore,
+                           notmuch_message_t *message, const char *header);

 /* Get the tags for 'message', returning a notmuch_tags_t object which
  * can be used to iterate over all tags.
diff --git a/lib/thread.cc b/lib/thread.cc
index 0435ee6..73edf83 100644
--- a/lib/thread.cc
+++ b/lib/thread.cc
@@ -213,7 +213,8 @@ _thread_cleanup_author (notmuch_thread_t *thread,
  * reference to it.
  */
 static void
-_thread_add_message (notmuch_thread_t *thread,
+_thread_add_message (notmuch_mailstore_t *mailstore,
+                    notmuch_thread_t *thread,
                     notmuch_message_t *message)
 {
     notmuch_tags_t *tags;
@@ -231,7 +232,7 @@ _thread_add_message (notmuch_thread_t *thread,
                         xstrdup (notmuch_message_get_message_id (message)),
                         message);

-    from = notmuch_message_get_header (message, "from");
+    from = notmuch_message_get_header (mailstore, message, "from");
     if (from)
        list = internet_address_list_parse_string (from);

@@ -253,7 +254,7 @@ _thread_add_message (notmuch_thread_t *thread,

     if (! thread->subject) {
        const char *subject;
-       subject = notmuch_message_get_header (message, "subject");
+       subject = notmuch_message_get_header (mailstore, message, "subject");
        thread->subject = talloc_strdup (thread, subject ? subject : "");
     }

@@ -267,13 +268,14 @@ _thread_add_message (notmuch_thread_t *thread,
 }

 static void
-_thread_set_subject_from_message (notmuch_thread_t *thread,
+_thread_set_subject_from_message (notmuch_mailstore_t *mailstore,
+                                 notmuch_thread_t *thread,
                                  notmuch_message_t *message)
 {
     const char *subject;
     const char *cleaned_subject;

-    subject = notmuch_message_get_header (message, "subject");
+    subject = notmuch_message_get_header (mailstore, message, "subject");
     if (! subject)
        return;

@@ -300,7 +302,8 @@ _thread_set_subject_from_message (notmuch_thread_t *thread,
  * oldest or newest matching subject is applied to the thread as a
  * whole. */
 static void
-_thread_add_matched_message (notmuch_thread_t *thread,
+_thread_add_matched_message (notmuch_mailstore_t *mailstore,
+                            notmuch_thread_t *thread,
                             notmuch_message_t *message,
                             notmuch_sort_t sort)
 {
@@ -312,13 +315,13 @@ _thread_add_matched_message (notmuch_thread_t *thread,
     if (date < thread->oldest || ! thread->matched_messages) {
        thread->oldest = date;
        if (sort == NOTMUCH_SORT_OLDEST_FIRST)
-           _thread_set_subject_from_message (thread, message);
+           _thread_set_subject_from_message (mailstore, thread, message);
     }

     if (date > thread->newest || ! thread->matched_messages) {
        thread->newest = date;
        if (sort != NOTMUCH_SORT_OLDEST_FIRST)
-           _thread_set_subject_from_message (thread, message);
+           _thread_set_subject_from_message (mailstore, thread, message);
     }

     thread->matched_messages++;
@@ -467,11 +470,12 @@ _notmuch_thread_create (void *ctx,
        if (doc_id == seed_doc_id)
            message = seed_message;

-       _thread_add_message (thread, message);
+       _thread_add_message (notmuch->mailstore, thread, message);

        if ( _notmuch_doc_id_set_contains (match_set, doc_id)) {
            _notmuch_doc_id_set_remove (match_set, doc_id);
-           _thread_add_matched_message (thread, message, sort);
+           _thread_add_matched_message (notmuch->mailstore, thread,
+                                        message, sort);
        }

        _notmuch_message_close (message);
diff --git a/notmuch-client.h b/notmuch-client.h
index 4518cb0..c1c30a2 100644
--- a/notmuch-client.h
+++ b/notmuch-client.h
@@ -68,14 +68,17 @@ struct notmuch_show_params;
 typedef struct notmuch_show_format {
     const char *message_set_start;
     void (*part) (const void *ctx,
+                 notmuch_mailstore_t *mailstore,
                  struct mime_node *node, int indent,
                  const struct notmuch_show_params *params);
     const char *message_start;
     void (*message) (const void *ctx,
+                    notmuch_mailstore_t *mailstore,
                     notmuch_message_t *message,
                     int indent);
     const char *header_start;
     void (*header) (const void *ctx,
+                   notmuch_mailstore_t *mailstore,
                    notmuch_message_t *message);
     void (*header_message_part) (GMimeMessage *message);
     const char *header_end;
@@ -226,6 +229,9 @@ void
 notmuch_config_set_database_type (notmuch_config_t *config,
                                  const char *database_type);

+notmuch_mailstore_t *
+notmuch_config_get_mailstore (notmuch_config_t *config);
+
 const char *
 notmuch_config_get_user_name (notmuch_config_t *config);

diff --git a/notmuch-config.c b/notmuch-config.c
index b8bee69..f611b26 100644
--- a/notmuch-config.c
+++ b/notmuch-config.c
@@ -584,6 +584,18 @@ notmuch_config_set_database_type (notmuch_config_t *config,
     config->database_type = NULL;
 }

+notmuch_mailstore_t *
+notmuch_config_get_mailstore (notmuch_config_t *config)
+{
+    /* This is just a stub since there's only one mailstore.
+     *
+     * When there are multiple mailstore types and "constructors" for
+     * them, this may have to be much more complicated.
+     */
+    const char *type = notmuch_config_get_database_type (config);
+    return notmuch_mailstore_get_by_name (type);
+}
+
 const char *
 notmuch_config_get_user_name (notmuch_config_t *config)
 {
diff --git a/notmuch-count.c b/notmuch-count.c
index 63459fb..0c7beef 100644
--- a/notmuch-count.c
+++ b/notmuch-count.c
@@ -57,7 +57,8 @@ notmuch_count_command (void *ctx, int argc, char *argv[])
     if (config == NULL)
        return 1;

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_ONLY);
     if (notmuch == NULL)
        return 1;
diff --git a/notmuch-dump.c b/notmuch-dump.c
index a735875..f7729dd 100644
--- a/notmuch-dump.c
+++ b/notmuch-dump.c
@@ -36,7 +36,8 @@ notmuch_dump_command (unused (void *ctx), int argc, char 
*argv[])
     if (config == NULL)
        return 1;

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_ONLY);
     if (notmuch == NULL)
        return 1;
diff --git a/notmuch-new.c b/notmuch-new.c
index 8dbebb3..355dde4 100644
--- a/notmuch-new.c
+++ b/notmuch-new.c
@@ -808,6 +808,7 @@ notmuch_new_command (void *ctx, int argc, char *argv[])
 {
     notmuch_config_t *config;
     notmuch_database_t *notmuch;
+    notmuch_mailstore_t *mailstore;
     add_files_state_t add_files_state;
     double elapsed;
     struct timeval tv_now, tv_start;
@@ -843,6 +844,7 @@ notmuch_new_command (void *ctx, int argc, char *argv[])
     add_files_state.new_tags = notmuch_config_get_new_tags (config, 
&add_files_state.new_tags_length);
     add_files_state.synchronize_flags = 
notmuch_config_get_maildir_synchronize_flags (config);
     db_path = notmuch_config_get_database_path (config);
+    mailstore = notmuch_config_get_mailstore (config);

     if (run_hooks) {
        ret = notmuch_run_hook (db_path, "pre-new");
@@ -861,10 +863,12 @@ notmuch_new_command (void *ctx, int argc, char *argv[])
            return 1;

        printf ("Found %d total files (that's not much mail).\n", count);
-       notmuch = notmuch_database_create (db_path);
+       notmuch = notmuch_database_create (mailstore,
+                                          db_path);
        add_files_state.total_files = count;
     } else {
-       notmuch = notmuch_database_open (db_path,
+       notmuch = notmuch_database_open (mailstore,
+                                        db_path,
                                         NOTMUCH_DATABASE_MODE_READ_WRITE);
        if (notmuch == NULL)
            return 1;
diff --git a/notmuch-reply.c b/notmuch-reply.c
index 6b244e6..cb1dd6e 100644
--- a/notmuch-reply.c
+++ b/notmuch-reply.c
@@ -256,14 +256,15 @@ scan_address_string (const char *recipients,
  * in either the 'To' or 'Cc' header of the message?
  */
 static int
-reply_to_header_is_redundant (notmuch_message_t *message)
+reply_to_header_is_redundant (notmuch_mailstore_t *mailstore,
+                             notmuch_message_t *message)
 {
     const char *reply_to, *to, *cc, *addr;
     InternetAddressList *list;
     InternetAddress *address;
     InternetAddressMailbox *mailbox;

-    reply_to = notmuch_message_get_header (message, "reply-to");
+    reply_to = notmuch_message_get_header (mailstore, message, "reply-to");
     if (reply_to == NULL || *reply_to == '\0')
        return 0;

@@ -279,8 +280,8 @@ reply_to_header_is_redundant (notmuch_message_t *message)
     mailbox = INTERNET_ADDRESS_MAILBOX (address);
     addr = internet_address_mailbox_get_addr (mailbox);

-    to = notmuch_message_get_header (message, "to");
-    cc = notmuch_message_get_header (message, "cc");
+    to = notmuch_message_get_header (mailstore, message, "to");
+    cc = notmuch_message_get_header (mailstore, message, "cc");

     if ((to && strstr (to, addr) != 0) ||
        (cc && strstr (cc, addr) != 0))
@@ -319,10 +320,13 @@ add_recipients_from_message (GMimeMessage *reply,
        { "cc",         NULL, GMIME_RECIPIENT_TYPE_CC  },
        { "bcc",        NULL, GMIME_RECIPIENT_TYPE_BCC }
     };
+    notmuch_mailstore_t *mailstore;
     const char *from_addr = NULL;
     unsigned int i;
     unsigned int n = 0;

+    mailstore = notmuch_config_get_mailstore (config);
+
     /* Some mailing lists munge the Reply-To header despite it being A Bad
      * Thing, see http://www.unicom.com/pw/reply-to-harmful.html
      *
@@ -334,7 +338,7 @@ add_recipients_from_message (GMimeMessage *reply,
      * that the address in the Reply-To header will always appear in
      * the reply.
      */
-    if (reply_to_header_is_redundant (message)) {
+    if (reply_to_header_is_redundant (mailstore, message)) {
        reply_to_map[0].header = "from";
        reply_to_map[0].fallback = NULL;
     }
@@ -342,10 +346,10 @@ add_recipients_from_message (GMimeMessage *reply,
     for (i = 0; i < ARRAY_SIZE (reply_to_map); i++) {
        const char *recipients;

-       recipients = notmuch_message_get_header (message,
+       recipients = notmuch_message_get_header (mailstore, message,
                                                 reply_to_map[i].header);
        if ((recipients == NULL || recipients[0] == '\0') && 
reply_to_map[i].fallback)
-           recipients = notmuch_message_get_header (message,
+           recipients = notmuch_message_get_header (mailstore, message,
                                                     reply_to_map[i].fallback);

        n += scan_address_string (recipients, config, reply,
@@ -374,6 +378,7 @@ add_recipients_from_message (GMimeMessage *reply,
 static const char *
 guess_from_received_header (notmuch_config_t *config, notmuch_message_t 
*message)
 {
+    notmuch_mailstore_t *mailstore;
     const char *received,*primary,*by;
     const char **other;
     char *tohdr;
@@ -387,6 +392,7 @@ guess_from_received_header (notmuch_config_t *config, 
notmuch_message_t *message

     primary = notmuch_config_get_user_primary_email (config);
     other = notmuch_config_get_user_other_email (config, &other_len);
+    mailstore = notmuch_config_get_mailstore (config);

     /* sadly, there is no standard way to find out to which email
      * address a mail was delivered - what is in the headers depends
@@ -403,7 +409,8 @@ guess_from_received_header (notmuch_config_t *config, 
notmuch_message_t *message
      * If none of these work, we give up and return NULL
      */
     for (i = 0; i < sizeof(to_headers)/sizeof(*to_headers); i++) {
-       tohdr = xstrdup(notmuch_message_get_header (message, to_headers[i]));
+       tohdr = xstrdup(notmuch_message_get_header (mailstore,
+                                                   message, to_headers[i]));
        if (tohdr && *tohdr) {
            /* tohdr is potentialy a list of email addresses, so here we
             * check if one of the email addresses is a substring of tohdr
@@ -428,7 +435,7 @@ guess_from_received_header (notmuch_config_t *config, 
notmuch_message_t *message
      * The Received: header is special in our get_header function
      * and is always concatenated.
      */
-    received = notmuch_message_get_header (message, "received");
+    received = notmuch_message_get_header (mailstore, message, "received");
     if (received == NULL)
        return NULL;

@@ -515,10 +522,12 @@ notmuch_reply_format_default(void *ctx,
     GMimeMessage *reply;
     notmuch_messages_t *messages;
     notmuch_message_t *message;
+    notmuch_mailstore_t *mailstore;
     const char *subject, *from_addr = NULL;
     const char *in_reply_to, *orig_references, *references;
     const notmuch_show_format_t *format = &format_reply;

+    mailstore = notmuch_config_get_mailstore (config);
     for (messages = notmuch_query_search_messages (query);
         notmuch_messages_valid (messages);
         notmuch_messages_move_to_next (messages))
@@ -532,7 +541,7 @@ notmuch_reply_format_default(void *ctx,
            return 1;
        }

-       subject = notmuch_message_get_header (message, "subject");
+       subject = notmuch_message_get_header (mailstore, message, "subject");
        if (subject) {
            if (strncasecmp (subject, "Re:", 3))
                subject = talloc_asprintf (ctx, "Re: %s", subject);
@@ -560,7 +569,8 @@ notmuch_reply_format_default(void *ctx,
        g_mime_object_set_header (GMIME_OBJECT (reply),
                                  "In-Reply-To", in_reply_to);

-       orig_references = notmuch_message_get_header (message, "references");
+       orig_references = notmuch_message_get_header (mailstore,
+                                                     message, "references");
        references = talloc_asprintf (ctx, "%s%s%s",
                                      orig_references ? orig_references : "",
                                      orig_references ? " " : "",
@@ -574,8 +584,8 @@ notmuch_reply_format_default(void *ctx,
        reply = NULL;

        printf ("On %s, %s wrote:\n",
-               notmuch_message_get_header (message, "date"),
-               notmuch_message_get_header (message, "from"));
+               notmuch_message_get_header (mailstore, message, "date"),
+               notmuch_message_get_header (mailstore, message, "from"));

        show_message_body (message, format, params);

@@ -595,9 +605,12 @@ notmuch_reply_format_headers_only(void *ctx,
     GMimeMessage *reply;
     notmuch_messages_t *messages;
     notmuch_message_t *message;
+    notmuch_mailstore_t *mailstore;
     const char *in_reply_to, *orig_references, *references;
     char *reply_headers;

+    mailstore = notmuch_config_get_mailstore (config);
+
     for (messages = notmuch_query_search_messages (query);
         notmuch_messages_valid (messages);
         notmuch_messages_move_to_next (messages))
@@ -618,7 +631,8 @@ notmuch_reply_format_headers_only(void *ctx,
                                  "In-Reply-To", in_reply_to);


-       orig_references = notmuch_message_get_header (message, "references");
+       orig_references = notmuch_message_get_header (mailstore, message,
+                                                     "references");

        /* We print In-Reply-To followed by References because git format-patch 
treats them
          * specially.  Git does not interpret the other headers specially
@@ -720,7 +734,8 @@ notmuch_reply_command (void *ctx, int argc, char *argv[])
        return 1;
     }

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_ONLY);
     if (notmuch == NULL)
        return 1;
diff --git a/notmuch-restore.c b/notmuch-restore.c
index 87d9772..b382b7b 100644
--- a/notmuch-restore.c
+++ b/notmuch-restore.c
@@ -40,7 +40,8 @@ notmuch_restore_command (unused (void *ctx), int argc, char 
*argv[])
     if (config == NULL)
        return 1;

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_WRITE);
     if (notmuch == NULL)
        return 1;
diff --git a/notmuch-search.c b/notmuch-search.c
index d504051..8ba3c48 100644
--- a/notmuch-search.c
+++ b/notmuch-search.c
@@ -470,7 +470,8 @@ notmuch_search_command (void *ctx, int argc, char *argv[])
     if (config == NULL)
        return 1;

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_ONLY);
     if (notmuch == NULL)
        return 1;
diff --git a/notmuch-show.c b/notmuch-show.c
index d930f94..81d4cf0 100644
--- a/notmuch-show.c
+++ b/notmuch-show.c
@@ -24,7 +24,8 @@ static void
 format_headers_message_part_text (GMimeMessage *message);

 static void
-format_part_text (const void *ctx, mime_node_t *node,
+format_part_text (const void *ctx, notmuch_mailstore_t *mailstore,
+                 mime_node_t *node,
                  int indent, const notmuch_show_params_t *params);

 static const notmuch_show_format_t format_text = {
@@ -36,10 +37,12 @@ static const notmuch_show_format_t format_text = {

 static void
 format_message_json (const void *ctx,
+                    notmuch_mailstore_t *mailstore,
                     notmuch_message_t *message,
                     unused (int indent));
 static void
 format_headers_json (const void *ctx,
+                    notmuch_mailstore_t *mailstore,
                     notmuch_message_t *message);

 static void
@@ -83,6 +86,7 @@ static const notmuch_show_format_t format_json = {

 static void
 format_message_mbox (const void *ctx,
+                    notmuch_mailstore_t *mailstore,
                     notmuch_message_t *message,
                     unused (int indent));

@@ -149,14 +153,15 @@ _get_tags_as_string (const void *ctx, notmuch_message_t 
*message)

 /* Get a nice, single-line summary of message. */
 static const char *
-_get_one_line_summary (const void *ctx, notmuch_message_t *message)
+_get_one_line_summary (const void *ctx, notmuch_mailstore_t *mailstore,
+                      notmuch_message_t *message)
 {
     const char *from;
     time_t date;
     const char *relative_date;
     const char *tags;

-    from = notmuch_message_get_header (message, "from");
+    from = notmuch_message_get_header (mailstore, message, "from");

     date = notmuch_message_get_date (message);
     relative_date = notmuch_time_relative_date (ctx, date);
@@ -168,7 +173,8 @@ _get_one_line_summary (const void *ctx, notmuch_message_t 
*message)
 }

 static void
-format_message_json (const void *ctx, notmuch_message_t *message, unused (int 
indent))
+format_message_json (const void *ctx, unused (notmuch_mailstore_t *mailstore),
+                    notmuch_message_t *message, unused (int indent))
 {
     notmuch_tags_t *tags;
     int first = 1;
@@ -262,6 +268,7 @@ _is_from_line (const char *line)
  */
 static void
 format_message_mbox (const void *ctx,
+                    notmuch_mailstore_t *mailstore,
                     notmuch_message_t *message,
                     unused (int indent))
 {
@@ -285,7 +292,7 @@ format_message_mbox (const void *ctx,
        return;
     }

-    from = notmuch_message_get_header (message, "from");
+    from = notmuch_message_get_header (mailstore, message, "from");
     from = _extract_email_address (ctx, from);

     date = notmuch_message_get_date (message);
@@ -327,7 +334,7 @@ format_headers_message_part_text (GMimeMessage *message)
 }

 static void
-format_headers_json (const void *ctx, notmuch_message_t *message)
+format_headers_json (const void *ctx, notmuch_mailstore_t *mailstore, 
notmuch_message_t *message)
 {
     const char *headers[] = {
        "Subject", "From", "To", "Cc", "Bcc", "Date"
@@ -339,7 +346,7 @@ format_headers_json (const void *ctx, notmuch_message_t 
*message)

     for (i = 0; i < ARRAY_SIZE (headers); i++) {
        name = headers[i];
-       value = notmuch_message_get_header (message, name);
+       value = notmuch_message_get_header (mailstore, message, name);
        if (value)
        {
            if (!first_header)
@@ -719,7 +726,8 @@ format_part_content_raw (GMimeObject *part)
 }

 static void
-format_part_text (const void *ctx, mime_node_t *node,
+format_part_text (const void *ctx, notmuch_mailstore_t *mailstore,
+                 mime_node_t *node,
                  int indent, const notmuch_show_params_t *params)
 {
     /* The disposition and content-type metadata are associated with
@@ -768,7 +776,8 @@ format_part_text (const void *ctx, mime_node_t *node,

        printf ("\fheader{\n");
        if (node->envelope_file)
-           printf ("%s\n", _get_one_line_summary (ctx, node->envelope_file));
+           printf ("%s\n", _get_one_line_summary (ctx, mailstore,
+                                                  node->envelope_file));
        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);
@@ -800,7 +809,8 @@ format_part_text (const void *ctx, mime_node_t *node,
     }

     for (i = 0; i < node->nchildren; i++)
-       format_part_text (ctx, mime_node_child (node, i), indent, params);
+       format_part_text (ctx, mailstore, mime_node_child (node, i),
+                         indent, params);

     if (GMIME_IS_MESSAGE (node->part))
        printf ("\fbody}\n");
@@ -811,6 +821,7 @@ format_part_text (const void *ctx, mime_node_t *node,
 static void
 show_message (void *ctx,
              const notmuch_show_format_t *format,
+             notmuch_mailstore_t *mailstore,
              notmuch_message_t *message,
              int indent,
              notmuch_show_params_t *params)
@@ -823,7 +834,7 @@ show_message (void *ctx,
                            &root) == NOTMUCH_STATUS_SUCCESS &&
            (part = mime_node_seek_dfs (root, (params->part < 0 ?
                                               0 : params->part))))
-           format->part (local, part, indent, params);
+           format->part (local, mailstore, part, indent, params);
        talloc_free (local);
        return;
     }
@@ -831,11 +842,11 @@ show_message (void *ctx,
     if (params->part <= 0) {
        fputs (format->message_start, stdout);
        if (format->message)
-           format->message(ctx, message, indent);
+           format->message(ctx, mailstore, message, indent);

        fputs (format->header_start, stdout);
        if (format->header)
-           format->header(ctx, message);
+           format->header(ctx, mailstore, message);
        fputs (format->header_end, stdout);

        fputs (format->body_start, stdout);
@@ -854,6 +865,7 @@ show_message (void *ctx,
 static void
 show_messages (void *ctx,
               const notmuch_show_format_t *format,
+              notmuch_mailstore_t *mailstore,
               notmuch_messages_t *messages,
               int indent,
               notmuch_show_params_t *params)
@@ -882,7 +894,7 @@ show_messages (void *ctx,
        next_indent = indent;

        if (match || params->entire_thread) {
-           show_message (ctx, format, message, indent, params);
+           show_message (ctx, format, mailstore, message, indent, params);
            next_indent = indent + 1;

            fputs (format->message_set_sep, stdout);
@@ -890,6 +902,7 @@ show_messages (void *ctx,

        show_messages (ctx,
                       format,
+                      mailstore,
                       notmuch_message_get_replies (message),
                       next_indent,
                       params);
@@ -905,6 +918,7 @@ show_messages (void *ctx,
 /* Formatted output of single message */
 static int
 do_show_single (void *ctx,
+               notmuch_mailstore_t *mailstore,
                notmuch_query_t *query,
                const notmuch_show_format_t *format,
                notmuch_show_params_t *params)
@@ -966,7 +980,7 @@ do_show_single (void *ctx,

     } else {

-       show_message (ctx, format, message, 0, params);
+       show_message (ctx, format, mailstore, message, 0, params);

     }

@@ -976,6 +990,7 @@ do_show_single (void *ctx,
 /* Formatted output of threads */
 static int
 do_show (void *ctx,
+        notmuch_mailstore_t *mailstore,
         notmuch_query_t *query,
         const notmuch_show_format_t *format,
         notmuch_show_params_t *params)
@@ -1003,7 +1018,7 @@ do_show (void *ctx,
            fputs (format->message_set_sep, stdout);
        first_toplevel = 0;

-       show_messages (ctx, format, messages, 0, params);
+       show_messages (ctx, format, mailstore, messages, 0, params);

        notmuch_thread_destroy (thread);

@@ -1027,6 +1042,7 @@ notmuch_show_command (void *ctx, unused (int argc), 
unused (char *argv[]))
 {
     notmuch_config_t *config;
     notmuch_database_t *notmuch;
+    notmuch_mailstore_t *mailstore;
     notmuch_query_t *query;
     char *query_string;
     int opt_index, ret;
@@ -1122,7 +1138,9 @@ notmuch_show_command (void *ctx, unused (int argc), 
unused (char *argv[]))
        return 1;
     }

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    mailstore = notmuch_config_get_mailstore (config);
+    notmuch = notmuch_database_open (mailstore,
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_ONLY);
     if (notmuch == NULL)
        return 1;
@@ -1134,9 +1152,9 @@ notmuch_show_command (void *ctx, unused (int argc), 
unused (char *argv[]))
     }

     if (params.part >= 0)
-       ret = do_show_single (ctx, query, format, &params);
+       ret = do_show_single (ctx, mailstore, query, format, &params);
     else
-       ret = do_show (ctx, query, format, &params);
+       ret = do_show (ctx, mailstore, query, format, &params);

     notmuch_query_destroy (query);
     notmuch_database_close (notmuch);
diff --git a/notmuch-tag.c b/notmuch-tag.c
index 36b9b09..5e8d74a 100644
--- a/notmuch-tag.c
+++ b/notmuch-tag.c
@@ -187,7 +187,8 @@ notmuch_tag_command (void *ctx, int argc, char *argv[])
     if (config == NULL)
        return 1;

-    notmuch = notmuch_database_open (notmuch_config_get_database_path (config),
+    notmuch = notmuch_database_open (notmuch_config_get_mailstore (config),
+                                    notmuch_config_get_database_path (config),
                                     NOTMUCH_DATABASE_MODE_READ_WRITE);
     if (notmuch == NULL)
        return 1;
diff --git a/test/symbol-test.cc b/test/symbol-test.cc
index 1548ca4..36c6ddb 100644
--- a/test/symbol-test.cc
+++ b/test/symbol-test.cc
@@ -4,7 +4,8 @@


 int main() {
-  (void) notmuch_database_open("fakedb", NOTMUCH_DATABASE_MODE_READ_ONLY);
+  (void) notmuch_database_open (notmuch_mailstore_get_by_name ("maildir"),
+                                "fakedb", NOTMUCH_DATABASE_MODE_READ_ONLY);

   try {
     (void) new Xapian::WritableDatabase("./nonexistant", Xapian::DB_OPEN);
-- 
1.7.5.4

Reply via email to