Wstrzykiwanie zależności polega na tym, że najpierw podajesz obiektowi jego zależność, a potem wykonujesz na nim metodę, która tą zależność wykorzystuje. Wstrzykiwanie może być przez konstruktor (lepiej, bo łatwiej utrzymać spójność obiektu) lub przez setter (gorzej, bo każdy korzystający z klasy musi pamiętać o odpaleniu settera).
Wstrzykiwanie przez konstruktor:
// tej klasie wstrzykujemy zależność przez konstruktor, a potem korzystamy z niej w metodzie zróbKromkę
class Klasa {
final ChlebakService zależność;
public Klasa(ChlebakService zależność) {
this.zależność = zależność;
}
Kromka zróbKromkę() {
return zależność.getChleb().pokrój();
}
}
Występuje w wersji klasycznej ręcznej (z użyciem słówka new
) jak i magicznej (przy użyciu adnotacji Autowired, Inject i tym podobnych).
Wstrzykiwanie przez setter:
class Klasa {
ChlebakService zależność = null;
void setZależność(ChlebakService zależność) {
this.zależność = zależność;
}
Kromka zróbKromkę() {
return zależność.getChleb().pokrój();
}
}
Brak wstrzykiwania - tworzenie zależności w konstruktorze. Konstruktor ma efekt uboczny (tworzenie nowego obiektu, potencjalnie robiącego I/O lub dużo obliczeń) co jest złe, bo utrudnia testowanie:
class Klasa {
final ChlebakService zależność = new ChlebakService();
Kromka zróbKromkę() {
return zależność.getChleb().pokrój();
}
}
Brak wstrzykiwania - zależnośc podajemy razem z jej wykorzystaniem, nie jest ona nigdzie w obiekcie zapisywana:
class Klasa {
Kromka zróbKromkę(ChlebakService zależność) {
return zależność.getChleb().pokrój();
}
}
Polecam najpierw przećwiczenie opcji pierwszej w wersji klasycznej, czyli wstrzykiwania przez konstruktor z użyciem słówka new
. Potem można przejść do opcji magicznej jeśli koledzy nalegają, ale ja bym się przed tym bronił.