doveadm-mail-fetch.c revision 7f03bac2ef9fae720ce96536b1e936066f093de4
c25356d5978632df6203437e1953bcb29e0c736fTimo Sirainen/* Copyright (c) 2010 Dovecot authors, see the included COPYING file */
c25356d5978632df6203437e1953bcb29e0c736fTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "lib.h"
80c1d98d3638b71e57a39cafa88b9122bf8169c6Timo Sirainen#include "array.h"
b780aa272b742a43579cdb523cc79cc8d4521306Timo Sirainen#include "istream.h"
de62ce819d59a529530da4b57be1b8d6dad13d6bTimo Sirainen#include "ostream.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "str.h"
94a8cb0ee1d85569ad1a2acacd92d3ce22f8a1cbTimo Sirainen#include "message-size.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "imap-utf7.h"
16c89b1260c9d07c01c83a9219424d3727069b2eTimo Sirainen#include "imap-util.h"
50031a6b36a6051512bd18f39e4bbabe54acf565Timo Sirainen#include "mail-user.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "mail-storage.h"
6a19e109ee8c5a6f688da83a86a7f6abeb71abddTimo Sirainen#include "mail-search.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "mail-namespace.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "doveadm-print.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "doveadm-mail.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "doveadm-mail-list-iter.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "doveadm-mail-iter.h"
31ddc75584c5cde53d2e78a737587f2e7fdcb0d2Timo Sirainen
8887bf3757d51d73887dd20b1db3334d867d3817Timo Sirainen#include <stdio.h>
8887bf3757d51d73887dd20b1db3334d867d3817Timo Sirainen
51b979b6414b940f04677a7e2d064be119345954Timo Sirainenstruct fetch_cmd_context {
51b979b6414b940f04677a7e2d064be119345954Timo Sirainen struct doveadm_mail_cmd_context ctx;
c53e8ee216904ffe6de4f6518d9f9f5107b7610eTimo Sirainen
589a9c6e8ee22071c14171c04bfc6bfe17121871Timo Sirainen struct ostream *output;
589a9c6e8ee22071c14171c04bfc6bfe17121871Timo Sirainen struct mail *mail;
ef5fb27361cc5e15766e85e28355750ff04b13c9Timo Sirainen
ef5fb27361cc5e15766e85e28355750ff04b13c9Timo Sirainen ARRAY_DEFINE(fields, const struct fetch_field);
ef5fb27361cc5e15766e85e28355750ff04b13c9Timo Sirainen ARRAY_TYPE(const_string) header_fields;
ef5fb27361cc5e15766e85e28355750ff04b13c9Timo Sirainen enum mail_fetch_field wanted_fields;
a53cb86b4d733d9c48ee4d285bed477c80825804Timo Sirainen
a53cb86b4d733d9c48ee4d285bed477c80825804Timo Sirainen const struct fetch_field *cur_field;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen};
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstruct fetch_field {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen const char *name;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen enum mail_fetch_field wanted_fields;
b7b81543899e306c71e6152516d8698416162bcbTimo Sirainen int (*print)(struct fetch_cmd_context *ctx);
fd3d711f219fd6813492acbe051e04327f0ca0f0Timo Sirainen};
6ec7cf71ccd0eed1f9cc1b0bda8960796b04160bTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_user(struct fetch_cmd_context *ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
fd3d711f219fd6813492acbe051e04327f0ca0f0Timo Sirainen doveadm_print(ctx->ctx.cur_mail_user->username);
db5164c9a1129af0cfb11fc18d88da361a8011fbTimo Sirainen return 0;
5da1aa5197a43d83f0fb3eeb83125c7cd73d1b62Timo Sirainen}
db5164c9a1129af0cfb11fc18d88da361a8011fbTimo Sirainen
5da1aa5197a43d83f0fb3eeb83125c7cd73d1b62Timo Sirainenstatic int fetch_mailbox(struct fetch_cmd_context *ctx)
5da1aa5197a43d83f0fb3eeb83125c7cd73d1b62Timo Sirainen{
5da1aa5197a43d83f0fb3eeb83125c7cd73d1b62Timo Sirainen const char *value;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen string_t *str = t_str_new(128);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_MAILBOX_NAME, &value) < 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return -1;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (imap_utf7_to_utf8(value, str) == 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print(str_c(str));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen else {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen /* not a valid mUTF-7 name, fallback to showing it as-is */
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print(value);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen }
8e7da21696c9f8a6d5e601243fb6172ec85d47b2Timo Sirainen return 0;
024815ea2ffdda9ea79919f18e865663977f73eaTimo Sirainen}
024815ea2ffdda9ea79919f18e865663977f73eaTimo Sirainen
16c89b1260c9d07c01c83a9219424d3727069b2eTimo Sirainenstatic int fetch_mailbox_guid(struct fetch_cmd_context *ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
811f2e26d9782d9cb99fdf82e18ffa0a77564fe2Timo Sirainen uint8_t guid[MAIL_GUID_128_SIZE];
811f2e26d9782d9cb99fdf82e18ffa0a77564fe2Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (mailbox_get_guid(ctx->mail->box, guid) < 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return -1;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print(mail_guid_128_to_string(guid));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_seq(struct fetch_cmd_context *ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
1d3f7c1278168d5b1cbfa9a2cc9929a0909056b4Timo Sirainen doveadm_print_num(ctx->mail->seq);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
1d3f7c1278168d5b1cbfa9a2cc9929a0909056b4Timo Sirainenstatic int fetch_uid(struct fetch_cmd_context *ctx)
1d3f7c1278168d5b1cbfa9a2cc9929a0909056b4Timo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print_num(ctx->mail->uid);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
51795bfe9d05d92fe942cb451aec2b9d16d32a11Timo Sirainenstatic int fetch_guid(struct fetch_cmd_context *ctx)
51795bfe9d05d92fe942cb451aec2b9d16d32a11Timo Sirainen{
51795bfe9d05d92fe942cb451aec2b9d16d32a11Timo Sirainen const char *value;
51795bfe9d05d92fe942cb451aec2b9d16d32a11Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_GUID, &value) < 0)
b84451fa6ada675ae504725702e0815967124cbbTimo Sirainen return -1;
b84451fa6ada675ae504725702e0815967124cbbTimo Sirainen doveadm_print(value);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
8aacc9e7c84f8376822823ec98c2f551d4919b2eTimo Sirainen}
8aacc9e7c84f8376822823ec98c2f551d4919b2eTimo Sirainen
8aacc9e7c84f8376822823ec98c2f551d4919b2eTimo Sirainenstatic int fetch_flags(struct fetch_cmd_context *ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen string_t *str = t_str_new(64);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen imap_write_flags(str, mail_get_flags(ctx->mail),
16c89b1260c9d07c01c83a9219424d3727069b2eTimo Sirainen mail_get_keywords(ctx->mail));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print(str_c(str));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen}
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainenstatic int fetch_hdr(struct fetch_cmd_context *ctx)
84ed9f8f3d0e5ed47607ef417618e49e4f865557Timo Sirainen{
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen struct istream *input;
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen struct message_size hdr_size;
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen const unsigned char *data;
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen size_t size;
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen int ret = 0;
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen
b9c44feadade0481b957f2978640afb3317bd1dfTimo Sirainen if (mail_get_stream(ctx->mail, &hdr_size, NULL, &input) < 0)
b9c44feadade0481b957f2978640afb3317bd1dfTimo Sirainen return -1;
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen input = i_stream_create_limit(input, hdr_size.physical_size);
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen while (!i_stream_is_eof(input)) {
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen if (i_stream_read_data(input, &data, &size, 0) == -1)
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen break;
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen if (size == 0)
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen break;
807b48fe1f6a57b01ed2cc20247d5b5e3facc562Timo Sirainen doveadm_print_stream(data, size);
807b48fe1f6a57b01ed2cc20247d5b5e3facc562Timo Sirainen i_stream_skip(input, size);
e169102fb38ce788b76c2a344bee7d77079dea05Timo Sirainen }
e169102fb38ce788b76c2a344bee7d77079dea05Timo Sirainen if (input->stream_errno != 0) {
e169102fb38ce788b76c2a344bee7d77079dea05Timo Sirainen i_error("read() failed: %m");
e169102fb38ce788b76c2a344bee7d77079dea05Timo Sirainen ret = -1;
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen }
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen i_stream_unref(&input);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print_stream(NULL, 0);
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainen return ret;
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainen}
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainen
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainenstatic int fetch_hdr_field(struct fetch_cmd_context *ctx)
250105a1440167ef000323cdb2721cd2a3688e1eTimo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen const char *const *value;
6bc98d3898c475ba7615ba2b016e5142c8b2c09fTimo Sirainen string_t *str = t_str_new(256);
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen bool add_lf = FALSE;
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen if (mail_get_headers(ctx->mail, ctx->cur_field->name, &value) < 0)
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen return -1;
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen for (; *value != NULL; value++) {
c8adec8db635f5efb13b9879a5f3fb523abdc969Timo Sirainen if (add_lf)
d6a1fa1d65c6d1996937802c2482c0f14dd821a7Timo Sirainen str_append_c(str, '\n');
d6a1fa1d65c6d1996937802c2482c0f14dd821a7Timo Sirainen str_append(str, *value);
807b48fe1f6a57b01ed2cc20247d5b5e3facc562Timo Sirainen add_lf = TRUE;
807b48fe1f6a57b01ed2cc20247d5b5e3facc562Timo Sirainen }
3f91e60401495a4046c73992fabaa5e77200a451Timo Sirainen doveadm_print(str_c(str));
cfbacf6ea5fb39ae5304e4d95a78d9d4751bdfe1Timo Sirainen return 0;
dc912088f84c263db1609435c2f5d7cb29bf1a33Timo Sirainen}
3f91e60401495a4046c73992fabaa5e77200a451Timo Sirainen
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainenstatic int fetch_body(struct fetch_cmd_context *ctx)
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen{
7761758f43d6150be4b07f4c54457ce662f78c4cTimo Sirainen struct istream *input;
6bc98d3898c475ba7615ba2b016e5142c8b2c09fTimo Sirainen struct message_size hdr_size;
62f4a199b5c9a0862f486cbf18e195cc621bbe25Timo Sirainen const unsigned char *data;
62f4a199b5c9a0862f486cbf18e195cc621bbe25Timo Sirainen size_t size;
62f4a199b5c9a0862f486cbf18e195cc621bbe25Timo Sirainen int ret = 0;
62f4a199b5c9a0862f486cbf18e195cc621bbe25Timo Sirainen
62f4a199b5c9a0862f486cbf18e195cc621bbe25Timo Sirainen if (mail_get_stream(ctx->mail, &hdr_size, NULL, &input) < 0)
6bc98d3898c475ba7615ba2b016e5142c8b2c09fTimo Sirainen return -1;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen i_stream_skip(input, hdr_size.physical_size);
659fe5d24825b160cae512538088020d97a60239Timo Sirainen while (!i_stream_is_eof(input)) {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (i_stream_read_data(input, &data, &size, 0) == -1)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen break;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (size == 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen break;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print_stream(data, size);
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainen i_stream_skip(input, size);
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen }
26ff8f8a4867bf8e9551a27a2de8c12cd138b065Timo Sirainen if (input->stream_errno != 0) {
0c909e3461607eadcd66f4eac69b7f34e37fccf1Timo Sirainen i_error("read() failed: %m");
0c909e3461607eadcd66f4eac69b7f34e37fccf1Timo Sirainen ret = -1;
de62ce819d59a529530da4b57be1b8d6dad13d6bTimo Sirainen }
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print_stream(NULL, 0);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return ret;
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainen}
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainen
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainenstatic int fetch_text(struct fetch_cmd_context *ctx)
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainen{
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainen struct istream *input;
020a39a395d2adb768e0179631b37bc78ecd9471Timo Sirainen const unsigned char *data;
020a39a395d2adb768e0179631b37bc78ecd9471Timo Sirainen size_t size;
1f43c8ac132c153c224c4fffe34b2c3075d87ef7Timo Sirainen int ret = 0;
b9c44feadade0481b957f2978640afb3317bd1dfTimo Sirainen
b9c44feadade0481b957f2978640afb3317bd1dfTimo Sirainen if (mail_get_stream(ctx->mail, NULL, NULL, &input) < 0)
b9c44feadade0481b957f2978640afb3317bd1dfTimo Sirainen return -1;
020a39a395d2adb768e0179631b37bc78ecd9471Timo Sirainen
020a39a395d2adb768e0179631b37bc78ecd9471Timo Sirainen while (!i_stream_is_eof(input)) {
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen if (i_stream_read_data(input, &data, &size, 0) == -1)
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen break;
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen if (size == 0)
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen break;
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen doveadm_print_stream(data, size);
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen i_stream_skip(input, size);
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen }
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen if (input->stream_errno != 0) {
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen i_error("read() failed: %m");
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen ret = -1;
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen }
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen doveadm_print_stream(NULL, 0);
6a19e109ee8c5a6f688da83a86a7f6abeb71abddTimo Sirainen return ret;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_size_physical(struct fetch_cmd_context *ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen uoff_t size;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen if (mail_get_physical_size(ctx->mail, &size) < 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return -1;
b780aa272b742a43579cdb523cc79cc8d4521306Timo Sirainen doveadm_print_num(size);
b780aa272b742a43579cdb523cc79cc8d4521306Timo Sirainen return 0;
b780aa272b742a43579cdb523cc79cc8d4521306Timo Sirainen}
b780aa272b742a43579cdb523cc79cc8d4521306Timo Sirainen
20a802016205bbcafc90f164f769ea801f88d014Timo Sirainenstatic int fetch_size_virtual(struct fetch_cmd_context *ctx)
e156adefc1260d31a145df2f5e9b3c82050d4163Timo Sirainen{
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen uoff_t size;
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen if (mail_get_virtual_size(ctx->mail, &size) < 0)
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen return -1;
47e0598840ecffa364ebed523e06939e22738f06Timo Sirainen doveadm_print_num(size);
47e0598840ecffa364ebed523e06939e22738f06Timo Sirainen return 0;
47e0598840ecffa364ebed523e06939e22738f06Timo Sirainen}
47e0598840ecffa364ebed523e06939e22738f06Timo Sirainen
20a802016205bbcafc90f164f769ea801f88d014Timo Sirainenstatic int fetch_date_received(struct fetch_cmd_context *ctx)
41e6eb07b411ea58352ba9d2cc8cf340325d49f3Timo Sirainen{
41e6eb07b411ea58352ba9d2cc8cf340325d49f3Timo Sirainen time_t t;
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen
41e6eb07b411ea58352ba9d2cc8cf340325d49f3Timo Sirainen if (mail_get_received_date(ctx->mail, &t) < 0)
41e6eb07b411ea58352ba9d2cc8cf340325d49f3Timo Sirainen return -1;
036626b19f14bef582f96e556913ae91b1d67881Timo Sirainen doveadm_print(unixdate2str(t));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
4d4d585520538a752e9f0a4a1c019a2918f52e56Timo Sirainen}
4d4d585520538a752e9f0a4a1c019a2918f52e56Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_date_sent(struct fetch_cmd_context *ctx)
15cc66ca72982a43e3bfa58f307adc57e9caa52dTimo Sirainen{
15cc66ca72982a43e3bfa58f307adc57e9caa52dTimo Sirainen time_t t;
a045c3aba2610c6ed0bf1c346df1c6d8f7b9fbfdTimo Sirainen int tz;
a045c3aba2610c6ed0bf1c346df1c6d8f7b9fbfdTimo Sirainen char chr;
a045c3aba2610c6ed0bf1c346df1c6d8f7b9fbfdTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (mail_get_date(ctx->mail, &t, &tz) < 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return -1;
d30da25fb6be1f1c667d93767c9194000194b618Timo Sirainen
d30da25fb6be1f1c667d93767c9194000194b618Timo Sirainen chr = tz < 0 ? '-' : '+';
d30da25fb6be1f1c667d93767c9194000194b618Timo Sirainen if (tz < 0) tz = -tz;
d30da25fb6be1f1c667d93767c9194000194b618Timo Sirainen doveadm_print(t_strdup_printf("%s (%c%02u%02u)", unixdate2str(t),
d30da25fb6be1f1c667d93767c9194000194b618Timo Sirainen chr, tz/60, tz%60));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen}
6a19e109ee8c5a6f688da83a86a7f6abeb71abddTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_date_saved(struct fetch_cmd_context *ctx)
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen time_t t;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (mail_get_save_date(ctx->mail, &t) < 0)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return -1;
df4018ae2f0a95be602f724ca70df7e0e3bd6a7dTimo Sirainen doveadm_print(unixdate2str(t));
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
6ef7e31619edfaa17ed044b45861d106a86191efTimo Sirainen}
ec77cd41241208345efd51c1fcce9030be30aa9bTimo Sirainen
ec77cd41241208345efd51c1fcce9030be30aa9bTimo Sirainenstatic int fetch_imap_envelope(struct fetch_cmd_context *ctx)
ec77cd41241208345efd51c1fcce9030be30aa9bTimo Sirainen{
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen const char *value;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
2a6af811ea3de3cf9e2f15e446674dd21b0705f3Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_IMAP_ENVELOPE, &value) < 0)
2a6af811ea3de3cf9e2f15e446674dd21b0705f3Timo Sirainen return -1;
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen doveadm_print(value);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen return 0;
7c95b03620a03a43dd72d39608cea5fc77393ad6Timo Sirainen}
db87d16551d1081ada01f787ea21aa3ed1402c31Timo Sirainen
9404a7b90dcb80d31bd37ee2493f03751acdb1bdTimo Sirainenstatic int fetch_imap_body(struct fetch_cmd_context *ctx)
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen{
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen const char *value;
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen
eac3948d67eff8623d51aeaea9eca582f3aec677Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_IMAP_BODY, &value) < 0)
2674b4f0cf8f3c203d8e56b29735f5e267038dafTimo Sirainen return -1;
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainen doveadm_print(value);
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainen return 0;
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainen}
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainen
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainenstatic int fetch_imap_bodystructure(struct fetch_cmd_context *ctx)
48270badadd82279bfe50ae3d187aea8b0b2b30eTimo Sirainen{
e376693bfa3985232c41df99c7010fca22612c89Timo Sirainen const char *value;
48136ae5a0eb49daa44e343553f3688a500307e2Timo Sirainen
48136ae5a0eb49daa44e343553f3688a500307e2Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_IMAP_BODYSTRUCTURE, &value) < 0)
2674b4f0cf8f3c203d8e56b29735f5e267038dafTimo Sirainen return -1;
e376693bfa3985232c41df99c7010fca22612c89Timo Sirainen doveadm_print(value);
e376693bfa3985232c41df99c7010fca22612c89Timo Sirainen return 0;
e376693bfa3985232c41df99c7010fca22612c89Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic int fetch_pop3_uidl(struct fetch_cmd_context *ctx)
97735b96d442568f65efa20f8c292a496498c17bTimo Sirainen{
97735b96d442568f65efa20f8c292a496498c17bTimo Sirainen const char *value;
97735b96d442568f65efa20f8c292a496498c17bTimo Sirainen
24fc71a693331ffe77e2b6d81c70aca6fa055e47Timo Sirainen if (mail_get_special(ctx->mail, MAIL_FETCH_UIDL_BACKEND, &value) < 0)
09c3a491f4f6ccebe290c7709bdc0d79a187610bTimo Sirainen return -1;
24fc71a693331ffe77e2b6d81c70aca6fa055e47Timo Sirainen doveadm_print(value);
d6a1fa1d65c6d1996937802c2482c0f14dd821a7Timo Sirainen return 0;
d6a1fa1d65c6d1996937802c2482c0f14dd821a7Timo Sirainen}
d6a1fa1d65c6d1996937802c2482c0f14dd821a7Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic const struct fetch_field fetch_fields[] = {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { "user", 0, fetch_user },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { "mailbox", 0, fetch_mailbox },
b92813e2f96d4b28f989528ed5dd6115da7d9bdbTimo Sirainen { "mailbox-guid", 0, fetch_mailbox_guid },
b92813e2f96d4b28f989528ed5dd6115da7d9bdbTimo Sirainen { "seq", 0, fetch_seq },
b92813e2f96d4b28f989528ed5dd6115da7d9bdbTimo Sirainen { "uid", 0, fetch_uid },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { "guid", 0, fetch_guid },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "flags", MAIL_FETCH_FLAGS, fetch_flags },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "hdr", MAIL_FETCH_STREAM_HEADER, fetch_hdr },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { "body", MAIL_FETCH_STREAM_BODY, fetch_body },
db5164c9a1129af0cfb11fc18d88da361a8011fbTimo Sirainen { "text", MAIL_FETCH_STREAM_HEADER |
db5164c9a1129af0cfb11fc18d88da361a8011fbTimo Sirainen MAIL_FETCH_STREAM_BODY, fetch_text },
db5164c9a1129af0cfb11fc18d88da361a8011fbTimo Sirainen { "size.physical", MAIL_FETCH_PHYSICAL_SIZE, fetch_size_physical },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { "size.virtual", MAIL_FETCH_VIRTUAL_SIZE, fetch_size_virtual },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "date.received", MAIL_FETCH_RECEIVED_DATE, fetch_date_received },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "date.sent", MAIL_FETCH_DATE, fetch_date_sent },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "date.saved", MAIL_FETCH_SAVE_DATE, fetch_date_saved },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "imap.envelope", MAIL_FETCH_IMAP_ENVELOPE, fetch_imap_envelope },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "imap.body", MAIL_FETCH_IMAP_BODY, fetch_imap_body },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "imap.bodystructure", MAIL_FETCH_IMAP_BODYSTRUCTURE, fetch_imap_bodystructure },
d152ccd0d29fae1bc6092bf198ee7eb843202f96Timo Sirainen { "pop3.uidl", MAIL_FETCH_UIDL_BACKEND, fetch_pop3_uidl }
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen};
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic const struct fetch_field *fetch_field_find(const char *name)
aa0647f2debf0d48d504a321186f66c85596aaf4Timo Sirainen{
2d39dc1a453546892109b35c0d9770369011a13dTimo Sirainen unsigned int i;
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen for (i = 0; i < N_ELEMENTS(fetch_fields); i++) {
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen if (strcmp(fetch_fields[i].name, name) == 0)
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen return &fetch_fields[i];
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen }
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen return NULL;
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen}
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainenstatic void print_fetch_fields(void)
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen{
8f8315e4b4e27ead12dd1c3da65bf4dee3762f18Timo Sirainen unsigned int i;
768b7f5783c8de119d7386321e5d0c72d5c2d9f6Timo Sirainen
768b7f5783c8de119d7386321e5d0c72d5c2d9f6Timo Sirainen fprintf(stderr, "Available fetch fields: %s", fetch_fields[0].name);
768b7f5783c8de119d7386321e5d0c72d5c2d9f6Timo Sirainen for (i = 1; i < N_ELEMENTS(fetch_fields); i++)
079f54c97145a0a5daa36c37eead3eae91b67a1eTimo Sirainen fprintf(stderr, " %s", fetch_fields[i].name);
079f54c97145a0a5daa36c37eead3eae91b67a1eTimo Sirainen fprintf(stderr, "\n");
079f54c97145a0a5daa36c37eead3eae91b67a1eTimo Sirainen}
079f54c97145a0a5daa36c37eead3eae91b67a1eTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic void parse_fetch_fields(struct fetch_cmd_context *ctx, const char *str)
b08b33d1f5ce3721dc2d83586c9cb0ca141331fdTimo Sirainen{
b08b33d1f5ce3721dc2d83586c9cb0ca141331fdTimo Sirainen const char *const *fields, *name;
6ef7e31619edfaa17ed044b45861d106a86191efTimo Sirainen const struct fetch_field *field;
6ef7e31619edfaa17ed044b45861d106a86191efTimo Sirainen struct fetch_field hdr_field;
3955d6726c939b3b30527c22b70c879fbe78692eTimo Sirainen
3955d6726c939b3b30527c22b70c879fbe78692eTimo Sirainen memset(&hdr_field, 0, sizeof(hdr_field));
89caf81340a4da959ef18c5f9b9c99824a53066bTimo Sirainen hdr_field.print = fetch_hdr_field;
89caf81340a4da959ef18c5f9b9c99824a53066bTimo Sirainen
89caf81340a4da959ef18c5f9b9c99824a53066bTimo Sirainen t_array_init(&ctx->fields, 32);
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen t_array_init(&ctx->header_fields, 32);
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen fields = t_strsplit_spaces(str, " ");
9f19a50d5966643c4d1c5ca06868ac2ad31bc4d5Timo Sirainen for (; *fields != NULL; fields++) {
d9de52132072d80b8c268094b879c0ef5a108db3Timo Sirainen name = t_str_lcase(*fields);
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen
d9de52132072d80b8c268094b879c0ef5a108db3Timo Sirainen doveadm_print_header_simple(name);
d9de52132072d80b8c268094b879c0ef5a108db3Timo Sirainen if (strncmp(name, "hdr.", 4) == 0) {
d5cebe7f98e63d4e2822863ef2faa4971e8b3a5dTimo Sirainen name += 4;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen hdr_field.name = name;
685393de106e55b61f754d420e378d05bd462ebbTimo Sirainen array_append(&ctx->fields, &hdr_field, 1);
87712707722ef7d73acb065546e61afa4455cd9eTimo Sirainen array_append(&ctx->header_fields, &name, 1);
3b80595fcf2001cf7b2fcc6290823e38f4a142fcTimo Sirainen } else {
3b80595fcf2001cf7b2fcc6290823e38f4a142fcTimo Sirainen field = fetch_field_find(name);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (field == NULL) {
8a3f549a3cb1d6dd980a4fa3db284653e256dae7Timo Sirainen print_fetch_fields();
8a3f549a3cb1d6dd980a4fa3db284653e256dae7Timo Sirainen i_fatal("Unknown fetch field: %s", name);
8a3f549a3cb1d6dd980a4fa3db284653e256dae7Timo Sirainen }
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen ctx->wanted_fields |= field->wanted_fields;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen array_append(&ctx->fields, field, 1);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen }
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen }
5a86309a6c58bdeb9921bf2989aaabaaa04a29abTimo Sirainen (void)array_append_space(&ctx->header_fields);
5a86309a6c58bdeb9921bf2989aaabaaa04a29abTimo Sirainen}
5a86309a6c58bdeb9921bf2989aaabaaa04a29abTimo Sirainen
c979eeda1f46483d9c963e265786b701d7683d77Timo Sirainenstatic void cmd_fetch_mail(struct fetch_cmd_context *ctx)
c979eeda1f46483d9c963e265786b701d7683d77Timo Sirainen{
94a8cb0ee1d85569ad1a2acacd92d3ce22f8a1cbTimo Sirainen const struct fetch_field *field;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen struct mail *mail = ctx->mail;
94a8cb0ee1d85569ad1a2acacd92d3ce22f8a1cbTimo Sirainen
17da42c31202b1b3e7e308121ea17d922c24da1bTimo Sirainen array_foreach(&ctx->fields, field) {
17da42c31202b1b3e7e308121ea17d922c24da1bTimo Sirainen ctx->cur_field = field;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen if (field->print(ctx) < 0) {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen struct mail_storage *storage =
b20fb5b1df9d604a7541f5118fc5b4b466d211efTimo Sirainen mailbox_get_storage(mail->box);
b20fb5b1df9d604a7541f5118fc5b4b466d211efTimo Sirainen
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen i_error("fetch(%s) failed for box=%s uid=%u: %s",
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen field->name, mailbox_get_vname(mail->box),
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen mail->uid, mail_storage_get_last_error(storage, NULL));
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen }
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen }
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen}
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainenstatic int
bb26f09873c18f342cd1ab2d0ee0b9018e6546d9Timo Sirainencmd_fetch_box(struct fetch_cmd_context *ctx, const struct mailbox_info *info)
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen{
73b50eecfc31750a312e2f940023f522eb07178cTimo Sirainen struct doveadm_mail_iter *iter;
c4db5f0fb7cea8160dc10b5f0ab57ab7c02bf8a5Timo Sirainen struct mailbox_transaction_context *trans;
c4db5f0fb7cea8160dc10b5f0ab57ab7c02bf8a5Timo Sirainen struct mail *mail;
c4db5f0fb7cea8160dc10b5f0ab57ab7c02bf8a5Timo Sirainen struct mailbox_header_lookup_ctx *headers = NULL;
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen if (doveadm_mail_iter_init(info, ctx->ctx.search_args,
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen &trans, &iter) < 0)
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen return -1;
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen
dd9712b013e5a14939deed84b2e391d89897d2cfTimo Sirainen if (array_count(&ctx->header_fields) > 1) {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen headers = mailbox_header_lookup_init(
b5ea11802f2bafbec06282a7b3b6704dc5fae584Timo Sirainen mailbox_transaction_get_mailbox(trans),
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen array_idx(&ctx->header_fields, 0));
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen }
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen mail = mail_alloc(trans, ctx->wanted_fields, headers);
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen if (headers != NULL)
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen mailbox_header_lookup_unref(&headers);
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen while (doveadm_mail_iter_next(iter, mail)) {
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen ctx->mail = mail;
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen T_BEGIN {
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen cmd_fetch_mail(ctx);
3da614c39dd29f536c485089e67839b4cf89fed3Timo Sirainen } T_END;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen ctx->mail = NULL;
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen }
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen mail_free(&mail);
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen return doveadm_mail_iter_deinit(&iter);
88187ee880b4829443e0d55ea7d145d9d5880217Timo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic void
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainencmd_fetch_run(struct doveadm_mail_cmd_context *_ctx, struct mail_user *user)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen struct fetch_cmd_context *ctx = (struct fetch_cmd_context *)_ctx;
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen const enum mailbox_list_iter_flags iter_flags =
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen MAILBOX_LIST_ITER_NO_AUTO_INBOX |
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen MAILBOX_LIST_ITER_RETURN_NO_FLAGS;
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen struct doveadm_mail_list_iter *iter;
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen const struct mailbox_info *info;
8cf32443413f811d514123c5c74c95c87594b0e3Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen iter = doveadm_mail_list_iter_init(user, _ctx->search_args, iter_flags);
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen while ((info = doveadm_mail_list_iter_next(iter)) != NULL) T_BEGIN {
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen (void)cmd_fetch_box(ctx, info);
0c909e3461607eadcd66f4eac69b7f34e37fccf1Timo Sirainen } T_END;
0c909e3461607eadcd66f4eac69b7f34e37fccf1Timo Sirainen doveadm_mail_list_iter_deinit(&iter);
de62ce819d59a529530da4b57be1b8d6dad13d6bTimo Sirainen}
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainenstatic void cmd_fetch_deinit(struct doveadm_mail_cmd_context *_ctx)
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen{
16c89b1260c9d07c01c83a9219424d3727069b2eTimo Sirainen struct fetch_cmd_context *ctx = (struct fetch_cmd_context *)_ctx;
c251a38df327599a62d341bf5c2282f31352faa5Timo Sirainen
c251a38df327599a62d341bf5c2282f31352faa5Timo Sirainen o_stream_unref(&ctx->output);
c251a38df327599a62d341bf5c2282f31352faa5Timo Sirainen}
c251a38df327599a62d341bf5c2282f31352faa5Timo Sirainen
ad48319996942463675b53877092ab7e13a7a75aTimo Sirainenstatic void cmd_fetch_init(struct doveadm_mail_cmd_context *_ctx,
ad48319996942463675b53877092ab7e13a7a75aTimo Sirainen const char *const args[])
ad48319996942463675b53877092ab7e13a7a75aTimo Sirainen{
4b89231f4ec9cc69f4aea715e1d34f405c7e317dTimo Sirainen struct fetch_cmd_context *ctx = (struct fetch_cmd_context *)_ctx;
4b89231f4ec9cc69f4aea715e1d34f405c7e317dTimo Sirainen const char *fetch_fields = args[0];
4b89231f4ec9cc69f4aea715e1d34f405c7e317dTimo Sirainen
ae8817f05005f57bba32479a610b52d083e2b6ebTimo Sirainen if (fetch_fields == NULL || args[1] == NULL)
ae8817f05005f57bba32479a610b52d083e2b6ebTimo Sirainen doveadm_mail_help_name("fetch");
ae8817f05005f57bba32479a610b52d083e2b6ebTimo Sirainen
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainen parse_fetch_fields(ctx, fetch_fields);
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainen _ctx->search_args = doveadm_mail_build_search_args(args + 1);
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainen
8872e5c991430f96138a46e36b7f3c2c40d8e5c2Timo Sirainen ctx->output = o_stream_create_fd(STDOUT_FILENO, 0, FALSE);
8872e5c991430f96138a46e36b7f3c2c40d8e5c2Timo Sirainen}
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainen
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainenstatic struct doveadm_mail_cmd_context *cmd_fetch_alloc(void)
651fc0f1e43fef3e02e0e7b5f498973b05f641d7Timo Sirainen{
6c2ddb9f586e6392552ddfb82ab55e57fcfc4110Timo Sirainen struct fetch_cmd_context *ctx;
6c2ddb9f586e6392552ddfb82ab55e57fcfc4110Timo Sirainen
16c89b1260c9d07c01c83a9219424d3727069b2eTimo Sirainen ctx = doveadm_mail_cmd_alloc(struct fetch_cmd_context);
6825360d446542046757b06064282301c4c6b27cTimo Sirainen ctx->ctx.v.init = cmd_fetch_init;
6ef7e31619edfaa17ed044b45861d106a86191efTimo Sirainen ctx->ctx.v.run = cmd_fetch_run;
6825360d446542046757b06064282301c4c6b27cTimo Sirainen ctx->ctx.v.deinit = cmd_fetch_deinit;
6825360d446542046757b06064282301c4c6b27cTimo Sirainen doveadm_print_init("pager");
6825360d446542046757b06064282301c4c6b27cTimo Sirainen return &ctx->ctx;
6825360d446542046757b06064282301c4c6b27cTimo Sirainen}
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainenstruct doveadm_mail_cmd cmd_fetch = {
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen cmd_fetch_alloc, "fetch", "<fields> <search query>"
8d80659e504ffb34bb0c6a633184fece35751b18Timo Sirainen};
bb10ebcf076c959c752f583746d83805d7686df8Timo Sirainen