I’m trying to build a system where a Server
has to work with multiple transports (TTransport
below). The caller instantiates the Server
with a concrete TTransportFactory
that can build the transport types they want to use at runtime (i.e. each accepted connection wraps a TcpStream
with the constructed transport to process incoming/outgoing bytes). I tried the code below but can’t get the trait bounds to work properly.
use std::cell::RefCell;
use std::rc::Rc;
//
// TTransport and TTransportFactory
//
pub trait TTransport { }
pub type RcTTransport = Rc<RefCell<Box<TTransport>>>;
pub trait TTransportFactory<T: TTransport> {
fn new(&self, inner: RcTTransport) -> T;
}
//
// TFakeTransport and TFakeTransportFactory
// (implements/builds an implementation of TTransport)
//
struct TFakeTransport { }
impl TTransport for TFakeTransport { }
struct TFakeTransportFactory { }
impl TTransportFactory<TFakeTransport> for TFakeTransportFactory {
fn new(&self, inner: RcTTransport) -> TFakeTransport {
unimplemented!()
}
}
//
// TServer (builds a TTransport)
//
struct TServer<T, F> where T: TTransport, F: TTransportFactory<T> {
factory: F,
}
impl<T, F> TServer<T, F> where T: TTransport, F: TTransportFactory<T> {
pub fn listen() {
unimplemented!()
}
}
A few questions:
- Is this a case where I have to use associated types? (i.e.
TTransport
is an associated type forTTransportFactory
? If so, how do I indicate its bound inServer
? - Does
TTransportFactory
have to return a boxedTTransport
?