refactor: use AppendCmd instead of AppendOptions

This commit is contained in:
Michael Bøcker-Larsen 2020-12-17 11:02:48 +08:00
parent 24445c5c65
commit cdf320fb0c
No known key found for this signature in database
GPG key ID: FEC5F9A03674F95A
2 changed files with 57 additions and 77 deletions

View file

@ -84,28 +84,16 @@ pub struct Connection<T: Read + Write> {
pub greeting_read: bool, pub greeting_read: bool,
} }
/// A set of options for the append command
#[derive(Default)]
pub struct AppendOptions<'a> {
/// Optional list of flags
pub flags: Option<&'a [Flag<'a>]>,
/// Optional internal date
pub date: Option<DateTime<FixedOffset>>,
}
/// A builder for the append command /// A builder for the append command
#[derive(Default)] pub struct AppendCmd<'a, T: Read + Write> {
pub struct AppendCmd<'a> { session: &'a Session<T>,
content: &'a [u8],
mailbox: &'a str,
flags: Vec<&'a Flag<'a>>, flags: Vec<&'a Flag<'a>>,
date: Option<DateTime<FixedOffset>>, date: Option<DateTime<FixedOffset>>,
} }
impl<'a> AppendCmd<'a> { impl<'a, T: Read + Write> AppendCmd<'a, T> {
/// Create a new AppendCmd builder
pub fn create() -> Self {
Self::default()
}
/// Append a flag /// Append a flag
pub fn flag(&mut self, flag: &'a Flag<'a>) -> &mut Self { pub fn flag(&mut self, flag: &'a Flag<'a>) -> &mut Self {
self.flags.push(flag); self.flags.push(flag);
@ -117,14 +105,40 @@ impl<'a> AppendCmd<'a> {
self.date = Some(date); self.date = Some(date);
self self
} }
}
impl<'a> Into<AppendOptions<'a>> for AppendCmd<'a> { /// Run command when set up
fn into(self) -> AppendOptions<'a> { #[must_use]
AppendOptions { pub fn run(&self) -> Result<()> {
flags: Some(&self.flags[..]), let flagstr = self
date: self.date, .flags
.into_iter()
.filter(|f| **f != Flag::Recent)
.map(|f| f.to_string())
.collect::<Vec<String>>()
.join(" ");
let datestr = if let Some(date) = self.date {
format!(" \"{}\"", date.format("%d-%h-%Y %T %z"))
} else {
"".to_string()
};
self.session.run_command(&format!(
"APPEND \"{}\" ({}){} {{{}}}",
self.mailbox,
flagstr,
datestr,
self.content.len()
))?;
let mut v = Vec::new();
self.session.readline(&mut v)?;
if !v.starts_with(b"+") {
return Err(Error::Append);
} }
self.session.stream.write_all(self.content)?;
self.session.stream.write_all(b"\r\n")?;
self.session.stream.flush()?;
self.session.read_response().map(|_| ())
} }
} }
@ -1147,42 +1161,14 @@ impl<T: Read + Write> Session<T> {
&mut self, &mut self,
mailbox: S, mailbox: S,
content: B, content: B,
options: impl Into<Option<AppendOptions<'a>>>, ) -> AppendCmd<'a, T> {
) -> Result<()> { AppendCmd {
let content = content.as_ref(); session: &self,
let options_ = options.into().unwrap_or(AppendOptions::default()); content: content.as_ref(),
mailbox: mailbox.as_ref(),
let flagstr = options_ flags: Vec::new(),
.flags date: None,
.unwrap_or(&[])
.iter()
.filter(|f| **f != Flag::Recent)
.map(|f| f.to_string())
.collect::<Vec<String>>()
.join(" ");
let datestr = if let Some(date) = options_.date {
format!(" \"{}\"", date.format("%d-%h-%Y %T %z"))
} else {
"".to_string()
};
self.run_command(&format!(
"APPEND \"{}\" ({}){} {{{}}}",
mailbox.as_ref(),
flagstr,
datestr,
content.len()
))?;
let mut v = Vec::new();
self.readline(&mut v)?;
if !v.starts_with(b"+") {
return Err(Error::Append);
} }
self.stream.write_all(content)?;
self.stream.write_all(b"\r\n")?;
self.stream.flush()?;
self.read_response().map(|_| ())
} }
/// The [`SEARCH` command](https://tools.ietf.org/html/rfc3501#section-6.4.4) searches the /// The [`SEARCH` command](https://tools.ietf.org/html/rfc3501#section-6.4.4) searches the

View file

@ -253,7 +253,8 @@ fn append() {
let mbox = "INBOX"; let mbox = "INBOX";
c.select(mbox).unwrap(); c.select(mbox).unwrap();
//append //append
c.append(mbox, e.message_to_string().unwrap(), None) c.append(mbox, e.message_to_string().unwrap())
.run()
.unwrap(); .unwrap();
// now we should see the e-mail! // now we should see the e-mail!
@ -302,15 +303,11 @@ fn append_with_flags() {
c.select(mbox).unwrap(); c.select(mbox).unwrap();
//append //append
let flags: &[Flag] = &[Flag::Seen, Flag::Flagged]; let flags: &[Flag] = &[Flag::Seen, Flag::Flagged];
c.append( c.append(mbox, e.message_to_string().unwrap())
mbox, .flag(Flag::Seen)
e.message_to_string().unwrap(), .flag(Flag::Flagged)
imap::AppendOptions { .run()
flags: Some(flags), .unwrap();
date: None,
},
)
.unwrap();
// now we should see the e-mail! // now we should see the e-mail!
let inbox = c.uid_search("ALL").unwrap(); let inbox = c.uid_search("ALL").unwrap();
@ -366,15 +363,12 @@ fn append_with_flags_and_date() {
let date = FixedOffset::east(8 * 3600) let date = FixedOffset::east(8 * 3600)
.ymd(2020, 12, 13) .ymd(2020, 12, 13)
.and_hms(13, 36, 36); .and_hms(13, 36, 36);
c.append( c.append(mbox, e.message_to_string().unwrap())
mbox, .flag(Flag::Seen)
e.message_to_string().unwrap(), .flag(Flag::Flagged)
imap::AppendOptions { .internal_date(date)
flags: Some(flags), .run()
date: Some(date), .unwrap();
},
)
.unwrap();
// now we should see the e-mail! // now we should see the e-mail!
let inbox = c.uid_search("ALL").unwrap(); let inbox = c.uid_search("ALL").unwrap();