1
0
mirror of https://github.com/fafhrd91/actix-net synced 2025-07-03 02:44:31 +02:00

convert Server::bind to accept a normal service factory

This commit is contained in:
Rob Ede
2021-10-25 18:03:52 +01:00
parent 81421c2ba9
commit 4c0eaca581
17 changed files with 277 additions and 128 deletions

View File

@ -1,6 +1,7 @@
# Changes
## Unreleased - 2021-xx-xx
* Add `.and_then_send()` & `AndThenSendServiceFactory` for creating `Send`able chained services. [#403]
## 2.0.1 - 2021-10-11

View File

@ -261,6 +261,91 @@ where
}
}
/// `.and_then_send()` service factory combinator
pub struct AndThenSendServiceFactory<A, B, Req>
where
A: ServiceFactory<Req>,
A::Config: Clone,
B: ServiceFactory<
A::Response,
Config = A::Config,
Error = A::Error,
InitError = A::InitError,
>,
{
inner_a: A,
inner_b: B,
_phantom: PhantomData<Req>,
}
impl<A, B, Req> AndThenSendServiceFactory<A, B, Req>
where
A: ServiceFactory<Req>,
A::Config: Clone,
B: ServiceFactory<
A::Response,
Config = A::Config,
Error = A::Error,
InitError = A::InitError,
>,
{
/// Create new `AndThenFactory` combinator
pub(crate) fn new(a: A, b: B) -> Self {
Self {
inner_a: a,
inner_b: b,
_phantom: PhantomData,
}
}
}
impl<A, B, Req> ServiceFactory<Req> for AndThenSendServiceFactory<A, B, Req>
where
A: ServiceFactory<Req>,
A::Config: Clone,
B: ServiceFactory<
A::Response,
Config = A::Config,
Error = A::Error,
InitError = A::InitError,
>,
{
type Response = B::Response;
type Error = A::Error;
type Config = A::Config;
type Service = AndThenService<A::Service, B::Service, Req>;
type InitError = A::InitError;
type Future = AndThenServiceFactoryResponse<A, B, Req>;
fn new_service(&self, cfg: A::Config) -> Self::Future {
AndThenServiceFactoryResponse::new(
self.inner_a.new_service(cfg.clone()),
self.inner_b.new_service(cfg),
)
}
}
impl<A: Clone, B: Clone, Req> Clone for AndThenSendServiceFactory<A, B, Req>
where
A: ServiceFactory<Req>,
A::Config: Clone,
B: ServiceFactory<
A::Response,
Config = A::Config,
Error = A::Error,
InitError = A::InitError,
>,
{
fn clone(&self) -> Self {
Self {
inner_a: self.inner_a.clone(),
inner_b: self.inner_b.clone(),
_phantom: PhantomData,
}
}
}
#[cfg(test)]
mod tests {
use alloc::rc::Rc;

View File

@ -1,10 +1,4 @@
use crate::{
and_then::{AndThenService, AndThenServiceFactory},
map::Map,
map_err::MapErr,
transform_err::TransformMapInitErr,
IntoService, IntoServiceFactory, Service, ServiceFactory, Transform,
};
use crate::{IntoService, IntoServiceFactory, Service, ServiceFactory, Transform, and_then::{AndThenSendServiceFactory, AndThenService, AndThenServiceFactory}, map::Map, map_err::MapErr, transform_err::TransformMapInitErr};
/// An extension trait for [`Service`]s that provides a variety of convenient adapters.
pub trait ServiceExt<Req>: Service<Req> {
@ -105,6 +99,22 @@ pub trait ServiceFactoryExt<Req>: ServiceFactory<Req> {
{
AndThenServiceFactory::new(self, factory.into_factory())
}
/// Call another service after call to this one has resolved successfully.
fn and_then_send<I, SF1>(self, factory: I) -> AndThenSendServiceFactory<Self, SF1, Req>
where
Self: Sized,
Self::Config: Clone,
I: IntoServiceFactory<SF1, Self::Response>,
SF1: ServiceFactory<
Self::Response,
Config = Self::Config,
Error = Self::Error,
InitError = Self::InitError,
>,
{
AndThenSendServiceFactory::new(self, factory.into_factory())
}
}
impl<SF, Req> ServiceFactoryExt<Req> for SF where SF: ServiceFactory<Req> {}

View File

@ -175,13 +175,13 @@ where
factory: I,
) -> PipelineFactory<
impl ServiceFactory<
Req,
Response = SF1::Response,
Error = SF::Error,
Config = SF::Config,
InitError = SF::InitError,
Req,
Response = SF1::Response,
Error = SF::Error,
Config = SF::Config,
InitError = SF::InitError,
Service = impl Service<Req, Response = SF1::Response, Error = SF::Error> + Clone,
> + Clone,
> + Clone,
Req,
>
where