dovecot-1.2: virtual: Added support for saving/copying messages ...

dovecot at dovecot.org dovecot at dovecot.org
Fri Feb 27 01:30:43 EET 2009


details:   http://hg.dovecot.org/dovecot-1.2/rev/93c25cfe2760
changeset: 8791:93c25cfe2760
user:      Timo Sirainen <tss at iki.fi>
date:      Thu Feb 26 18:30:02 2009 -0500
description:
virtual: Added support for saving/copying messages to virtual mailboxes.

diffstat:

8 files changed, 179 insertions(+), 33 deletions(-)
src/plugins/virtual/Makefile.am           |    4 -
src/plugins/virtual/virtual-config.c      |    8 ++
src/plugins/virtual/virtual-mail.c        |   40 +++++++-----
src/plugins/virtual/virtual-save.c        |   93 +++++++++++++++++++++++++++++
src/plugins/virtual/virtual-storage.c     |   11 +--
src/plugins/virtual/virtual-storage.h     |   18 ++++-
src/plugins/virtual/virtual-transaction.c |   15 ++--
src/plugins/virtual/virtual-transaction.h |   23 +++++++

diffs (truncated from 349 to 300 lines):

diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/Makefile.am
--- a/src/plugins/virtual/Makefile.am	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/Makefile.am	Thu Feb 26 18:30:02 2009 -0500
@@ -17,12 +17,14 @@ lib20_virtual_plugin_la_SOURCES = \
 	virtual-plugin.c \
 	virtual-search.c \
 	virtual-storage.c \
+	virtual-save.c \
 	virtual-sync.c \
 	virtual-transaction.c
 
 noinst_HEADERS = \
 	virtual-plugin.h \
-	virtual-storage.h
+	virtual-storage.h \
+	virtual-transaction.h
 
 install-exec-local:
 	for d in imap pop3 lda; do \
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-config.c
--- a/src/plugins/virtual/virtual-config.c	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/virtual-config.c	Thu Feb 26 18:30:02 2009 -0500
@@ -125,6 +125,14 @@ virtual_config_parse_line(struct virtual
 		name = bbox->name[0] == '-' ? bbox->name + 1 : bbox->name;
 		bbox->glob = imap_match_init(ctx->pool, name, TRUE, ctx->sep);
 		ctx->have_wildcards = TRUE;
+	} else if (bbox->name[0] == '!') {
+		/* save messages here */
+		if (ctx->mbox->save_bbox != NULL) {
+			*error_r = "Multiple save mailboxes defined";
+			return -1;
+		}
+		bbox->name++;
+		ctx->mbox->save_bbox = bbox;
 	}
 	array_append(&ctx->mbox->backend_boxes, &bbox, 1);
 	return 0;
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-mail.c
--- a/src/plugins/virtual/virtual-mail.c	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/virtual-mail.c	Thu Feb 26 18:30:02 2009 -0500
@@ -4,6 +4,7 @@
 #include "array.h"
 #include "index-mail.h"
 #include "virtual-storage.h"
+#include "virtual-transaction.h"
 
 struct virtual_mail {
 	struct index_mail imail;
@@ -75,13 +76,32 @@ backend_mail_find(struct virtual_mail *v
 	return NULL;
 }
 
+struct mail *
+virtual_mail_set_backend_mail(struct mail *mail,
+			      struct virtual_backend_box *bbox)
+{
+	struct virtual_mail *vmail = (struct virtual_mail *)mail;
+	struct mailbox_transaction_context *backend_trans;
+	struct mailbox_header_lookup_ctx *backend_headers;
+
+	backend_trans = virtual_transaction_get(mail->transaction, bbox->box);
+
+	backend_headers = vmail->wanted_headers == NULL ? NULL :
+		mailbox_header_lookup_init(bbox->box,
+					   vmail->wanted_headers->headers);
+	vmail->backend_mail = mail_alloc(backend_trans, vmail->wanted_fields,
+					 backend_headers);
+	if (backend_headers != NULL)
+		mailbox_header_lookup_unref(&backend_headers);
+	array_append(&vmail->backend_mails, &vmail->backend_mail, 1);
+	return vmail->backend_mail;
+}
+
 static void virtual_mail_set_seq(struct mail *mail, uint32_t seq)
 {
 	struct virtual_mail *vmail = (struct virtual_mail *)mail;
 	struct virtual_mailbox *mbox = (struct virtual_mailbox *)mail->box;
 	struct virtual_backend_box *bbox;
-	struct mailbox_transaction_context *backend_trans;
-	struct mailbox_header_lookup_ctx *backend_headers;
 	const struct virtual_mail_index_record *vrec;
 	const void *data;
 	bool expunged;
@@ -92,20 +112,8 @@ static void virtual_mail_set_seq(struct 
 
 	bbox = virtual_backend_box_lookup(mbox, vrec->mailbox_id);
 	vmail->backend_mail = backend_mail_find(vmail, bbox->box);
-	if (vmail->backend_mail == NULL) {
-		backend_trans =
-			virtual_transaction_get(mail->transaction, bbox->box);
-
-		backend_headers = vmail->wanted_headers == NULL ? NULL :
-			mailbox_header_lookup_init(bbox->box,
-						vmail->wanted_headers->headers);
-		vmail->backend_mail = mail_alloc(backend_trans,
-						 vmail->wanted_fields,
-						 backend_headers);
-		if (backend_headers != NULL)
-			mailbox_header_lookup_unref(&backend_headers);
-		array_append(&vmail->backend_mails, &vmail->backend_mail, 1);
-	}
+	if (vmail->backend_mail == NULL)
+		virtual_mail_set_backend_mail(mail, bbox);
 	if (!mail_set_uid(vmail->backend_mail, vrec->real_uid))
 		i_unreached();
 	memset(&vmail->imail.data, 0, sizeof(vmail->imail.data));
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-save.c
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/plugins/virtual/virtual-save.c	Thu Feb 26 18:30:02 2009 -0500
@@ -0,0 +1,93 @@
+/* Copyright (c) 2009 Dovecot authors, see the included COPYING file */
+
+#include "lib.h"
+#include "virtual-transaction.h"
+#include "virtual-storage.h"
+
+struct virtual_save_context {
+	struct mail_save_context ctx;
+	struct mail_save_context *backend_save_ctx;
+};
+
+struct mail_save_context *
+virtual_save_alloc(struct mailbox_transaction_context *_t)
+{
+	struct virtual_transaction_context *t =
+		(struct virtual_transaction_context *)_t;
+	struct virtual_mailbox *mbox = (struct virtual_mailbox *)_t->box;
+	struct mailbox_transaction_context *backend_trans;
+	struct virtual_save_context *ctx;
+
+	if (t->save_ctx != NULL)
+		return &t->save_ctx->ctx;
+
+	ctx = t->save_ctx = i_new(struct virtual_save_context, 1);
+	ctx->ctx.transaction = &t->ictx.mailbox_ctx;
+
+	if (mbox->save_bbox != NULL) {
+		backend_trans =
+			virtual_transaction_get(_t, mbox->save_bbox->box);
+		ctx->backend_save_ctx = mailbox_save_alloc(backend_trans);
+	}
+	return &ctx->ctx;
+}
+
+int virtual_save_begin(struct mail_save_context *_ctx, struct istream *input)
+{
+	struct virtual_save_context *ctx = (struct virtual_save_context *)_ctx;
+	struct virtual_mailbox *mbox =
+		(struct virtual_mailbox *)_ctx->transaction->box;
+	struct mail *mail;
+
+	if (ctx->backend_save_ctx == NULL) {
+		mail_storage_set_error(_ctx->transaction->box->storage,
+			MAIL_ERROR_NOTPOSSIBLE,
+			"Can't save messages to this virtual mailbox");
+		return -1;
+	}
+
+	mailbox_save_set_flags(ctx->backend_save_ctx, _ctx->flags,
+			       _ctx->keywords);
+	mailbox_save_set_received_date(ctx->backend_save_ctx,
+				       _ctx->received_date,
+				       _ctx->received_tz_offset);
+	mailbox_save_set_from_envelope(ctx->backend_save_ctx,
+				       _ctx->from_envelope);
+	mailbox_save_set_guid(ctx->backend_save_ctx, _ctx->guid);
+
+	if (_ctx->dest_mail != NULL) {
+		mail = virtual_mail_set_backend_mail(_ctx->dest_mail,
+						     mbox->save_bbox);
+		mailbox_save_set_dest_mail(ctx->backend_save_ctx, mail);
+	}
+	return mailbox_save_begin(&ctx->backend_save_ctx, input);
+}
+
+int virtual_save_continue(struct mail_save_context *_ctx)
+{
+	struct virtual_save_context *ctx = (struct virtual_save_context *)_ctx;
+
+	return mailbox_save_continue(ctx->backend_save_ctx);
+}
+
+int virtual_save_finish(struct mail_save_context *_ctx)
+{
+	struct virtual_save_context *ctx = (struct virtual_save_context *)_ctx;
+
+	return mailbox_save_finish(&ctx->backend_save_ctx);
+}
+
+void virtual_save_cancel(struct mail_save_context *_ctx)
+{
+	struct virtual_save_context *ctx = (struct virtual_save_context *)_ctx;
+
+	if (ctx->backend_save_ctx != NULL)
+		mailbox_save_cancel(&ctx->backend_save_ctx);
+}
+
+void virtual_save_free(struct virtual_save_context *ctx)
+{
+	if (ctx->backend_save_ctx != NULL)
+		mailbox_save_cancel(&ctx->backend_save_ctx);
+	i_free(ctx);
+}
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-storage.c
--- a/src/plugins/virtual/virtual-storage.c	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/virtual-storage.c	Thu Feb 26 18:30:02 2009 -0500
@@ -10,6 +10,7 @@
 #include "mail-copy.h"
 #include "mail-search.h"
 #include "virtual-plugin.h"
+#include "virtual-transaction.h"
 #include "virtual-storage.h"
 
 #include <stdio.h>
@@ -668,11 +669,11 @@ struct mailbox virtual_mailbox = {
 		virtual_search_deinit,
 		virtual_search_next_nonblock,
 		virtual_search_next_update_seq,
-		NULL,
-		NULL,
-		NULL,
-		NULL,
-		NULL,
+		virtual_save_alloc,
+		virtual_save_begin,
+		virtual_save_continue,
+		virtual_save_finish,
+		virtual_save_cancel,
 		mail_storage_copy,
 		index_storage_is_inconsistent
 	}
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-storage.h
--- a/src/plugins/virtual/virtual-storage.h	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/virtual-storage.h	Thu Feb 26 18:30:02 2009 -0500
@@ -12,6 +12,8 @@
 
 #define VIRTUAL_CONTEXT(obj) \
 	MODULE_CONTEXT(obj, virtual_storage_module)
+
+struct virtual_save_context;
 
 struct virtual_mail_index_header {
 	/* Increased by one each time the header is modified */
@@ -108,6 +110,8 @@ struct virtual_mailbox {
 
 	/* Mailboxes this virtual mailbox consists of, sorted by mailbox_id */
 	ARRAY_TYPE(virtual_backend_box) backend_boxes;
+	/* backend mailbox where to save messages when saving to this mailbox */
+	struct virtual_backend_box *save_bbox;
 
 	ARRAY_TYPE(mailbox_virtual_patterns) list_include_patterns;
 	ARRAY_TYPE(mailbox_virtual_patterns) list_exclude_patterns;
@@ -129,9 +133,6 @@ virtual_backend_box_lookup_name(struct v
 virtual_backend_box_lookup_name(struct virtual_mailbox *mbox, const char *name);
 struct virtual_backend_box *
 virtual_backend_box_lookup(struct virtual_mailbox *mbox, uint32_t mailbox_id);
-struct mailbox_transaction_context *
-virtual_transaction_get(struct mailbox_transaction_context *trans,
-			struct mailbox *backend_box);
 
 struct mail_search_context *
 virtual_search_init(struct mailbox_transaction_context *t,
@@ -146,9 +147,20 @@ virtual_mail_alloc(struct mailbox_transa
 virtual_mail_alloc(struct mailbox_transaction_context *t,
 		   enum mail_fetch_field wanted_fields,
 		   struct mailbox_header_lookup_ctx *wanted_headers);
+struct mail *
+virtual_mail_set_backend_mail(struct mail *mail,
+			      struct virtual_backend_box *bbox);
 
 struct mailbox_sync_context *
 virtual_storage_sync_init(struct mailbox *box, enum mailbox_sync_flags flags);
+
+struct mail_save_context *
+virtual_save_alloc(struct mailbox_transaction_context *t);
+int virtual_save_begin(struct mail_save_context *ctx, struct istream *input);
+int virtual_save_continue(struct mail_save_context *ctx);
+int virtual_save_finish(struct mail_save_context *ctx);
+void virtual_save_cancel(struct mail_save_context *ctx);
+void virtual_save_free(struct virtual_save_context *ctx);
 
 void virtual_copy_error(struct mail_storage *dest, struct mail_storage *src);
 void virtual_box_copy_error(struct mailbox *dest, struct mailbox *src);
diff -r 7224c45d4719 -r 93c25cfe2760 src/plugins/virtual/virtual-transaction.c
--- a/src/plugins/virtual/virtual-transaction.c	Thu Feb 26 18:29:18 2009 -0500
+++ b/src/plugins/virtual/virtual-transaction.c	Thu Feb 26 18:30:02 2009 -0500
@@ -3,14 +3,7 @@
 #include "lib.h"
 #include "array.h"
 #include "virtual-storage.h"
-
-struct virtual_transaction_context {
-	struct index_transaction_context ictx;
-	union mail_index_transaction_module_context module_ctx;
-
-	ARRAY_DEFINE(backend_transactions,
-		     struct mailbox_transaction_context *);
-};
+#include "virtual-transaction.h"
 


More information about the dovecot-cvs mailing list