1use std::sync::mpsc::{channel, sync_channel, Receiver, Sender, SyncSender};
5
6use crate::{BoundedMailbox, BoundedTaskMailbox, Handler, Mailbox, MailboxError, Message, Service};
7
8pub struct MsgMailbox<M: Message> {
13 service_mailbox: Box<dyn MsgMailboxT<M>>,
14}
15
16impl<M: Message> MsgMailbox<M> {
17 pub(super) fn mock() -> (Self, Receiver<M>) {
19 let (sender, receiver) = channel();
20 let mock = MockMsgMailbox::new(sender);
21 (
22 MsgMailbox {
23 service_mailbox: mock.duplicate(),
24 },
25 receiver,
26 )
27 }
28
29 pub(super) fn bounded_mock(channel_size: usize) -> (Self, Receiver<M>) {
31 let (sender, receiver) = sync_channel(channel_size);
32 let mock = BoundedMockMsgMailbox::new(sender);
33 (
34 MsgMailbox {
35 service_mailbox: mock.duplicate(),
36 },
37 receiver,
38 )
39 }
40
41 pub fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
42 self.service_mailbox.send_and_forget(message)
43 }
44 pub fn send_and_wait_for_reply(&self, message: M) -> Result<M::Reply, MailboxError> {
45 self.service_mailbox.send_and_wait_for_reply(message)
46 }
47}
48
49impl<M: Message> Clone for MsgMailbox<M> {
50 fn clone(&self) -> Self {
51 MsgMailbox {
52 service_mailbox: self.service_mailbox.duplicate(),
53 }
54 }
55}
56
57trait MsgMailboxT<M: Message>: Send + Sync {
58 fn send_and_forget(&self, message: M) -> Result<(), MailboxError>;
59 fn send_and_wait_for_reply(&self, message: M) -> Result<M::Reply, MailboxError>;
60 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>>;
61}
62
63impl<M, S> MsgMailboxT<M> for Mailbox<S>
64where
65 S: Service + 'static,
66 M: Message,
67 S: Handler<M>,
68{
69 fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
70 self.send_and_forget(message)
71 }
72 fn send_and_wait_for_reply(&self, message: M) -> Result<M::Reply, MailboxError> {
73 self.send_and_wait_for_reply(message)
74 }
75 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>> {
76 Box::new(self.clone())
77 }
78}
79
80impl<M, S> MsgMailboxT<M> for BoundedMailbox<S>
81where
82 S: Service + 'static,
83 M: Message,
84 S: Handler<M>,
85{
86 fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
87 self.send_and_forget(message)
88 }
89 fn send_and_wait_for_reply(&self, message: M) -> Result<M::Reply, MailboxError> {
90 self.send_and_wait_for_reply(message)
91 }
92 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>> {
93 Box::new(self.clone())
94 }
95}
96
97impl<M, S> MsgMailboxT<M> for BoundedTaskMailbox<S>
98where
99 S: Service + 'static,
100 M: Message,
101 S: Handler<M>,
102{
103 fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
104 self.send_and_forget(message)
105 }
106 fn send_and_wait_for_reply(&self, message: M) -> Result<M::Reply, MailboxError> {
107 self.send_and_wait_for_reply(message)
108 }
109 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>> {
110 Box::new(self.clone())
111 }
112}
113
114impl<M, S> From<Mailbox<S>> for MsgMailbox<M>
115where
116 M: Message,
117 S: Service,
118 S: Handler<M>,
119 S: 'static,
120{
121 fn from(mailbox: Mailbox<S>) -> Self {
122 MsgMailbox {
123 service_mailbox: Box::new(mailbox),
124 }
125 }
126}
127
128impl<M, S> From<BoundedMailbox<S>> for MsgMailbox<M>
129where
130 M: Message,
131 S: Service,
132 S: Handler<M>,
133 S: 'static,
134{
135 fn from(mailbox: BoundedMailbox<S>) -> Self {
136 MsgMailbox {
137 service_mailbox: Box::new(mailbox),
138 }
139 }
140}
141
142impl<M, S> From<BoundedTaskMailbox<S>> for MsgMailbox<M>
143where
144 M: Message,
145 S: Service,
146 S: Handler<M>,
147 S: 'static,
148{
149 fn from(mailbox: BoundedTaskMailbox<S>) -> Self {
150 MsgMailbox {
151 service_mailbox: Box::new(mailbox),
152 }
153 }
154}
155
156pub(super) struct MockMsgMailbox<M> {
157 sender: Sender<M>,
158}
159
160impl<M> MockMsgMailbox<M> {
161 pub fn new(sender: Sender<M>) -> Self {
162 MockMsgMailbox { sender }
163 }
164}
165
166impl<M: Message> MsgMailboxT<M> for MockMsgMailbox<M> {
167 fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
168 if self.sender.send(message).is_err() {
169 return Err(MailboxError::SendChannelClosed);
170 }
171
172 Ok(())
173 }
174
175 fn send_and_wait_for_reply(&self, _message: M) -> Result<M::Reply, MailboxError> {
176 unimplemented!("We have not implemented send_and_wait_for_reply for MockMsgMailbox yet.")
177 }
178
179 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>> {
180 Box::new(MockMsgMailbox {
181 sender: self.sender.clone(),
182 })
183 }
184}
185
186pub(super) struct BoundedMockMsgMailbox<M> {
187 sender: SyncSender<M>,
188}
189
190impl<M> BoundedMockMsgMailbox<M> {
191 pub fn new(sender: SyncSender<M>) -> Self {
192 BoundedMockMsgMailbox { sender }
193 }
194}
195
196impl<M: Message> MsgMailboxT<M> for BoundedMockMsgMailbox<M> {
197 fn send_and_forget(&self, message: M) -> Result<(), MailboxError> {
198 self.sender.try_send(message).map_err(|e| match e {
199 std::sync::mpsc::TrySendError::Full(_) => MailboxError::SendChannelFull,
200 std::sync::mpsc::TrySendError::Disconnected(_) => MailboxError::SendChannelClosed,
201 })
202 }
203
204 fn send_and_wait_for_reply(&self, _message: M) -> Result<M::Reply, MailboxError> {
205 unimplemented!(
206 "We have not implemented send_and_wait_for_reply for BoundedMockMsgMailbox yet."
207 )
208 }
209
210 fn duplicate(&self) -> Box<dyn MsgMailboxT<M>> {
211 Box::new(BoundedMockMsgMailbox {
212 sender: self.sender.clone(),
213 })
214 }
215}