]> git.notmuchmail.org Git - notmuch/blobdiff - database.cc
Fix bit-twiddling brain damage in notmuch_query_search
[notmuch] / database.cc
index 415040bc7000c4f9cb195e25cb9119d72c15a29d..3d9672707b20a6213dc00cf4f83404da03508d5b 100644 (file)
 
 using namespace std;
 
+#define ARRAY_SIZE(arr) (sizeof (arr) / sizeof (arr[0]))
+
+/* These prefix values are specifically chosen to be compatible
+ * with sup, (http://sup.rubyforge.org), written by
+ * William Morgan <wmorgan-sup@masanjin.net>, and released
+ * under the GNU GPL v2.
+ */
+
+typedef struct {
+    const char *name;
+    const char *prefix;
+} prefix_t;
+
+prefix_t BOOLEAN_PREFIX[] = {
+    { "type", "K" },
+    { "tag", "L" },
+    { "msgid", "Q" },
+    { "thread", "H" },
+    { "ref", "R" },
+    { "timestamp", "KTS" },
+};
+
+const char *
+_find_prefix (const char *name)
+{
+    unsigned int i;
+
+    for (i = 0; i < ARRAY_SIZE (BOOLEAN_PREFIX); i++)
+       if (strcmp (name, BOOLEAN_PREFIX[i].name) == 0)
+           return BOOLEAN_PREFIX[i].prefix;
+
+    fprintf (stderr, "Internal error: No prefix exists for '%s'\n", name);
+    exit (1);
+
+    return "";
+}
+
 const char *
 notmuch_status_to_string (notmuch_status_t status)
 {
@@ -40,6 +77,8 @@ notmuch_status_to_string (notmuch_status_t status)
        return "Something went wrong trying to read or write a file";
     case NOTMUCH_STATUS_FILE_NOT_EMAIL:
        return "File is not an email";
+    case NOTMUCH_STATUS_DUPLICATE_MESSAGE_ID:
+       return "Message ID is identical to a message in database";
     case NOTMUCH_STATUS_NULL_POINTER:
        return "Erroneous NULL pointer";
     case NOTMUCH_STATUS_TAG_TOO_LONG:
@@ -503,11 +542,12 @@ find_timestamp_document (notmuch_database_t *notmuch, const char *db_key,
 static char *
 timestamp_db_key (const char *key)
 {
-    if (strlen (key) + 1 > NOTMUCH_TERM_MAX) {
+    int term_len = strlen (_find_prefix ("timestamp")) + strlen (key);
+
+    if (term_len > NOTMUCH_TERM_MAX)
        return notmuch_sha1_of_string (key);
-    } else {
+    else
        return strdup (key);
-    }
 }
 
 notmuch_status_t
@@ -656,23 +696,8 @@ notmuch_database_add_message (notmuch_database_t *notmuch,
        /* Has a message previously been added with the same ID? */
        old_filename = notmuch_message_get_filename (message);
        if (old_filename && strlen (old_filename)) {
-           /* XXX: This is too noisy to actually print, and what do we
-            * really expect the user to do? Go manually delete a
-            * redundant message or merge two similar messages?
-            * Instead we should handle this transparently.
-            *
-            * What we likely want to move to is adding both filenames
-            * to the database so that subsequent indexing will pick up
-            * terms from both files.
-            */
-#if 0
-           fprintf (stderr,
-                    "Note: Attempting to add a message with a duplicate message ID:\n"
-                    "Old: %s\n"   "New: %s\n",
-                    old_filename, filename);
-           fprintf (stderr, "The old filename will be used, but any new terms\n"
-                    "from the new message will added to the database.\n");
-#endif
+           ret = NOTMUCH_STATUS_DUPLICATE_MESSAGE_ID;
+           goto DONE;
        } else {
            _notmuch_message_set_filename (message, filename);
            _notmuch_message_add_term (message, "type", "mail");