Inversion of Control and Dependency Injection
The Problem: Tight Coupling
If a class creates its own dependencies with new, it is tightly coupled to them. You cannot swap the implementation (e.g. a fake payment gateway in tests) without editing the class.
class OrderService {
// OrderService decides which gateway to use. Hard to test, hard to change.
private final RazorpayGateway gateway = new RazorpayGateway();
}The Fix: Ask for Dependencies
Dependency Injection (DI): a class declares what it needs (usually in its constructor) and someone else gives it. Inversion of Control (IoC): that "someone else" is the framework. Control over object creation is inverted, from your class to the Spring IoC container (also called the ApplicationContext).
Example
DI in plain Java: OrderService depends on an interface, and main (playing the role of Spring) decides which implementation to inject.
public class Main {
public static void main(String[] args) {
// "the container": creates objects and wires them together
OrderService prod = new OrderService(new RazorpayGateway());
OrderService test = new OrderService(new FakeGateway());
prod.placeOrder(101, 2998);
test.placeOrder(102, 499);
}
}
interface PaymentGateway {
String charge(long orderId, int amount);
}
class RazorpayGateway implements PaymentGateway {
public String charge(long orderId, int amount) { return "Razorpay charged Rs." + amount + " for order " + orderId; }
}
class FakeGateway implements PaymentGateway {
public String charge(long orderId, int amount) { return "FAKE payment ok for order " + orderId + " (no money moved)"; }
}
class OrderService {
private final PaymentGateway gateway; // depends on the interface only
OrderService(PaymentGateway gateway) { // dependency is injected
this.gateway = gateway;
}
void placeOrder(long orderId, int amount) {
System.out.println(gateway.charge(orderId, amount));
}
}Output
Razorpay charged Rs.2998 for order 101 FAKE payment ok for order 102 (no money moved)
What Spring Adds
Your classes (@Component, @Service ...) Configuration (@Bean, properties)
\ /
v v
+-------------------------------------------+
| Spring IoC container (ApplicationContext)|
| 1. finds classes 2. creates beans |
| 3. injects dependencies 4. manages life |
+-------------------------------------------+
|
v
ready-to-use, wired objects (beans)An object created and managed by Spring is called a bean. Benefits: loose coupling, easy testing with mocks, one place to configure, and features like transactions and security can be added around beans automatically.