]> git.notmuchmail.org Git - notmuch/blobdiff - lib/database.cc
lib: rename _n_d_create to _n_d_find_or_create
[notmuch] / lib / database.cc
index 43bfac4e2216e4b56ec3652d1855e68089e25992..2aff56bebd04e3c94356b71c8bf5893bb5278c66 100644 (file)
@@ -58,6 +58,17 @@ typedef struct {
 #define DB_ACTION Xapian::DB_CREATE_OR_OPEN
 #endif
 
+#define LOG_XAPIAN_EXCEPTION(message, error) _log_xapian_exception (__location__, message, error)
+
+static void
+_log_xapian_exception (const char *where, notmuch_database_t *notmuch,  const Xapian::Error error) {
+    _notmuch_database_log (notmuch,
+                          "A Xapian exception occurred at %s: %s\n",
+                          where,
+                          error.get_msg ().c_str ());
+    notmuch->exception_reported = true;
+}
+
 /* Here's the current schema for our database (for NOTMUCH_DATABASE_VERSION):
  *
  * We currently have three different types of documents (mail, ghost,
@@ -385,8 +396,8 @@ _setup_query_field (const prefix_t *prefix, notmuch_database_t *notmuch)
        Xapian::FieldProcessor *fp;
 
        if (STRNCMP_LITERAL (prefix->name, "date") == 0)
-           fp = (new DateFieldProcessor ())->release ();
-       else if (STRNCMP_LITERAL (prefix->name, "query") == 0)
+           fp = (new DateFieldProcessor(NOTMUCH_VALUE_TIMESTAMP))->release ();
+       else if (STRNCMP_LITERAL(prefix->name, "query") == 0)
            fp = (new QueryFieldProcessor (*notmuch->query_parser, notmuch))->release ();
        else if (STRNCMP_LITERAL (prefix->name, "thread") == 0)
            fp = (new ThreadFieldProcessor (*notmuch->query_parser, notmuch))->release ();
@@ -1036,17 +1047,16 @@ notmuch_database_open_verbose (const char *path,
        notmuch->query_parser = new Xapian::QueryParser;
        notmuch->term_gen = new Xapian::TermGenerator;
        notmuch->term_gen->set_stemmer (Xapian::Stem ("english"));
-       notmuch->value_range_processor = new Xapian::NumberValueRangeProcessor (NOTMUCH_VALUE_TIMESTAMP);
-       notmuch->date_range_processor = new ParseTimeValueRangeProcessor (NOTMUCH_VALUE_TIMESTAMP);
-       notmuch->last_mod_range_processor = new Xapian::NumberValueRangeProcessor (NOTMUCH_VALUE_LAST_MOD, "lastmod:");
-
+       notmuch->value_range_processor = new Xapian::NumberRangeProcessor (NOTMUCH_VALUE_TIMESTAMP);
+       notmuch->date_range_processor = new ParseTimeRangeProcessor (NOTMUCH_VALUE_TIMESTAMP, "date:");
+       notmuch->last_mod_range_processor = new Xapian::NumberRangeProcessor (NOTMUCH_VALUE_LAST_MOD, "lastmod:");
        notmuch->query_parser->set_default_op (Xapian::Query::OP_AND);
        notmuch->query_parser->set_database (*notmuch->xapian_db);
        notmuch->query_parser->set_stemmer (Xapian::Stem ("english"));
        notmuch->query_parser->set_stemming_strategy (Xapian::QueryParser::STEM_SOME);
-       notmuch->query_parser->add_valuerangeprocessor (notmuch->value_range_processor);
-       notmuch->query_parser->add_valuerangeprocessor (notmuch->date_range_processor);
-       notmuch->query_parser->add_valuerangeprocessor (notmuch->last_mod_range_processor);
+       notmuch->query_parser->add_rangeprocessor (notmuch->value_range_processor);
+       notmuch->query_parser->add_rangeprocessor (notmuch->date_range_processor);
+       notmuch->query_parser->add_rangeprocessor (notmuch->last_mod_range_processor);
 
        for (i = 0; i < ARRAY_SIZE (prefix_table); i++) {
            const prefix_t *prefix = &prefix_table[i];
@@ -1077,6 +1087,10 @@ notmuch_database_open_verbose (const char *path,
        *database = notmuch;
     else
        talloc_free (notmuch);
+
+    if (notmuch)
+       notmuch->open = true;
+
     return status;
 }
 
@@ -1088,7 +1102,7 @@ notmuch_database_close (notmuch_database_t *notmuch)
     /* Many Xapian objects (and thus notmuch objects) hold references to
      * the database, so merely deleting the database may not suffice to
      * close it.  Thus, we explicitly close it here. */
-    if (notmuch->xapian_db != NULL) {
+    if (notmuch->open) {
        try {
            /* If there's an outstanding transaction, it's unclear if
             * closing the Xapian database commits everything up to
@@ -1111,20 +1125,7 @@ notmuch_database_close (notmuch_database_t *notmuch)
            }
        }
     }
-
-    delete notmuch->term_gen;
-    notmuch->term_gen = NULL;
-    delete notmuch->query_parser;
-    notmuch->query_parser = NULL;
-    delete notmuch->xapian_db;
-    notmuch->xapian_db = NULL;
-    delete notmuch->value_range_processor;
-    notmuch->value_range_processor = NULL;
-    delete notmuch->date_range_processor;
-    notmuch->date_range_processor = NULL;
-    delete notmuch->last_mod_range_processor;
-    notmuch->last_mod_range_processor = NULL;
-
+    notmuch->open = false;
     return status;
 }
 
@@ -1337,6 +1338,20 @@ notmuch_database_destroy (notmuch_database_t *notmuch)
     notmuch_status_t status;
 
     status = notmuch_database_close (notmuch);
+
+    delete notmuch->term_gen;
+    notmuch->term_gen = NULL;
+    delete notmuch->query_parser;
+    notmuch->query_parser = NULL;
+    delete notmuch->xapian_db;
+    notmuch->xapian_db = NULL;
+    delete notmuch->value_range_processor;
+    notmuch->value_range_processor = NULL;
+    delete notmuch->date_range_processor;
+    notmuch->date_range_processor = NULL;
+    delete notmuch->last_mod_range_processor;
+    notmuch->last_mod_range_processor = NULL;
+
     talloc_free (notmuch);
 
     return status;
@@ -1356,7 +1371,13 @@ notmuch_database_get_version (notmuch_database_t *notmuch)
     const char *str;
     char *end;
 
-    version_string = notmuch->xapian_db->get_metadata ("version");
+    try {
+       version_string = notmuch->xapian_db->get_metadata ("version");
+    } catch (const Xapian::Error &error) {
+       LOG_XAPIAN_EXCEPTION (notmuch, error);
+       return 0;
+    }
+
     if (version_string.empty ())
        return 0;
 
@@ -1374,9 +1395,17 @@ notmuch_database_get_version (notmuch_database_t *notmuch)
 notmuch_bool_t
 notmuch_database_needs_upgrade (notmuch_database_t *notmuch)
 {
-    return notmuch->mode == NOTMUCH_DATABASE_MODE_READ_WRITE &&
-          ((NOTMUCH_FEATURES_CURRENT & ~notmuch->features) ||
-           (notmuch_database_get_version (notmuch) < NOTMUCH_DATABASE_VERSION));
+    unsigned int version;
+
+    if (notmuch->mode != NOTMUCH_DATABASE_MODE_READ_WRITE)
+       return FALSE;
+
+    if (NOTMUCH_FEATURES_CURRENT & ~notmuch->features)
+       return TRUE;
+
+    version = notmuch_database_get_version (notmuch);
+
+    return (version > 0 && version < NOTMUCH_DATABASE_VERSION);
 }
 
 static volatile sig_atomic_t do_progress_notify = 0;
@@ -1401,8 +1430,8 @@ handle_sigalrm (unused (int signal))
  */
 notmuch_status_t
 notmuch_database_upgrade (notmuch_database_t *notmuch,
-                         void (*progress_notify)(void *closure,
-                                                 double progress),
+                         void (*progress_notify) (void *closure,
+                                                  double progress),
                          void *closure)
 {
     void *local = talloc_new (NULL);
@@ -1576,8 +1605,8 @@ notmuch_database_upgrade (notmuch_database_t *notmuch,
                mtime = Xapian::sortable_unserialise (
                    document.get_value (NOTMUCH_VALUE_TIMESTAMP));
 
-               directory = _notmuch_directory_create (notmuch, term.c_str () + 10,
-                                                      NOTMUCH_FIND_CREATE, &status);
+               directory = _notmuch_directory_find_or_create (notmuch, term.c_str () + 10,
+                                                              NOTMUCH_FIND_CREATE, &status);
                notmuch_directory_set_mtime (directory, mtime);
                notmuch_directory_destroy (directory);
 
@@ -1849,7 +1878,7 @@ _notmuch_database_find_directory_id (notmuch_database_t *notmuch,
        return NOTMUCH_STATUS_SUCCESS;
     }
 
-    directory = _notmuch_directory_create (notmuch, path, flags, &status);
+    directory = _notmuch_directory_find_or_create (notmuch, path, flags, &status);
     if (status || ! directory) {
        *directory_id = -1;
        return status;
@@ -1959,8 +1988,8 @@ notmuch_database_get_directory (notmuch_database_t *notmuch,
     *directory = NULL;
 
     try {
-       *directory = _notmuch_directory_create (notmuch, path,
-                                               NOTMUCH_FIND_LOOKUP, &status);
+       *directory = _notmuch_directory_find_or_create (notmuch, path,
+                                                       NOTMUCH_FIND_LOOKUP, &status);
     } catch (const Xapian::Error &error) {
        _notmuch_database_log (notmuch, "A Xapian exception occurred getting directory: %s.\n",
                               error.get_msg ().c_str ());