Hi there,
I ran into an issue yesterday (dovecot 2.0) whereby when we dsync messages from
a local machine (sdbox) to a remote (Maildir) which have different
pop3_uidl_formats configured, the uidl format is not preserved. There doesn't
seem to be any way to force this in the code, although I suspect that Maildir
sources with saved pop3 uidls would pass them correctly. Attached is a rough
patch against 2.0.21 dsync which will generate the uidls on the client before
passing them over to the destination. This only works for %u and %v currently,
also because dsync doesn't read the whole config file you need to specify -o
pop3_uidl_format=... to dsync.
Mark
--- dovecot-2.0.21/src/dsync/dsync-worker-local.c 2012-02-12 21:12:34.000000000 +0000
+++ dovecot-2.0.21.new/src/dsync/dsync-worker-local.c 2013-04-11 09:05:05.000000000 +0100
@@ -9,6 +9,7 @@
#include "istream.h"
#include "settings-parser.h"
#include "mailbox-log.h"
+#include "var-expand.h"
#include "mail-user.h"
#include "mail-namespace.h"
#include "mail-storage.h"
@@ -1832,7 +1833,16 @@
struct dsync_msg_static_data data;
struct mailbox_transaction_context *trans;
struct mailbox *box;
+ char uid_valid_str[MAX_INT_STRLEN];
+ char uid_str[MAX_INT_STRLEN];
+ struct mailbox_status status;
+
+ struct var_expand_table tab[] = {
+ { 'v', NULL, "uidvalidity" },
+ { 'u', NULL, "uid" },
+ };
+ string_t *str = t_str_new(128);
i_assert(!worker->reading_mail);
if (!dsync_guid_equals(&worker->get_mailbox, &get->mailbox)) {
@@ -1864,7 +1874,19 @@
DSYNC_MSG_GET_RESULT_FAILED, NULL, get->context);
} else {
worker->reading_mail = TRUE;
+ if( data.pop3_uidl[0] == '\0' ) {
+ mailbox_get_status(worker->get_mail->box, STATUS_UIDVALIDITY, &status);
+ i_snprintf(uid_valid_str, sizeof(uid_valid_str), "%u", status.uidvalidity);
+ tab[0].value = uid_valid_str;
+ i_snprintf(uid_str, sizeof(uid_str), "%u", get->uid);
+ tab[1].value = uid_str;
+ const struct mail_storage_settings *set = mailbox_get_settings( worker->get_mail->box );
+
+ var_expand(str, set->pop3_uidl_format, tab);
+ data.pop3_uidl = str_c( str );
+ } else
data.pop3_uidl = t_strdup(data.pop3_uidl);
+
data.input = i_stream_create_limit(data.input, (uoff_t)-1);
i_stream_set_destroy_callback(data.input,
local_worker_msg_get_done,