Pod constructor
const
Pod({})
Marks a method as a pod provider, enabling it to participate in the dependency injection (DI) lifecycle of the application.
The method annotated with @Pod
should return an instance of a component,
service, or configuration object. This returned value is automatically
registered in the application’s DI container and, by default, managed
as a singleton.
🔧 How It Works:
- The enclosing class is typically annotated with
@Configuration
or@AutoConfiguration
. - During application startup, all methods annotated with
@Pod
are executed, and their return values are registered in the application context. - These pods are then available for injection into other classes via constructor injection, factory injection, or field injection (depending on the framework).
📌 Features:
- Default lifecycle is singleton (created once and reused).
- Supports lazy initialization depending on the framework’s DI engine.
- May support pod naming or conditional creation in extended versions.
🧪 Example:
@Configuration()
class AppConfig {
@Pod()
Logger createLogger() {
return Logger('AppLogger');
}
@Pod()
HttpClient httpClient(Logger logger) {
return HttpClient(logger: logger);
}
}
In the example above:
createLogger()
returns aLogger
instance registered as a pod.httpClient()
depends onLogger
, which is automatically injected by the container.
🔄 Pod Lifecycle (Simplified):
- Framework initializes configuration class
- All @Pod methods are executed
- Results are cached as singleton pods
- Pods are injected into constructors or other pods as needed
🔥 Advanced Use Cases (Possible Extensions):
- Conditional pods:
@ConditionalOnMissingPod
,@Profile('dev')
- Scoped pods: e.g., per request, per session (via
@Scope
) - Named pods:
@Pod(name: 'myLogger')
These can be added through optional parameters or decorators in future.
❗ Constraints:
- The method must be non-private.
- The method must return a value;
void
is not allowed. - Must be defined within a class marked with
@Configuration
,@AutoConfiguration
, etc. - Cyclic dependencies must be handled explicitly or avoided.
✅ Usage Recommendations:
- Prefer pod methods over manual instantiation in app code.
- Keep logic inside pod methods minimal — do initialization but not business logic.
- Group related pods in separate configuration classes for clarity.
🧱 Related Annotations:
@Configuration
– Marks the containing class as a source of pod definitions.@AutoConfiguration
– Similar but auto-discovered.@Aspect
– Used for cross-cutting concerns.@Inject
,@Autowired
– For consuming/injecting defined pods.
🎯 Target:
Can only be applied to methods:
@Pod()
MyService myService() => MyService();
Pod annotation for pod definition methods
This annotation marks a method as a pod producer.
Example Usage:
@Configuration()
class DatabaseConfig {
@Pod()
@Scope('singleton')
DatabaseConnection primaryDatabase() {
return DatabaseConnection(
url: 'postgresql://localhost:5432/primary',
maxConnections: 20,
);
}
@Pod('readOnlyDatabase')
@Scope('prototype')
DatabaseConnection readOnlyDatabase() {
return DatabaseConnection(
url: 'postgresql://localhost:5432/readonly',
readOnly: true,
);
}
}
Implementation
const Pod({
this.value,
this.autowireMode = AutowireMode.NO,
this.initMethods = const [],
this.destroyMethods = const [],
this.enforceInitMethods = false,
this.enforceDestroyMethods = false
});