Skip to main content

IServiceCollectionExt

Trait IServiceCollectionExt 

Source
pub trait IServiceCollectionExt: Sized {
    // Required methods
    fn add_mediator(self) -> Self;
    fn add_request_endpoints(self) -> Self;
    fn add_controllers(self) -> Self;
    fn add_middleware<T>(self) -> Self
       where T: IMiddleware + Default + Send + Sync + 'static;
    fn add_pipeline<T>(self) -> Self
       where T: IPipelineBehavior + Default + Send + Sync + 'static;
    fn add_pipeline_with<F>(self, factory: F) -> Self
       where F: Fn(&dyn IServiceResolver) -> Arc<dyn IPipelineBehavior> + Send + Sync + 'static;
    fn add_hosted_service<T>(self) -> Self
       where T: IHostedService + Default + Send + Sync + 'static;
}
Expand description

Extension methods for rust_dix::ServiceCollection to enable framework-level service registration patterns.

Required Methods§

Source

fn add_mediator(self) -> Self

Register the mediator in the DI container.

The actual IRequestHandler and IEventHandler implementations are registered via #[rust_dix::module] blocks (re-exported as webx::module).

Source

fn add_request_endpoints(self) -> Self

Signal that endpoints should be auto-discovered from #[get] / #[endpoint] annotations at compile time. The actual route table is built during Host::build() by scanning the inventory for RouteEntry items.

Source

fn add_controllers(self) -> Self

Register controller types scoped per request.

Source

fn add_middleware<T>(self) -> Self
where T: IMiddleware + Default + Send + Sync + 'static,

Register a middleware type in the DI container as a singleton.

Source

fn add_pipeline<T>(self) -> Self
where T: IPipelineBehavior + Default + Send + Sync + 'static,

Register a pipeline behavior in the DI container as a singleton.

Requires Default, so it is only usable for behaviors without dependencies. Use IServiceCollectionExt::add_pipeline_with when the behavior needs anything from the container.

Source

fn add_pipeline_with<F>(self, factory: F) -> Self
where F: Fn(&dyn IServiceResolver) -> Arc<dyn IPipelineBehavior> + Send + Sync + 'static,

Register a pipeline behavior built from a factory as a singleton.

Unlike IServiceCollectionExt::add_pipeline, the factory receives the DI resolver, so the behavior can take constructor dependencies — exactly what the MediatR-style “constructor injection” for pipeline behaviors means here. The factory runs once (singleton), on first resolution / build-time validation; the resolver is not available inside IPipelineBehavior::handle.

The factory is also executed during build() (cycle and captive-dependency validation), so it must resolve dependencies through the resolver it is given — resolver.provider_arc() is None there. &dyn IServiceResolver is object-safe, so get/get_owned (which require a sized resolver) are unavailable; resolve type-erased instead:

ⓘ
use std::sync::Arc;
use webx::{IServiceCollectionExt, IPipelineBehavior};

svc.add_pipeline_with(|resolver| {
    let clock: Arc<Clock> = resolver
        .get_any(std::any::type_name::<Clock>())
        .and_then(|service| service.downcast::<Arc<Clock>>().ok())
        .map(|service| Arc::clone(&*service))
        .expect("register Clock before the pipeline");
    Arc::new(TimingBehavior { clock }) as Arc<dyn IPipelineBehavior>
})

Capturing the dependency when registering is equally valid (and shorter) when the value already exists outside the container:

ⓘ
let clock = Arc::clone(&clock);
svc.add_pipeline_with(move |_| Arc::new(TimingBehavior { clock }))
Source

fn add_hosted_service<T>(self) -> Self
where T: IHostedService + Default + Send + Sync + 'static,

Register a hosted service in the DI container as a singleton.

Hosted services are started when the host starts (before accepting requests) and stopped during graceful shutdown.

Analogous to ASP.NET Core’s AddHostedService<T>().

§Example
ⓘ
Host::builder()
    .register(|svc| {
        svc.add_hosted_service::<DbInitService>()
    })
    .build()
    .run()
    .await

Dyn Compatibility§

This trait is not dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety".

Implementations on Foreign Types§

Source§

impl IServiceCollectionExt for ServiceCollection

Implementors§