Różnica między @Component, @Service, @Repository i @Controller w Springu

You are currently viewing Różnica między @Component, @Service, @Repository i @Controller w Springu

Wstęp

Spring to jeden z najpopularniejszych frameworków w świecie Javy. Jednym z jego kluczowych elementów jest zarządzanie komponentami za pomocą adnotacji, takich jak @Component, @Service, @Repository i @Controller. Chociaż wszystkie pełnią podobną rolę – rejestrowanie klas w kontenerze Springa – to każda z nich ma swoje specyficzne przeznaczenie. Pozostaje pytanie czym się różnią i kiedy, której używać.

@Component – podstawowa adnotacja

@Component to najbardziej ogólna adnotacja służąca do oznaczania klas jako komponentów Springa. Każda klasa oznaczona tą adnotacją jest rejestrowana w kontekście aplikacji jako Spring Bean.

@Component
public class MyComponent {
    public void doSomething() {
        System.out.println("Wykonuję zadanie!");
    }
}

@Component można stosować do dowolnych komponentów aplikacji, jednak w większości przypadków używa się bardziej precyzyjnych adnotacji, takich jak @Service, @Repository czy @Controller. Samej adnotacji użyjemy do bardziej ogólnego użytku, która nie pasuje do żadnego typu z trzech pozostałych np. klasy pomocnicze jak walidacja czy obliczenia matematyczne, konfiguracja z zewnętrznymi bibliotekami.

@Service – warstwa logiki biznesowej

Adnotacja @Service rozszerza funkcjonalność @Component i oznacza, że dana klasa zawiera logikę biznesową aplikacji. Dzięki temu nasz kod staje się czytelniejszy, bo wchodząc do takiego serwisu, wiemy, że mamy do czynienia z jakąś logiką biznesową np. operacje na encjach.

@Service
public class UserService {
    public String getUserInfo() {
        return "Dane użytkownika";
    }
}

@Repository – warstwa dostępu do danych

Adnotacja @Repository jest dedykowana dla klas odpowiedzialnych za dostęp do danych. Ważna cechą tej adnotacji jest to, że Spring widząc ją, automatycznie przechwyci wyjątki związane z bazą danych (zostaną przetłumaczone na wyjątek DataAccessException).

@Repository
public interface UserRepository extends JpaRepository<User, Long> {
    User findByUsername(String username);
}

@Controller – obsługa żądań HTTP

@Controller to adnotacja dedykowana dla warstwy kontrolerów w Springu. Oznacza klasę, która obsługuje żądania HTTP i zwraca widoki.

@Controller
public class UserController {

    @GetMapping("/users")
    public String getUser(Model model) {
        model.addAttribute("username", "Jan Kowalski");
        return "userView";
    }
}

Jeśli chcesz, aby kontroler zwracał dane JSON/XML, zamiast HTML, użyj @RestController lub dodaj do adnotacji @Controller, adnotację @ResponseBody.

@RunWith(SpringRunner.class)
@RestController
public class UserController {
    
    @GetMapping("/api/users")
    public String getUser() {
        return "Jan Kowalski";
    }
}

Testowanie aplikacji, a odpowiednia adnotacja komponentu

Kiedy nasza aplikacja Spring Boot się rozrasta, testowanie jej w całości staje się coraz większym wyzwaniem – testy działają wolno i bywają trudne w utrzymaniu. pełne testy integracyjne mogą ciągnąć się wiekami i być skomplikowane w utrzymaniu. Na szczęście twórcy frameworka pomyśleli i o tym, dając nam mechanizm testowania slices – czyli wybranych fragmentów aplikacji (np. tylko warstwy webowej albo dostępu do danych). Co to oznacza w praktyce? Prostsze i bardziej skoncentrowane testy, a przede wszystkim – ogromna oszczędność czasu przy ich uruchamianiu.

Testy slice

Na początku przybliżmy sobie czym jest to testowanie fragmentami (test slices). Testy te pozwalają na testowanie określonych warstw aplikacji w izolacji, bez uruchamiania całego kontekstu aplikacji. Dzięki nim możemy skupić się tylko na konkretnej funkcjonalności, np. warstwie webowej, repozytoriach, czy kontrolerach REST, bez ładowania wszystkich komponentów.

Spring Boot dostarcza specjalne adnotacje dla różnych rodzajów testów slices. W tabeli poniżej opisałem te adnotacje wraz z relacją do odpowiednich adnotacji dla komponentów.

Adnotacja komponentuAdnotacja testu sliceTestowane komponenty
@Controller@WebMvcTestKontrolery MVC, filtry, konfiguracja webowa
@RestController@WebMvcTestKontrolery REST, konfiguracja webowa
@Repository@DataJpaTestRepozytoria Spring Data, konfiguracja JPA
@ServiceBrak bezpośredniego odpowiednika – zwykle mockowane w testach innych warstwLogika biznesowa
@ComponentBrak bezpośredniego odpowiednika – zależnie od przeznaczeniaRóżne komponenty aplikacji

Oczywiście istnieje więcej typów adnotacji dla testów slice. W dokumentacji Springa jest opisana cała lista dostępnych adnotacji wraz z kontekstem jaki wczytuje (link do dokumentacji).

Przykład testów slice

Mechanizm testów slices działa poprzez selektywne ładowanie tylko tych komponentów, które są wymagane dla danej warstwy. Na przykład, @WebMvcTest ładuje tylko kontrolery oraz konfigurację związaną z MVC, pomijając repozytoria, serwisy i inne komponenty. Komponenty, które nie są automatycznie ładowane, można zamockować za pomocą @MockBean lub zaimportować używając @Import.

@WebMvcTest(UserController.class)
class UserControllerTest {
    @Autowired
    private MockMvc mockMvc;
    
    @MockBean
    private UserService userService;
    
    @Test
    void shouldReturnUser() throws Exception {
        // test implementacja
    }
}

Podsumowanie

Każda z wymienionych adnotacji ma swoje konkretne przeznaczenie:

AdnotacjaZastosowanieSpecjalizacja
@ComponentOgólna adnotacja dla komponentówNie
@ServiceWarstwa logiki biznesowejTak
@RepositoryWarstwa dostępu do danychTak
@ControllerObsługa żądań HTTPTak

Jeśli tworzysz komponent ogólnego przeznaczenia, możesz użyć @Component. Dla logiki biznesowej wybierz @Service, dla operacji na bazie danych – @Repository, a dla kontrolerów HTTP – @Controller.

Dobrze dobrane adnotacje sprawiają, że kod jest czytelniejszy, bardziej modułowy i łatwiejszy w zarządzaniu. Jeśli chcesz pisać aplikacje w Springu zgodnie z najlepszymi praktykami, warto trzymać się tego podziału!

Subskrybuj
Powiadom o
guest
0 komentarzy
Najstarsze
Najnowsze Najwięcej głosów
Opinie w linii
Zobacz wszystkie komentarze