summaryrefslogtreecommitdiffstats
path: root/melib/src/mailbox.rs
blob: 49cc35c6c71b2c0693f23ca8a5423077f736f568 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
/*
 * meli - mailbox module.
 *
 * Copyright 2017 Manos Pitsidianakis
 *
 * This file is part of meli.
 *
 * meli is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * meli is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with meli. If not, see <http://www.gnu.org/licenses/>.
 */

/*!
 * Mail related code.
 *
 * This module handles reading emails from various backends, handling account data etc
 */

pub mod email;
pub use self::email::*;
/* Mail backends. Currently only maildir is supported */
pub mod backends;
use self::backends::Folder;
use crate::error::Result;
pub mod thread;
pub use self::thread::{SortField, SortOrder, ThreadNode, Threads};

mod collection;
pub use self::collection::*;

use std::option::Option;

/// `Mailbox` represents a folder of mail.
#[derive(Debug, Clone, Default)]
pub struct Mailbox {
    pub folder: Folder,
    name: String,
    pub collection: Collection,
    has_sent: bool,
}

impl Mailbox {
    pub fn new(folder: Folder, envelopes: Result<Vec<Envelope>>) -> Result<Mailbox> {
        let mut envelopes: Vec<Envelope> = envelopes?;
        envelopes.sort_by(|a, b| a.date().cmp(&b.date()));
        let collection = Collection::new(envelopes, &folder);
        let name = folder.name().into();
        Ok(Mailbox {
            folder,
            collection,
            name,
            ..Default::default()
        })
    }

    pub fn name(&self) -> &str {
        &self.name
    }

    pub fn is_empty(&self) -> bool {
        self.collection.is_empty()
    }
    pub fn len(&self) -> usize {
        self.collection.len()
    }
    pub fn thread_to_mail_mut(&mut self, i: usize) -> &mut Envelope {
        self.collection
            .envelopes
            .entry(self.collection.threads.thread_to_mail(i))
            .or_default()
    }
    pub fn thread_to_mail(&self, i: usize) -> &Envelope {
        &self.collection.envelopes[&self.collection.threads.thread_to_mail(i)]
    }
    pub fn threaded_mail(&self, i: usize) -> EnvelopeHash {
        self.collection.threads.thread_to_mail(i)
    }
    pub fn mail_and_thread(&mut self, i: EnvelopeHash) -> (&mut Envelope, &ThreadNode) {
        let thread;
        {
            let x = &mut self.collection.envelopes.entry(i).or_default();
            thread = &self.collection.threads[x.thread()];
        }
        (self.collection.envelopes.entry(i).or_default(), thread)
    }
    pub fn thread(&self, i: usize) -> &ThreadNode {
        &self.collection.threads.thread_nodes()[i]
    }

    pub fn insert_sent_folder(&mut self, _sent: &Mailbox) {
        /*if !self.has_sent {
            for envelope in sent.collection.envelopes.values() {
                self.insert_reply(envelope);
            }
            self.has_sent = true;
        }*/
    }

    pub fn rename(&mut self, old_hash: EnvelopeHash, new_hash: EnvelopeHash) {
        self.collection.rename(old_hash, new_hash);
    }

    pub fn update(&mut self, old_hash: EnvelopeHash, envelope: Envelope) {
        self.collection.update_envelope(old_hash, envelope);
    }

    pub fn insert(&mut self, envelope: Envelope) -> &Envelope {
        let hash = envelope.hash();
        self.collection.insert(envelope);
        &self.collection[&hash]
    }

    pub fn insert_reply(&mut self, envelope: &Envelope) {
        if cfg!(feature = "debug_log") {
            eprintln!("mailbox insert reply {}", self.name);
        }
        self.collection.insert_reply(envelope);
    }

    pub fn remove(&mut self, envelope_hash: EnvelopeHash) {
        self.collection.remove(envelope_hash);
        //   if cfg!(feature = "debug_log") { eprintln!("envelope_hash: {}\ncollection:\n{:?}", envelope_hash, self.collection); }
    }
}