kit_rs/container/
provider.rs

1//! Service auto-registration for Kit framework
2//!
3//! This module provides automatic service registration via macros:
4//! - `#[service(ConcreteType)]` - auto-register trait bindings
5//! - `#[derive(Injectable)]` - auto-register concrete types as singletons
6//!
7//! # Example - Trait binding
8//!
9//! ```rust,ignore
10//! use kit::service;
11//!
12//! // Auto-register: dyn CacheStore → RedisCache
13//! #[service(RedisCache)]
14//! pub trait CacheStore: Send + Sync + 'static {
15//!     fn get(&self, key: &str) -> Option<String>;
16//!     fn set(&self, key: &str, value: &str);
17//! }
18//!
19//! pub struct RedisCache;
20//! impl Default for RedisCache {
21//!     fn default() -> Self { Self }
22//! }
23//! impl CacheStore for RedisCache { ... }
24//! ```
25//!
26//! # Example - Concrete singleton
27//!
28//! ```rust,ignore
29//! use kit::injectable;
30//!
31//! #[injectable]
32//! pub struct AppState {
33//!     pub counter: u32,
34//! }
35//!
36//! // Resolve via:
37//! let state: AppState = App::get().unwrap();
38//! ```
39
40/// Entry for inventory-collected service bindings (trait → impl)
41///
42/// Used internally by the `#[service(ConcreteType)]` macro to register
43/// service bindings at compile time.
44pub struct ServiceBindingEntry {
45    /// Function to register the service binding
46    pub register: fn(),
47    /// Service name for debugging/logging
48    pub name: &'static str,
49}
50
51/// Entry for inventory-collected singleton registrations (concrete types)
52///
53/// Used internally by the `#[derive(Injectable)]` macro to register
54/// concrete singletons at compile time.
55pub struct SingletonEntry {
56    /// Function to register the singleton
57    pub register: fn(),
58    /// Type name for debugging/logging
59    pub name: &'static str,
60}
61
62// Inventory collection for auto-registered service bindings
63inventory::collect!(ServiceBindingEntry);
64
65// Inventory collection for auto-registered singletons
66inventory::collect!(SingletonEntry);
67
68/// Register all service bindings from inventory
69///
70/// This is called automatically by `Server::from_config()`.
71/// It registers all services marked with `#[service(ConcreteType)]`.
72pub fn register_service_bindings() {
73    for entry in inventory::iter::<ServiceBindingEntry> {
74        (entry.register)();
75    }
76}
77
78/// Register all singleton entries from inventory
79///
80/// This is called automatically by `Server::from_config()`.
81/// It registers all types marked with `#[derive(Injectable)]`.
82pub fn register_singletons() {
83    for entry in inventory::iter::<SingletonEntry> {
84        (entry.register)();
85    }
86}
87
88/// Full bootstrap sequence for services
89///
90/// Called automatically by `Server::from_config()`.
91pub fn bootstrap() {
92    register_service_bindings();
93    register_singletons();
94}