use std::marker; use futures::{Async, Future, Poll}; use {NewService, Service}; /// `Map` service combinator pub struct Map { a: A, f: F, r: marker::PhantomData, } impl Map where A: Service, F: Fn(A::Response) -> R, { /// Create new `Map` combinator pub fn new(a: A, f: F) -> Self { Self { a, f, r: marker::PhantomData, } } } impl Service for Map where A: Service, F: Fn(A::Response) -> R, F: Clone, { type Request = A::Request; type Response = R; type Error = A::Error; type Future = MapFuture; fn poll_ready(&mut self) -> Poll<(), Self::Error> { self.a.poll_ready() } fn call(&mut self, req: Self::Request) -> Self::Future { MapFuture::new(self.a.call(req), self.f.clone()) } } pub struct MapFuture where A: Service, F: Fn(A::Response) -> R, { f: F, fut: A::Future, } impl MapFuture where A: Service, F: Fn(A::Response) -> R, { fn new(fut: A::Future, f: F) -> Self { MapFuture { f, fut } } } impl Future for MapFuture where A: Service, F: Fn(A::Response) -> R, { type Item = R; type Error = A::Error; fn poll(&mut self) -> Poll { match self.fut.poll()? { Async::Ready(resp) => Ok(Async::Ready((self.f)(resp))), Async::NotReady => Ok(Async::NotReady), } } } /// `MapNewService` new service combinator pub struct MapNewService { a: A, f: F, r: marker::PhantomData, } impl MapNewService where A: NewService, F: Fn(A::Response) -> R, { /// Create new `Map` new service instance pub fn new(a: A, f: F) -> Self { Self { a, f, r: marker::PhantomData, } } } impl Clone for MapNewService where A: NewService + Clone, F: Fn(A::Response) -> R + Clone, { fn clone(&self) -> Self { Self { a: self.a.clone(), f: self.f.clone(), r: marker::PhantomData, } } } impl NewService for MapNewService where A: NewService, F: Fn(A::Response) -> R + Clone, { type Request = A::Request; type Response = R; type Error = A::Error; type Service = Map; type InitError = A::InitError; type Future = MapNewServiceFuture; fn new_service(&self) -> Self::Future { MapNewServiceFuture::new(self.a.new_service(), self.f.clone()) } } pub struct MapNewServiceFuture where A: NewService, F: Fn(A::Response) -> R, { fut: A::Future, f: Option, } impl MapNewServiceFuture where A: NewService, F: Fn(A::Response) -> R, { fn new(fut: A::Future, f: F) -> Self { MapNewServiceFuture { f: Some(f), fut } } } impl Future for MapNewServiceFuture where A: NewService, F: Fn(A::Response) -> R, { type Item = Map; type Error = A::InitError; fn poll(&mut self) -> Poll { if let Async::Ready(service) = self.fut.poll()? { Ok(Async::Ready(Map::new(service, self.f.take().unwrap()))) } else { Ok(Async::NotReady) } } }