]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
doveadm: Added doveadm_proxy_port setting to make it work with proxying.
authorTimo Sirainen <tss@iki.fi>
Fri, 20 May 2011 10:05:16 +0000 (13:05 +0300)
committerTimo Sirainen <tss@iki.fi>
Fri, 20 May 2011 10:05:16 +0000 (13:05 +0300)
src/doveadm/Makefile.am
src/doveadm/doveadm-mail-server.c
src/doveadm/doveadm-mail.c
src/doveadm/doveadm-mail.h
src/doveadm/doveadm-settings.c
src/doveadm/doveadm-settings.h
src/doveadm/main.c

index 29d0b6b06ed90bcf0ccd8e6ea83d2ad781759407..b05250b9b85d488996d981169ef542a6eb1dc478 100644 (file)
@@ -70,9 +70,11 @@ common = \
        doveadm-mail-move.c \
        doveadm-mail-list-iter.c \
        doveadm-mail-search.c \
+       doveadm-mail-server.c \
        doveadm-print.c \
        doveadm-settings.c \
-       doveadm-util.c
+       doveadm-util.c \
+       server-connection.c
 
 doveadm_SOURCES = \
        $(common) \
@@ -87,7 +89,6 @@ doveadm_SOURCES = \
        doveadm-kick.c \
        doveadm-log.c \
        doveadm-master.c \
-       doveadm-mail-server.c \
        doveadm-mutf7.c \
        doveadm-penalty.c \
        doveadm-print-flow.c \
@@ -96,8 +97,7 @@ doveadm_SOURCES = \
        doveadm-print-table.c \
        doveadm-pw.c \
        doveadm-sis.c \
-       doveadm-who.c \
-       server-connection.c
+       doveadm-who.c
 
 doveadm_server_SOURCES = \
        $(common) \
index b2c12f136c09b682cd0b4dddd922a19885a4f184..06a17dfc9df5e47b2308982267d73e06eb294d24 100644 (file)
@@ -7,6 +7,7 @@
 #include "strescape.h"
 #include "ioloop.h"
 #include "master-service.h"
+#include "auth-master.h"
 #include "mail-storage.h"
 #include "mail-storage-service.h"
 #include "server-connection.h"
@@ -142,33 +143,74 @@ static void doveadm_server_flush_one(struct doveadm_server *server)
                 !DOVEADM_MAIL_SERVER_FAILED());
 }
 
-static const char *userdb_field_find(const char *const *fields, const char *key)
+static int
+doveadm_mail_server_user_get_host(struct doveadm_mail_cmd_context *ctx,
+                                 const char *username, const char **host_r,
+                                 const char **error_r)
 {
-       unsigned int i, len = strlen(key);
-
-       if (fields == NULL)
-               return NULL;
-
-       for (i = 0; fields[i] != NULL; i++) {
-               if (strncmp(fields[i], key, len) == 0) {
-                       if (fields[i][len] == '\0')
-                               return "";
-                       if (fields[i][len] == '=')
-                               return fields[i]+len+1;
+       struct mail_storage_service_input input;
+       struct auth_master_connection *auth_conn;
+       struct auth_user_info info;
+       pool_t pool;
+       const char *proxy_host, *const *fields;
+       unsigned int i;
+       bool proxying;
+       int ret;
+
+       *host_r = doveadm_settings->doveadm_socket_path;
+
+       if (doveadm_settings->doveadm_proxy_port == 0)
+               return 0;
+
+       /* make sure we have an auth connection */
+       memset(&input, 0, sizeof(input));
+       input.service = "doveadm";
+       mail_storage_service_init_settings(ctx->storage_service, &input);
+
+       memset(&info, 0, sizeof(info));
+       info.service = master_service_get_name(master_service);
+
+       pool = pool_alloconly_create("auth lookup", 1024);
+       auth_conn = mail_storage_service_get_auth_conn(ctx->storage_service);
+       ret = auth_master_pass_lookup(auth_conn, username, &info,
+                                     pool, &fields);
+       if (ret < 0) {
+               *error_r = fields[0] != NULL ?
+                       t_strdup(fields[0]) : "passdb lookup failed";
+       } else if (ret == 0) {
+               /* user not found from passdb. it could be in userdb though,
+                  so just continue with the default host */
+       } else {
+               proxy_host = NULL;
+               for (i = 0; fields[i] != NULL; i++) {
+                       if (strncmp(fields[i], "proxy", 5) == 0 &&
+                           (fields[i][5] == '\0' || fields[i][5] == '='))
+                               proxying = TRUE;
+                       else if (strncmp(fields[i], "host=", 5) == 0)
+                               proxy_host = fields[i]+5;
+               }
+               if (!proxying)
+                       ret = 0;
+               else if (proxy_host == NULL) {
+                       *error_r = "Proxy is missing destination host";
+                       ret = -1;
+               } else {
+                       *host_r = t_strdup_printf("%s:%u", proxy_host,
+                                       doveadm_settings->doveadm_proxy_port);
                }
        }
-       return NULL;
+       pool_unref(&pool);
+       return ret;
 }
 
 int doveadm_mail_server_user(struct doveadm_mail_cmd_context *ctx,
-                            struct mail_storage_service_user *user,
-                            const char **error_r)
+                            const char *username, const char **error_r)
 {
-       const struct mail_storage_service_input *input;
        struct doveadm_server *server;
        struct server_connection *conn;
        const char *host;
        char *username_dup;
+       int ret;
 
        i_assert(cmd_ctx == ctx || cmd_ctx == NULL);
        cmd_ctx = ctx;
@@ -177,34 +219,32 @@ int doveadm_mail_server_user(struct doveadm_mail_cmd_context *ctx,
           so undo any sticks we might have added already */
        doveadm_print_unstick_headers();
 
-       input = mail_storage_service_user_get_input(user);
-       if (userdb_field_find(input->userdb_fields, "proxy") != NULL) {
-               host = userdb_field_find(input->userdb_fields, "host");
-               if (host == NULL) {
-                       *error_r = "Proxy is missing destination host";
-                       return -1;
-               }
-       } else {
-               host = doveadm_settings->doveadm_socket_path;
+       ret = doveadm_mail_server_user_get_host(ctx, username, &host, error_r);
+       if (ret < 0)
+               return -1;
+       if (ret == 0 &&
+           (doveadm_settings->doveadm_worker_count == 0 || doveadm_server)) {
+               /* run it ourself */
+               return 0;
        }
 
        server = doveadm_server_get(host);
        conn = doveadm_server_find_unused_conn(server);
        if (conn != NULL)
-               doveadm_mail_server_handle(conn, input->username);
+               doveadm_mail_server_handle(conn, username);
        else if (array_count(&server->connections) <
-                       doveadm_settings->doveadm_worker_count) {
+                       I_MAX(doveadm_settings->doveadm_worker_count, 1)) {
                conn = server_connection_create(server);
-               doveadm_mail_server_handle(conn, input->username);
+               doveadm_mail_server_handle(conn, username);
        } else {
                if (array_count(&server->queue) >= DOVEADM_SERVER_QUEUE_MAX)
                        doveadm_server_flush_one(server);
 
-               username_dup = i_strdup(input->username);
+               username_dup = i_strdup(username);
                array_append(&server->queue, &username_dup, 1);
        }
        *error_r = "doveadm server failure";
-       return DOVEADM_MAIL_SERVER_FAILED() ? -1 : 0;
+       return DOVEADM_MAIL_SERVER_FAILED() ? -1 : 1;
 }
 
 static struct doveadm_server *doveadm_server_find_used(void)
index d5747147d593d50ebe85f5a5a99e7a842628526a..8fd5e5d1efd3a30ee82afab291b6715cb354e11a 100644 (file)
@@ -193,6 +193,12 @@ doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx,
 
        i_set_failure_prefix(t_strdup_printf("doveadm(%s): ", input->username));
 
+       /* see if we want to execute this command via (another)
+          doveadm server */
+       ret = doveadm_mail_server_user(ctx, input->username, error_r);
+       if (ret != 0)
+               return ret;
+
        ret = mail_storage_service_lookup(ctx->storage_service, input,
                                          &service_user, &error);
        if (ret <= 0) {
@@ -203,13 +209,6 @@ doveadm_mail_next_user(struct doveadm_mail_cmd_context *ctx,
                return ret;
        }
 
-       if (doveadm_settings->doveadm_worker_count > 0 && !doveadm_server) {
-               /* execute this command via doveadm server */
-               ret = doveadm_mail_server_user(ctx, service_user, error_r);
-               mail_storage_service_user_free(&service_user);
-               return ret < 0 ? -1 : 1;
-       }
-
        ret = mail_storage_service_next(ctx->storage_service, service_user,
                                        &ctx->cur_mail_user);
        if (ret < 0) {
index f53e5ddd150d58934f0a6c5bbbd5e0ca10421c4f..a442418e5a8ad67fac9d055caaf395dc282c9ac7 100644 (file)
@@ -85,8 +85,7 @@ void doveadm_mail_single_user(struct doveadm_mail_cmd_context *ctx,
                              char *argv[], const char *username,
                              enum mail_storage_service_flags service_flags);
 int doveadm_mail_server_user(struct doveadm_mail_cmd_context *ctx,
-                            struct mail_storage_service_user *user,
-                            const char **error_r);
+                            const char *username, const char **error_r);
 void doveadm_mail_server_flush(void);
 
 int doveadm_mailbox_find_and_sync(struct mail_user *user, const char *mailbox,
index 521d8643c9b92e5c31928da6ee1cdfa1b79a2b00..e4ae8ea6221bf9dd03260d2dcd3759421657ac8c 100644 (file)
@@ -57,6 +57,7 @@ static const struct setting_define doveadm_setting_defines[] = {
        DEF(SET_STR, mail_plugin_dir),
        DEF(SET_STR, doveadm_socket_path),
        DEF(SET_UINT, doveadm_worker_count),
+       DEF(SET_UINT, doveadm_proxy_port),
 
        { SET_STRLIST, "plugin", offsetof(struct doveadm_settings, plugin_envs), NULL },
 
@@ -69,6 +70,7 @@ const struct doveadm_settings doveadm_default_settings = {
        .mail_plugin_dir = MODULEDIR,
        .doveadm_socket_path = "doveadm-server",
        .doveadm_worker_count = 0,
+       .doveadm_proxy_port = 0,
 
        .plugin_envs = ARRAY_INIT
 };
index 511510eef8aa6fc708878d5509b71670352b79b9..2b2eb4232a334e1068cbb6d7627aacefaf48231f 100644 (file)
@@ -7,6 +7,7 @@ struct doveadm_settings {
        const char *mail_plugin_dir;
        const char *doveadm_socket_path;
        unsigned int doveadm_worker_count;
+       unsigned int doveadm_proxy_port;
 
        ARRAY_DEFINE(plugin_envs, const char *);
 };
index 494bd1d1e09336025df7f34aca5ca6c299fc112c..daade734b2bb249fbbd8c0c6b5216ab1a4773f08 100644 (file)
@@ -18,17 +18,6 @@ const struct doveadm_print_vfuncs *doveadm_print_vfuncs_all[] = {
 
 struct client_connection *doveadm_client;
 
-int doveadm_mail_server_user(struct doveadm_mail_cmd_context *ctx ATTR_UNUSED,
-                            struct mail_storage_service_user *user ATTR_UNUSED,
-                            const char **error_r ATTR_UNUSED)
-{
-       /* this function should be called only by doveadm client code */
-       i_unreached();
-}
-void doveadm_mail_server_flush(void)
-{
-}
-
 static void doveadm_die(void)
 {
        /* do nothing. doveadm connections should be over soon. */