evolution-data-server r9641 - in trunk/camel: . providers/groupwise providers/imap providers/local providers/nntp
- From: sragavan svn gnome org
- To: svn-commits-list gnome org
- Subject: evolution-data-server r9641 - in trunk/camel: . providers/groupwise providers/imap providers/local providers/nntp
- Date: Mon, 6 Oct 2008 10:27:15 +0000 (UTC)
Author: sragavan
Date: Mon Oct 6 10:27:15 2008
New Revision: 9641
URL: http://svn.gnome.org/viewvc/evolution-data-server?rev=9641&view=rev
Log:
2008-10-06 Srinivasa Ragavan <sragavan novell com>
** Fixes lots of bugs and breaks ABI
* camel/camel-db.c: Added new APIs and support for cloning handles.
* camel/camel-db.h:
* camel/camel-folder-search.c:
* camel/camel-folder-search.h:
* camel/camel-folder-summary.c:
* camel/camel-folder-summary.h:
* camel/camel-folder.c:
* camel/camel-folder.h:
* camel/camel-search-sql-sexp.c:
* camel/camel-store.c: Adds two handles to sqlite
* camel/camel-store.h:
* camel/camel-vee-folder.c:
* camel/camel-vee-summary.c:
* camel/camel-vtrash-folder.c:
* camel/providers/groupwise/camel-groupwise-folder.c:
* camel/providers/imap/camel-imap-folder.c:
* camel/providers/imap/camel-imap-store.c:
* camel/providers/imap/camel-imap-summary.c:
* camel/providers/local/camel-local-folder.c:
* camel/providers/local/camel-local-store.c:
* camel/providers/local/camel-maildir-summary.c:
* camel/providers/local/camel-mbox-summary.c:
* camel/providers/local/camel-mh-summary.c:
* camel/providers/local/camel-spool-summary.c:
* camel/providers/nntp/camel-nntp-folder.c:
Modified:
trunk/camel/ChangeLog
trunk/camel/camel-db.c
trunk/camel/camel-db.h
trunk/camel/camel-folder-search.c
trunk/camel/camel-folder-search.h
trunk/camel/camel-folder-summary.c
trunk/camel/camel-folder-summary.h
trunk/camel/camel-folder.c
trunk/camel/camel-folder.h
trunk/camel/camel-search-sql-sexp.c
trunk/camel/camel-store.c
trunk/camel/camel-store.h
trunk/camel/camel-vee-folder.c
trunk/camel/camel-vee-summary.c
trunk/camel/camel-vtrash-folder.c
trunk/camel/providers/groupwise/camel-groupwise-folder.c
trunk/camel/providers/imap/camel-imap-folder.c
trunk/camel/providers/imap/camel-imap-store.c
trunk/camel/providers/imap/camel-imap-summary.c
trunk/camel/providers/local/camel-local-folder.c
trunk/camel/providers/local/camel-local-store.c
trunk/camel/providers/local/camel-maildir-summary.c
trunk/camel/providers/local/camel-mbox-summary.c
trunk/camel/providers/local/camel-mh-summary.c
trunk/camel/providers/local/camel-spool-summary.c
trunk/camel/providers/nntp/camel-nntp-folder.c
Modified: trunk/camel/camel-db.c
==============================================================================
--- trunk/camel/camel-db.c (original)
+++ trunk/camel/camel-db.c Mon Oct 6 10:27:15 2008
@@ -36,17 +36,14 @@
#include "camel-debug.h"
-#ifdef CAMEL_DB_DEBUG
-/* Enable d(x) if you want */
-#define d(x)
-/* Yeah it leaks, so fix it while debugging */
-#define START(stmt) g_print ("\n===========\nDB SQL operation [%s] started\n", stmt); cdb->timer = g_timer_new ();
-#define END g_timer_stop (cdb->timer); g_print ("DB Operation ended. Time Taken : %f\n###########\n", g_timer_elapsed (cdb->timer, NULL));
-#else
#define d(x) if (camel_debug("sqlite")) x
-#define START(x)
-#define END
-#endif
+#define START(stmt) if (camel_debug("dbtime")) { g_print ("\n===========\nDB SQL operation [%s] started\n", stmt); if (!cdb->priv->timer) { cdb->priv->timer = g_timer_new (); } else { g_timer_reset(cdb->priv->timer);} }
+#define END if (camel_debug("dbtime")) { g_timer_stop (cdb->priv->timer); g_print ("DB Operation ended. Time Taken : %f\n###########\n", g_timer_elapsed (cdb->priv->timer, NULL)); }
+
+struct _CamelDBPrivate {
+ GTimer *timer;
+ char *file_name;
+};
static GStaticRecMutex trans_lock = G_STATIC_REC_MUTEX_INIT;
@@ -115,9 +112,9 @@
cdb = g_new (CamelDB, 1);
cdb->db = db;
cdb->lock = g_mutex_new ();
- /* These will be written once the Summary takes control of the CDB. */
- cdb->sort_by = NULL;
- cdb->collate = NULL;
+ cdb->priv = g_new(CamelDBPrivate, 1);
+ cdb->priv->file_name = g_strdup(path);
+ cdb->priv->timer = NULL;
d(g_print ("\nDatabase succesfully opened \n"));
/* Which is big / costlier ? A Stack frame or a pointer */
@@ -135,6 +132,12 @@
return cdb;
}
+CamelDB *
+camel_db_clone (CamelDB *cdb, CamelException *ex)
+{
+ return camel_db_open(cdb->priv->file_name, ex);
+}
+
void
camel_db_close (CamelDB *cdb)
{
@@ -155,9 +158,6 @@
return 0;
g_mutex_lock (cdb->lock);
- cdb->sort_by = col;
- cdb->collate = collate;
- cdb->collate_cb = func;
d(g_print("Creating Collation %s on %s with %p\n", collate, col, func));
if (collate && func)
ret = sqlite3_create_collation(cdb->db, collate, SQLITE_UTF8, NULL, func);
@@ -192,7 +192,6 @@
return -1;
g_static_rec_mutex_lock (&trans_lock);
- d(g_print ("\n\aBEGIN TRANSACTION \n\a"));
g_mutex_lock (cdb->lock);
return (cdb_sql_exec (cdb->db, "BEGIN", ex));
}
@@ -204,7 +203,6 @@
if (!cdb)
return -1;
- d(g_print ("\nCOMMIT TRANSACTION \n"));
START("COMMIT");
ret = cdb_sql_exec (cdb->db, "COMMIT", ex);
END;
@@ -221,7 +219,6 @@
{
int ret;
- d(g_print ("\nABORT TRANSACTION \n"));
ret = cdb_sql_exec (cdb->db, "ROLLBACK", ex);
g_mutex_unlock (cdb->lock);
g_static_rec_mutex_unlock (&trans_lock);
@@ -236,8 +233,6 @@
if (!cdb)
return -1;
- d(g_print("Adding the following query to transaction: %s\n", stmt));
-
return (cdb_sql_exec (cdb->db, stmt, ex));
}
@@ -256,11 +251,9 @@
if (ret)
goto end;
- d(g_print ("\nBEGIN Transaction\n"));
while (qry_list) {
query = qry_list->data;
- d(g_print ("\nInside Transaction: [%s] \n", query));
ret = cdb_sql_exec (cdb->db, query, ex);
if (ret)
goto end;
@@ -271,7 +264,6 @@
END;
end:
g_mutex_unlock (cdb->lock);
- d(g_print ("\nTransaction Result: [%d] \n", ret));
return ret;
}
@@ -289,7 +281,7 @@
return 0;
}
-static int
+int
camel_db_count_message_info (CamelDB *cdb, const char *query, guint32 *count, CamelException *ex)
{
int ret = -1;
@@ -583,12 +575,12 @@
}
int
-camel_db_get_folder_uids (CamelDB *db, char *folder_name, GPtrArray *array, CamelException *ex)
+camel_db_get_folder_uids (CamelDB *db, char *folder_name, char *sort_by, char *collate, GPtrArray *array, CamelException *ex)
{
char *sel_query;
int ret;
- sel_query = sqlite3_mprintf("SELECT uid FROM %Q%s%s%s%s", folder_name, db->sort_by ? " order by " : "", db->sort_by ? db->sort_by: "", (db->sort_by && db->collate) ? " collate " : "", (db->sort_by && db->collate) ? db->collate : "");
+ sel_query = sqlite3_mprintf("SELECT uid FROM %Q%s%s%s%s", folder_name, sort_by ? " order by " : "", sort_by ? sort_by: "", (sort_by && collate) ? " collate " : "", (sort_by && collate) ? collate : "");
ret = camel_db_select (db, sel_query, read_uids_callback, array, ex);
sqlite3_free (sel_query);
@@ -755,10 +747,12 @@
char *del_query;
char *ins_query;
+ /* NB: UGLIEST Hack. We can't modify the schema now. We are using msg_security (an unsed one to notify of FLAGGED/Dirty infos */
+
ins_query = sqlite3_mprintf ("INSERT INTO %Q VALUES (%Q, %d, %d, %d, %d, %d, %d, %d, %d, %d, %d, %ld, %ld, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q, %Q )",
folder_name, record->uid, record->flags,
record->msg_type, record->read, record->deleted, record->replied,
- record->important, record->junk, record->attachment, record->msg_security,
+ record->important, record->junk, record->attachment, record->dirty,
record->size, record->dsent, record->dreceived,
record->subject, record->from, record->to,
record->cc, record->mlist, record->followup_flag,
Modified: trunk/camel/camel-db.h
==============================================================================
--- trunk/camel/camel-db.h (original)
+++ trunk/camel/camel-db.h Mon Oct 6 10:27:15 2008
@@ -8,17 +8,14 @@
#include "camel-exception.h"
+typedef struct _CamelDBPrivate CamelDBPrivate;
+
typedef int(*CamelDBCollate)(void*,int,const void*,int,const void*);
struct _CamelDB {
sqlite3 *db;
GMutex *lock;
- const char *sort_by;
- const char *collate;
- CamelDBCollate collate_cb;
-#ifdef CAMEL_DB_DEBUG
- GTimer *timer;
-#endif
+ CamelDBPrivate *priv;
};
#define CAMEL_DB_FREE_CACHE_SIZE 2 * 1024 * 1024
@@ -59,7 +56,7 @@
char *uid;
guint32 flags;
guint32 msg_type;
- guint32 msg_security;
+ guint32 dirty;
gboolean read;
gboolean deleted;
gboolean replied;
@@ -107,6 +104,7 @@
CamelDB * camel_db_open (const char *path, CamelException *ex);
+CamelDB * camel_db_clone (CamelDB *cdb, CamelException *ex);
void camel_db_close (CamelDB *cdb);
int camel_db_command (CamelDB *cdb, const char *stmt, CamelException *ex);
@@ -145,7 +143,7 @@
int camel_db_count_visible_unread_message_info (CamelDB *cdb, const char *table_name, guint32 *count, CamelException *ex);
int camel_db_count_junk_not_deleted_message_info (CamelDB *cdb, const char *table_name, guint32 *count, CamelException *ex);
-
+int camel_db_count_message_info (CamelDB *cdb, const char *query, guint32 *count, CamelException *ex);
void camel_db_camel_mir_free (CamelMIRecord *record);
int camel_db_create_vfolder (CamelDB *db, const char *folder_name, CamelException *ex);
@@ -156,7 +154,7 @@
int camel_db_add_to_vfolder (CamelDB *db, char *folder_name, char *vuid, CamelException *ex);
int camel_db_add_to_vfolder_transaction (CamelDB *db, char *folder_name, char *vuid, CamelException *ex);
-int camel_db_get_folder_uids (CamelDB *db, char *folder_name, GPtrArray *array, CamelException *ex);
+int camel_db_get_folder_uids (CamelDB *db, char *folder_name, char *sort_by, char *collate, GPtrArray *array, CamelException *ex);
GPtrArray * camel_db_get_folder_junk_uids (CamelDB *db, char *folder_name, CamelException *ex);
GPtrArray * camel_db_get_folder_deleted_uids (CamelDB *db, char *folder_name, CamelException *ex);
Modified: trunk/camel/camel-folder-search.c
==============================================================================
--- trunk/camel/camel-folder-search.c (original)
+++ trunk/camel/camel-folder-search.c Mon Oct 6 10:27:15 2008
@@ -393,6 +393,133 @@
}
/**
+ * camel_folder_search_count:
+ * @search:
+ * @expr:
+ * @uids: to search against, NULL for all uid's.
+ * @ex:
+ *
+ * Run a search. Search must have had Folder already set on it, and
+ * it must implement summaries.
+ *
+ * Return value: Number of messages that match the query.
+ **/
+
+guint32
+camel_folder_search_count(CamelFolderSearch *search, const char *expr, CamelException *ex)
+{
+ ESExpResult *r;
+ GPtrArray *summary_set;
+ int i;
+ CamelDB *cdb;
+ char *sql_query, *tmp, *tmp1;
+ GHashTable *results;
+ guint32 count = 0;
+
+ struct _CamelFolderSearchPrivate *p = _PRIVATE(search);
+
+ g_assert(search->folder);
+
+ p->ex = ex;
+
+ /* We route body-contains search and uid search through memory and not via db. */
+ if (strstr((const char *) expr, "body-contains")) {
+ /* setup our search list only contains those we're interested in */
+ search->summary = camel_folder_get_summary(search->folder);
+
+ summary_set = search->summary;
+
+ /* only re-parse if the search has changed */
+ if (search->last_search == NULL
+ || strcmp(search->last_search, expr)) {
+ e_sexp_input_text(search->sexp, expr, strlen(expr));
+ if (e_sexp_parse(search->sexp) == -1) {
+ camel_exception_setv(ex, 1, _("Cannot parse search expression: %s:\n%s"), e_sexp_error(search->sexp), expr);
+ goto fail;
+ }
+
+ g_free(search->last_search);
+ search->last_search = g_strdup(expr);
+ }
+ r = e_sexp_eval(search->sexp);
+ if (r == NULL) {
+ if (!camel_exception_is_set(ex))
+ camel_exception_setv(ex, 1, _("Error executing search expression: %s:\n%s"), e_sexp_error(search->sexp), expr);
+ goto fail;
+ }
+
+ /* now create a folder summary to return?? */
+ if (r->type == ESEXP_RES_ARRAY_PTR) {
+ d(printf("got result\n"));
+
+ /* reorder result in summary order */
+ results = g_hash_table_new(g_str_hash, g_str_equal);
+ for (i=0;i<r->value.ptrarray->len;i++) {
+ d(printf("adding match: %s\n", (char *)g_ptr_array_index(r->value.ptrarray, i)));
+ g_hash_table_insert(results, g_ptr_array_index(r->value.ptrarray, i), GINT_TO_POINTER (1));
+ }
+
+ for (i=0;i<summary_set->len;i++) {
+ char *uid = g_ptr_array_index(summary_set, i);
+ if (g_hash_table_lookup(results, uid))
+ count++;
+ }
+ g_hash_table_destroy(results);
+ }
+
+ e_sexp_result_free(search->sexp, r);
+
+ } else {
+ /* Sync the db, so that we search the db for changes */
+ camel_folder_summary_save_to_db (search->folder->summary, ex);
+
+ dd(printf ("sexp is : [%s]\n", expr));
+ if (g_getenv("SQL_SEARCH_OLD"))
+ sql_query = camel_sexp_to_sql (expr);
+ else
+ sql_query = camel_sexp_to_sql_sexp (expr);
+ tmp1 = camel_db_sqlize_string(search->folder->full_name);
+ tmp = g_strdup_printf ("SELECT COUNT (*) FROM %s %s %s", tmp1, sql_query ? "WHERE":"", sql_query?sql_query:"");
+ camel_db_free_sqlized_string (tmp1);
+ g_free (sql_query);
+ dd(printf("Equivalent sql %s\n", tmp));
+
+ cdb = (CamelDB *) (search->folder->parent_store->cdb_r);
+ camel_db_count_message_info (cdb, tmp, &count, ex);
+ if (ex && camel_exception_is_set(ex)) {
+ const char *exception = camel_exception_get_description (ex);
+ if (strncmp(exception, "no such table", 13) == 0) {
+ g_warning ("Error during searching %s: %s\n", tmp, exception);
+ camel_exception_clear (ex); /* Suppress no such table */
+ }
+ }
+ g_free (tmp);
+
+ }
+
+fail:
+ /* these might be allocated by match-threads */
+ if (p->threads)
+ camel_folder_thread_messages_unref(p->threads);
+ if (p->threads_hash)
+ g_hash_table_destroy(p->threads_hash);
+ if (search->summary_set)
+ g_ptr_array_free(search->summary_set, TRUE);
+ if (search->summary)
+ camel_folder_free_summary(search->folder, search->summary);
+
+ p->threads = NULL;
+ p->threads_hash = NULL;
+ search->folder = NULL;
+ search->summary = NULL;
+ search->summary_set = NULL;
+ search->current = NULL;
+ search->body_index = NULL;
+
+ return count;
+}
+
+/**
* camel_folder_search_search:
* @search:
* @expr:
@@ -497,7 +624,7 @@
dd(printf("Equivalent sql %s\n", tmp));
matches = g_ptr_array_new();
- cdb = (CamelDB *) (search->folder->cdb);
+ cdb = (CamelDB *) (search->folder->parent_store->cdb_r);
camel_db_select (cdb, tmp, (CamelDBSelectCB) read_uid_callback, matches, ex);
if (ex && camel_exception_is_set(ex)) {
const char *exception = camel_exception_get_description (ex);
Modified: trunk/camel/camel-folder-search.h
==============================================================================
--- trunk/camel/camel-folder-search.h (original)
+++ trunk/camel/camel-folder-search.h Mon Oct 6 10:27:15 2008
@@ -126,6 +126,7 @@
GPtrArray *camel_folder_search_execute_expression(CamelFolderSearch *search, const char *expr, CamelException *ex);
GPtrArray *camel_folder_search_search(CamelFolderSearch *search, const char *expr, GPtrArray *uids, CamelException *ex);
+guint32 camel_folder_search_count(CamelFolderSearch *search, const char *expr, CamelException *ex);
void camel_folder_search_free_result(CamelFolderSearch *search, GPtrArray *);
G_END_DECLS
Modified: trunk/camel/camel-folder-summary.c
==============================================================================
--- trunk/camel/camel-folder-summary.c (original)
+++ trunk/camel/camel-folder-summary.c Mon Oct 6 10:27:15 2008
@@ -492,6 +492,16 @@
return res;
}
+CamelMessageInfo *
+camel_folder_summary_peek_info (CamelFolderSummary *s, const char *uid)
+{
+ CamelMessageInfo *info = g_hash_table_lookup(s->loaded_infos, uid);
+
+ if (info)
+ camel_message_info_ref(info);
+ return info;
+}
+
struct _db_pass_data {
CamelFolderSummary *summary;
gboolean double_ref;
@@ -511,7 +521,7 @@
if (!info) {
CamelDB *cdb;
- CamelException ex;// May be this should come from the caller
+ CamelException ex;
char *folder_name;
struct _db_pass_data data;
@@ -520,7 +530,7 @@
s->flags &= ~CAMEL_SUMMARY_DIRTY;
folder_name = s->folder->full_name;
- cdb = s->folder->cdb;
+ cdb = s->folder->parent_store->cdb_r;
CAMEL_SUMMARY_UNLOCK(s, ref_lock);
CAMEL_SUMMARY_UNLOCK(s, summary_lock);
@@ -531,12 +541,9 @@
ret = camel_db_read_message_info_record_with_uid (cdb, folder_name, uid, &data, camel_read_mir_callback, &ex);
- if (ret != 0) {
- // if (strcmp (folder_name, "UNMATCHED"))
- //g_warning ("Unable to read uid %s from folder %s: %s", uid, folder_name, camel_exception_get_description(&ex));
-
+ if (ret != 0)
return NULL;
- }
+
CAMEL_SUMMARY_LOCK(s, summary_lock);
CAMEL_SUMMARY_LOCK(s, ref_lock);
@@ -548,8 +555,7 @@
/* Makes no sense now as the exception is local as of now. FIXME: Pass exception from caller */
camel_exception_set (&ex, CAMEL_EXCEPTION_SYSTEM, _(errmsg));
- // if (strcmp (folder_name, "UNMATCHED"))
- g_warning ("No uid[%s] exists in %s\n", uid, folder_name);
+ d(g_warning ("No uid[%s] exists in %s\n", uid, folder_name));
camel_exception_clear (&ex);
g_free (errmsg);
}
@@ -861,7 +867,7 @@
d(printf ("\ncamel_folder_summary_reload_from_db called \n"));
folder_name = s->folder->full_name;
- cdb = s->folder->cdb;
+ cdb = s->folder->parent_store->cdb_r;
/* FIXME FOR SANKAR: No need to pass the address of summary here. */
data.summary = s;
@@ -874,7 +880,7 @@
if (!g_getenv("CAMEL_FREE_INFOS") && !s->timeout_handle)
s->timeout_handle = g_timeout_add_seconds (SUMMARY_CACHE_DROP, (GSourceFunc) cfs_try_release_memory, s);
- printf("Triggering summary_reloaded on %s %p\n", s->folder->full_name, s);
+ d(printf("Triggering summary_reloaded on %s %p\n", s->folder->full_name, s));
camel_object_trigger_event(s, "summary_reloaded", s);
return ret == 0 ? 0 : -1;
}
@@ -907,9 +913,9 @@
return ret;
folder_name = s->folder->full_name;
- cdb = s->folder->cdb;
+ cdb = s->folder->parent_store->cdb_r;
- ret = camel_db_get_folder_uids (cdb, folder_name, s->uids, ex);
+ ret = camel_db_get_folder_uids (cdb, folder_name, (char *)s->sort_by, (char *)s->collate, s->uids, ex);
/* camel_folder_summary_dump (s); */
#if 0
@@ -1124,7 +1130,7 @@
CamelMessageInfo *mi;
CamelMessageInfoBase *info;
int ret = 0;
- CamelDB *cdb = s->folder->cdb;
+ CamelDB *cdb = s->folder->parent_store->cdb_w;
CamelFIRecord *record;
CamelException ex;
@@ -1273,7 +1279,7 @@
CamelMessageInfoBase *mi = (CamelMessageInfoBase *)value;
CamelFolderSummary *s = (CamelFolderSummary *)mi->summary;
char *folder_name = s->folder->full_name;
- CamelDB *cdb = s->folder->cdb;
+ CamelDB *cdb = s->folder->parent_store->cdb_w;
CamelMIRecord *mir;
if (!mi->dirty)
@@ -1304,7 +1310,7 @@
static int
save_message_infos_to_db (CamelFolderSummary *s, CamelException *ex)
{
- CamelDB *cdb = s->folder->cdb;
+ CamelDB *cdb = s->folder->parent_store->cdb_w;
char *folder_name;
folder_name = s->folder->full_name;
@@ -1324,7 +1330,7 @@
int
camel_folder_summary_save_to_db (CamelFolderSummary *s, CamelException *ex)
{
- CamelDB *cdb = s->folder->cdb;
+ CamelDB *cdb = s->folder->parent_store->cdb_w;
CamelFIRecord *record;
int ret, count;
@@ -1378,7 +1384,7 @@
int
camel_folder_summary_header_save_to_db (CamelFolderSummary *s, CamelException *ex)
{
- CamelDB *cdb = s->folder->cdb;
+ CamelDB *cdb = s->folder->parent_store->cdb_w;
CamelFIRecord *record;
int ret;
@@ -1557,7 +1563,7 @@
d(printf ("\ncamel_folder_summary_load_from_db called \n"));
s->flags &= ~CAMEL_SUMMARY_DIRTY;
- cdb = store->cdb;
+ cdb = store->cdb_r;
record = g_new0 (CamelFIRecord, 1);
camel_db_read_folder_info_record (cdb, folder_name, &record, ex);
@@ -2070,7 +2076,7 @@
s->flags &= ~CAMEL_SUMMARY_DIRTY;
folder_name = s->folder->full_name;
- cdb = s->folder->cdb;
+ cdb = s->folder->parent_store->cdb_w;
CAMEL_SUMMARY_LOCK(s, summary_lock);
if (camel_folder_summary_count(s) == 0) {
@@ -2137,7 +2143,7 @@
s->meta_summary->msg_expunged = TRUE;
CAMEL_SUMMARY_UNLOCK(s, summary_lock);
- if (!ret && camel_db_delete_uid (s->folder->cdb, s->folder->full_name, camel_message_info_uid(info), NULL) != 0)
+ if (!ret && camel_db_delete_uid (s->folder->parent_store->cdb_w, s->folder->full_name, camel_message_info_uid(info), NULL) != 0)
return ;
camel_message_info_free(info);
@@ -2174,7 +2180,7 @@
CAMEL_SUMMARY_UNLOCK(s, ref_lock);
CAMEL_SUMMARY_UNLOCK(s, summary_lock);
- if (!ret && camel_db_delete_uid (s->folder->cdb, s->folder->full_name, tmpid, NULL) != 0) {
+ if (!ret && camel_db_delete_uid (s->folder->parent_store->cdb_w, s->folder->full_name, tmpid, NULL) != 0) {
g_free(tmpid);
return ;
}
@@ -2299,7 +2305,7 @@
camel_exception_init (&ex);
folder_name = s->folder->full_name;
- cdb = s->folder->cdb;
+ cdb = s->folder->parent_store->cdb_w;
/* FIXME[disk-summary] lifecycle of infos should be checked.
* Add should add to db and del should del to db. Sync only
@@ -2615,8 +2621,8 @@
CamelDB *db;
char *table_name;
- db = s->folder->cdb;
- //table_name = safe_table (camel_file_util_safe_filename (s->folder->full_name));
+ /* Though we are going to read, we do this during write, so lets use it that way */
+ db = s->folder->parent_store->cdb_w;
table_name = s->folder->full_name;
io(printf("Savining header to db\n"));
@@ -3147,6 +3153,7 @@
record->replied = mi->flags & CAMEL_MESSAGE_ANSWERED ? 1 : 0;
record->important = mi->flags & CAMEL_MESSAGE_FLAGGED ? 1 : 0;
record->junk = mi->flags & CAMEL_MESSAGE_JUNK ? 1 : 0;
+ record->dirty = mi->flags & CAMEL_MESSAGE_FOLDER_FLAGGED ? 1 : 0;
record->attachment = mi->flags & CAMEL_MESSAGE_ATTACHMENTS ? 1 : 0;
record->size = mi->size;
Modified: trunk/camel/camel-folder-summary.h
==============================================================================
--- trunk/camel/camel-folder-summary.h (original)
+++ trunk/camel/camel-folder-summary.h Mon Oct 6 10:27:15 2008
@@ -247,6 +247,12 @@
struct _CamelFolderMetaSummary *meta_summary; /* Meta summary */
time_t cache_load_time;
guint timeout_handle;
+
+ const char *collate;
+ const char *sort_by;
+
+ /* Future ABI expansion */
+ gpointer later[4];
};
struct _CamelFolderSummaryClass {
@@ -348,6 +354,9 @@
/* add a new raw summary item */
void camel_folder_summary_add (CamelFolderSummary *summary, CamelMessageInfo *info);
+/* Peek from mem only */
+CamelMessageInfo * camel_folder_summary_peek_info (CamelFolderSummary *s, const char *uid);
+
/* Get only the uids of dirty/changed things to sync to server/db */
GPtrArray * camel_folder_summary_get_changed (CamelFolderSummary *s);
/* Gets the size of loaded mi's */
Modified: trunk/camel/camel-folder.c
==============================================================================
--- trunk/camel/camel-folder.c (original)
+++ trunk/camel/camel-folder.c Mon Oct 6 10:27:15 2008
@@ -102,6 +102,8 @@
static void ref_message_info (CamelFolder *folder, CamelMessageInfo *info);
static GPtrArray *search_by_expression (CamelFolder *folder, const char *exp, CamelException *ex);
+static guint32 count_by_expression (CamelFolder *folder, const char *exp, CamelException *ex);
+
static GPtrArray *search_by_uids (CamelFolder *folder, const char *exp, GPtrArray *uids, CamelException *ex);
static void search_free (CamelFolder * folder, GPtrArray *result);
@@ -150,6 +152,7 @@
camel_folder_class->get_summary = get_summary;
camel_folder_class->free_summary = free_summary;
camel_folder_class->search_by_expression = search_by_expression;
+ camel_folder_class->count_by_expression = count_by_expression;
camel_folder_class->search_by_uids = search_by_uids;
camel_folder_class->search_free = search_free;
camel_folder_class->get_message_info = get_message_info;
@@ -205,11 +208,6 @@
camel_folder_change_info_free(p->changed_frozen);
- if (camel_folder->cdb) {
- camel_db_close (camel_folder->cdb);
- camel_folder->cdb = NULL;
- }
-
g_static_rec_mutex_free(&p->lock);
g_static_mutex_free(&p->change_lock);
@@ -273,27 +271,6 @@
store_db_path = g_build_filename (store_path, CAMEL_DB_FILE, NULL);
g_free (store_path);
}
-
- folder->cdb = camel_db_open (store_db_path, &ex);
- if (camel_exception_is_set (&ex)) {
- char *store_path;
-
- g_print ("Failure for store_db_path : [%s]\n", store_db_path);
- g_free (store_db_path);
-
- store_path = camel_session_get_storage_path ((CamelSession *)camel_service_get_session (service), service, &ex);
- store_db_path = g_build_filename (store_path, CAMEL_DB_FILE, NULL);
- g_free (store_path);
- camel_exception_clear(&ex);
- folder->cdb = camel_db_open (store_db_path, &ex);
- if (camel_exception_is_set (&ex)) {
- g_print("Retry with %s failed\n", store_db_path);
- g_free(store_db_path);
- camel_exception_clear(&ex);
- return;
- }
- }
- g_free (store_db_path);
}
@@ -1387,6 +1364,47 @@
return ret;
}
+static guint32
+count_by_expression (CamelFolder *folder, const char *expression,
+ CamelException *ex)
+{
+ camel_exception_setv (ex, CAMEL_EXCEPTION_FOLDER_INVALID,
+ _("Unsupported operation: count by expression: for %s"),
+ camel_type_to_name (CAMEL_OBJECT_GET_TYPE (folder)));
+
+ w(g_warning ("CamelFolder::count_by_expression not implemented for "
+ "'%s'", camel_type_to_name (CAMEL_OBJECT_GET_TYPE (folder))));
+
+ return 0;
+}
+
+
+/**
+ * camel_folder_count_by_expression:
+ * @folder: a #CamelFolder object
+ * @expr: a search expression
+ * @ex: a #CamelException
+ *
+ * Searches the folder for count of messages matching the given search expression.
+ *
+ * Returns: an interger
+ **/
+guint32
+camel_folder_count_by_expression (CamelFolder *folder, const char *expression,
+ CamelException *ex)
+{
+ guint32 ret;
+
+ g_return_val_if_fail (CAMEL_IS_FOLDER (folder), 0);
+ g_return_val_if_fail (folder->folder_flags & CAMEL_FOLDER_HAS_SEARCH_CAPABILITY, 0);
+
+ /* NOTE: that it is upto the callee to lock */
+
+ ret = CF_CLASS (folder)->count_by_expression (folder, expression, ex);
+
+ return ret;
+}
+
static GPtrArray *
search_by_uids(CamelFolder *folder, const char *exp, GPtrArray *uids, CamelException *ex)
{
@@ -1603,7 +1621,7 @@
CAMEL_FOLDER_REC_UNLOCK (folder, lock);
/* Delete the references of the folder from the DB.*/
- camel_db_delete_folder (folder->cdb, folder->full_name, NULL);
+ camel_db_delete_folder (folder->parent_store->cdb_w, folder->full_name, NULL);
camel_object_trigger_event (folder, "deleted", NULL);
}
@@ -1641,7 +1659,7 @@
old = g_strdup(folder->full_name);
CF_CLASS (folder)->rename(folder, new);
- camel_db_rename_folder (folder->cdb, old, new, NULL);
+ camel_db_rename_folder (folder->parent_store->cdb_w, old, new, NULL);
camel_object_trigger_event (folder, "renamed", old);
g_free(old);
}
Modified: trunk/camel/camel-folder.h
==============================================================================
--- trunk/camel/camel-folder.h (original)
+++ trunk/camel/camel-folder.h Mon Oct 6 10:27:15 2008
@@ -109,7 +109,9 @@
guint32 folder_flags;
guint32 permanent_flags;
- CamelDB *cdb;
+
+ /* Future ABI expansion */
+ gpointer later[4];
};
#define CAMEL_FOLDER_HAS_SUMMARY_CAPABILITY (1<<0)
@@ -208,6 +210,7 @@
gboolean (*is_frozen) (CamelFolder *folder);
CamelFolderQuotaInfo * (*get_quota_info) (CamelFolder *folder);
+ guint32 (*count_by_expression) (CamelFolder *, const char *, CamelException *);
} CamelFolderClass;
/* Standard Camel function */
@@ -314,6 +317,7 @@
GPtrArray * camel_folder_search_by_expression (CamelFolder *folder, const char *expr, CamelException *ex);
GPtrArray * camel_folder_search_by_uids (CamelFolder *folder, const char *expr, GPtrArray *uids, CamelException *ex);
void camel_folder_search_free (CamelFolder *folder, GPtrArray *result);
+guint32 camel_folder_count_by_expression (CamelFolder *folder, const char *expression, CamelException *ex);
/* summary info */
CamelMessageInfo *camel_folder_get_message_info (CamelFolder *folder, const char *uid);
Modified: trunk/camel/camel-search-sql-sexp.c
==============================================================================
--- trunk/camel/camel-search-sql-sexp.c (original)
+++ trunk/camel/camel-search-sql-sexp.c Mon Oct 6 10:27:15 2008
@@ -534,6 +534,26 @@
return r;
}
+static ESExpResult *
+sql_exp (struct _ESExp *f, int argc, struct _ESExpResult **argv, void *data)
+{
+ ESExpResult *r;
+ int i;
+ GString *str = g_string_new (NULL);
+
+ d(printf("executing sql-exp\n"));
+
+ r = e_sexp_result_new(f, ESEXP_RES_STRING);
+ for (i=0;i<argc;i++) {
+ if (argv[i]->type == ESEXP_RES_STRING && argv[i]->value.string)
+ g_string_append (str, argv[i]->value.string);
+ }
+ r->value.string = str->str;
+ g_string_free (str, FALSE);
+
+ return r;
+}
+
/* 'builtin' functions */
static struct {
char *name;
@@ -562,6 +582,8 @@
{ "get-received-date", get_received_date, 0},
{ "get-current-date", get_current_date, 0},
{ "get-size", get_size, 0},
+ { "sql-exp", sql_exp, 0},
+
/* { "uid", CAMEL_STRUCT_OFFSET(CamelFolderSearchClass, uid), 1 }, */
};
@@ -585,6 +607,8 @@
e_sexp_parse (sexp);
r = e_sexp_eval (sexp);
+ if (!r)
+ return NULL;
if (r->type == ESEXP_RES_STRING) {
res = g_strdup (r->value.string);
} else
@@ -664,6 +688,7 @@
int i=0;
char *txt[] = {
+#if 0
"(match-all (header-contains \"From\" \"org\"))",
"(and (match-all (and (not (system-flag \"deleted\")) (not (system-flag \"junk\")))) (and (or (match-all (or (header-ends-with \"To\" \"novell.com\") (header-ends-with \"Cc\" \"novell.com\"))) (match-all (or (= (user-tag \"label\") \"work\") (user-flag \"work\"))) )))",
@@ -704,7 +729,10 @@
"(not (or (header-matches \"from\" \"bugzilla-daemon bugzilla ximian com\") (header-matches \"from\" \"bugzilla-daemon bugzilla gnome org\") (header-matches \"from\" \"bugzilla_noreply novell com\") (header-matches \"from\" \"bugzilla-daemon mozilla org\") (header-matches \"from\" \"root dist suse de\") (header-matches \"from\" \"root hilbert3 suse de\") (header-matches \"from\" \"root hilbert4 suse de\") (header-matches \"from\" \"root hilbert5 suse de\") (header-matches \"from\" \"root hilbert6 suse de\") (header-matches \"from\" \"root suse de\") (header-matches \"from\" \"swamp_noreply suse de\") (and (header-matches \"from\" \"hermes opensuse org\") (header-starts-with \"subject\" \"submit-Request\"))))",
"(and (match-threads \"replies_parents\" (and (match-all (or (header-matches \"to\" \"maw ximian com\") (header-matches \"to\" \"mw ximian com\") (header-matches \"to\" \"maw novell com\") (header-matches \"to\" \"maw AMERICAS3 AMERICAS novell com\") (header-matches \"cc\" \"maw ximian com\") (header-matches \"cc\" \"mw ximian com\") (header-matches \"cc\" \"maw novell com\") (header-matches \"cc\" \"maw AMERICAS3 AMERICAS novell com\"))) (match-all (not (or (header-matches \"from\" \"bugzilla-daemon bugzilla ximian com\") (header-matches \"from\" \"bugzilla-daemon bugzilla gnome org\") (header-matches \"from\" \"bugzilla_noreply novell com\") (header-matches \"from\" \"bugzilla-daemon mozilla org\") (header-matches \"from\" \"root dist suse de\") (header-matches \"from\" \"root hilbert3 suse de\") (header-matches \"from\" \"root hilbert4 suse de\") (header-matches \"from\" \"root hilbert5 suse de\") (header-matches \"from\" \"root hilbert6 suse de\") (header-matc
hes \"from\" \"root suse de\") (header-matches \"from\" \"swamp_noreply suse de\") (and (header-matches \"from\" \"hermes opensuse org\") (header-starts-with \"subject\" \"submit-Request\"))))) (match-all (> (get-sent-date) (- (get-current-date) 1209600))) )) (match-all (and (not (system-flag \"deleted\")) (not (system-flag \"junk\")))))",
"and ((match-all (system-flag \"Deleted\")) (match-all (system-flag \"junk\")))",
- "(and (match-threads \"replies_parents\" (and (match-all (or (header-matches \"to\" \"maw ximian com\")))))))"
+ "(and (match-threads \"replies_parents\" (and (match-all (or (header-matches \"to\" \"maw ximian com\")))))))",
+ "(and (sql-exp \"folder_key = 'ASDGASd' AND folder_key = 'DSFWEA'\") (match-threads \"replies_parents\" (and (match-all (or (header-matches \"to\" \"maw ximian com\")))))))"
+#endif
+ "(and (match-all (and (not (system-flag \"deleted\")) (not (system-flag \"junk\")))) (and (or (match-all list-post.*zypp-devel) ) ))"
};
for (i=0; i < G_N_ELEMENTS(txt); i++) {
Modified: trunk/camel/camel-store.c
==============================================================================
--- trunk/camel/camel-store.c (original)
+++ trunk/camel/camel-store.c Mon Oct 6 10:27:15 2008
@@ -159,9 +159,14 @@
g_static_rec_mutex_free (&store->priv->folder_lock);
- if (store->cdb) {
- camel_db_close (store->cdb);
- store->cdb = NULL;
+ if (store->cdb_r) {
+ camel_db_close (store->cdb_r);
+ store->cdb_r = NULL;
+ }
+
+ if (store->cdb_w) {
+ camel_db_close (store->cdb_w);
+ store->cdb_w = NULL;
}
g_free (store->priv);
@@ -228,7 +233,8 @@
g_free (store_path);
- store->cdb = camel_db_open (store_db_path, ex);
+ /* This is for reading from the store */
+ store->cdb_r = camel_db_open (store_db_path, ex);
printf("store_db_path %s\n", store_db_path);
if (camel_exception_is_set (ex)) {
char *store_path;
@@ -240,7 +246,7 @@
store_db_path = g_build_filename (store_path, CAMEL_DB_FILE, NULL);
g_free (store_path);
camel_exception_clear(ex);
- store->cdb = camel_db_open (store_db_path, ex);
+ store->cdb_r = camel_db_open (store_db_path, ex);
if (camel_exception_is_set (ex)) {
g_print("Retry with %s failed\n", store_db_path);
g_free(store_db_path);
@@ -250,13 +256,15 @@
}
g_free (store_db_path);
- if (camel_db_create_folders_table (store->cdb, ex))
- printf ("something went wrong terribly\n");
+ if (camel_db_create_folders_table (store->cdb_r, ex))
+ g_warning ("something went wrong terribly during db creation \n");
else
- printf ("folders table successfully created \n");
+ d(printf ("folders table successfully created \n"));
if (camel_exception_is_set (ex))
return;
+ /* This is for writing to the store */
+ store->cdb_w = camel_db_clone (store->cdb_r, ex);
if (camel_url_get_param(url, "filter"))
store->flags |= CAMEL_STORE_FILTER_INBOX;
Modified: trunk/camel/camel-store.h
==============================================================================
--- trunk/camel/camel-store.h (original)
+++ trunk/camel/camel-store.h Mon Oct 6 10:27:15 2008
@@ -122,10 +122,14 @@
struct _CamelStorePrivate *priv;
CamelObjectBag *folders;
- CamelDB *cdb;
+ CamelDB *cdb_r;
+ CamelDB *cdb_w;
guint32 flags;
guint32 mode;
+
+ /* Future ABI expansion */
+ gpointer later[4];
};
/* open mode for folder */
Modified: trunk/camel/camel-vee-folder.c
==============================================================================
--- trunk/camel/camel-vee-folder.c (original)
+++ trunk/camel/camel-vee-folder.c Mon Oct 6 10:27:15 2008
@@ -64,6 +64,7 @@
static void vee_append_message(CamelFolder *folder, CamelMimeMessage *message, const CamelMessageInfo *info, char **appended_uid, CamelException *ex);
static void vee_transfer_messages_to(CamelFolder *source, GPtrArray *uids, CamelFolder *dest, GPtrArray **transferred_uids, gboolean delete_originals, CamelException *ex);
+static guint32 vee_count_by_expression(CamelFolder *folder, const char *expression, CamelException *ex);
static GPtrArray *vee_search_by_expression(CamelFolder *folder, const char *expression, CamelException *ex);
static GPtrArray *vee_search_by_uids(CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex);
@@ -482,27 +483,17 @@
g_list_free(list);
}
-static int
+static guint32
count_folder (CamelFolder *f, char *expr, CamelException *ex)
{
- GPtrArray *match;
- int count = 0;
-
- /* FIXME: Why don't we write a count_search_by_expression. It can be just fast. */
- match = camel_folder_search_by_expression(f, expr, ex);
- if (match) {
- count = match->len;
- camel_folder_search_free (f, match);
- }
-
- return count;
+ return camel_folder_count_by_expression(f, expr, ex);
}
static int
count_result (CamelFolderSummary *summary, char *query, CamelException *ex)
{
CamelFolder *folder = summary->folder;
CamelVeeFolder *vf = (CamelVeeFolder *)folder;
- int count=0;
+ guint32 count=0;
char *expr = g_strdup_printf ("(and %s %s)", vf->expression ? vf->expression : "", query);
GList *node;
struct _CamelVeeFolderPrivate *p = _PRIVATE(vf);
@@ -525,7 +516,8 @@
CamelDB *db;
char *table_name;
- db = s->folder->parent_store->cdb;
+ /* We do this during write, so lets use write handle, though we gonna read */
+ db = s->folder->parent_store->cdb_w;
table_name = s->folder->full_name;
record->folder_name = table_name;
@@ -641,6 +633,40 @@
return msg;
}
+static guint32
+vee_count_by_expression(CamelFolder *folder, const char *expression, CamelException *ex)
+{
+ GList *node;
+ char *expr;
+ guint32 count = 0;
+ CamelVeeFolder *vf = (CamelVeeFolder *)folder;
+ struct _CamelVeeFolderPrivate *p = _PRIVATE(vf);
+ GHashTable *searched = g_hash_table_new(NULL, NULL);
+ CamelVeeFolder *folder_unmatched = vf->parent_vee_store ? vf->parent_vee_store->folder_unmatched : NULL;
+
+ if (vf != folder_unmatched)
+ expr = g_strdup_printf ("(and %s %s)", vf->expression ? vf->expression : "", expression);
+ else
+ expr = g_strdup (expression);
+
+ node = p->folders;
+ while (node) {
+ CamelFolder *f = node->data;
+
+ /* make sure we only search each folder once - for unmatched folder to work right */
+ if (g_hash_table_lookup(searched, f) == NULL) {
+ count += camel_folder_count_by_expression(f, expr, ex);
+ g_hash_table_insert(searched, f, f);
+ }
+ node = g_list_next(node);
+ }
+
+
+ g_free(expr);
+
+ g_hash_table_destroy(searched);
+ return count;
+}
static GPtrArray *
vee_search_by_expression(CamelFolder *folder, const char *expression, CamelException *ex)
{
@@ -1006,7 +1032,7 @@
/* FIXME[disk-summary] Make all these as transactions, just
* testing atm */
if (u->rebuilt)
- camel_db_add_to_vfolder_transaction (((CamelFolder *) u->vf)->parent_store->cdb, ((CamelFolder *) u->vf)->full_name, (char *) camel_message_info_uid(mi), NULL);
+ camel_db_add_to_vfolder_transaction (((CamelFolder *) u->vf)->parent_store->cdb_w, ((CamelFolder *) u->vf)->full_name, (char *) camel_message_info_uid(mi), NULL);
if (!CAMEL_IS_VEE_FOLDER(u->source) && u->unmatched_uids != NULL) {
if (g_hash_table_lookup_extended(u->unmatched_uids, camel_message_info_uid(mi), (void **)&oldkey, &oldval)) {
n = GPOINTER_TO_INT (oldval);
@@ -1136,13 +1162,13 @@
/* now matchhash contains any new uid's, add them, etc */
if (rebuilded) {
- camel_db_begin_transaction (folder->parent_store->cdb, NULL);
+ camel_db_begin_transaction (folder->parent_store->cdb_w, NULL);
}
g_hash_table_foreach(matchhash, (GHFunc)folder_added_uid, &u);
if (rebuilded)
- camel_db_end_transaction (folder->parent_store->cdb, NULL);
+ camel_db_end_transaction (folder->parent_store->cdb_w, NULL);
if (folder_unmatched != NULL) {
/* scan unmatched, remove any that have vanished, etc */
@@ -1313,7 +1339,7 @@
return;
vuid = camel_message_info_uid(vinfo);
- camel_db_add_to_vfolder_transaction (folder->parent_store->cdb, folder->full_name, (char *)vuid, NULL);
+ camel_db_add_to_vfolder_transaction (folder->parent_store->cdb_w, folder->full_name, (char *)vuid, NULL);
camel_folder_change_info_add_uid(vf->changes, vuid);
/* old flags and new flags should be same, since we sync all times */
update_summary (vinfo, camel_message_info_flags(vinfo), 0, TRUE, FALSE);
@@ -1355,8 +1381,8 @@
}
camel_folder_change_info_remove_uid(vf->changes, vuid);
/* FIXME[disk-summary] Handle exception */
- camel_db_delete_uid_from_vfolder_transaction (folder->parent_store->cdb, folder->full_name, vuid, NULL);
- camel_folder_summary_remove_uid(folder->summary, vuid);
+ camel_db_delete_uid_from_vfolder_transaction (folder->parent_store->cdb_w, folder->full_name, vuid, NULL);
+ camel_folder_summary_remove_uid_fast(folder->summary, vuid);
if ((vf->flags & CAMEL_STORE_FOLDER_PRIVATE) == 0 && !CAMEL_IS_VEE_FOLDER(sub) && folder_unmatched != NULL) {
if (keep) {
@@ -1522,7 +1548,7 @@
CAMEL_VEE_FOLDER_LOCK(vf, summary_lock);
if (matches_changed || matches_added || changes->uid_removed->len||present)
- camel_db_begin_transaction (folder->parent_store->cdb, NULL);
+ camel_db_begin_transaction (folder->parent_store->cdb_w, NULL);
if (folder_unmatched != NULL)
CAMEL_VEE_FOLDER_LOCK(folder_unmatched, summary_lock);
@@ -1655,7 +1681,7 @@
}
if (matches_changed || matches_added || changes->uid_removed->len || present)
- camel_db_end_transaction (folder->parent_store->cdb, NULL);
+ camel_db_end_transaction (folder->parent_store->cdb_w, NULL);
CAMEL_VEE_FOLDER_UNLOCK(vf, summary_lock);
/* Cleanup stuff on our folder */
@@ -2000,7 +2026,7 @@
/* Recreate the table when the query changes, only if we are not setting it first */
if (vf->expression)
- camel_db_recreate_vfolder (((CamelFolder *) vf)->parent_store->cdb, ((CamelFolder *) vf)->full_name, NULL);
+ camel_db_recreate_vfolder (((CamelFolder *) vf)->parent_store->cdb_w, ((CamelFolder *) vf)->full_name, NULL);
g_free(vf->expression);
@@ -2042,6 +2068,7 @@
folder_class->search_by_expression = vee_search_by_expression;
folder_class->search_by_uids = vee_search_by_uids;
+ folder_class->count_by_expression = vee_count_by_expression;
folder_class->rename = vee_rename;
folder_class->delete = vee_delete;
@@ -2166,7 +2193,7 @@
/* Save the counts to DB */
record = summary_header_to_db (vf->summary, ex);
- camel_db_write_folder_info_record (vf->parent_store->cdb, record, ex);
+ camel_db_write_folder_info_record (vf->parent_store->cdb_w, record, ex);
g_free (record);
}
@@ -2184,7 +2211,7 @@
/* Save the counts to DB */
if (!vf->deleted) {
record = summary_header_to_db (((CamelFolder *)vf)->summary, NULL);
- camel_db_write_folder_info_record (((CamelFolder *) vf)->parent_store->cdb, record, NULL);
+ camel_db_write_folder_info_record (((CamelFolder *) vf)->parent_store->cdb_w, record, NULL);
g_free (record);
}
Modified: trunk/camel/camel-vee-summary.c
==============================================================================
--- trunk/camel/camel-vee-summary.c (original)
+++ trunk/camel/camel-vee-summary.c Mon Oct 6 10:27:15 2008
@@ -65,7 +65,7 @@
return (CamelMessageInfo *)to;
}
-#define HANDLE_NULL_INFO(value) if (!rmi) { g_warning (G_STRLOC ": real info is NULL for %s, safeguarding\n", mi->uid); return value; }
+#define HANDLE_NULL_INFO(value) if (!rmi) { d(g_warning (G_STRLOC ": real info is NULL for %s, safeguarding\n", mi->uid)); return value; }
static const void *
vee_info_ptr (const CamelMessageInfo *mi, int id)
@@ -333,7 +333,7 @@
/* FIXME[disk-summary] fix exceptions and note return values */
/* FIXME[disk-summary] if Evo's junk/trash vfolders make it VJunk
* VTrash instead of .#evolution/Junk-or-whatever */
- camel_db_create_vfolder (parent->cdb, parent->full_name, NULL);
+ camel_db_create_vfolder (parent->parent_store->cdb_w, parent->full_name, NULL);
/* FIXME[disk-summary] handle excep and ret */
camel_folder_summary_header_load_from_db ((CamelFolderSummary *)s, parent->parent_store, parent->full_name, NULL);
@@ -348,7 +348,7 @@
GPtrArray *array;
/* FIXME[disk-summary] fix exception passing */
- array = camel_db_get_vuids_from_vfolder(cfs->folder->cdb, cfs->folder->full_name, shash, NULL);
+ array = camel_db_get_vuids_from_vfolder(cfs->folder->parent_store->cdb_r, cfs->folder->full_name, shash, NULL);
g_free(shash);
Modified: trunk/camel/camel-vtrash-folder.c
==============================================================================
--- trunk/camel/camel-vtrash-folder.c (original)
+++ trunk/camel/camel-vtrash-folder.c Mon Oct 6 10:27:15 2008
@@ -523,14 +523,14 @@
CAMEL_VEE_FOLDER_LOCK(vf, summary_lock);
if (((CamelVTrashFolder *)vf)->bit == CAMEL_MESSAGE_DELETED) {
- infos = camel_db_get_folder_deleted_uids (sub->cdb, sub->full_name, NULL);
+ infos = camel_db_get_folder_deleted_uids (sub->parent_store->cdb_w, sub->full_name, NULL);
if (infos) {
((CamelFolder *)vf)->summary->saved_count += infos->len;
((CamelFolder *)vf)->summary->deleted_count += infos->len;
}
}
else if (((CamelVTrashFolder *)vf)->bit == CAMEL_MESSAGE_JUNK)
- infos = camel_db_get_folder_junk_uids (sub->cdb, sub->full_name, NULL);
+ infos = camel_db_get_folder_junk_uids (sub->parent_store->cdb_w, sub->full_name, NULL);
if (!infos) {
CAMEL_VEE_FOLDER_UNLOCK(vf, summary_lock);
Modified: trunk/camel/providers/groupwise/camel-groupwise-folder.c
==============================================================================
--- trunk/camel/providers/groupwise/camel-groupwise-folder.c (original)
+++ trunk/camel/providers/groupwise/camel-groupwise-folder.c Mon Oct 6 10:27:15 2008
@@ -451,6 +451,20 @@
return matches;
}
+static guint32
+groupwise_folder_count_by_expression (CamelFolder *folder, const char *expression, CamelException *ex)
+{
+ CamelGroupwiseFolder *gw_folder = CAMEL_GROUPWISE_FOLDER(folder);
+ guint32 matches;
+
+ CAMEL_GROUPWISE_FOLDER_LOCK(gw_folder, search_lock);
+ camel_folder_search_set_folder (gw_folder->search, folder);
+ matches = camel_folder_search_count (gw_folder->search, expression, ex);
+ CAMEL_GROUPWISE_FOLDER_UNLOCK(gw_folder, search_lock);
+
+ return matches;
+}
+
static GPtrArray *
groupwise_folder_search_by_uids(CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex)
{
@@ -2402,6 +2416,7 @@
camel_folder_class->get_message = groupwise_folder_get_message;
camel_folder_class->rename = groupwise_folder_rename;
camel_folder_class->search_by_expression = groupwise_folder_search_by_expression;
+ camel_folder_class->count_by_expression = groupwise_folder_count_by_expression;
camel_folder_class->search_by_uids = groupwise_folder_search_by_uids;
camel_folder_class->search_free = groupwise_folder_search_free;
camel_folder_class->append_message = groupwise_append_message;
Modified: trunk/camel/providers/imap/camel-imap-folder.c
==============================================================================
--- trunk/camel/providers/imap/camel-imap-folder.c (original)
+++ trunk/camel/providers/imap/camel-imap-folder.c Mon Oct 6 10:27:15 2008
@@ -123,6 +123,7 @@
/* searching */
static GPtrArray *imap_search_by_expression (CamelFolder *folder, const char *expression, CamelException *ex);
+static guint32 imap_count_by_expression (CamelFolder *folder, const char *expression, CamelException *ex);
static GPtrArray *imap_search_by_uids (CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex);
static void imap_search_free (CamelFolder *folder, GPtrArray *uids);
@@ -155,6 +156,7 @@
camel_folder_class->get_message = imap_get_message;
camel_folder_class->rename = imap_rename;
camel_folder_class->search_by_expression = imap_search_by_expression;
+ camel_folder_class->count_by_expression = imap_count_by_expression;
camel_folder_class->search_by_uids = imap_search_by_uids;
camel_folder_class->search_free = imap_search_free;
camel_folder_class->thaw = imap_thaw;
@@ -1483,7 +1485,7 @@
* the cached data may be useful in replaying a COPY later.
*/
}
- camel_db_delete_uids (folder->cdb, folder->full_name, list, ex);
+ camel_db_delete_uids (folder->parent_store->cdb_w, folder->full_name, list, ex);
g_slist_free(list);
camel_folder_summary_save_to_db (folder->summary, ex);
@@ -1568,7 +1570,7 @@
* the cached data may be useful in replaying a COPY later.
*/
}
- camel_db_delete_uids (folder->cdb, folder->full_name, list, ex);
+ camel_db_delete_uids (folder->parent_store->cdb_w, folder->full_name, list, ex);
g_slist_free (list);
camel_folder_summary_save_to_db (folder->summary, ex);
camel_object_trigger_event (CAMEL_OBJECT (folder), "folder_changed", changes);
@@ -2399,6 +2401,24 @@
return matches;
}
+static guint32
+imap_count_by_expression (CamelFolder *folder, const char *expression, CamelException *ex)
+{
+ CamelImapFolder *imap_folder = CAMEL_IMAP_FOLDER (folder);
+ guint32 matches;
+
+ /* we could get around this by creating a new search object each time,
+ but i doubt its worth it since any long operation would lock the
+ command channel too */
+ CAMEL_IMAP_FOLDER_LOCK(folder, search_lock);
+
+ camel_folder_search_set_folder (imap_folder->search, folder);
+ matches = camel_folder_search_count(imap_folder->search, expression, ex);
+
+ CAMEL_IMAP_FOLDER_UNLOCK(folder, search_lock);
+
+ return matches;
+}
static GPtrArray *
imap_search_by_uids(CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex)
{
@@ -3506,7 +3526,7 @@
}
/* Delete all in one transaction */
- camel_db_delete_uids (folder->cdb, folder->full_name, deleted, ex);
+ camel_db_delete_uids (folder->parent_store->cdb_w, folder->full_name, deleted, ex);
g_slist_foreach (deleted, (GFunc) g_free, NULL);
g_slist_free (deleted);
}
Modified: trunk/camel/providers/imap/camel-imap-store.c
==============================================================================
--- trunk/camel/providers/imap/camel-imap-store.c (original)
+++ trunk/camel/providers/imap/camel-imap-store.c Mon Oct 6 10:27:15 2008
@@ -1126,7 +1126,7 @@
g_unlink (state_file);
g_free (state_file);
- camel_db_delete_folder (((CamelStore *)imap_store)->cdb, folder_name, ex);
+ camel_db_delete_folder (((CamelStore *)imap_store)->cdb_w, folder_name, ex);
camel_imap_message_cache_delete (folder_dir, ex);
state_file = g_strdup_printf("%s/subfolders", folder_dir);
@@ -1378,6 +1378,7 @@
}
}
if (!authenticated) {
+ printf("EXCEP %d %d %d\n", camel_exception_get_id(ex), CAMEL_EXCEPTION_USER_CANCEL, CAMEL_EXCEPTION_SERVICE_UNAVAILABLE);
if (camel_exception_get_id (ex) == CAMEL_EXCEPTION_USER_CANCEL ||
camel_exception_get_id (ex) == CAMEL_EXCEPTION_SERVICE_UNAVAILABLE)
return FALSE;
Modified: trunk/camel/providers/imap/camel-imap-summary.c
==============================================================================
--- trunk/camel/providers/imap/camel-imap-summary.c (original)
+++ trunk/camel/providers/imap/camel-imap-summary.c Mon Oct 6 10:27:15 2008
@@ -34,6 +34,7 @@
#include "camel-folder.h"
#include "camel-file-utils.h"
#include "camel-string-utils.h"
+#include "camel-store.h"
#include "camel-imap-summary.h"
#include "camel-imap-utils.h"
@@ -140,12 +141,23 @@
static int
sort_uid_cmp (void *enc, int len1, void * data1, int len2, void *data2)
{
- char *sa1 = (char*)g_utf8_normalize (data1, len1, G_NORMALIZE_DEFAULT);
- char *sa2 = (char*)g_utf8_normalize (data2, len2, G_NORMALIZE_DEFAULT);
- int a1 = strtoul (sa1, NULL, 10);
- int a2 = strtoul (sa2, NULL, 10);
+ static char *sa1=NULL, *sa2=NULL;
+ static int l1=0, l2=0;
+ int a1, a2;
+
+ if (l1 < len1+1) {
+ sa1 = g_realloc (sa1, len1+1);
+ l1 = len1+1;
+ }
+ if (l2 < len2+1) {
+ sa2 = g_realloc (sa2, len2+1);
+ l2 = len2+1;
+ }
+ strncpy (sa1, data1, len1);sa1[len1] = 0;
+ strncpy (sa2, data2, len2);sa2[len2] = 0;
- g_free(sa1); g_free(sa2);
+ a1 = strtoul (sa1, NULL, 10);
+ a2 = strtoul (sa2, NULL, 10);
return (a1 < a1) ? -1 : (a1 > a2) ? 1 : 0;
}
@@ -168,8 +180,11 @@
camel_exception_init (&ex);
summary->folder = folder;
- if (folder)
- camel_db_set_collate (folder->cdb, "uid", "uid_sort", (CamelDBCollate)sort_uid_cmp);
+ if (folder) {
+ camel_db_set_collate (folder->parent_store->cdb_r, "uid", "imap_uid_sort", (CamelDBCollate)sort_uid_cmp);
+ summary->sort_by = "uid";
+ summary->collate = "imap_uid_sort";
+ }
camel_folder_summary_set_build_content (summary, TRUE);
camel_folder_summary_set_filename (summary, filename);
Modified: trunk/camel/providers/local/camel-local-folder.c
==============================================================================
--- trunk/camel/providers/local/camel-local-folder.c (original)
+++ trunk/camel/providers/local/camel-local-folder.c Mon Oct 6 10:27:15 2008
@@ -81,6 +81,7 @@
static void local_expunge(CamelFolder *folder, CamelException *ex);
static GPtrArray *local_search_by_expression(CamelFolder *folder, const char *expression, CamelException *ex);
+static guint32 local_count_by_expression(CamelFolder *folder, const char *expression, CamelException *ex);
static GPtrArray *local_search_by_uids(CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex);
static void local_search_free(CamelFolder *folder, GPtrArray * result);
@@ -106,6 +107,7 @@
camel_folder_class->expunge = local_expunge;
camel_folder_class->search_by_expression = local_search_by_expression;
+ camel_folder_class->count_by_expression = local_count_by_expression;
camel_folder_class->search_by_uids = local_search_by_uids;
camel_folder_class->search_free = local_search_free;
@@ -590,6 +592,26 @@
return matches;
}
+static guint32
+local_count_by_expression(CamelFolder *folder, const char *expression, CamelException *ex)
+{
+ CamelLocalFolder *local_folder = CAMEL_LOCAL_FOLDER(folder);
+ gint matches;
+
+ CAMEL_LOCAL_FOLDER_LOCK(folder, search_lock);
+
+ if (local_folder->search == NULL)
+ local_folder->search = camel_folder_search_new();
+
+ camel_folder_search_set_folder(local_folder->search, folder);
+ camel_folder_search_set_body_index(local_folder->search, local_folder->index);
+ matches = camel_folder_search_count (local_folder->search, expression, ex);
+
+ CAMEL_LOCAL_FOLDER_UNLOCK(folder, search_lock);
+
+ return matches;
+}
+
static GPtrArray *
local_search_by_uids(CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex)
{
Modified: trunk/camel/providers/local/camel-local-store.c
==============================================================================
--- trunk/camel/providers/local/camel-local-store.c (original)
+++ trunk/camel/providers/local/camel-local-store.c Mon Oct 6 10:27:15 2008
@@ -106,12 +106,6 @@
store = ((CamelStore *)local_store);
d(printf ("\n\aLocal Store Finalize \n\a"));
- if (store && store->cdb) {
- d(printf ("\n\aClosing Store DB for hte local provider \n\a"));
- camel_db_close (store->cdb);
- store->cdb = NULL;
- }
-
}
CamelType
Modified: trunk/camel/providers/local/camel-maildir-summary.c
==============================================================================
--- trunk/camel/providers/local/camel-maildir-summary.c (original)
+++ trunk/camel/providers/local/camel-maildir-summary.c Mon Oct 6 10:27:15 2008
@@ -41,6 +41,7 @@
#include "camel-mime-message.h"
#include "camel-operation.h"
#include "camel-private.h"
+#include "camel-store.h"
#include "camel-string-utils.h"
#include "camel-maildir-summary.h"
@@ -168,8 +169,11 @@
CamelMaildirSummary *o = (CamelMaildirSummary *)camel_object_new(camel_maildir_summary_get_type ());
((CamelFolderSummary *)o)->folder = folder;
- if (folder)
- camel_db_set_collate (folder->cdb, "dreceived", NULL, NULL);
+ if (folder) {
+ camel_db_set_collate (folder->parent_store->cdb_r, "dreceived", NULL, NULL);
+ ((CamelFolderSummary *)o)->sort_by = "dreceived";
+ ((CamelFolderSummary *)o)->collate = NULL;
+ }
camel_local_summary_construct((CamelLocalSummary *)o, filename, maildirdir, index);
return o;
}
Modified: trunk/camel/providers/local/camel-mbox-summary.c
==============================================================================
--- trunk/camel/providers/local/camel-mbox-summary.c (original)
+++ trunk/camel/providers/local/camel-mbox-summary.c Mon Oct 6 10:27:15 2008
@@ -213,14 +213,25 @@
static int
frompos_sort (void *enc, int len1, void * data1, int len2, void *data2)
{
- char *sa1 = (char*)g_utf8_normalize (data1, len1, G_NORMALIZE_DEFAULT);
- char *sa2 = (char*)g_utf8_normalize (data2, len2, G_NORMALIZE_DEFAULT);
- int a1 = strtoul (sa1, NULL, 10);
- int a2 = strtoul (sa2, NULL, 10);
+ static char *sa1=NULL, *sa2=NULL;
+ static int l1=0, l2=0;
+ int a1, a2;
- g_free(sa1); g_free(sa2);
+ if (l1 < len1+1) {
+ sa1 = g_realloc (sa1, len1+1);
+ l1 = len1+1;
+ }
+ if (l2 < len2+1) {
+ sa2 = g_realloc (sa2, len2+1);
+ l2 = len2+1;
+ }
+ strncpy (sa1, data1, len1);sa1[len1] = 0;
+ strncpy (sa2, data2, len2);sa2[len2] = 0;
- return a1 > a2;
+ a1 = strtoul (sa1, NULL, 10);
+ a2 = strtoul (sa2, NULL, 10);
+
+ return (a1 < a1) ? -1 : (a1 > a2) ? 1 : 0;
}
/**
@@ -237,9 +248,13 @@
((CamelFolderSummary *)new)->folder = folder;
if (folder) {
+ CamelFolderSummary *summary = (CamelFolderSummary *)new;
+
/* Set the functions for db sorting */
- /* FIXME: Add column names though a #define */
- camel_db_set_collate (folder->cdb, "bdata", "frompos_sort", (CamelDBCollate)frompos_sort);
+ camel_db_set_collate (folder->parent_store->cdb_r, "bdata", "mbox_frompos_sort", (CamelDBCollate)frompos_sort);
+ summary->sort_by = "bdata";
+ summary->collate = "mbox_frompos_sort";
+
}
camel_local_summary_construct((CamelLocalSummary *)new, filename, mbox_name, index);
return new;
@@ -367,7 +382,8 @@
&& camel_local_summary_decode_x_evolution((CamelLocalSummary *)s, xev, &mi->info) == 0) {
uid = camel_message_info_uid(mi);
d(printf("found valid x-evolution: %s\n", uid));
- info = (CamelMboxMessageInfo *)camel_folder_summary_uid(s, uid);
+ /* If one is there, it should be there already */
+ info = (CamelMboxMessageInfo *) camel_folder_summary_peek_info (s, uid);
if (info) {
if ((info->info.info.flags & CAMEL_MESSAGE_FOLDER_NOTSEEN)) {
info->info.info.flags &= ~CAMEL_MESSAGE_FOLDER_NOTSEEN;
@@ -567,6 +583,8 @@
If we're not starting from the start, we must be starting
from the old end, so everything must be treated as new */
count = camel_folder_summary_count(s);
+ if (count != camel_folder_summary_cache_size(s)) /* It makes sense to load summary, if it isn't there. */
+ camel_folder_summary_reload_from_db (s, ex);
for (i=0;i<count;i++) {
mi = (CamelMboxMessageInfo *)camel_folder_summary_index(s, i);
if (offset == 0)
@@ -613,7 +631,7 @@
}
/* Delete all in one transaction */
- camel_db_delete_uids (s->folder->cdb, s->folder->full_name, del, ex);
+ camel_db_delete_uids (s->folder->parent_store->cdb_w, s->folder->full_name, del, ex);
g_slist_foreach (del, (GFunc) camel_pstring_free, NULL);
g_slist_free (del);
@@ -789,6 +807,30 @@
return -1;
}
+static gint
+cms_sort_frompos (gpointer a, gpointer b, gpointer data)
+{
+ CamelFolderSummary *summary = (CamelFolderSummary *)data;
+ CamelMboxMessageInfo *info1, *info2;
+ int ret = 0;
+
+ /* Things are in memory already. Sorting speeds up syncing, if things are sorted by from pos. */
+ info1 = (CamelMboxMessageInfo *)camel_folder_summary_uid (summary, *(char **)a);
+ info2 = (CamelMboxMessageInfo *)camel_folder_summary_uid (summary, *(char **)b);
+
+ if (info1->frompos > info2->frompos)
+ ret = 1;
+ else if (info1->frompos < info2->frompos)
+ ret = -1;
+ else
+ ret = 0;
+ camel_message_info_free (info1);
+ camel_message_info_free (info2);
+
+ return ret;
+
+}
+
/* perform a quick sync - only system flags have changed */
static int
mbox_summary_sync_quick(CamelMboxSummary *mbs, gboolean expunge, CamelFolderChangeInfo *changeinfo, CamelException *ex)
@@ -836,6 +878,9 @@
/* Sync only the changes */
summary = camel_folder_summary_get_changed ((CamelFolderSummary *)mbs);
+ if (summary->len)
+ g_ptr_array_sort_with_data (summary, (GCompareDataFunc)cms_sort_frompos, (gpointer) mbs);
+
for (i = 0; i < summary->len; i++) {
int xevoffset;
int pc = (i+1)*100/summary->len;
@@ -909,6 +954,7 @@
camel_mime_parser_drop_step(mp);
info->info.info.flags &= 0xffff;
+ info->info.info.dirty = TRUE;
camel_message_info_free((CamelMessageInfo *)info);
}
@@ -979,10 +1025,10 @@
g_ptr_array_free (summary, TRUE);
if (quick && expunge) {
- int dcount =0;
+ guint32 dcount =0;
- if (camel_db_count_deleted_message_info (s->folder->cdb, s->folder->full_name, &dcount, ex) == -1)
+ if (camel_db_count_deleted_message_info (s->folder->parent_store->cdb_w, s->folder->full_name, &dcount, ex) == -1)
return -1;
if (dcount)
quick = FALSE;
@@ -1191,7 +1237,7 @@
info = NULL;
}
}
- camel_db_delete_uids (s->folder->cdb, s->folder->full_name, del, ex);
+ camel_db_delete_uids (s->folder->parent_store->cdb_w, s->folder->full_name, del, ex);
g_slist_foreach (del, (GFunc) camel_pstring_free, NULL);
g_slist_free (del);
@@ -1211,6 +1257,7 @@
info->info.info.flags &= ~(CAMEL_MESSAGE_FOLDER_NOXEV
|CAMEL_MESSAGE_FOLDER_FLAGGED
|CAMEL_MESSAGE_FOLDER_XEVCHANGE);
+ ((CamelMessageInfo *)info)->dirty = TRUE;
camel_folder_summary_touch(s);
}
camel_message_info_free((CamelMessageInfo *)info);
Modified: trunk/camel/providers/local/camel-mh-summary.c
==============================================================================
--- trunk/camel/providers/local/camel-mh-summary.c (original)
+++ trunk/camel/providers/local/camel-mh-summary.c Mon Oct 6 10:27:15 2008
@@ -34,6 +34,7 @@
#include <glib/gi18n-lib.h>
+#include "camel-store.h"
#include "camel-mime-message.h"
#include "camel-private.h"
@@ -116,12 +117,23 @@
static int
sort_uid_cmp (void *enc, int len1, void * data1, int len2, void *data2)
{
- char *sa1 = (char*)g_utf8_normalize (data1, len1, G_NORMALIZE_DEFAULT);
- char *sa2 = (char*)g_utf8_normalize (data2, len2, G_NORMALIZE_DEFAULT);
- int a1 = strtoul (sa1, NULL, 10);
- int a2 = strtoul (sa2, NULL, 10);
+ static char *sa1=NULL, *sa2=NULL;
+ static int l1=0, l2=0;
+ int a1, a2;
+
+ if (l1 < len1+1) {
+ sa1 = g_realloc (sa1, len1+1);
+ l1 = len1+1;
+ }
+ if (l2 < len2+1) {
+ sa2 = g_realloc (sa2, len2+1);
+ l2 = len2+1;
+ }
+ strncpy (sa1, data1, len1);sa1[len1] = 0;
+ strncpy (sa2, data2, len2);sa2[len2] = 0;
- g_free(sa1); g_free(sa2);
+ a1 = strtoul (sa1, NULL, 10);
+ a2 = strtoul (sa2, NULL, 10);
return (a1 < a1) ? -1 : (a1 > a2) ? 1 : 0;
}
@@ -139,8 +151,11 @@
((CamelFolderSummary *)o)->folder = folder;
if (folder) {
- camel_db_set_collate (folder->cdb, "uid", "uid_sort", (CamelDBCollate)sort_uid_cmp);
+ camel_db_set_collate (folder->parent_store->cdb_r, "uid", "mh_uid_sort", (CamelDBCollate)sort_uid_cmp);
+ ((CamelFolderSummary *)o)->sort_by = "uid";
+ ((CamelFolderSummary *)o)->collate = "mh_uid_sort";
}
+
camel_local_summary_construct((CamelLocalSummary *)o, filename, mhdir, index);
return o;
}
Modified: trunk/camel/providers/local/camel-spool-summary.c
==============================================================================
--- trunk/camel/providers/local/camel-spool-summary.c (original)
+++ trunk/camel/providers/local/camel-spool-summary.c Mon Oct 6 10:27:15 2008
@@ -37,6 +37,7 @@
#include "camel-file-utils.h"
#include "camel-mime-message.h"
#include "camel-operation.h"
+#include "camel-store.h"
#include "camel-spool-summary.h"
@@ -108,14 +109,25 @@
static int
frompos_sort (void *enc, int len1, void * data1, int len2, void *data2)
{
- char *sa1 = (char*)g_utf8_normalize (data1, len1, G_NORMALIZE_DEFAULT);
- char *sa2 = (char*)g_utf8_normalize (data2, len2, G_NORMALIZE_DEFAULT);
- int a1 = strtoul (sa1, NULL, 10);
- int a2 = strtoul (sa2, NULL, 10);
+ static char *sa1=NULL, *sa2=NULL;
+ static int l1=0, l2=0;
+ int a1, a2;
- g_free(sa1); g_free(sa2);
+ if (l1 < len1+1) {
+ sa1 = g_realloc (sa1, len1+1);
+ l1 = len1+1;
+ }
+ if (l2 < len2+1) {
+ sa2 = g_realloc (sa2, len2+1);
+ l2 = len2+1;
+ }
+ strncpy (sa1, data1, len1);sa1[len1] = 0;
+ strncpy (sa2, data2, len2);sa2[len2] = 0;
+
+ a1 = strtoul (sa1, NULL, 10);
+ a2 = strtoul (sa2, NULL, 10);
- return a1 > a2;
+ return (a1 < a1) ? -1 : (a1 > a2) ? 1 : 0;
}
CamelSpoolSummary *
@@ -125,9 +137,9 @@
((CamelFolderSummary *)new)->folder = folder;
if (folder) {
- /* Set the functions for db sorting */
- /* FIXME: Add column names though a #define */
- camel_db_set_collate (folder->cdb, "bdata", "frompos_sort", (CamelDBCollate)frompos_sort);
+ camel_db_set_collate (folder->parent_store->cdb_r, "bdata", "spool_frompos_sort", (CamelDBCollate)frompos_sort);
+ ((CamelFolderSummary *)new)->sort_by = "bdata";
+ ((CamelFolderSummary *)new)->collate = "spool_frompos_sort";
}
camel_local_summary_construct((CamelLocalSummary *)new, NULL, mbox_name, NULL);
camel_folder_summary_load_from_db ((CamelFolderSummary *)new, NULL);
Modified: trunk/camel/providers/nntp/camel-nntp-folder.c
==============================================================================
--- trunk/camel/providers/nntp/camel-nntp-folder.c (original)
+++ trunk/camel/providers/nntp/camel-nntp-folder.c Mon Oct 6 10:27:15 2008
@@ -274,6 +274,25 @@
return matches;
}
+static guint32
+nntp_folder_count_by_expression (CamelFolder *folder, const char *expression, CamelException *ex)
+{
+ CamelNNTPFolder *nntp_folder = CAMEL_NNTP_FOLDER (folder);
+ guint32 count;
+
+ CAMEL_NNTP_FOLDER_LOCK(nntp_folder, search_lock);
+
+ if (nntp_folder->search == NULL)
+ nntp_folder->search = camel_folder_search_new ();
+
+ camel_folder_search_set_folder (nntp_folder->search, folder);
+ count = camel_folder_search_count(nntp_folder->search, expression, ex);
+
+ CAMEL_NNTP_FOLDER_UNLOCK(nntp_folder, search_lock);
+
+ return count;
+}
+
static GPtrArray *
nntp_folder_search_by_uids (CamelFolder *folder, const char *expression, GPtrArray *uids, CamelException *ex)
{
@@ -461,6 +480,7 @@
camel_folder_class->set_message_flags = nntp_folder_set_message_flags;
camel_folder_class->get_message = nntp_folder_get_message;
camel_folder_class->search_by_expression = nntp_folder_search_by_expression;
+ camel_folder_class->count_by_expression = nntp_folder_count_by_expression;
camel_folder_class->search_by_uids = nntp_folder_search_by_uids;
camel_folder_class->search_free = nntp_folder_search_free;
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]