daemon_engine/
lib.rs

1//#![feature(await_macro, async_await, futures_api)]
2
3/**
4 * rust-daemon
5 * Core module, re-exports client and server components
6 *
7 * https://github.com/ryankurte/rust-daemon
8 * Copyright 2018 Ryan Kurte
9 */
10
11extern crate libc;
12extern crate users;
13
14extern crate futures;
15extern crate bytes;
16
17#[macro_use]
18extern crate tokio;
19extern crate tokio_io;
20extern crate tokio_codec;
21extern crate tokio_uds;
22extern crate tokio_tcp;
23extern crate tokio_udp;
24extern crate tokio_timer;
25
26extern crate serde;
27extern crate serde_json;
28
29#[cfg(test)]
30#[macro_use]
31extern crate serde_derive;
32
33extern crate tokio_serde_json_mirror as tokio_serde_json;
34
35#[macro_use]
36extern crate log;
37extern crate uuid;
38
39trait GenericServer {
40    type Address;
41    type Request;
42    type Response;
43    
44    fn send(&mut self, _: Self::Address);
45    //fn incoming(&mut self) -> Option<UnboundedReceiver<Request<>>>;
46}
47
48/// Server provides a generic server over a stream and codec
49/// This is used to implement daemon servers (ie. long running processes w/ network communication)
50pub mod server;
51pub use crate::server::Server;
52
53/// Connection provides a generic connection over a stream and codec
54/// This is used to implement clients (ie. for a command line utility)
55pub mod connection;
56pub use crate::connection::Connection;
57
58/// Codecs implement protocol handling over connectors
59pub mod codecs;
60
61/// TCP implements a TCP socket server and connection
62pub mod tcp;
63pub use crate::tcp::{TcpServer, TcpInfo, TcpConnection};
64
65/// UDP implements a UDP socket connection
66/// As UDP is connection-less, no server is required
67pub mod udp;
68pub use crate::udp::{UdpConnection, UdpInfo};
69
70/// Unix implements a Unix socket server and connection
71pub mod unix;
72pub use crate::unix::{UnixServer, UnixInfo, UnixConnection};
73
74/// Error implements errors returned by the daemon
75pub mod error;
76pub use crate::error::Error as DaemonError;
77
78
79/// JsonCodec re-exports the JSON codec for convenience
80/// This is an alias of JsonCodec with default JsonError, use codecs::json::JsonCodec to specify error type manually
81pub type JsonCodec<Req, Resp> = codecs::json::JsonCodec<Req, Resp, codecs::json::JsonError>;
82
83use futures::{future, Future, sync::oneshot};
84
85/// AsyncWait implements a `.wait()` equivalent that works from any contex.
86/// This is required because at some point in the past `.wait()` stopped doing this,
87/// and thus calling it in a polling context causes everything to lock up.
88/// see: https://github.com/tokio-rs/tokio-core/issues/182 and related issues.
89/// ``` norun
90/// // This will block forever if run in the main thread context
91/// let _client = TcpConnection::<JsonCodec<Request, Response>>::new(&addr, JsonCodec::new()).wait().unwrap();
92/// // This will work in the expected manner and return once connection has completed
93/// let _client = TcpConnection::<JsonCodec<Request, Response>>::new(&addr, JsonCodec::new()).async_wait().unwrap();
94/// ```
95pub trait AsyncWait<I, E> {
96    fn async_wait(self) -> Result<I, E>;
97}
98
99impl <F, I, E> AsyncWait<I, E> for F 
100where 
101    F: Future<Item=I, Error=E> + Send + 'static,
102    I: Send + 'static,
103    E: Send + 'static,
104{
105    fn async_wait(self) -> Result<I, E> {
106        let (tx, rx) = oneshot::channel::<Result<I, E>>();
107
108        tokio::spawn(self.then(|res| tx.send(res) ).map(|_v| () ).map_err(|_e| () ));
109
110        rx.wait().unwrap()
111    }
112}
113