contack 0.9.2

A simple and easy contact library.
Documentation
//! Struct for representing contact information.

#[cfg(feature = "diesel_support")]
use crate::schema::*;
use crate::*;

/// Represents contact information as it should appear
/// in sql.
#[cfg_attr(
    feature = "diesel_support",
    derive(Queryable, Identifiable, Insertable, AsChangeset),
    primary_key(pid),
    table_name = "contacts_contact_information"
)]
#[cfg_attr(feature = "sqlx", derive(sqlx::FromRow))]
pub struct SqlContactInformation {
    /// The pid, used for representing this. Should be
    /// unique.
    pub pid: String,

    /// The Preference Value
    pub pref: i16,

    /// The Value (for example johndoe@example.com)
    pub value: String,

    /// The platform which this is on
    pub platform: ContactPlatform,

    /// The type
    pub typ: Option<Type>,

    /// The UUID of the associated contact.
    pub uid: String,
}

impl SqlContactInformation {
    /// Empties contact information from a contact.
    ///
    /// Extracts, by means of emptying the contact information in a contact,
    /// the contact information so that it can be used by diesel. Later,
    /// use `insert_contact_information` to replace it back.
    ///
    /// This does involve cloning, as the UUID of the contact must be
    /// cloned for these structs to work :/.
    #[must_use]
    pub fn extract_contact_information(contact: &mut Contact) -> Vec<Self> {
        let uid = contact.uid.clone();
        // Get the contact information, replacing it with an empty vec.
        let ci =
            contact.contact_information.drain(..);

        // Loop through everything in the contact information.
        ci
            .map(|x| Self::convert_from(x, uid.clone()))
            .collect()
    }

    /// Converts a normal `ContactInformation` into a `SqlContactInformation`
    #[must_use]
    pub fn convert_from(ci: ContactInformation, uid: String) -> Self {
        Self {
            pid: ci.pid,
            pref: ci.pref.into(),
            value: ci.value,
            platform: ci.platform,
            typ: ci.typ,
            uid,
        }
    }

    /// Add contact information to a contact based of a vec of
    /// `ContactInformation`.
    pub fn insert_contact_information(ci: Vec<Self>, contact: &mut Contact) {
        contact
            .contact_information
            .append(&mut ci.into_iter().map(Into::into).collect());
    }
}

impl From<SqlContactInformation> for ContactInformation {
    fn from(ci: SqlContactInformation) -> Self {
        Self {
            pid: ci.pid,
            pref: ci.pref.try_into().unwrap_or(1),
            value: ci.value,
            platform: ci.platform,
            typ: ci.typ,
        }
    }
}