use crate::connectorx::destinations::{Consume, Destination, DestinationPartition};
use crate::connectorx::errors::{ConnectorXError, Result as CXResult};
use crate::connectorx::sources::{PartitionParser, Produce, Source, SourcePartition};
#[doc(hidden)]
pub trait TypeSystem: Copy + Clone + Send + Sync {
fn check<T: TypeAssoc<Self>>(self) -> CXResult<()> {
T::check(self)
}
}
#[doc(hidden)]
pub trait TypeAssoc<TS: TypeSystem> {
fn check(ts: TS) -> CXResult<()>;
}
#[doc(hidden)]
pub trait Realize<F>
where
F: ParameterizedFunc,
{
fn realize(self) -> CXResult<F::Function>;
}
#[doc(hidden)]
pub trait ParameterizedFunc {
type Function;
fn realize<T>() -> Self::Function
where
Self: ParameterizedOn<T>,
{
Self::parameterize()
}
}
#[doc(hidden)]
pub trait ParameterizedOn<T>: ParameterizedFunc {
fn parameterize() -> Self::Function;
}
pub trait TypeConversion<T, U> {
fn convert(val: T) -> U;
}
pub trait Transport {
type TSS: TypeSystem;
type TSD: TypeSystem;
type S: Source;
type D: Destination;
type Error: From<ConnectorXError>
+ From<<Self::S as Source>::Error>
+ From<<Self::D as Destination>::Error>
+ Send
+ std::fmt::Debug;
fn convert_typesystem(ts: Self::TSS) -> CXResult<Self::TSD>;
fn convert_type<T1, T2>(val: T1) -> T2
where
Self: TypeConversion<T1, T2>,
{
<Self as TypeConversion<T1, T2>>::convert(val)
}
fn process<'s, 'd, 'r>(
ts1: Self::TSS,
ts2: Self::TSD,
src: &'r mut <<Self::S as Source>::Partition as SourcePartition>::Parser<'s>,
dst: &'r mut <Self::D as Destination>::Partition<'d>,
) -> Result<(), Self::Error>
where
Self: 'd;
#[allow(clippy::type_complexity)]
fn processor<'s, 'd>(
ts1: Self::TSS,
ts2: Self::TSD,
) -> CXResult<
fn(
src: &mut <<Self::S as Source>::Partition as SourcePartition>::Parser<'s>,
dst: &mut <Self::D as Destination>::Partition<'d>,
) -> Result<(), Self::Error>,
>
where
Self: 'd;
}
#[doc(hidden)]
pub fn process<'s, 'd, 'r, T1, T2, TP, S, D, ES, ED, ET>(
src: &'r mut <<S as Source>::Partition as SourcePartition>::Parser<'s>,
dst: &'r mut <D as Destination>::Partition<'d>,
) -> Result<(), ET>
where
T1: TypeAssoc<<S as Source>::TypeSystem>,
S: Source<Error = ES>,
<S as Source>::Partition: SourcePartition<Error = ES>,
<<S as Source>::Partition as SourcePartition>::Parser<'s>: Produce<'r, T1, Error = ES>,
ES: From<ConnectorXError> + Send,
T2: TypeAssoc<<D as Destination>::TypeSystem>,
D: Destination<Error = ED>,
<D as Destination>::Partition<'d>: Consume<T2, Error = ED>,
ED: From<ConnectorXError> + Send,
TP: TypeConversion<T1, T2>,
ET: From<ES> + From<ED>,
{
let val: T1 = PartitionParser::parse(src)?;
let val: T2 = <TP as TypeConversion<T1, _>>::convert(val);
DestinationPartition::write(dst, val)?;
Ok(())
}