Struct rudi::Context

source ·
pub struct Context { /* private fields */ }
Expand description

A context is a container for all the providers and instances.

It is the main entry point for the dependency injection. It is also used to create new instances.

When creating a Context, you can use options to change the default creation behavior, see ContextOptions for details.

§Example

Creating context with customized modules:

use rudi::{components, modules, Context, DynProvider, Module, Transient};

#[Transient]
struct A;

struct Module1;

impl Module for Module1 {
    fn providers() -> Vec<DynProvider> {
        components![A]
    }
}

#[derive(Debug)]
#[Transient]
struct B;

struct Module2;

impl Module for Module2 {
    fn providers() -> Vec<DynProvider> {
        components![B]
    }
}

let mut cx = Context::create(modules![Module1, Module2]);

let b = cx.resolve::<B>();

assert!(cx.resolve_option::<A>().is_some());
assert_eq!(format!("{:?}", b), "B");

With the auto-register feature enabled (which is enabled by default), it is also possible to create contexts in a simpler way:

use rudi::{Context, Transient};

#[Transient]
struct A;

#[derive(Debug)]
#[Transient]
struct B;

let mut cx = Context::auto_register();
// This is a simplified version of the following
// let mut cx = Context::create(modules![AutoRegisterModule]);

let b = cx.resolve::<B>();

assert!(cx.resolve_option::<A>().is_some());
assert_eq!(format!("{:?}", b), "B");

If the following conditions are met:

  1. in context, there exists a provider whose constructor is async.
  2. the eager_create method of the provider is set to true, e.g., SingletonProvider::eager_create.
  3. the eager_create method of the module to which the provide belongs is set to true, i.e., Module::eager_create.
  4. the eager_create field of the context, is set to true, i.e., ContextOptions::eager_create.

Then when creating the context, you must use the async creation methods, Context::create_async or Context::auto_register_async:

use rudi::{Context, Singleton, Transient};

#[Singleton]
async fn Foo() -> i32 {
    1
}

#[derive(Debug)]
#[Transient(async)]
struct A(i32);

#[tokio::main]
async fn main() {
    let mut cx = Context::options()
        .eager_create(true)
        .auto_register_async()
        .await;

    assert!(cx.resolve_option_async::<A>().await.is_some());
}

Implementations§

source§

impl Context

source

pub fn create(modules: Vec<ResolveModule>) -> Context

Creates a new context with the given modules.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider whose constructor is async and the provider will be eagerly created.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{components, modules, Context, DynProvider, Module, Transient};

#[Transient]
struct A;

struct MyModule;

impl Module for MyModule {
    fn providers() -> Vec<DynProvider> {
        components![A]
    }
}

let mut cx = Context::create(modules![MyModule]);
assert!(cx.resolve_option::<A>().is_some());
source

pub fn auto_register() -> Context

Available on crate feature auto-register only.

Creates a new context with the AutoRegisterModule.

Same as Context::create(modules![AutoRegisterModule]).

See Context::create for more details.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider whose constructor is async and the provider will be eagerly created.
  • Panics if there is a provider that panics on construction.
source

pub async fn create_async(modules: Vec<ResolveModule>) -> Context

Async version of Context::create.

If no provider in the context has an async constructor and that provider needs to be eagerly created, this method is the same as Context::create.

See Context::create for more details.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider that panics on construction.
source

pub async fn auto_register_async() -> Context

Available on crate feature auto-register only.

Async version of Context::auto_register.

If no provider in the context has an async constructor and that provider needs to be eagerly created, this method is the same as Context::auto_register.

See Context::auto_register for more details.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider that panics on construction.
source

pub fn options() -> ContextOptions

Returns a new ContextOptions object.

This function return a new ContextOptions object that you can use to create a context with specific options if create() or auto_register() are not appropriate.

It is equivalent to ContextOptions::default(), but allows you to write more readable code. Instead of ContextOptions::default().eager_create(true).auto_register(), you can write Context::options().eager_create(true).auto_register(). This also avoids the need to import ContextOptions.

See the ContextOptions for more details.

§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton]
struct A;

let cx = Context::options().eager_create(true).auto_register();

assert!(cx.contains_single::<A>());
source

pub fn allow_override(&self) -> bool

Returns whether the context should allow overriding existing providers.

source

pub fn allow_only_single_eager_create(&self) -> bool

Returns whether the context should only eagerly create Singleton and SingleOwner instances.

source

pub fn eager_create(&self) -> bool

Returns whether the context should eagerly create instances.

source

pub fn single_registry(&self) -> &HashMap<Key, DynSingle>

Returns a reference to the single registry.

source

pub fn provider_registry(&self) -> &HashMap<Key, DynProvider>

Returns a reference to the provider registry.

source

pub fn loaded_modules(&self) -> &Vec<Type>

Returns a reference to the loaded modules.

source

pub fn conditional_providers(&self) -> &Vec<(bool, DynProvider)>

Returns a reference to the conditional providers.

source

pub fn eager_create_functions(&self) -> &Vec<(Definition, EagerCreateFunction)>

Returns a reference to the eager create functions.

source

pub fn dependency_chain(&self) -> &Vec<Key>

Returns a reference to the dependency chain.

source

pub fn insert_singleton<T>(&mut self, instance: T)
where T: 'static + Clone,

Appends a standalone Singleton instance to the context with default name "".

§Panics
  • Panics if a Provider<T> with the same name as the inserted instance exists in the Context and the context’s allow_override is false.
§Example
use rudi::Context;

let mut cx = Context::default();
cx.insert_singleton(42);
assert_eq!(cx.get_single::<i32>(), &42);
source

pub fn insert_singleton_with_name<T, N>(&mut self, instance: T, name: N)
where T: 'static + Clone, N: Into<Cow<'static, str>>,

Appends a standalone Singleton instance to the context with name.

§Panics
  • Panics if a Provider<T> with the same name as the inserted instance exists in the Context and the context’s allow_override is false.
§Example
use rudi::Context;

let mut cx = Context::default();

cx.insert_singleton_with_name(1, "one");
cx.insert_singleton_with_name(2, "two");

assert_eq!(cx.get_single_with_name::<i32>("one"), &1);
assert_eq!(cx.get_single_with_name::<i32>("two"), &2);
source

pub fn insert_single_owner<T>(&mut self, instance: T)
where T: 'static,

Appends a standalone SingleOwner instance to the context with default name "".

§Panics
  • Panics if a Provider<T> with the same name as the inserted instance exists in the Context and the context’s allow_override is false.
§Example
use rudi::Context;

#[derive(PartialEq, Eq, Debug)]
struct NotClone(i32);

let mut cx = Context::default();
cx.insert_single_owner(NotClone(42));
assert_eq!(cx.get_single::<NotClone>(), &NotClone(42));
source

pub fn insert_single_owner_with_name<T, N>(&mut self, instance: T, name: N)
where T: 'static, N: Into<Cow<'static, str>>,

Appends a standalone SingleOwner instance to the context with name.

§Panics
  • Panics if a Provider<T> with the same name as the inserted instance exists in the Context and the context’s allow_override is false.
§Example
use rudi::Context;

#[derive(PartialEq, Eq, Debug)]
struct NotClone(i32);

let mut cx = Context::default();

cx.insert_single_owner_with_name(NotClone(1), "one");
cx.insert_single_owner_with_name(NotClone(2), "two");

assert_eq!(cx.get_single_with_name::<NotClone>("one"), &NotClone(1));
assert_eq!(cx.get_single_with_name::<NotClone>("two"), &NotClone(2));
source

pub fn load_modules(&mut self, modules: Vec<ResolveModule>)

Load the given modules.

This method first flattens all the given modules together with their submodules into a collection of modules without submodules, then takes out the providers of each module in this collection, flattens all the providers together with their bound providers into a collection of providers without bound providers, and finally deposits the providers one by one into context.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
§Example
use rudi::{modules, AutoRegisterModule, Context, Singleton};

#[derive(Clone)]
#[Singleton]
struct A;

let mut cx = Context::default();
assert!(cx.get_provider::<A>().is_none());

cx.load_modules(modules![AutoRegisterModule]);
assert!(cx.get_provider::<A>().is_some());
source

pub fn unload_modules(&mut self, modules: Vec<ResolveModule>)

Unload the given modules.

This method will convert the given module into a collection of providers like the Context::load_modules method, and then remove all providers in the context that are equal to the providers in the collection and their possible instances.

§Example
use rudi::{modules, AutoRegisterModule, Context, Singleton};

#[derive(Clone)]
#[Singleton]
struct A;

let mut cx = Context::default();
assert!(cx.get_provider::<A>().is_none());

cx.load_modules(modules![AutoRegisterModule]);
assert!(cx.get_provider::<A>().is_some());

cx.unload_modules(modules![AutoRegisterModule]);
assert!(cx.get_provider::<A>().is_none());
source

pub fn flush(&mut self)

Flush the context.

This method has two purposes:

  1. Evaluate the condition of providers whose condition is Some.

    If the evaluation result is true, the provider will be loaded into the context, otherwise it will be removed from the context.

  2. Construct instances that will be eagerly created.

    Whether an instance need to be created eagerly depends on the eager_create field of the Provider that defines it, the eager_create field of the Module to which this Provider belongs, and the eager_create field of the Context to which this Module belongs. As long as one of these is true, the instance need to be created eagerly.

    Whether an instance is allowed to be created eagerly depends on the scope field in the definition field of the Provider that defines it, and the allow_only_single_eager_create field of the Context to which this Provider belongs. If allow_only_single_eager_create is false, or allow_only_single_eager_create is true and scope is Singleton or SingleOwner, the instance is allowed to be created eagerly.

    When an instance need to be created eagerly and is allowed to be created eagerly, it will be created eagerly.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider whose constructor is async and the provider will be eagerly created.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{modules, AutoRegisterModule, Context, Singleton, Transient};

#[Transient(condition = |_| true)]
struct A;

#[derive(Clone)]
#[Singleton(eager_create)]
struct B;

let mut cx = Context::default();

cx.load_modules(modules![AutoRegisterModule]);

assert!(!cx.contains_provider::<A>());
assert!(!cx.contains_single::<B>());

cx.flush();

// evaluate condition
assert!(cx.contains_provider::<A>());
// construct instance
assert!(cx.contains_single::<B>());
§Note

This method needs to be called after the Context::load_modules method, but why not put the logic of this method in the load_modules method? Please see the example below:

use rudi::{components, modules, Context, DynProvider, Module, Transient};

fn a_condition(cx: &Context) -> bool {
    cx.contains_provider::<B>()
}

#[Transient(condition = a_condition)]
struct A;

#[Transient]
struct B;

struct AModule;

impl Module for AModule {
    fn providers() -> Vec<DynProvider> {
        components![A]
    }
}

struct BModule;

impl Module for BModule {
    fn providers() -> Vec<DynProvider> {
        components![B]
    }
}

fn main() {
    let mut cx = Context::default();

    // Method 1, call `load_modules` and then call `flush` immediately
    cx.load_modules(modules![AModule]);
    cx.flush();
    cx.load_modules(modules![BModule]);
    cx.flush();

    // The evaluation result of `A`'s `condition` is `false`, so `A` will not be created
    assert!(!cx.contains_provider::<A>());

    let mut cx = Context::default();

    // Method 2, call all `load_modules` first, then call `flush`
    cx.load_modules(modules![AModule]);
    cx.load_modules(modules![BModule]);
    cx.flush();

    // The evaluation result of `A`'s `condition` is `true`, so `A` will be created
    assert!(cx.contains_provider::<A>());
}
source

pub async fn flush_async(&mut self)

Async version of Context::flush.

If no provider in the context has an async constructor and that provider needs to be eagerly created, this method is the same as Context::flush.

See Context::flush for more details.

§Panics
  • Panics if there are multiple providers with the same key and the context’s allow_override is false.
  • Panics if there is a provider that panics on construction.
source

pub fn resolve<T: 'static>(&mut self) -> T

Returns a Singleton or Transient instance based on the given type and default name "".

§Panics
  • Panics if no provider is registered for the given type and default name "".
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or Transient.
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton]
struct A;

let mut cx = Context::auto_register();
let a = cx.resolve::<A>();
assert_eq!(format!("{:?}", a), "A");
source

pub fn resolve_with_name<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> T

Returns a Singleton or Transient instance based on the given type and name.

§Panics
  • Panics if no provider is registered for the given type and name.
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or Transient.
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(name = "a")]
struct A;

let mut cx = Context::auto_register();
let a = cx.resolve_with_name::<A>("a");
assert_eq!(format!("{:?}", a), "A");
source

pub fn resolve_option<T: 'static>(&mut self) -> Option<T>

Returns an optional Singleton or Transient instance based on the given type and default name "".

§Note

If no provider is registered for the given type and default name "", or the provider is not a Singleton or Transient, this method will return None, otherwise it will return Some.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton]
struct A;

let mut cx = Context::auto_register();
assert!(cx.resolve_option::<A>().is_some());
source

pub fn resolve_option_with_name<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> Option<T>

Returns an optional Singleton or Transient instance based on the given type and name.

§Note

If no provider is registered for the given type and name, or the provider is not a Singleton or Transient, this method will return None, otherwise it will return Some.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(name = "a")]
struct A;

let mut cx = Context::auto_register();
assert!(cx.resolve_option_with_name::<A>("a").is_some());
source

pub fn resolve_by_type<T: 'static>(&mut self) -> Vec<T>

Returns a collection of Singleton and Transient instances of the given type.

§Note

This method will return a collection of Singleton and Transient, if some providers are SingleOwner, they will not be contained in the collection.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
fn A() -> i32 {
    1
}

#[Transient(name = "b")]
fn B() -> i32 {
    2
}

let mut cx = Context::auto_register();
assert_eq!(cx.resolve_by_type::<i32>().into_iter().sum::<i32>(), 3);
source

pub fn just_create_single<T: 'static>(&mut self)

Creates a Singleton or SingleOwner instance based on the given type and default name "" but does not return it.

§Panics
  • Panics if no provider is registered for the given type and default name "".
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or SingleOwner.
§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton]
struct A;

let mut cx = Context::auto_register();
assert!(!cx.contains_single::<A>());
cx.just_create_single::<A>();
assert!(cx.contains_single::<A>());
source

pub fn just_create_single_with_name<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> )

Creates a Singleton or SingleOwner instance based on the given type and name but does not return it.

§Panics
  • Panics if no provider is registered for the given type and name.
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or SingleOwner.
§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(name = "a")]
struct A;

let mut cx = Context::auto_register();
assert!(!cx.contains_single_with_name::<A>("a"));
cx.just_create_single_with_name::<A>("a");
assert!(cx.contains_single_with_name::<A>("a"));
source

pub fn try_just_create_single<T: 'static>(&mut self) -> bool

Try to create a Singleton or SingleOwner instance based on the given type and default name "" but does not return it.

§Note

If no provider is registered for the given type and default name "", or the provider is not a Singleton or SingleOwner, this method will return false, otherwise it will return true.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[derive(Clone)]
#[Singleton]
struct A;

#[Transient]
struct B;

let mut cx = Context::auto_register();

assert!(!cx.contains_single::<A>());
assert!(!cx.contains_single::<B>());

assert!(cx.try_just_create_single::<A>());
assert!(!cx.try_just_create_single::<B>());

assert!(cx.contains_single::<A>());
assert!(!cx.contains_single::<B>());
source

pub fn try_just_create_single_with_name<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> bool

Try to create a Singleton or SingleOwner instance based on the given type and name but does not return it.

§Note

If no provider is registered for the given type and default name "", or the provider is not a Singleton or SingleOwner, this method will return false, otherwise it will return true.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[derive(Clone)]
#[Singleton(name = "a")]
struct A;

#[Transient(name = "b")]
struct B;

let mut cx = Context::auto_register();

assert!(!cx.contains_single_with_name::<A>("a"));
assert!(!cx.contains_single_with_name::<B>("b"));

assert!(cx.try_just_create_single_with_name::<A>("a"));
assert!(!cx.try_just_create_single_with_name::<B>("b"));

assert!(cx.contains_single_with_name::<A>("a"));
assert!(!cx.contains_single_with_name::<B>("b"));
source

pub fn try_just_create_singles_by_type<T: 'static>(&mut self) -> Vec<bool>

Try to create Singleton and SingleOwner instances based on the given type but does not return them.

§Note

This method will return a collection of booleans, if a provider is a Singleton or SingleOwner, the corresponding boolean value will be true, otherwise it will be false.

§Panics
  • Panics if there is a provider whose constructor is async.
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[Singleton(name = "one")]
fn One() -> i32 {
    1
}

#[Transient(name = "two")]
fn Two() -> i32 {
    2
}

fn main() {
    let mut cx = Context::auto_register();

    assert!(!cx.contains_single::<i32>());

    let results = cx.try_just_create_singles_by_type::<i32>();

    assert!(results.contains(&true));
    assert!(results.contains(&false));

    assert_eq!(cx.get_singles_by_type::<i32>(), vec![&1]);
}
source

pub async fn resolve_async<T: 'static>(&mut self) -> T

Async version of Context::resolve.

§Panics
  • Panics if no provider is registered for the given type and default name "".
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or Transient.
§Example
use rudi::{Context, Transient};

#[Transient]
async fn Number() -> i32 {
    1
}

#[Transient(async)]
struct A(i32);

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert_eq!(cx.resolve_async::<i32>().await, 1);
    assert!(cx.resolve_option_async::<A>().await.is_some());
}
source

pub async fn resolve_with_name_async<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> T

Async version of Context::resolve_with_name.

§Panics
  • Panics if no provider is registered for the given type and name.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or Transient.
§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
async fn Number() -> i32 {
    1
}

#[Transient(async, name = "A")]
struct A(#[di(name = "a")] i32);

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert_eq!(cx.resolve_with_name_async::<i32>("a").await, 1);
    assert!(cx.resolve_option_with_name_async::<A>("A").await.is_some());
}
source

pub async fn resolve_option_async<T: 'static>(&mut self) -> Option<T>

Async version of Context::resolve_option.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Transient};

#[Transient]
async fn Number() -> i32 {
    1
}

#[Transient(async)]
struct A(i32);

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert_eq!(cx.resolve_async::<i32>().await, 1);
    assert!(cx.resolve_option_async::<A>().await.is_some());
}
source

pub async fn resolve_option_with_name_async<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> Option<T>

Async version of Context::resolve_option_with_name.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
async fn Number() -> i32 {
    1
}

#[Transient(async, name = "A")]
struct A(#[di(name = "a")] i32);

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert_eq!(cx.resolve_with_name_async::<i32>("a").await, 1);
    assert!(cx.resolve_option_with_name_async::<A>("A").await.is_some());
}
source

pub async fn resolve_by_type_async<T: 'static>(&mut self) -> Vec<T>

Async version of Context::resolve_by_type.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
async fn A() -> i32 {
    1
}

#[Transient(name = "b")]
async fn B() -> i32 {
    2
}

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert_eq!(
        cx.resolve_by_type_async::<i32>()
            .await
            .into_iter()
            .sum::<i32>(),
        3
    );
}
source

pub async fn just_create_single_async<T: 'static>(&mut self)

Async version of Context::just_create_single.

§Panics
  • Panics if no provider is registered for the given type and default name "".
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or SingleOwner.
§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(async)]
struct A;

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert!(!cx.contains_single::<A>());
    cx.just_create_single_async::<A>().await;
    assert!(cx.contains_single::<A>());
}
source

pub async fn just_create_single_with_name_async<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> )

Async version of Context::just_create_single_with_name.

§Panics
  • Panics if no provider is registered for the given type and name.
  • Panics if there is a provider that panics on construction.
  • Panics if the provider is not a Singleton or SingleOwner.
§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(async, name = "a")]
struct A;

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();
    assert!(!cx.contains_single_with_name::<A>("a"));
    cx.just_create_single_with_name_async::<A>("a").await;
    assert!(cx.contains_single_with_name::<A>("a"));
}
source

pub async fn try_just_create_single_async<T: 'static>(&mut self) -> bool

Async version of Context::try_just_create_single.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[derive(Clone)]
#[Singleton(async)]
struct A;

#[Transient(async)]
struct B;

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();

    assert!(!cx.contains_single::<A>());
    assert!(!cx.contains_single::<B>());

    assert!(cx.try_just_create_single_async::<A>().await);
    assert!(!cx.try_just_create_single_async::<B>().await);

    assert!(cx.contains_single::<A>());
    assert!(!cx.contains_single::<B>());
}
source

pub async fn try_just_create_single_with_name_async<T: 'static>( &mut self, name: impl Into<Cow<'static, str>> ) -> bool

Async version of Context::try_just_create_single_with_name.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[derive(Clone)]
#[Singleton(async, name = "a")]
struct A;

#[Transient(async, name = "b")]
struct B;

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();

    assert!(!cx.contains_single_with_name::<A>("a"));
    assert!(!cx.contains_single_with_name::<B>("b"));

    assert!(cx.try_just_create_single_with_name_async::<A>("a").await);
    assert!(!cx.try_just_create_single_with_name_async::<B>("b").await);

    assert!(cx.contains_single_with_name::<A>("a"));
    assert!(!cx.contains_single_with_name::<B>("b"));
}
source

pub async fn try_just_create_singles_by_type_async<T: 'static>( &mut self ) -> Vec<bool>

Async version of Context::try_just_create_singles_by_type.

§Panics
  • Panics if there is a provider that panics on construction.
§Example
use rudi::{Context, Singleton, Transient};

#[Singleton(name = "one")]
async fn One() -> i32 {
    1
}

#[Transient(name = "two")]
async fn Two() -> i32 {
    2
}

#[tokio::main]
async fn main() {
    let mut cx = Context::auto_register();

    assert!(!cx.contains_single::<i32>());

    let results = cx.try_just_create_singles_by_type_async::<i32>().await;

    assert!(results.contains(&true));
    assert!(results.contains(&false));

    assert_eq!(cx.get_singles_by_type::<i32>(), vec![&1]);
}
source

pub fn contains_provider<T: 'static>(&self) -> bool

Returns true if the context contains a provider for the specified type and default name "".

§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton]
struct A;

let cx = Context::auto_register();
assert!(cx.contains_provider::<A>());
source

pub fn contains_provider_with_name<T: 'static>( &self, name: impl Into<Cow<'static, str>> ) -> bool

Returns true if the context contains a provider for the specified type and name.

§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(name = "a")]
struct A;

let cx = Context::auto_register();
assert!(cx.contains_provider_with_name::<A>("a"));
source

pub fn get_provider<T: 'static>(&self) -> Option<&Provider<T>>

Returns a reference to an provider based on the given type and default name "".

§Example
use rudi::{Context, Transient};

#[Transient]
struct A;

let cx = Context::auto_register();
assert!(cx.get_provider::<A>().is_some());
source

pub fn get_provider_with_name<T: 'static>( &self, name: impl Into<Cow<'static, str>> ) -> Option<&Provider<T>>

Returns a reference to an provider based on the given type and name.

§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
struct A;

let cx = Context::auto_register();
assert!(cx.get_provider_with_name::<A>("a").is_some());
source

pub fn get_providers_by_type<T: 'static>(&self) -> Vec<&Provider<T>>

Returns a collection of references to providers based on the given type.

§Example
use rudi::{Context, Transient};

#[Transient(name = "a")]
fn A() -> i32 {
    1
}

#[Transient(name = "b")]
fn B() -> i32 {
    2
}

fn main() {
    let cx = Context::auto_register();
    assert_eq!(cx.get_providers_by_type::<i32>().len(), 2);
}
source

pub fn contains_single<T: 'static>(&self) -> bool

Returns true if the context contains a Singleton or SingleOwner instance for the specified type and default name "".

§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(eager_create)]
struct A;

let cx = Context::auto_register();
assert!(cx.contains_single::<A>());
source

pub fn contains_single_with_name<T: 'static>( &self, name: impl Into<Cow<'static, str>> ) -> bool

Returns true if the context contains a Singleton or SingleOwner instance for the specified type and name.

§Example
use rudi::{Context, Singleton};

#[derive(Clone)]
#[Singleton(eager_create, name = "a")]
struct A;

let cx = Context::auto_register();
assert!(cx.contains_single_with_name::<A>("a"));
source

pub fn get_single<T: 'static>(&self) -> &T

Returns a reference to a Singleton or SingleOwner instance based on the given type and default name "".

§Panics
  • Panics if no single instance is registered for the given type and default name "".
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(eager_create)]
struct A;

let cx = Context::auto_register();
let a = cx.get_single::<A>();
assert_eq!(format!("{:?}", a), "A");
source

pub fn get_single_with_name<T: 'static>( &self, name: impl Into<Cow<'static, str>> ) -> &T

Returns a reference to a Singleton or SingleOwner instance based on the given type and name.

§Panics
  • Panics if no single instance is registered for the given type and name.
§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(eager_create, name = "a")]
struct A;

let cx = Context::auto_register();
let a = cx.get_single_with_name::<A>("a");
assert_eq!(format!("{:?}", a), "A");
source

pub fn get_single_option<T: 'static>(&self) -> Option<&T>

Returns an optional reference to a Singleton or SingleOwner instance based on the given type and default name "".

§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(eager_create)]
struct A;

let cx = Context::auto_register();
assert!(cx.get_single_option::<A>().is_some());
source

pub fn get_single_option_with_name<T: 'static>( &self, name: impl Into<Cow<'static, str>> ) -> Option<&T>

Returns an optional reference to a Singleton or SingleOwner instance based on the given type and name.

§Example
use rudi::{Context, Singleton};

#[derive(Clone, Debug)]
#[Singleton(eager_create, name = "a")]
struct A;

let cx = Context::auto_register();
assert!(cx.get_single_option_with_name::<A>("a").is_some());
source

pub fn get_singles_by_type<T: 'static>(&self) -> Vec<&T>

Returns a collection of references to Singleton and SingleOwner instances based on the given type.

§Example
use rudi::{Context, Singleton};

#[Singleton(eager_create, name = "a")]
fn A() -> i32 {
    1
}

#[Singleton(eager_create, name = "b")]
fn B() -> i32 {
    2
}

fn main() {
    let cx = Context::auto_register();
    assert_eq!(cx.get_singles_by_type::<i32>().into_iter().sum::<i32>(), 3);
}

Trait Implementations§

source§

impl Default for Context

source§

fn default() -> Self

Returns the “default value” for a type. Read more

Auto Trait Implementations§

§

impl Freeze for Context

§

impl !RefUnwindSafe for Context

§

impl !Send for Context

§

impl !Sync for Context

§

impl Unpin for Context

§

impl !UnwindSafe for Context

Blanket Implementations§

source§

impl<T> Any for T
where T: 'static + ?Sized,

source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
source§

impl<T> Borrow<T> for T
where T: ?Sized,

source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
source§

impl<T> From<T> for T

source§

fn from(t: T) -> T

Returns the argument unchanged.

source§

impl<T> Instrument for T

source§

fn instrument(self, span: Span) -> Instrumented<Self>

Instruments this type with the provided Span, returning an Instrumented wrapper. Read more
source§

fn in_current_span(self) -> Instrumented<Self>

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
source§

impl<T, U> Into<U> for T
where U: From<T>,

source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

§

type Error = Infallible

The type returned in the event of a conversion error.
source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
source§

impl<T> WithSubscriber for T

source§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self>
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a WithDispatch wrapper. Read more
source§

fn with_current_subscriber(self) -> WithDispatch<Self>

Attaches the current default Subscriber to this type, returning a WithDispatch wrapper. Read more