Dependency Injection (DI) in Go (Golang) follows the same basic principles as in other programming languages, but with a focus on simplicity and explicitness, given Go’s minimalist design. DI is used to decouple the creation of an object’s dependencies from its behavior, making the code more modular, testable, and maintainable.
Step-by-Step Explanation of Dependency Injection in Go
-
Define Interfaces for Dependencies:
- Identify the components of your application that can be abstracted behind interfaces. These interfaces represent the contracts that your components must fulfill.
- Example: If a component needs to access a database, define an interface for database operations.
-
Implement the Dependencies:
- Create concrete implementations of these interfaces. These implementations are the actual dependencies that will be injected.
- Example: Implement the database interface with a MySQL or PostgreSQL driver.
-
Design Your Components to Receive Dependencies:
- Write your components (such as structs and their methods in Go) to receive dependencies through their constructors or setter methods. This is where the actual injection happens.
- Example: A service struct takes a database interface implementation as a parameter in its constructor.
-
Create a Centralized Place for Dependency Construction (Optional):
- While not a requirement, some applications benefit from having a central place where dependencies are constructed. This can be a main function or a special factory function.
- This step often involves “wiring up” your application by creating the concrete dependencies and passing them to the components that need them.
-
Inject the Dependencies:
- Instantiate your dependencies and inject them into the components that require them.
- Example: In your
main
function, create a database connection and pass it to the service constructor.
-
Use the Components:
- With dependencies injected, your components are ready to be used. The key point here is that the components are not aware of how their dependencies are created, making them easier to test and maintain.
Example in Go
Here’s a simple example to illustrate DI in Go:
In this example:
Database
is an interface that abstracts database operations.MySQL
is a concrete implementation of theDatabase
interface.Service
is a struct that depends on theDatabase
interface. It receives its dependency through its constructorNewService
.- In the
main
function, we create aMySQL
instance and inject it into a newService
instance.
This structure makes it easy to swap out the MySQL
implementation with another implementation of the Database
interface, such as a mock database for testing, without changing the Service
code.
https://quii.gitbook.io/learn-go-with-tests/go-fundamentals/dependency-injection