melib: {create,delete}_folder returns updated folders
Potential parent folders will have their children fields updated, so just return all folders.memfd
parent
9a46e58029
commit
f38d03e43a
|
@ -272,11 +272,17 @@ pub trait MailBackend: ::std::fmt::Debug + Send + Sync {
|
||||||
unimplemented!()
|
unimplemented!()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn create_folder(&mut self, _path: String) -> Result<Folder> {
|
fn create_folder(
|
||||||
|
&mut self,
|
||||||
|
_path: String,
|
||||||
|
) -> Result<(FolderHash, FnvHashMap<FolderHash, Folder>)> {
|
||||||
Err(MeliError::new("Unimplemented."))
|
Err(MeliError::new("Unimplemented."))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn delete_folder(&mut self, _folder_hash: FolderHash) -> Result<()> {
|
fn delete_folder(
|
||||||
|
&mut self,
|
||||||
|
_folder_hash: FolderHash,
|
||||||
|
) -> Result<FnvHashMap<FolderHash, Folder>> {
|
||||||
Err(MeliError::new("Unimplemented."))
|
Err(MeliError::new("Unimplemented."))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -442,7 +442,10 @@ impl MailBackend for ImapType {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn create_folder(&mut self, mut path: String) -> Result<Folder> {
|
fn create_folder(
|
||||||
|
&mut self,
|
||||||
|
mut path: String,
|
||||||
|
) -> Result<(FolderHash, FnvHashMap<FolderHash, Folder>)> {
|
||||||
/* Must transform path to something the IMAP server will accept
|
/* Must transform path to something the IMAP server will accept
|
||||||
*
|
*
|
||||||
* Each root mailbox has a hierarchy delimeter reported by the LIST entry. All paths
|
* Each root mailbox has a hierarchy delimeter reported by the LIST entry. All paths
|
||||||
|
@ -487,16 +490,13 @@ impl MailBackend for ImapType {
|
||||||
}
|
}
|
||||||
let ret: Result<()> = ImapResponse::from(&response).into();
|
let ret: Result<()> = ImapResponse::from(&response).into();
|
||||||
ret?;
|
ret?;
|
||||||
|
let new_hash = get_path_hash!(path.as_str());
|
||||||
folders.clear();
|
folders.clear();
|
||||||
drop(folders);
|
drop(folders);
|
||||||
self.folders().map_err(|err| format!("Mailbox create was succesful (returned `{}`) but listing mailboxes afterwards returned `{}`", response, err))?;
|
Ok((new_hash, self.folders().map_err(|err| MeliError::new(format!("Mailbox create was succesful (returned `{}`) but listing mailboxes afterwards returned `{}`", response, err)))?))
|
||||||
let new_hash = get_path_hash!(path.as_str());
|
|
||||||
Ok(BackendFolder::clone(
|
|
||||||
&self.folders.read().unwrap()[&new_hash],
|
|
||||||
))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn delete_folder(&mut self, folder_hash: FolderHash) -> Result<()> {
|
fn delete_folder(&mut self, folder_hash: FolderHash) -> Result<FnvHashMap<FolderHash, Folder>> {
|
||||||
let mut folders = self.folders.write().unwrap();
|
let mut folders = self.folders.write().unwrap();
|
||||||
let permissions = folders[&folder_hash].permissions();
|
let permissions = folders[&folder_hash].permissions();
|
||||||
if !permissions.delete_mailbox {
|
if !permissions.delete_mailbox {
|
||||||
|
@ -541,12 +541,10 @@ impl MailBackend for ImapType {
|
||||||
conn_lck.read_response(&mut response)?;
|
conn_lck.read_response(&mut response)?;
|
||||||
}
|
}
|
||||||
let ret: Result<()> = ImapResponse::from(&response).into();
|
let ret: Result<()> = ImapResponse::from(&response).into();
|
||||||
if ret.is_ok() {
|
ret?;
|
||||||
folders.clear();
|
folders.clear();
|
||||||
drop(folders);
|
drop(folders);
|
||||||
self.folders().map_err(|err| format!("Mailbox delete was succesful (returned `{}`) but listing mailboxes afterwards returned `{}`", response, err))?;
|
self.folders().map_err(|err| format!("Mailbox delete was succesful (returned `{}`) but listing mailboxes afterwards returned `{}`", response, err).into())
|
||||||
}
|
|
||||||
ret
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn set_folder_subscription(&mut self, folder_hash: FolderHash, new_val: bool) -> Result<()> {
|
fn set_folder_subscription(&mut self, folder_hash: FolderHash, new_val: bool) -> Result<()> {
|
||||||
|
|
|
@ -636,7 +636,10 @@ impl MailBackend for MaildirType {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
fn create_folder(&mut self, new_path: String) -> Result<Folder> {
|
fn create_folder(
|
||||||
|
&mut self,
|
||||||
|
new_path: String,
|
||||||
|
) -> Result<(FolderHash, FnvHashMap<FolderHash, Folder>)> {
|
||||||
let mut path = self.path.clone();
|
let mut path = self.path.clone();
|
||||||
path.push(&new_path);
|
path.push(&new_path);
|
||||||
if !path.starts_with(&self.path) {
|
if !path.starts_with(&self.path) {
|
||||||
|
@ -655,6 +658,11 @@ impl MailBackend for MaildirType {
|
||||||
});
|
});
|
||||||
|
|
||||||
let folder_hash = get_path_hash!(&path);
|
let folder_hash = get_path_hash!(&path);
|
||||||
|
if let Some(parent) = parent {
|
||||||
|
self.folders
|
||||||
|
.entry(parent)
|
||||||
|
.and_modify(|entry| entry.children.push(folder_hash));
|
||||||
|
}
|
||||||
let new_folder = MaildirFolder {
|
let new_folder = MaildirFolder {
|
||||||
hash: folder_hash,
|
hash: folder_hash,
|
||||||
path: PathBuf::from(&new_path),
|
path: PathBuf::from(&new_path),
|
||||||
|
@ -669,12 +677,14 @@ impl MailBackend for MaildirType {
|
||||||
total: Default::default(),
|
total: Default::default(),
|
||||||
};
|
};
|
||||||
|
|
||||||
let ret = BackendFolder::clone(debug!(&new_folder));
|
|
||||||
self.folders.insert(folder_hash, new_folder);
|
self.folders.insert(folder_hash, new_folder);
|
||||||
Ok(ret)
|
Ok((folder_hash, self.folders()?))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn delete_folder(&mut self, _folder_hash: FolderHash) -> Result<()> {
|
fn delete_folder(
|
||||||
|
&mut self,
|
||||||
|
_folder_hash: FolderHash,
|
||||||
|
) -> Result<FnvHashMap<FolderHash, Folder>> {
|
||||||
Err(MeliError::new("Unimplemented."))
|
Err(MeliError::new("Unimplemented."))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -354,16 +354,12 @@ impl Collection {
|
||||||
self.message_ids
|
self.message_ids
|
||||||
.insert(envelope.message_id().raw().to_vec(), hash);
|
.insert(envelope.message_id().raw().to_vec(), hash);
|
||||||
self.envelopes.write().unwrap().insert(hash, envelope);
|
self.envelopes.write().unwrap().insert(hash, envelope);
|
||||||
if !self
|
self.threads
|
||||||
.threads
|
|
||||||
.entry(folder_hash)
|
.entry(folder_hash)
|
||||||
.or_default()
|
.or_default()
|
||||||
.insert_reply(&mut self.envelopes, hash)
|
.insert(&mut self.envelopes, hash);
|
||||||
{
|
if self.sent_folder.map(|f| f == folder_hash).unwrap_or(false) {
|
||||||
self.threads
|
self.insert_reply(hash);
|
||||||
.entry(folder_hash)
|
|
||||||
.or_default()
|
|
||||||
.insert(&mut self.envelopes, hash);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -865,7 +865,7 @@ impl Account {
|
||||||
}
|
}
|
||||||
match op {
|
match op {
|
||||||
FolderOperation::Create(path) => {
|
FolderOperation::Create(path) => {
|
||||||
let mut folder = self
|
let (folder_hash, mut folders) = self
|
||||||
.backend
|
.backend
|
||||||
.write()
|
.write()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
|
@ -873,40 +873,51 @@ impl Account {
|
||||||
self.sender
|
self.sender
|
||||||
.send(ThreadEvent::UIEvent(UIEvent::MailboxCreate((
|
.send(ThreadEvent::UIEvent(UIEvent::MailboxCreate((
|
||||||
self.index,
|
self.index,
|
||||||
folder.hash(),
|
folder_hash,
|
||||||
))))
|
))))
|
||||||
.unwrap();
|
.unwrap();
|
||||||
let mut new = FileFolderConf::default();
|
let mut new = FileFolderConf::default();
|
||||||
new.folder_conf.subscribe = super::ToggleFlag::InternalVal(true);
|
new.folder_conf.subscribe = super::ToggleFlag::InternalVal(true);
|
||||||
new.folder_conf.usage = if folder.special_usage() != SpecialUsageMailbox::Normal {
|
new.folder_conf.usage =
|
||||||
Some(folder.special_usage())
|
if folders[&folder_hash].special_usage() != SpecialUsageMailbox::Normal {
|
||||||
} else {
|
Some(folders[&folder_hash].special_usage())
|
||||||
let tmp = SpecialUsageMailbox::detect_usage(folder.name());
|
} else {
|
||||||
if tmp != Some(SpecialUsageMailbox::Normal) && tmp != None {
|
let tmp = SpecialUsageMailbox::detect_usage(folders[&folder_hash].name());
|
||||||
let _ = folder.set_special_usage(tmp.unwrap());
|
if tmp != Some(SpecialUsageMailbox::Normal) && tmp != None {
|
||||||
}
|
folders.entry(folder_hash).and_modify(|entry| {
|
||||||
tmp
|
let _ = entry.set_special_usage(tmp.unwrap());
|
||||||
};
|
});
|
||||||
|
}
|
||||||
|
tmp
|
||||||
|
};
|
||||||
|
/* if new folder has parent, we need to update its children field */
|
||||||
|
if let Some(parent_hash) = folders[&folder_hash].parent() {
|
||||||
|
self.folder_entries.entry(parent_hash).and_modify(|parent| {
|
||||||
|
parent.ref_folder = folders.remove(&parent_hash).unwrap();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
let folder_hash = folder.hash();
|
|
||||||
self.folder_entries.insert(
|
self.folder_entries.insert(
|
||||||
folder_hash,
|
folder_hash,
|
||||||
FolderEntry {
|
FolderEntry {
|
||||||
name: folder.path().to_string(),
|
name: folders[&folder_hash].path().to_string(),
|
||||||
status: MailboxStatus::Parsing(0, 0),
|
status: MailboxStatus::Parsing(0, 0),
|
||||||
conf: new,
|
conf: new,
|
||||||
worker: Account::new_worker(
|
worker: Account::new_worker(
|
||||||
folder.clone(),
|
folders[&folder_hash].clone(),
|
||||||
&mut self.backend,
|
&mut self.backend,
|
||||||
&self.work_context,
|
&self.work_context,
|
||||||
self.notify_fn.clone(),
|
self.notify_fn.clone(),
|
||||||
),
|
),
|
||||||
ref_folder: folder,
|
ref_folder: folders.remove(&folder_hash).unwrap(),
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
self.collection
|
self.collection
|
||||||
.threads
|
.threads
|
||||||
.insert(folder_hash, Threads::default());
|
.insert(folder_hash, Threads::default());
|
||||||
|
self.collection
|
||||||
|
.mailboxes
|
||||||
|
.insert(folder_hash, Default::default());
|
||||||
build_folders_order(
|
build_folders_order(
|
||||||
&mut self.tree,
|
&mut self.tree,
|
||||||
&self.folder_entries,
|
&self.folder_entries,
|
||||||
|
@ -927,7 +938,7 @@ impl Account {
|
||||||
} else {
|
} else {
|
||||||
return Err(MeliError::new("Mailbox with that path not found."));
|
return Err(MeliError::new("Mailbox with that path not found."));
|
||||||
};
|
};
|
||||||
self.backend.write().unwrap().delete_folder(folder_hash)?;
|
let mut folders = self.backend.write().unwrap().delete_folder(folder_hash)?;
|
||||||
self.sender
|
self.sender
|
||||||
.send(ThreadEvent::UIEvent(UIEvent::MailboxDelete((
|
.send(ThreadEvent::UIEvent(UIEvent::MailboxDelete((
|
||||||
self.index,
|
self.index,
|
||||||
|
@ -944,8 +955,24 @@ impl Account {
|
||||||
self.sent_folder = None;
|
self.sent_folder = None;
|
||||||
}
|
}
|
||||||
self.collection.threads.remove(&folder_hash);
|
self.collection.threads.remove(&folder_hash);
|
||||||
|
/* if deleted folder had parent, we need to update its children field */
|
||||||
|
if let Some(parent_hash) = self
|
||||||
|
.folder_entries
|
||||||
|
.remove(&folder_hash)
|
||||||
|
.unwrap()
|
||||||
|
.ref_folder
|
||||||
|
.parent()
|
||||||
|
{
|
||||||
|
self.folder_entries.entry(parent_hash).and_modify(|parent| {
|
||||||
|
parent.ref_folder = folders.remove(&parent_hash).unwrap();
|
||||||
|
});
|
||||||
|
}
|
||||||
self.collection.mailboxes.remove(&folder_hash);
|
self.collection.mailboxes.remove(&folder_hash);
|
||||||
self.folder_entries.remove(&folder_hash);
|
build_folders_order(
|
||||||
|
&mut self.tree,
|
||||||
|
&self.folder_entries,
|
||||||
|
&mut self.folders_order,
|
||||||
|
);
|
||||||
// FIXME Kill worker as well
|
// FIXME Kill worker as well
|
||||||
|
|
||||||
// FIXME remove from settings as well
|
// FIXME remove from settings as well
|
||||||
|
@ -1063,7 +1090,6 @@ fn build_folders_order(
|
||||||
folder_entries: &FnvHashMap<FolderHash, FolderEntry>,
|
folder_entries: &FnvHashMap<FolderHash, FolderEntry>,
|
||||||
folders_order: &mut Vec<FolderHash>,
|
folders_order: &mut Vec<FolderHash>,
|
||||||
) {
|
) {
|
||||||
let mut stack: SmallVec<[FolderHash; 8]> = SmallVec::new();
|
|
||||||
tree.clear();
|
tree.clear();
|
||||||
folders_order.clear();
|
folders_order.clear();
|
||||||
for (h, f) in folder_entries.iter() {
|
for (h, f) in folder_entries.iter() {
|
||||||
|
@ -1079,20 +1105,14 @@ fn build_folders_order(
|
||||||
depth,
|
depth,
|
||||||
};
|
};
|
||||||
for &c in folder_entries[&h].ref_folder.children() {
|
for &c in folder_entries[&h].ref_folder.children() {
|
||||||
node.children.push(rec(c, folder_entries, depth + 1));
|
if folder_entries.contains_key(&c) {
|
||||||
|
node.children.push(rec(c, folder_entries, depth + 1));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
node
|
node
|
||||||
};
|
};
|
||||||
|
|
||||||
tree.push(rec(*h, &folder_entries, 0));
|
tree.push(rec(*h, &folder_entries, 0));
|
||||||
for &c in f.ref_folder.children() {
|
|
||||||
stack.push(c);
|
|
||||||
}
|
|
||||||
while let Some(next) = stack.pop() {
|
|
||||||
for c in folder_entries[&next].ref_folder.children() {
|
|
||||||
stack.push(*c);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -213,7 +213,10 @@ impl MailBackend for PluginBackend {
|
||||||
fn save(&self, _bytes: &[u8], _folder: &str, _flags: Option<Flag>) -> Result<()> {
|
fn save(&self, _bytes: &[u8], _folder: &str, _flags: Option<Flag>) -> Result<()> {
|
||||||
Err(MeliError::new("Unimplemented."))
|
Err(MeliError::new("Unimplemented."))
|
||||||
}
|
}
|
||||||
fn create_folder(&mut self, _name: String) -> Result<Folder> {
|
fn create_folder(
|
||||||
|
&mut self,
|
||||||
|
_name: String,
|
||||||
|
) -> Result<(FolderHash, FnvHashMap<FolderHash, Folder>)> {
|
||||||
Err(MeliError::new("Unimplemented."))
|
Err(MeliError::new("Unimplemented."))
|
||||||
}
|
}
|
||||||
fn tags(&self) -> Option<Arc<RwLock<BTreeMap<u64, String>>>> {
|
fn tags(&self) -> Option<Arc<RwLock<BTreeMap<u64, String>>>> {
|
||||||
|
|
Loading…
Reference in New Issue