Also resync UIDs in folders that are not configured (#2289)

This commit is contained in:
Hocuri
2022-03-10 16:12:24 +01:00
committed by GitHub
parent 332cb0896b
commit d9441a6bdd
3 changed files with 43 additions and 27 deletions

View File

@@ -2,10 +2,12 @@ use std::{collections::BTreeMap, time::Instant};
use anyhow::{Context as _, Result};
use crate::config::Config;
use crate::imap::Imap;
use crate::{config::Config, log::LogExt};
use crate::log::LogExt;
use crate::{context::Context, imap::FolderMeaning};
use async_std::prelude::*;
use async_std::stream::StreamExt;
use super::{get_folder_meaning, get_folder_meaning_by_name};
@@ -27,22 +29,12 @@ impl Imap {
info!(context, "Starting full folder scan");
self.prepare(context).await?;
let session = self.session.as_mut();
let session = session.context("scan_folders(): IMAP No Connection established")?;
let folders: Vec<_> = session.list(Some(""), Some("*")).await?.collect().await;
let folders = self.list_folders(context).await?;
let watched_folders = get_watched_folders(context).await?;
let mut folder_configs = BTreeMap::new();
for folder in folders {
let folder = match folder {
Ok(f) => f,
Err(e) => {
warn!(context, "Can't get folder: {}", e);
continue;
}
};
// Gmail labels are not folders and should be skipped. For example,
// emails appear in the inbox and under "All Mail" as soon as it is
// received. The code used to wrongly conclude that the email had
@@ -101,6 +93,20 @@ impl Imap {
last_scan.replace(Instant::now());
Ok(true)
}
/// Returns the names of all folders on the IMAP server.
pub async fn list_folders(
self: &mut Imap,
context: &Context,
) -> Result<Vec<async_imap::types::Name>> {
let session = self.session.as_mut();
let session = session.context("No IMAP connection")?;
let list = session
.list(Some(""), Some("*"))
.await?
.filter_map(|f| f.ok_or_log_msg(context, "list_folders() can't get folder"));
Ok(list.collect().await)
}
}
pub(crate) async fn get_watched_folder_configs(context: &Context) -> Result<Vec<Config>> {

View File

@@ -365,29 +365,38 @@ impl Job {
Status::Finished(Ok(()))
}
/// Synchronizes UIDs for sentbox, inbox and mvbox.
/// Synchronizes UIDs for all folders.
async fn resync_folders(&mut self, context: &Context, imap: &mut Imap) -> Status {
if let Err(err) = imap.prepare(context).await {
warn!(context, "could not connect: {:?}", err);
return Status::RetryLater;
}
let sentbox_folder = job_try!(context.get_config(Config::ConfiguredSentboxFolder).await);
if let Some(sentbox_folder) = sentbox_folder {
job_try!(imap.resync_folder_uids(context, sentbox_folder).await);
let all_folders = match imap.list_folders(context).await {
Ok(v) => v,
Err(e) => {
warn!(context, "Listing folders for resync failed: {:#}", e);
return Status::RetryLater;
}
};
let mut any_failed = false;
for folder in all_folders {
if let Err(e) = imap
.resync_folder_uids(context, folder.name().to_string())
.await
{
warn!(context, "{:#}", e);
any_failed = true;
}
}
let inbox_folder = job_try!(context.get_config(Config::ConfiguredInboxFolder).await);
if let Some(inbox_folder) = inbox_folder {
job_try!(imap.resync_folder_uids(context, inbox_folder).await);
if any_failed {
Status::RetryLater
} else {
Status::Finished(Ok(()))
}
let mvbox_folder = job_try!(context.get_config(Config::ConfiguredMvboxFolder).await);
if let Some(mvbox_folder) = mvbox_folder {
job_try!(imap.resync_folder_uids(context, mvbox_folder).await);
}
Status::Finished(Ok(()))
}
async fn markseen_msg_on_imap(&mut self, context: &Context, imap: &mut Imap) -> Status {