Topic: 6 Understanding Dependency Injection
This is our sixth topic from Learn Flutter: Basic to Advance series
Hello devs, Today, we'll discuss Dependency Injection. Many tasks that we typically write manually in code can be automated with the help of dependency injection. We simply need to instruct the DI framework about the dependencies we require and how they should be instantiated.
Dependency Injection
Dependency injection is a technique in Flutter where objects or "dependencies" are provided to other objects that need them.
So it's just like you would hand out party hats and balloons to your guests, DI ensures that widgets or classes get the data, services, or other objects they need to work properly.
Alright devs, so the question is why do we use Dependency injection and why not write code manually?
Why use Dependency Injection?
DI makes your code more flexible and modular. Instead of hard-coding dependencies inside widgets or classes, you can inject them from outside. This makes it easier to test, maintain, and change your code later.
It also promotes reusability. You can reuse widgets or classes with different dependencies by injecting them accordingly.
So yeah that's why we use the DI in our App. Okay so now we look out how DI is Work.
How Does Dependency Injection Work in Flutter?
In Flutter, you can use packages like
get_it
,provider
, or even built-in Flutter mechanisms likeInheritedWidget
to perform dependency injection.For example, with
get_it
, you register dependencies (like a data service or a configuration object) and then retrieve them wherever needed in your app.With
provider
, you can useProvider.of
orConsumer
widgets to access dependencies from higher up in the widget tree.
Alright, devs Let's check one example of Dependency injection using getIt and After that the second example of DI using Provider.
Get_It Example
First, add the get_it
package to your pubspec.yaml
file:
dependencies:
flutter:
sdk: flutter
get_it: ^7.3.1 # Or the latest version available
Then, import the necessary packages and set up the dependency injection:
import 'package:flutter/material.dart';
import 'package:get_it/get_it.dart';
// Define a class for the user data
class UserData {
final String name;
final int age;
UserData({required this.name, required this.age});
}
void main() {
// Initialize GetIt for dependency injection
GetIt locator = GetIt.instance;
// Register the UserData class as a dependency
locator.registerLazySingleton<UserData>(() => UserData(name: 'John Doe', age: 30));
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('Dependency Injection Example'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
// Access user data using GetIt
Column(
children: [
Text('Name: ${locator<UserData>().name}'),
Text('Age: ${locator<UserData>().age}'),
],
),
SizedBox(height: 20),
ElevatedButton(
onPressed: () {
// Update user data using GetIt
locator<UserData>().name = 'Jane Smith';
locator<UserData>().age = 25;
// Since UserData is a singleton, changes are reflected everywhere
},
child: Text('Update User Data'),
),
],
),
),
),
);
}
}
In this example:
We import the
GetIt
package and initialize it aslocator
.We register
UserData
as a lazy singleton withlocator.registerLazySingleton
.Inside the
MyApp
widget, we accessUserData
usinglocator<UserData>()
and display its properties in the UI.We also have a button that updates the user data directly through
locator<UserData>()
, showcasing how changes are reflected globally due toUserData
being a singleton.
This example demonstrates how to use get_it
for dependency injection in Flutter to manage and access dependencies across your app.
Provider Example
First, make sure to add the provider
package to your pubspec.yaml
file:
dependencies:
flutter:
sdk: flutter
provider: ^5.0.0 # Or the latest version available
Then, import the necessary packages and set up the dependency injection:
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
// Define a class for the user data
class UserData {
final String name;
final int age;
UserData({required this.name, required this.age});
}
// Create a provider for the user data
class UserDataProvider extends ChangeNotifier {
UserData _userData = UserData(name: 'John Doe', age: 30);
UserData get userData => _userData;
void updateUser(UserData newData) {
_userData = newData;
notifyListeners(); // Notify listeners when data changes
}
}
void main() {
runApp(
ChangeNotifierProvider(
create: (context) => UserDataProvider(),
child: MyApp(),
),
);
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('Dependency Injection Example'),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
// Access user data using provider
Consumer<UserDataProvider>(
builder: (context, userDataProvider, child) {
final userData = userDataProvider.userData;
return Column(
children: [
Text('Name: ${userData.name}'),
Text('Age: ${userData.age}'),
],
);
},
),
SizedBox(height: 20),
ElevatedButton(
onPressed: () {
// Update user data using provider
Provider.of<UserDataProvider>(context, listen: false)
.updateUser(UserData(name: 'Jane Smith', age: 25));
},
child: Text('Update User Data'),
),
],
),
),
),
);
}
}
In this example:
We define a
UserData
class to represent user information.We create a
UserDataProvider
class that extendsChangeNotifier
to manage the user data.We use the
provider
package to provide theUserDataProvider
to the widget tree usingChangeNotifierProvider
.Inside the
MyApp
widget, we useConsumer
to access the user data fromUserDataProvider
and display it in the UI.We also have a button that triggers an update to the user data through the
updateUser
method inUserDataProvider
.
This example demonstrates how to use the provider
package for dependency injection in Flutter to manage and update data across your app.
Alright devs, This is the end of our blog i hope this blog helps you to easily understand Dependency Injection. Okay, then We catch up on our next topic async, await, and async*.
Connect with Me:
Hey there! If you enjoyed reading this blog and found it informative, why not connect with me on LinkedIn? π You can also follow my Instagram page for more mobile development-related content. π²π¨βπ» Letβs stay connected, share knowledge and have some fun in the exciting world of app development! π