use error;
use response::Serializer;
use routing::{RouteMatch, RouteSet};
use util::BufStream;
use bytes::Buf;
use futures::{Future, Poll};
use futures::future::FutureResult;
use http;
use std::marker::PhantomData;
pub trait Resource: Clone {
type Destination: Clone + Send + Sync + 'static;
type RequestBody: BufStream;
type Buf: Buf;
type Body: BufStream<Item = Self::Buf, Error = ::Error>;
type Future: ResourceFuture<Body = Self::Body>;
fn dispatch(
&mut self,
destination: Self::Destination,
route_match: &RouteMatch,
body: Self::RequestBody,
) -> Self::Future;
}
pub trait ResourceFuture {
type Body;
fn poll_response(&mut self, request: &http::Request<()>)
-> Poll<http::Response<Self::Body>, ::Error>;
}
pub trait IntoResource<S, RequestBody>
where S: Serializer,
RequestBody: BufStream,
{
type Destination: Clone + Send + Sync + 'static;
type Resource: Resource<Destination = Self::Destination,
RequestBody = RequestBody>;
fn routes(&self) -> RouteSet<Self::Destination>;
fn into_resource(self, serializer: S) -> Self::Resource;
}
impl<T, B> ResourceFuture for T
where
T: Future<Item = http::Response<B>, Error = ::Error>
{
type Body = B;
fn poll_response(&mut self, _: &http::Request<()>) -> Poll<T::Item, ::Error> {
self.poll()
}
}
#[derive(Debug)]
pub struct Unit<B> {
_p: PhantomData<B>,
}
impl<B> Unit<B> {
pub fn new() -> Self {
Unit { _p: PhantomData }
}
}
impl<B> Resource for Unit<B>
where B: BufStream,
{
type Destination = ();
type RequestBody = B;
type Buf = <Self::Body as BufStream>::Item;
type Body = error::Map<String>;
type Future = FutureResult<http::Response<Self::Body>, ::Error>;
fn dispatch(&mut self, _: (), _: &RouteMatch, _: Self::RequestBody) -> Self::Future {
unreachable!();
}
}
impl<B> Clone for Unit<B> {
fn clone(&self) -> Self {
Unit::new()
}
}