sofie-db 0.1.0

The handler model (inputs, events, replies), aggregates, read models, the query builder, the unit of work, migrations, the worker and the database seam.
Documentation
use std::fmt;
use std::hash::{Hash, Hasher};
use std::marker::PhantomData;

use serde::{Deserialize, Deserializer, Serialize, Serializer};
use sofie_core::{Cast, ColumnReader, ColumnSpec, Result, Show, Shown, SqlValue, Uuid};
use sofie_values::{Input, Present};

pub struct Id<A> {
    uuid: Uuid,
    aggregate: PhantomData<fn() -> A>,
}

impl<A> Id<A> {
    #[must_use]
    pub const fn from_uuid(uuid: Uuid) -> Self {
        Self {
            uuid,
            aggregate: PhantomData,
        }
    }

    #[must_use]
    pub const fn uuid(self) -> Uuid {
        self.uuid
    }
}

impl<A> Clone for Id<A> {
    fn clone(&self) -> Self {
        *self
    }
}

impl<A> Copy for Id<A> {}

impl<A> sofie_core::Ordered for Id<A> {}

impl<A> PartialEq for Id<A> {
    fn eq(&self, other: &Self) -> bool {
        self.uuid == other.uuid
    }
}

impl<A> Eq for Id<A> {}

impl<A> Hash for Id<A> {
    fn hash<H: Hasher>(&self, state: &mut H) {
        self.uuid.hash(state);
    }
}

impl<A> fmt::Debug for Id<A> {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        fmt::Display::fmt(&self.uuid, f)
    }
}

impl<A> fmt::Display for Id<A> {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        fmt::Display::fmt(&self.uuid, f)
    }
}

impl<A> Cast for Id<A> {
    const COLUMNS: &'static [ColumnSpec] = Uuid::COLUMNS;

    fn encode(&self, out: &mut Vec<SqlValue>) {
        self.uuid.encode(out);
    }

    fn decode(row: &mut dyn ColumnReader) -> Result<Self> {
        Uuid::decode(row).map(Self::from_uuid)
    }
}

impl<A> Show for Id<A> {
    fn show(&self) -> Shown<'_> {
        Shown::Uuid(self.uuid)
    }
}

impl<A> Serialize for Id<A> {
    fn serialize<S: Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
        serializer.collect_str(&self.uuid)
    }
}

impl<'de, A> Deserialize<'de> for Id<A> {
    fn deserialize<D: Deserializer<'de>>(deserializer: D) -> Result<Self, D::Error> {
        Uuid::deserialize(deserializer).map(Self::from_uuid)
    }
}

impl<A> Present for Id<A> {
    const INPUT: Input = Uuid::INPUT;
    const SEARCH: sofie_values::Search = Uuid::SEARCH;

    fn csv(&self) -> String {
        self.uuid.csv()
    }
}