[dovecot-cvs] dovecot/src/imap cmd-copy.c,1.8,1.9

cras at procontrol.fi cras at procontrol.fi
Wed Jul 23 04:40:52 EEST 2003


Update of /home/cvs/dovecot/src/imap
In directory danu:/tmp/cvs-serv408/imap

Modified Files:
	cmd-copy.c 
Log Message:
API change for copying messages.



Index: cmd-copy.c
===================================================================
RCS file: /home/cvs/dovecot/src/imap/cmd-copy.c,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -d -r1.8 -r1.9
--- cmd-copy.c	15 Jul 2003 18:26:42 -0000	1.8
+++ cmd-copy.c	23 Jul 2003 00:40:49 -0000	1.9
@@ -3,11 +3,39 @@
 #include "common.h"
 #include "commands.h"
 
+static int fetch_and_copy(struct mail_copy_context *copy_ctx,
+			  struct mailbox *box, const char *messageset,
+			  int uidset, int *all_found)
+{
+	struct mail_fetch_context *fetch_ctx;
+	struct mail *mail;
+	int failed = FALSE;
+
+	fetch_ctx = box->fetch_init(box, MAIL_FETCH_STREAM_HEADER |
+				    MAIL_FETCH_STREAM_BODY, NULL,
+				    messageset, uidset);
+	if (fetch_ctx == NULL)
+		return FALSE;
+
+	while ((mail = box->fetch_next(fetch_ctx)) != NULL) {
+		if (!mail->copy(mail, copy_ctx)) {
+			failed = TRUE;
+			break;
+		}
+	}
+
+	if (!box->fetch_deinit(fetch_ctx, all_found))
+		return FALSE;
+
+	return !failed;
+}
+
 int cmd_copy(struct client *client)
 {
 	struct mailbox *destbox;
+        struct mail_copy_context *copy_ctx;
 	const char *messageset, *mailbox;
-	int ret;
+	int failed = FALSE, all_found = TRUE;
 
 	/* <message set> <mailbox> */
 	if (!client_read_string_args(client, 2, &messageset, &mailbox))
@@ -28,17 +56,31 @@
 		return TRUE;
 	}
 
-	/* copy the mail */
-	ret = client->mailbox->copy(client->mailbox, destbox,
-				    messageset, client->cmd_uid);
+	/* FIXME: copying from mailbox to itself is kind of kludgy here.
+	   currently it works simply because copy_init() will lock mbox
+	   exclusively and fetching wont drop it. */
+	copy_ctx = destbox->copy_init(destbox);
+	if (copy_ctx == NULL)
+		failed = TRUE;
+	else {
+		if (!fetch_and_copy(copy_ctx, client->mailbox,
+				    messageset, client->cmd_uid, &all_found))
+			failed = TRUE;
 
-	if (ret) {
+		if (!destbox->copy_deinit(copy_ctx, failed || !all_found))
+			failed = TRUE;
+	}
+
+	if (failed)
+		client_send_storage_error(client);
+	else if (!all_found) {
+		/* some messages were expunged, sync them */
+		client_sync_full(client);
+		client_send_tagline(client,
+			"NO Some of the requested messages no longer exist.");
+	} else {
 		client_sync_full_fast(client);
 		client_send_tagline(client, "OK Copy completed.");
-	} else {
-		/* if COPY fails because of expunges they'll get synced here */
-		client_sync_full(client);
-		client_send_storage_error(client);
 	}
 
 	destbox->close(destbox);



More information about the dovecot-cvs mailing list