nitinol_process/channel/
event.rs

1use super::ProcessApplier;
2use crate::{Process, Context};
3use async_trait::async_trait;
4use nitinol_core::event::Event;
5use tokio::sync::oneshot;
6use crate::errors::ChannelDropped;
7
8#[async_trait]
9pub trait EventApplicator<E: Event>: 'static + Sync + Send {
10    async fn apply(&mut self, event: E, ctx: &mut Context);
11}
12
13pub(crate) struct ApplicativeReceptor<E: Event> {
14    pub(crate) event: E,
15    pub(crate) oneshot: oneshot::Sender<()>,
16}
17
18#[async_trait]
19impl<E: Event, T: Process> ProcessApplier<T> for ApplicativeReceptor<E>
20where
21    T: EventApplicator<E>,
22{
23    async fn apply(self: Box<Self>, entity: &mut T, ctx: &mut Context) -> Result<(), ChannelDropped> {
24        self.oneshot
25            .send(entity.apply(self.event, ctx).await)
26            .map_err(|_| ChannelDropped)?;
27        ctx.sequence += 1;
28        Ok(())
29    }
30}
31
32
33#[async_trait]
34pub trait TryEventApplicator<E: Event>: 'static + Sync + Send {
35    type Rejection: 'static + Sync + Send;
36    async fn try_apply(&mut self, event: E, ctx: &mut Context) -> Result<(), Self::Rejection>;
37}
38
39pub(crate) struct TryApplicativeReceptor<E: Event, T: Process>
40where
41    T: TryEventApplicator<E>,
42{
43    pub(crate) event: E,
44    pub(crate) oneshot: oneshot::Sender<Result<(), T::Rejection>>,
45}
46
47#[async_trait]
48impl<E: Event, T: Process> ProcessApplier<T> for TryApplicativeReceptor<E, T>
49where
50    T: TryEventApplicator<E>,
51{
52    async fn apply(self: Box<Self>, entity: &mut T, ctx: &mut Context) -> Result<(), ChannelDropped> {
53        self.oneshot
54            .send(entity.try_apply(self.event, ctx).await)
55            .map_err(|_| ChannelDropped)?;
56        ctx.sequence += 1;
57        Ok(())
58    }
59}