use alloc::{collections::BTreeSet, string::String, vec::Vec};
use chrono::{DateTime, FixedOffset};
use crate::{address::Address, flag::types::Flag};
#[derive(Clone, Debug)]
pub struct FlagUpdate {
pub id: String,
pub flags: BTreeSet<Flag>,
}
#[derive(Clone, Debug)]
pub enum EnvelopeDiff {
FullListRequired { new_state: Option<Vec<u8>> },
Incremental {
new_state: Vec<u8>,
flag_updates: Vec<FlagUpdate>,
new_envelopes: Vec<Envelope>,
vanished_ids: Vec<String>,
},
}
#[derive(Clone, Debug, PartialEq, Eq)]
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
#[cfg_attr(feature = "serde", serde(rename_all = "kebab-case"))]
pub struct Envelope {
pub id: String,
#[cfg_attr(feature = "serde", serde(default))]
pub message_id: Option<String>,
#[cfg_attr(feature = "serde", serde(default))]
pub flags: BTreeSet<Flag>,
#[cfg_attr(feature = "serde", serde(default))]
pub subject: String,
#[cfg_attr(feature = "serde", serde(default))]
pub from: Vec<Address>,
#[cfg_attr(feature = "serde", serde(default))]
pub to: Vec<Address>,
#[cfg_attr(feature = "serde", serde(default))]
pub date: Option<DateTime<FixedOffset>>,
#[cfg_attr(feature = "serde", serde(default))]
pub size: u64,
#[cfg_attr(feature = "serde", serde(default))]
pub has_attachment: Option<bool>,
}
pub fn normalize_message_id(raw: &str) -> Option<String> {
use alloc::string::ToString;
let trimmed = raw.trim();
let inner = trimmed
.strip_prefix('<')
.and_then(|s| s.strip_suffix('>'))
.unwrap_or(trimmed)
.trim();
if inner.is_empty() {
None
} else {
Some(inner.to_string())
}
}