use std::marker::PhantomData;
use std::sync::mpsc::{channel, RecvError, SendError, Sender};
use std::{any::Any, marker::Send};
use super::types::{ids, Message, Packet};
#[derive(Clone)]
pub struct SendChannel<T> {
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
send_type: PhantomData<T>,
}
impl<T> SendChannel<T> {
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
pub(crate) fn junction_id(&self) -> ids::JunctionId {
self.junction_id
}
pub(crate) fn strip(&self) -> StrippedSendChannel<T> {
StrippedSendChannel::new(self.id)
}
}
impl<T> SendChannel<T>
where
T: Any + Send,
{
pub(crate) fn new(
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
) -> SendChannel<T> {
SendChannel {
id,
junction_id,
sender,
send_type: PhantomData,
}
}
pub fn send(&self, value: T) -> Result<(), SendError<Packet>> {
self.sender.send(Packet::Message {
channel_id: self.id,
msg: Message::new(value),
})
}
}
pub(crate) struct StrippedSendChannel<T> {
id: ids::ChannelId,
send_type: PhantomData<T>,
}
impl<T> StrippedSendChannel<T> {
pub(crate) fn new(id: ids::ChannelId) -> StrippedSendChannel<T> {
StrippedSendChannel {
id,
send_type: PhantomData,
}
}
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
}
#[derive(Clone)]
pub struct RecvChannel<R> {
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
recv_type: PhantomData<R>,
}
impl<R> RecvChannel<R> {
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
pub(crate) fn junction_id(&self) -> ids::JunctionId {
self.junction_id
}
pub(crate) fn strip(&self) -> StrippedRecvChannel<R> {
StrippedRecvChannel::new(self.id)
}
}
impl<R> RecvChannel<R>
where
R: Any + Send,
{
pub(crate) fn new(
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
) -> RecvChannel<R> {
RecvChannel {
id,
junction_id,
sender,
recv_type: PhantomData,
}
}
pub fn recv(&self) -> Result<R, RecvError> {
let (tx, rx) = channel::<R>();
self.sender
.send(Packet::Message {
channel_id: self.id,
msg: Message::new(tx),
})
.unwrap();
rx.recv()
}
}
pub(crate) struct StrippedRecvChannel<R> {
id: ids::ChannelId,
recv_type: PhantomData<R>,
}
impl<R> StrippedRecvChannel<R> {
pub(crate) fn new(id: ids::ChannelId) -> StrippedRecvChannel<R> {
StrippedRecvChannel {
id,
recv_type: PhantomData,
}
}
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
}
#[derive(Clone)]
pub struct BidirChannel<T, R> {
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
send_type: PhantomData<T>,
recv_type: PhantomData<R>,
}
impl<T, R> BidirChannel<T, R> {
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
pub(crate) fn junction_id(&self) -> ids::JunctionId {
self.junction_id
}
pub(crate) fn strip(&self) -> StrippedBidirChannel<T, R> {
StrippedBidirChannel::new(self.id)
}
}
impl<T, R> BidirChannel<T, R>
where
T: Any + Send,
R: Any + Send,
{
pub(crate) fn new(
id: ids::ChannelId,
junction_id: ids::JunctionId,
sender: Sender<Packet>,
) -> BidirChannel<T, R> {
BidirChannel {
id,
junction_id,
sender,
send_type: PhantomData,
recv_type: PhantomData,
}
}
pub fn send_recv(&self, msg: T) -> Result<R, RecvError> {
let (tx, rx) = channel::<R>();
self.sender
.send(Packet::Message {
channel_id: self.id,
msg: Message::new((msg, tx)),
})
.unwrap();
rx.recv()
}
}
pub(crate) struct StrippedBidirChannel<T, R> {
id: ids::ChannelId,
send_type: PhantomData<T>,
recv_type: PhantomData<R>,
}
impl<T, R> StrippedBidirChannel<T, R> {
pub(crate) fn new(id: ids::ChannelId) -> StrippedBidirChannel<T, R> {
StrippedBidirChannel {
id,
send_type: PhantomData,
recv_type: PhantomData,
}
}
pub(crate) fn id(&self) -> ids::ChannelId {
self.id
}
}