doveadm-mail-mailbox-metadata.c revision 4a48987ed0ba1632e90a50f2ba65393e07e9bcea
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen/* Copyright (c) 2014-2017 Dovecot authors, see the included COPYING file */
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen#include "lib.h"
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen#include "str.h"
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen#include "mail-namespace.h"
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen#include "mail-storage.h"
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen#include "doveadm-print.h"
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen#include "doveadm-mail.h"
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen#include "doveadm-mailbox-list-iter.h"
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainenstruct metadata_cmd_context {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct doveadm_mail_cmd_context ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *mailbox;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen enum mail_attribute_type key_type;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *key;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_attribute_value value;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen bool empty_mailbox_name;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen};
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainenstatic int
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainencmd_mailbox_metadata_open_mailbox(struct metadata_cmd_context *mctx,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mail_user *user,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen const char *op,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_namespace **ns_r,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mailbox **box_r)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen mctx->empty_mailbox_name = mctx->mailbox[0] == '\0';
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (mctx->empty_mailbox_name) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (!mctx->ctx.allow_empty_mailbox_name) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen i_error("Failed to %s: %s", op,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen "mailbox name cannot be empty");
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen mctx->ctx.exit_code = EX_USAGE;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return -1;
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen /* server attribute */
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen *ns_r = mail_namespace_find_inbox(user->namespaces);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen *box_r = mailbox_alloc((*ns_r)->list, "INBOX", 0);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen mctx->key = t_strconcat(MAILBOX_ATTRIBUTE_PREFIX_DOVECOT_PVT_SERVER,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen mctx->key, NULL);
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen } else {
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen /* mailbox attributes */
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen *ns_r = mail_namespace_find(user->namespaces, mctx->mailbox);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen *box_r = mailbox_alloc((*ns_r)->list, mctx->mailbox, 0);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen }
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen if (mailbox_open(*box_r) < 0) {
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen i_error("Failed to open mailbox: %s",
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen mailbox_get_last_error(*box_r, NULL));
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen doveadm_mail_failed_mailbox(&mctx->ctx, *box_r);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen mailbox_free(box_r);
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen return -1;
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen }
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen return 0;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen}
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainenstatic int
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainencmd_mailbox_metadata_set_run(struct doveadm_mail_cmd_context *_ctx,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mail_user *user)
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen{
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mail_namespace *ns;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mailbox *box;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mailbox_transaction_context *trans;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen int ret;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen ret = cmd_mailbox_metadata_open_mailbox(ctx, user, "set attribute",
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen &ns, &box);
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen if (ret != 0)
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen return ret;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen trans = mailbox_transaction_begin(box, ctx->empty_mailbox_name ?
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen MAILBOX_TRANSACTION_FLAG_EXTERNAL : 0);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen ret = ctx->value.value == NULL ?
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_attribute_unset(trans, ctx->key_type, ctx->key) :
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_attribute_set(trans, ctx->key_type, ctx->key, &ctx->value);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen if (ret < 0) {
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen i_error("Failed to set attribute: %s",
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_get_last_error(box, NULL));
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen doveadm_mail_failed_mailbox(_ctx, box);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_transaction_rollback(&trans);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen } else if (mailbox_transaction_commit(&trans) < 0) {
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen i_error("Failed to commit transaction: %s",
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_get_last_error(box, NULL));
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen doveadm_mail_failed_mailbox(_ctx, box);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen ret = -1;
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen }
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen mailbox_free(&box);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen return ret;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen}
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainenstatic void
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainencmd_mailbox_metadata_parse_key(const char *arg,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen enum mail_attribute_type *type_r,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char **key_r)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen arg = t_str_lcase(arg);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (strncmp(arg, "/private/", 9) == 0) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen *type_r = MAIL_ATTRIBUTE_TYPE_PRIVATE;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen *key_r = arg + 9;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen } else if (strncmp(arg, "/shared/", 8) == 0) {
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen *type_r = MAIL_ATTRIBUTE_TYPE_SHARED;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen *key_r = arg + 8;
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen } else if (strcmp(arg, "/private") == 0) {
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen *type_r = MAIL_ATTRIBUTE_TYPE_PRIVATE;
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen *key_r = "";
323a9de5b41c4f9e4a26f22b92205678114ae14eTimo Sirainen } else if (strcmp(arg, "/shared") == 0) {
323a9de5b41c4f9e4a26f22b92205678114ae14eTimo Sirainen *type_r = MAIL_ATTRIBUTE_TYPE_SHARED;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen *key_r = "";
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen } else {
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainen i_fatal_status(EX_USAGE, "Invalid metadata key '%s': "
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen "Must begin with /private or /shared", arg);
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen }
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen}
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainenstatic void
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainencmd_mailbox_metadata_set_init(struct doveadm_mail_cmd_context *_ctx,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *const args[])
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *key;
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen if (str_array_length(args) != 3)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_mail_help_name("mailbox metadata set");
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen cmd_mailbox_metadata_parse_key(args[1], &ctx->key_type, &key);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->mailbox = p_strdup(_ctx->pool, args[0]);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->key = p_strdup(_ctx->pool, key);
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen ctx->value.value = p_strdup(_ctx->pool, args[2]);
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainenstatic struct doveadm_mail_cmd_context *cmd_mailbox_metadata_set_alloc(void)
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct metadata_cmd_context *ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen ctx = doveadm_mail_cmd_alloc(struct metadata_cmd_context);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->ctx.v.init = cmd_mailbox_metadata_set_init;
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen ctx->ctx.v.run = cmd_mailbox_metadata_set_run;
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen return &ctx->ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainenstatic void
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainencmd_mailbox_metadata_unset_init(struct doveadm_mail_cmd_context *_ctx,
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen const char *const args[])
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen{
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen const char *key;
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen if (str_array_length(args) != 2)
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainen doveadm_mail_help_name("mailbox metadata unset");
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainen cmd_mailbox_metadata_parse_key(args[1], &ctx->key_type, &key);
b8b085f7bc6f1c0367802a9f00062bbbd981690dTimo Sirainen
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ctx->mailbox = p_strdup(_ctx->pool, args[0]);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ctx->key = p_strdup(_ctx->pool, key);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen}
23878bd03d1de531e3261a25598beec621351910Timo Sirainen
23878bd03d1de531e3261a25598beec621351910Timo Sirainenstatic struct doveadm_mail_cmd_context *cmd_mailbox_metadata_unset_alloc(void)
23878bd03d1de531e3261a25598beec621351910Timo Sirainen{
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct metadata_cmd_context *ctx;
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen ctx = doveadm_mail_cmd_alloc(struct metadata_cmd_context);
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen ctx->ctx.v.init = cmd_mailbox_metadata_unset_init;
4ca6f6e2ae7be7c5f04ea5ef176a7c4a47ea3d33Timo Sirainen ctx->ctx.v.run = cmd_mailbox_metadata_set_run;
7ed711d973b319320da100d3e905ef7b99ed69d6Timo Sirainen return &ctx->ctx;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainenstatic int
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainencmd_mailbox_metadata_get_run(struct doveadm_mail_cmd_context *_ctx,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_user *user)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_namespace *ns;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mailbox *box;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_attribute_value value;
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen int ret;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ret = cmd_mailbox_metadata_open_mailbox(ctx, user, "get attribute",
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen &ns, &box);
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen if (ret != 0)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return ret;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ret = mailbox_attribute_get_stream(box, ctx->key_type, ctx->key, &value);
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen if (ret < 0) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen i_error("Failed to get attribute: %s",
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen mailbox_get_last_error(box, NULL));
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_mail_failed_mailbox(_ctx, box);
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen } else if (ret == 0) {
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen /* not found, print as empty */
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen doveadm_print("");
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen } else if (value.value_stream != NULL) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_print_istream(value.value_stream);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen } else {
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen doveadm_print(value.value);
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen mailbox_free(&box);
11352dc3e4b29f3d2763c82f8ea4f99e8daf4fa3Timo Sirainen return ret;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainenstatic void
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainencmd_mailbox_metadata_get_init(struct doveadm_mail_cmd_context *_ctx,
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen const char *const args[])
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen{
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *key;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (str_array_length(args) != 2)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_mail_help_name("mailbox metadata get");
23878bd03d1de531e3261a25598beec621351910Timo Sirainen cmd_mailbox_metadata_parse_key(args[1], &ctx->key_type, &key);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->mailbox = p_strdup(_ctx->pool, args[0]);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ctx->key = p_strdup(_ctx->pool, key);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_print_header("value", "value",
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen DOVEADM_PRINT_HEADER_FLAG_HIDE_TITLE);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainenstatic struct doveadm_mail_cmd_context *cmd_mailbox_metadata_get_alloc(void)
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct metadata_cmd_context *ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen ctx = doveadm_mail_cmd_alloc(struct metadata_cmd_context);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->ctx.v.init = cmd_mailbox_metadata_get_init;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->ctx.v.run = cmd_mailbox_metadata_get_run;
23878bd03d1de531e3261a25598beec621351910Timo Sirainen doveadm_print_init(DOVEADM_PRINT_TYPE_FLOW);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen return &ctx->ctx;
23878bd03d1de531e3261a25598beec621351910Timo Sirainen}
23878bd03d1de531e3261a25598beec621351910Timo Sirainen
23878bd03d1de531e3261a25598beec621351910Timo Sirainenstatic int
23878bd03d1de531e3261a25598beec621351910Timo Sirainencmd_mailbox_metadata_list_run_iter(struct metadata_cmd_context *ctx,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mailbox *box,
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen enum mail_attribute_type type)
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen{
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct mailbox_attribute_iter *iter;
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen const char *key;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen iter = mailbox_attribute_iter_init(box, type, ctx->key);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen while ((key = mailbox_attribute_iter_next(iter)) != NULL)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_print(key);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (mailbox_attribute_iter_deinit(&iter) < 0) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen i_error("Mailbox %s: Failed to iterate mailbox attributes: %s",
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen mailbox_get_vname(box),
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen mailbox_get_last_error(box, NULL));
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return -1;
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return 0;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainenstatic int
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainencmd_mailbox_metadata_list_run(struct doveadm_mail_cmd_context *_ctx,
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen struct mail_user *user)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct mail_namespace *ns;
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen struct mailbox *box;
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen int ret = 0;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen ret = cmd_mailbox_metadata_open_mailbox(ctx, user, "list attributes",
11352dc3e4b29f3d2763c82f8ea4f99e8daf4fa3Timo Sirainen &ns, &box);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (ret != 0)
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen return ret;
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen if (ctx->key[0] == '\0' || ctx->key_type == MAIL_ATTRIBUTE_TYPE_PRIVATE) {
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen if (cmd_mailbox_metadata_list_run_iter(ctx, box, MAIL_ATTRIBUTE_TYPE_PRIVATE) < 0) {
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen doveadm_mail_failed_mailbox(_ctx, box);
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen ret = -1;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (ctx->key[0] == '\0' || ctx->key_type == MAIL_ATTRIBUTE_TYPE_SHARED) {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen if (cmd_mailbox_metadata_list_run_iter(ctx, box, MAIL_ATTRIBUTE_TYPE_SHARED) < 0) {
23878bd03d1de531e3261a25598beec621351910Timo Sirainen doveadm_mail_failed_mailbox(_ctx, box);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ret = -1;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen }
23878bd03d1de531e3261a25598beec621351910Timo Sirainen }
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen mailbox_free(&box);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return ret;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainenstatic void
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainencmd_mailbox_metadata_list_init(struct doveadm_mail_cmd_context *_ctx,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *const args[])
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen struct metadata_cmd_context *ctx = (struct metadata_cmd_context *)_ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen const char *key = NULL;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
23878bd03d1de531e3261a25598beec621351910Timo Sirainen if (args[0] == NULL)
23878bd03d1de531e3261a25598beec621351910Timo Sirainen doveadm_mail_help_name("mailbox metadata list");
23878bd03d1de531e3261a25598beec621351910Timo Sirainen if (args[1] != NULL)
23878bd03d1de531e3261a25598beec621351910Timo Sirainen cmd_mailbox_metadata_parse_key(args[1], &ctx->key_type, &key);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ctx->mailbox = p_strdup(_ctx->pool, args[0]);
23878bd03d1de531e3261a25598beec621351910Timo Sirainen ctx->key = key == NULL ? "" : p_strdup(_ctx->pool, key);
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen doveadm_print_header("key", "key",
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen DOVEADM_PRINT_HEADER_FLAG_HIDE_TITLE);
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen}
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainenstatic struct doveadm_mail_cmd_context *cmd_mailbox_metadata_list_alloc(void)
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen{
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen struct metadata_cmd_context *ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx = doveadm_mail_cmd_alloc(struct metadata_cmd_context);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->ctx.v.init = cmd_mailbox_metadata_list_init;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen ctx->ctx.v.run = cmd_mailbox_metadata_list_run;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen doveadm_print_init(DOVEADM_PRINT_TYPE_FLOW);
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen return &ctx->ctx;
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen}
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainenstruct doveadm_cmd_ver2 doveadm_cmd_mailbox_metadata_set_ver2 = {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .name = "mailbox metadata set",
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen .mail_cmd = cmd_mailbox_metadata_set_alloc,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .usage = DOVEADM_CMD_MAIL_USAGE_PREFIX"[-s] <mailbox> <key> <value>",
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAMS_START
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo SirainenDOVEADM_CMD_MAIL_COMMON
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAM('s', "allow-empty-mailbox-name", CMD_PARAM_BOOL, 0)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAM('\0', "mailbox", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAM('\0', "key", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAM('\0', "value", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAMS_END
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen};
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
11352dc3e4b29f3d2763c82f8ea4f99e8daf4fa3Timo Sirainenstruct doveadm_cmd_ver2 doveadm_cmd_mailbox_metadata_unset_ver2 = {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .name = "mailbox metadata unset",
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen .mail_cmd = cmd_mailbox_metadata_unset_alloc,
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen .usage = DOVEADM_CMD_MAIL_USAGE_PREFIX"[-s] <mailbox> <key>",
05093f69a5ac540a569c4e675686ed96e61667c6Timo SirainenDOVEADM_CMD_PARAMS_START
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo SirainenDOVEADM_CMD_MAIL_COMMON
05093f69a5ac540a569c4e675686ed96e61667c6Timo SirainenDOVEADM_CMD_PARAM('s', "allow-empty-mailbox-name", CMD_PARAM_BOOL, 0)
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo SirainenDOVEADM_CMD_PARAM('\0', "mailbox", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
05093f69a5ac540a569c4e675686ed96e61667c6Timo SirainenDOVEADM_CMD_PARAM('\0', "key", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo SirainenDOVEADM_CMD_PARAMS_END
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen};
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainen
05093f69a5ac540a569c4e675686ed96e61667c6Timo Sirainenstruct doveadm_cmd_ver2 doveadm_cmd_mailbox_metadata_get_ver2 = {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .name = "mailbox metadata get",
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .mail_cmd = cmd_mailbox_metadata_get_alloc,
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .usage = DOVEADM_CMD_MAIL_USAGE_PREFIX"[-s] <mailbox> <key>",
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAMS_START
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_MAIL_COMMON
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAM('s', "allow-empty-mailbox-name", CMD_PARAM_BOOL, 0)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAM('\0', "mailbox", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAM('\0', "key", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
9cf4bb70f014849735aab4226691edcdf56b3271Timo SirainenDOVEADM_CMD_PARAMS_END
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen};
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen
636f017be100bce67d66fd3ae1544a47681efd33Timo Sirainenstruct doveadm_cmd_ver2 doveadm_cmd_mailbox_metadata_list_ver2 = {
9cf4bb70f014849735aab4226691edcdf56b3271Timo Sirainen .name = "mailbox metadata list",
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen .mail_cmd = cmd_mailbox_metadata_list_alloc,
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen .usage = DOVEADM_CMD_MAIL_USAGE_PREFIX"[-s] <mailbox> [<key prefix>]",
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAMS_START
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_MAIL_COMMON
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAM('s', "allow-empty-mailbox-name", CMD_PARAM_BOOL, 0)
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAM('\0', "mailbox", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAM('\0', "key-prefix", CMD_PARAM_STR, CMD_PARAM_FLAG_POSITIONAL)
23878bd03d1de531e3261a25598beec621351910Timo SirainenDOVEADM_CMD_PARAMS_END
e09c7dc961cb9cab04ec7cc79215c2f6318fbde0Timo Sirainen};
1db62753d9e3b5d71018889c8ef0a3722a307455Timo Sirainen