]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-storage: Replace MAILBOXDIR with mailbox_root_directory_name setting
authorTimo Sirainen <timo.sirainen@open-xchange.com>
Fri, 27 Oct 2023 10:40:25 +0000 (13:40 +0300)
committerAki Tuomi <aki.tuomi@open-xchange.com>
Wed, 12 Feb 2025 10:34:10 +0000 (12:34 +0200)
13 files changed:
src/lib-storage/index/dbox-common/dbox-storage.c
src/lib-storage/index/dbox-common/dbox-storage.h
src/lib-storage/index/dbox-multi/mdbox-settings.c
src/lib-storage/index/dbox-multi/mdbox-storage.c
src/lib-storage/index/dbox-single/sdbox-settings.c
src/lib-storage/index/index-storage.c
src/lib-storage/list/mailbox-list-fs-iter.c
src/lib-storage/list/mailbox-list-fs.c
src/lib-storage/list/mailbox-list-index-backend.c
src/lib-storage/mail-storage-settings.c
src/lib-storage/mail-storage-settings.h
src/lib-storage/mailbox-list.c
src/lib-storage/mailbox-list.h

index 757e629c0b33d7793d7adc3cf675e1f0656c1271..94ad50b7f33e58b1c17b52eb114a2d974a45829b 100644 (file)
@@ -27,8 +27,6 @@ void dbox_storage_get_list_settings(const struct mail_namespace *ns ATTR_UNUSED,
                set->subscription_fname = DBOX_SUBSCRIPTION_FILE_NAME;
        if (*set->maildir_name == '\0')
                set->maildir_name = DBOX_MAILDIR_NAME;
-       if (*set->mailbox_dir_name == '\0')
-               set->mailbox_dir_name = DBOX_MAILBOX_DIR_NAME;
 }
 
 static bool
@@ -257,7 +255,7 @@ int dbox_mailbox_check_existence(struct mailbox *box)
                ret = stat(box_path, &st);
        } else if (ret == 0 &&
                   !box->list->mail_set->mailbox_list_iter_from_index_dir &&
-                  *box->list->set.mailbox_dir_name == '\0') {
+                  *box->list->mail_set->parsed_mailbox_root_directory_prefix == '\0') {
                /* There are index files for this mailbox and no separate
                mailboxes directory is configured. */
                return 0;
index dc67dd25c52bb9105fc64ddc4367e7107e812c7a..ba186fbcac60561a4794fbafd0a08e9c352c1805 100644 (file)
@@ -13,8 +13,10 @@ struct dbox_save_context;
 #define DBOX_TEMP_FILE_PREFIX ".temp."
 #define DBOX_ALT_SYMLINK_NAME "dbox-alt-root"
 
+/* <settings checks> */
 #define DBOX_MAILBOX_DIR_NAME "mailboxes"
 #define DBOX_MAILDIR_NAME "dbox-Mails"
+/* </settings checks> */
 
 /* Delete temp files having ctime older than this. */
 #define DBOX_TMP_DELETE_SECS (36*60*60)
index b47846386b5c2b186d9e84cdd740376210bc95c9..f08b40f701ab6e0691242075c35901769fe958a1 100644 (file)
@@ -3,6 +3,7 @@
 #include "lib.h"
 #include "settings-parser.h"
 #include "mail-storage-settings.h"
+#include "dbox-storage.h"
 #include "mdbox-settings.h"
 
 #undef DEF
@@ -24,11 +25,17 @@ static const struct mdbox_settings mdbox_default_settings = {
        .mdbox_rotate_interval = 0
 };
 
+static const struct setting_keyvalue mdbox_default_filter_settings_keyvalue[] = {
+       { "mdbox/mailbox_root_directory_name", DBOX_MAILBOX_DIR_NAME },
+       { NULL, NULL }
+};
+
 const struct setting_parser_info mdbox_setting_parser_info = {
        .name = "mdbox",
 
        .defines = mdbox_setting_defines,
        .defaults = &mdbox_default_settings,
+       .default_filter_settings = mdbox_default_filter_settings_keyvalue,
 
        .struct_size = sizeof(struct mdbox_settings),
        .pool_offset1 = 1 + offsetof(struct mdbox_settings, pool),
index 2d3a65cb43847de848ce6774d4526ed330889920..4278c95bb894f7c1ccf3a35e108d1447c64a6f7c 100644 (file)
@@ -51,8 +51,8 @@ int mdbox_storage_create(struct mail_storage *_storage,
 
        storage->preallocate_space = storage->set->mdbox_preallocate_space;
 
-       if (*ns->list->set.mailbox_dir_name == '\0') {
-               *error_r = "mdbox: MAILBOXDIR must not be empty";
+       if (*ns->list->mail_set->mailbox_root_directory_name == '\0') {
+               *error_r = "mdbox: mailbox_root_directory_name must not be empty";
                return -1;
        }
 
index 8e26bf6328c42c599a26766a7fb426b25c5ad3b1..388f5da478d7292533fa326e5947bc65e4794440 100644 (file)
@@ -14,11 +14,17 @@ static const struct setting_define sdbox_setting_defines[] = {
 static const struct sdbox_settings sdbox_default_settings = {
 };
 
+static const struct setting_keyvalue sdbox_default_filter_settings_keyvalue[] = {
+       { "sdbox/mailbox_root_directory_name", DBOX_MAILBOX_DIR_NAME },
+       { NULL, NULL }
+};
+
 const struct setting_parser_info sdbox_setting_parser_info = {
        .name = "sdbox",
 
        .defines = sdbox_setting_defines,
        .defaults = &sdbox_default_settings,
+       .default_filter_settings = sdbox_default_filter_settings_keyvalue,
 
        .struct_size = sizeof(struct sdbox_settings),
        .pool_offset1 = 1 + offsetof(struct sdbox_settings, pool),
index c88b7566bf55be051aa525155ba4f61999cee7d7..7d59292fbe3f4b77cf6928030f109588e0726a3f 100644 (file)
@@ -681,7 +681,7 @@ int index_storage_mailbox_create(struct mailbox *box, bool directory)
                /* directory already exists */
                if (create_parent_dir)
                        return 1;
-               if (!directory && *box->list->set.mailbox_dir_name == '\0') {
+               if (!directory && *box->list->mail_set->mailbox_root_directory_name == '\0') {
                        /* For example: layout=fs, path=~/Maildir/foo
                           might itself exist, but does it have the
                           cur|new|tmp subdirs? */
index c594a042c26c2cc36cf84ecd112f1a8917dddf14..1f811dd65358f5417ae6614b9b547fee2c168bd6 100644 (file)
@@ -259,6 +259,8 @@ fs_list_get_storage_path(struct fs_list_iterate_context *ctx,
        }
        if (*path != '/') {
                /* non-absolute path. add the mailbox root dir as prefix. */
+               const struct mail_storage_settings *set =
+                       ctx->ctx.list->mail_set;
                enum mailbox_list_path_type type =
                        ctx->ctx.iter_from_index_dir ?
                        MAILBOX_LIST_PATH_TYPE_INDEX :
@@ -266,10 +268,10 @@ fs_list_get_storage_path(struct fs_list_iterate_context *ctx,
                if (!mailbox_list_get_root_path(ctx->ctx.list, type, &root))
                        return FALSE;
                if (ctx->ctx.iter_from_index_dir &&
-                   ctx->ctx.list->set.mailbox_dir_name[0] != '\0') {
+                   set->parsed_mailbox_root_directory_prefix[0] != '\0') {
                        /* append "mailboxes/" to the index root */
                        root = t_strconcat(root, "/",
-                               ctx->ctx.list->set.mailbox_dir_name, NULL);
+                               set->parsed_mailbox_root_directory_prefix, NULL);
                }
                path = *path == '\0' ? root :
                        t_strconcat(root, "/", path, NULL);
index 4b05d159730aff300a85353e1395cd3cb9d7f961..cd6713413a02fbaf73b95954a0f7351144294128 100644 (file)
@@ -47,16 +47,19 @@ static char fs_list_get_hierarchy_sep(struct mailbox_list *list ATTR_UNUSED)
 }
 
 static const char *
-fs_list_get_path_to(const struct mailbox_list_settings *set,
+fs_list_get_path_to(struct mailbox_list *list,
                    const char *root_dir, const char *name)
 {
+       const struct mailbox_list_settings *set = &list->set;
+
        if (*set->maildir_name != '\0' && set->index_control_use_maildir_name) {
                return t_strdup_printf("%s/%s%s/%s", root_dir,
-                                      set->mailbox_dir_name, name,
-                                      set->maildir_name);
+                       list->mail_set->parsed_mailbox_root_directory_prefix,
+                       name, set->maildir_name);
        } else {
                return t_strdup_printf("%s/%s%s", root_dir,
-                                      set->mailbox_dir_name, name);
+                       list->mail_set->parsed_mailbox_root_directory_prefix,
+                       name);
        }
 }
 
@@ -65,6 +68,7 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
                 enum mailbox_list_path_type type, const char **path_r)
 {
        const struct mailbox_list_settings *set = &_list->set;
+       const struct mail_storage_settings *mail_set = _list->mail_set;
        const char *root_dir, *error;
 
        if (name == NULL) {
@@ -88,7 +92,8 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
        case MAILBOX_LIST_PATH_TYPE_DIR:
                if (*set->maildir_name != '\0') {
                        *path_r = t_strdup_printf("%s/%s%s", set->root_dir,
-                                                 set->mailbox_dir_name, name);
+                               mail_set->parsed_mailbox_root_directory_prefix,
+                               name);
                        return 1;
                }
                break;
@@ -99,7 +104,8 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
                        /* maildir_name is for the mailbox, caller is asking
                           for the directory name */
                        *path_r = t_strdup_printf("%s/%s%s", set->alt_dir,
-                                                 set->mailbox_dir_name, name);
+                               mail_set->parsed_mailbox_root_directory_prefix,
+                               name);
                        return 1;
                }
                root_dir = set->alt_dir;
@@ -113,13 +119,13 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
                break;
        case MAILBOX_LIST_PATH_TYPE_CONTROL:
                if (set->control_dir != NULL) {
-                       *path_r = fs_list_get_path_to(set, set->control_dir, name);
+                       *path_r = fs_list_get_path_to(_list, set->control_dir, name);
                        return 1;
                }
                break;
        case MAILBOX_LIST_PATH_TYPE_INDEX_CACHE:
                if (set->index_cache_dir != NULL) {
-                       *path_r = fs_list_get_path_to(set, set->index_cache_dir, name);
+                       *path_r = fs_list_get_path_to(_list, set->index_cache_dir, name);
                        return 1;
                }
                /* fall through */
@@ -127,14 +133,14 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
                if (set->index_dir != NULL) {
                        if (*set->index_dir == '\0')
                                return 0;
-                       *path_r = fs_list_get_path_to(set, set->index_dir, name);
+                       *path_r = fs_list_get_path_to(_list, set->index_dir, name);
                        return 1;
                }
                break;
        case MAILBOX_LIST_PATH_TYPE_INDEX_PRIVATE:
                if (set->index_pvt_dir == NULL)
                        return 0;
-               *path_r = fs_list_get_path_to(set, set->index_pvt_dir, name);
+               *path_r = fs_list_get_path_to(_list, set->index_pvt_dir, name);
                return 1;
        case MAILBOX_LIST_PATH_TYPE_LIST_INDEX:
        case MAILBOX_LIST_PATH_TYPE_COUNT:
@@ -159,11 +165,11 @@ fs_list_get_path(struct mailbox_list *_list, const char *name,
                return 0;
        if (*set->maildir_name == '\0') {
                *path_r = t_strdup_printf("%s/%s%s", root_dir,
-                                         set->mailbox_dir_name, name);
+                       mail_set->parsed_mailbox_root_directory_prefix, name);
        } else {
                *path_r = t_strdup_printf("%s/%s%s/%s", root_dir,
-                                         set->mailbox_dir_name, name,
-                                         set->maildir_name);
+                       mail_set->parsed_mailbox_root_directory_prefix,
+                       name, set->maildir_name);
        }
        return 1;
 }
@@ -228,7 +234,7 @@ fs_list_delete_maildir(struct mailbox_list *list, const char *name)
        int ret;
 
        if (*list->set.maildir_name != '\0' &&
-           *list->set.mailbox_dir_name != '\0') {
+           *list->mail_set->parsed_mailbox_root_directory_prefix != '\0') {
                trash_dir = mailbox_list_fs_get_trash_dir(list);
                ret = mailbox_list_delete_maildir_via_trash(list, name,
                                                            trash_dir);
index 08334f6cb9a16743b64cee9b851d058fea9b38a9..443f3a7ecb8bdd919133a85ec2292381b259f41b 100644 (file)
@@ -110,8 +110,8 @@ index_get_guid_path(struct mailbox_list *_list, const char *root_dir,
                    const guid_128_t mailbox_guid)
 {
        return t_strdup_printf("%s/%s%s", root_dir,
-                              _list->set.mailbox_dir_name,
-                              guid_128_to_string(mailbox_guid));
+               _list->mail_set->parsed_mailbox_root_directory_prefix,
+               guid_128_to_string(mailbox_guid));
 }
 
 static int
index 73cc2c91c025e2a8b3391437bf7c5495df61ece0..e47e24689e319d7e80c307384ac1c9d77f1e4caf 100644 (file)
@@ -80,6 +80,7 @@ static const struct setting_define mail_storage_setting_defines[] = {
        DEF(BOOL_HIDDEN, mailbox_list_iter_from_index_dir),
        DEF(BOOL_HIDDEN, mailbox_list_drop_noselect),
        DEF(BOOL_HIDDEN, mailbox_list_validate_fs_names),
+       DEF(STR_HIDDEN, mailbox_root_directory_name),
        DEF(STR, mail_volatile_path),
        DEF(BOOL_HIDDEN, mail_full_filesystem_access),
        DEF(BOOL, maildir_stat_dirs),
@@ -145,6 +146,7 @@ const struct mail_storage_settings mail_storage_default_settings = {
        .mailbox_list_iter_from_index_dir = FALSE,
        .mailbox_list_drop_noselect = TRUE,
        .mailbox_list_validate_fs_names = TRUE,
+       .mailbox_root_directory_name = "",
        .mail_volatile_path = "",
        .mail_full_filesystem_access = FALSE,
        .maildir_stat_dirs = FALSE,
@@ -727,6 +729,15 @@ mail_storage_settings_ext_check(struct event *event, void *_set, pool_t pool,
                }
 #endif
        }
+       if (set->mailbox_root_directory_name[0] == '\0')
+               set->parsed_mailbox_root_directory_prefix = "";
+       else if (strchr(set->mailbox_root_directory_name, '/') != NULL) {
+               *error_r = "mailbox_root_directory_name must not contain '/'";
+               return FALSE;
+       } else {
+               set->parsed_mailbox_root_directory_prefix = p_strconcat(pool,
+                       set->mailbox_root_directory_name, "/", NULL);
+       }
 
        if (!mail_storage_settings_check_namespaces(event, set, error_r))
                return FALSE;
@@ -974,6 +985,7 @@ static const size_t mail_storage_2nd_reset_offsets[] = {
        OFFSET(mail_location),
        OFFSET(mailbox_list_index_prefix),
        OFFSET(mailbox_list_iter_from_index_dir),
+       OFFSET(mailbox_root_directory_name),
        OFFSET(mail_volatile_path),
 };
 
index 06d5a0f588ab80cf48819066cfbc0922fe160b6d..4ef742b8c7e55dd7a200130e6ffc6ff14dded135 100644 (file)
@@ -60,6 +60,7 @@ struct mail_storage_settings {
        bool mailbox_list_iter_from_index_dir;
        bool mailbox_list_drop_noselect;
        bool mailbox_list_validate_fs_names;
+       const char *mailbox_root_directory_name;
        const char *mail_volatile_path;
        bool mail_full_filesystem_access;
        bool maildir_stat_dirs;
@@ -89,6 +90,9 @@ struct mail_storage_settings {
        /* Directory part of mailbox_list_index_prefix. NULL defaults to index
           directory. The path may be relative to the index directory. */
        const char *parsed_list_index_dir;
+       /* If set, store mailboxes under root_dir/mailbox_dir_name/.
+          This setting contains either "" or "dir/" with trailing "/". */
+       const char *parsed_mailbox_root_directory_prefix;
 
        const char *unexpanded_mailbox_list_path[MAILBOX_LIST_PATH_TYPE_COUNT];
        bool unexpanded_mailbox_list_override[MAILBOX_LIST_PATH_TYPE_COUNT];
index cfa4a903d0ebec1d946b2f68d451766ec13734fb..1f86878484767198738c962df2453f3c9b1f4234 100644 (file)
@@ -178,22 +178,11 @@ int mailbox_list_create(const char *driver, struct event *event,
                p_strdup(list->pool, set->subscription_fname);
        list->set.maildir_name =
                p_strdup(list->pool, set->maildir_name);
-       list->set.mailbox_dir_name =
-               p_strdup(list->pool, set->mailbox_dir_name);
        list->set.alt_dir = p_strdup(list->pool, set->alt_dir);
        list->set.alt_dir_nocheck = set->alt_dir_nocheck;
        list->set.index_control_use_maildir_name =
                set->index_control_use_maildir_name;
 
-       if (*set->mailbox_dir_name == '\0')
-               list->set.mailbox_dir_name = "";
-       else if (set->mailbox_dir_name[strlen(set->mailbox_dir_name)-1] == '/') {
-               list->set.mailbox_dir_name =
-                       p_strdup(list->pool, set->mailbox_dir_name);
-       } else {
-               list->set.mailbox_dir_name =
-                       p_strconcat(list->pool, set->mailbox_dir_name, "/", NULL);
-       }
        if (set->storage_name_escape_char != '\0')
                list->set.storage_name_escape_char = set->storage_name_escape_char;
        list->set.vname_escape_char = set->vname_escape_char;
@@ -273,7 +262,6 @@ static const char *split_next_arg(const char *const **_args)
 void mailbox_list_settings_init_defaults(struct mailbox_list_settings *set_r)
 {
        i_zero(set_r);
-       set_r->mailbox_dir_name = "";
        set_r->maildir_name = "";
 }
 
@@ -342,8 +330,6 @@ mailbox_list_settings_parse_full(struct mail_user *user, const char *data,
                        dest = &set_r->subscription_fname;
                else if (strcmp(key, "DIRNAME") == 0)
                        dest = &set_r->maildir_name;
-               else if (strcmp(key, "MAILBOXDIR") == 0)
-                       dest = &set_r->mailbox_dir_name;
                else if (strcmp(key, "FULLDIRNAME") == 0) {
                        set_r->index_control_use_maildir_name = TRUE;
                        dest = &set_r->maildir_name;
@@ -379,6 +365,7 @@ int mailbox_list_settings_parse(struct mail_user *user, const char *data,
 
 static bool
 mailbox_list_set_get_root_path(const struct mailbox_list_settings *set,
+                              const char *parsed_mailbox_root_directory_prefix,
                               enum mailbox_list_path_type type,
                               const char **path_r);
 
@@ -418,7 +405,9 @@ const char *mailbox_list_get_unexpanded_path(struct mailbox_list *list,
        default:
                break;
        }
-       if (!mailbox_list_set_get_root_path(&set, type, &path))
+       if (!mailbox_list_set_get_root_path(&set,
+                       list->mail_set->parsed_mailbox_root_directory_prefix,
+                       type, &path))
                return "";
        return path;
 }
@@ -1415,6 +1404,7 @@ const char *mailbox_list_get_root_forced(struct mailbox_list *list,
 
 static bool
 mailbox_list_set_get_root_path(const struct mailbox_list_settings *set,
+                              const char *parsed_mailbox_root_directory_prefix,
                               enum mailbox_list_path_type type,
                               const char **path_r)
 {
@@ -1428,20 +1418,20 @@ mailbox_list_set_get_root_path(const struct mailbox_list_settings *set,
                path = set->alt_dir;
                break;
        case MAILBOX_LIST_PATH_TYPE_MAILBOX:
-               if (*set->mailbox_dir_name == '\0')
+               if (*parsed_mailbox_root_directory_prefix == '\0')
                        path = set->root_dir;
                else {
                        path = t_strconcat(set->root_dir, "/",
-                                          set->mailbox_dir_name, NULL);
+                               parsed_mailbox_root_directory_prefix, NULL);
                        path = t_strndup(path, strlen(path)-1);
                }
                break;
        case MAILBOX_LIST_PATH_TYPE_ALT_MAILBOX:
-               if (*set->mailbox_dir_name == '\0')
+               if (*parsed_mailbox_root_directory_prefix == '\0')
                        path = set->alt_dir;
                else if (set->alt_dir != NULL) {
                        path = t_strconcat(set->alt_dir, "/",
-                                          set->mailbox_dir_name, NULL);
+                               parsed_mailbox_root_directory_prefix, NULL);
                        path = t_strndup(path, strlen(path)-1);
                }
                break;
@@ -1495,6 +1485,7 @@ bool mailbox_list_default_get_root_path(struct mailbox_list *list,
                        }
                        /* relative path */
                        if (!mailbox_list_set_get_root_path(&list->set,
+                                       list->mail_set->parsed_mailbox_root_directory_prefix,
                                        MAILBOX_LIST_PATH_TYPE_INDEX, &path))
                                i_unreached();
                        path = t_strconcat(path, "/",
@@ -1502,9 +1493,12 @@ bool mailbox_list_default_get_root_path(struct mailbox_list *list,
                }
                /* default to index directory */
                return mailbox_list_set_get_root_path(&list->set,
-                               MAILBOX_LIST_PATH_TYPE_INDEX, path_r);
+                       list->mail_set->parsed_mailbox_root_directory_prefix,
+                       MAILBOX_LIST_PATH_TYPE_INDEX, path_r);
        default:
-               return mailbox_list_set_get_root_path(&list->set, type, path_r);
+               return mailbox_list_set_get_root_path(&list->set,
+                       list->mail_set->parsed_mailbox_root_directory_prefix,
+                       type, path_r);
        }
        *path_r = path;
        return path != NULL;
index 0b3d37ca8581f7f9f9c3ecd88e77777dad57a7cd..09ebddb8019d62e2dfa75ef8cee5cd1b0dd45dc2 100644 (file)
@@ -135,9 +135,6 @@ struct mailbox_list_settings {
           If mailbox_name is "Maildir", you have a non-selectable mailbox
           "mail" and a selectable mailbox "mail/foo". */
        const char *maildir_name;
-       /* if set, store mailboxes under root_dir/mailbox_dir_name/.
-          this setting contains either "" or "dir/". */
-       const char *mailbox_dir_name;
 
        /* Used for escaping the mailbox name in storage (storage_name). If the
           UTF-8 vname has characters that can't reversibly (or safely) be