force_inject 0.4.0 copy "force_inject: ^0.4.0" to clipboard
force_inject: ^0.4.0 copied to clipboard

A zero-dependency DI container for Dart, inspired by .NET Core. This is the Way.

πŸ”Œ ForceInject #

pub package publisher: diegogarcia.ca

πŸ› οΈ A lightweight, zero runtime dependency Dependency Injection (DI) container for Dart.
🌌 Inspired by .NET Core and powered by the Force.
This is the Way.

✨ Features #

  • Constructor-based dependency injection
  • Support for singleton, transient, and scoped lifetimes
  • Named & tagged service resolution
  • Scoped service overrides for testing and previews
  • No code generation, no mirrors
  • No runtime dependencies β€” pure Dart
  • Fully compatible with Flutter, CLI, and server
  • Inspired by C#/.NET Core DI patterns
  • Lightweight, test-friendly, and easy to integrate

βš™οΈ Dependencies #

ForceInject is designed to have no runtime dependencies.

We use the Dart team's official meta package only for static annotations like @protected and @visibleForTesting.

This ensures:

  • βœ… No runtime or platform bloat
  • βœ… Full IDE and analyzer support
  • βœ… Maximum compatibility with Flutter, backend, and CLI

πŸš€ Getting Started #

1. Register your services #

final services = ServiceCollection();

services.addSingleton<ILogger, ConsoleLogger>();
services.addTransient<UserService, UserService>();

ServiceProvider.registerConstructor<ConsoleLogger>(() => ConsoleLogger(), []);
ServiceProvider.registerConstructor<UserService>(
  (ILogger logger) => UserService(logger),
  [ILogger],
);

2. Build the provider #

final provider = services.buildServiceProvider();

3. Resolve services #

final userService = provider.get<UserService>();
userService.sayHello(); // [LOG]: Hello from UserService!

Need a per-screen or per-request services? Create a ServiceScope: #

final scope = provider.createScope();
final viewModel = scope.get<MyViewModel>();
scope.dispose(); // clean up when done

βš™οΈ Lifetimes #

Type Description
singleton One shared instance across the application
transient A new instance is created every time
scoped One instance per ServiceScope β€” ideal for screen/request lifetimes

πŸ”§ Advanced Usage #

πŸ” Scoped Overrides #

You can override services inside a scope to inject mocks or alternate implementations:

final scope = provider.createScope();
scope.overrideService<Logger>(FakeLogger());

final logger = scope.get<Logger>(); // Returns FakeLogger

You can also provide overrides on creation:

final scope = provider.createScope(overrides: {
  Logger: FakeLogger(),
});

This is great for testing, previews, or A/B environments.

πŸ§ͺ Testing & Mocks #

Check out test/ for unit tests and real-world setup examples.
You can also override services dynamically using .overrideService() for fine-grained control.

πŸ“¦ Why ForceInject? #

Dart is an elegant language, but backend structure is still evolving.
ForceInject gives you the power of .NET’s DI model, but in pure Dart β€” making your code modular, testable, and maintainable.

No magic. No mirrors. Just clean, focused architecture.
πŸ’¬ "When your services are confused, inject them you must." – Yodart

πŸ§ͺ Examples #

This package includes several complete examples you can explore:

  • 🧱minimal_dart_di
    A simple Dart CLI app using ForceInject with singleton and transient services.

  • πŸ“±minimal_flutter_di
    A clean Flutter app using scoped DI and a ValueNotifier-based ViewModel.

  • πŸ“±Scoped Widget DI A clean Flutter app using Scoped Widget DI.

  • πŸ“±Async ViewModel DI A clean Flutter app using Scoped Widget DI with life cycle control with async initialization.

To run the Flutter example:

cd example/minimal_flutter_di
flutter create .
flutter pub get
flutter run

Read the README.md inside the minimal_flutter_di project for more details.

Support me (@diegomgarcia) with Patreon #

Patreon

Or make a donation buying me a coffee:

Buy Me A Coffee

You can also show support by showing on your repository that you use this lib on it with a direct link to it.

πŸ“œ License #

MIT – Free to use, modify, or extend.
May the DI be with you. βš”οΈ

1
likes
140
points
56
downloads

Publisher

verified publisherdiegogarcia.ca

Weekly Downloads

A zero-dependency DI container for Dart, inspired by .NET Core. This is the Way.

Repository (GitHub)

Documentation

API reference

License

MIT (license)

Dependencies

meta

More

Packages that depend on force_inject