• Najnowsze pytania
  • Bez odpowiedzi
  • Zadaj pytanie
  • Kategorie
  • Tagi
  • Zdobyte punkty
  • Ekipa ninja
  • IRC
  • FAQ
  • Regulamin
  • Książki warte uwagi

Parameter 0 of constructor in Service required a bean of type Repository that could not be found

42 Warsaw Coding Academy
0 głosów
1,698 wizyt
pytanie zadane 31 sierpnia 2022 w Java przez Lulex Użytkownik (820 p.)

Cześć,

próbuję dodać do mojego rest api dynamiczne wyszukiwanie po request paramterach. Udało się znaleźć fajne rozwiązanie jednak oczywiście coś nie działa :) .... Chciałem dodać  specification-arg-resolver 

Dodałem dependency:

<dependency>
     <groupId>net.kaczmarzyk</groupId>
     <artifactId>specification-arg-resolver</artifactId>
</dependency>

i postępowałem zgodnie z tutorialem .

W Controllerze mam zrobione chyba wszystko poprawnie:

@RestController
@RequestMapping("/drivers")
@RequiredArgsConstructor
public class DriverController {
    private final DriverService driverService;

    @GetMapping("/test2")
    public Set<DriverDto> test2(
            @And({
                    @Spec(path = "name", spec = Equal.class),
                    @Spec(path = "surname", spec = Equal.class)
            }) Specification<DriverEntity> customerSpec,
            Pageable pageable) {
        Set<DriverEntity> driverEntities = driverService.getAllWithSpec(customerSpec, pageable);
        return modelMapperService.mapSetToSetOfEnteredClass(driverEntities, DriverDto.class);
    }
}

metoda getAllWithSpec() w serwisie wygląda następująco:

@Service
@RequiredArgsConstructor
public class DriverService {
    private final DriverEntityRepository driverEntityRepository;

    public Set<DriverEntity> getAllWithSpec(Specification<DriverEntity> customerSpec, Pageable pageable) {
        return driverEntityRepository.findAll(customerSpec, pageable);
    }
}

Tak jak w specyfikacji dodałem również:

@Configuration
@EnableJpaRepositories
public class MyConfig implements WebMvcConfigurer {

    @Override
    public void addArgumentResolvers(List<HandlerMethodArgumentResolver> argumentResolvers) {
        argumentResolvers.add(new SpecificationArgumentResolver());
    }
}

No i teraz zaczynają się schody... Przy próbie odpalenia apki pojawia się:

***************************
APPLICATION FAILED TO START
***************************

Description:

Parameter 0 of constructor in com.exampleservice.DriverService required a bean of type 'com.example.repository.DriverEntityRepository' that could not be found.


Action:

Consider defining a bean of type 'com.example.repository.DriverEntityRepository' in your configuration.


Process finished with exit code 1

 

I nie do końca rozumiem czemu się tak dzieje... 

Gdy zakomentuję ten MyConfig to aplikacja startuje, ale przy próbie wysłania requesta np 

http://localhost:8081/drivers/test2?name=Tom&surname=Smith

pojawia się błąd:

java.lang.IllegalStateException: No primary or single unique constructor found for interface org.springframework.data.jpa.domain.Specification

i z tego co mi się udało znaleźć jest on spowodowany brakiem właśnie MyConfig. Będę wdzięczny za wszystkie pomysły :)

2 odpowiedzi

0 głosów
odpowiedź 31 sierpnia 2022 przez Lulex Użytkownik (820 p.)

Dobra, nie było tematu.

Usunąłem 

@EnableJpaRepositories

z MyConfig i poszło. Wyszukiwanie działa poprawnie.

komentarz 1 września 2022 przez Wiciorny Ekspert (280,970 p.)
teraz tylko zastanów się dlaczego z ową adnotacją którą użyłeś, nie działał program poprawnie.
W ten sposób nauczysz się chociaż, co dana adnotacja wnosi lub nie, a nie będziesz używał czegoś bez ówczesnego sprawdzenia np. dokumentacji.

To cenna uwaga na przyszłość, bo potem, ktoś Cię zapyta: co robi i jak działa @Service vs @Repository, albo @RestController vs @Controller
0 głosów
odpowiedź 1 września 2022 przez Wiciorny Ekspert (280,970 p.)

Problemem jest jeden fakt, że oczekujesz konstruktora z argumentami dla  jednego ze składowych
 

@Service
@RequiredArgsConstructor
public class DriverService {
    private final DriverEntityRepository driverEntityRepository;
 
    public Set<DriverEntity> getAllWithSpec(Specification<DriverEntity> customerSpec, Pageable pageable) {
        return driverEntityRepository.findAll(customerSpec, pageable);
    }
}

Dokładnie to   DriverEntityRepository driverEntityRepository; 
Jako obiekt zależny, nie posiada żadnej informacji jak ma być wstrzyknięty poprzez zależność, natomiast korzystasz z adnotacji.
 

@RequiredArgsConstructorgeneruje konstruktor z 1 parametrem dla każdego pola, które wymaga specjalnej obsługi. Wszystkie niezainicjowane finalpola otrzymują parametr, a także wszystkie pola oznaczone jako @NonNullniezainicjowane w miejscu, w którym są zadeklarowane. W przypadku pól oznaczonych @NonNull, generowane jest również jawne sprawdzenie wartości null. Konstruktor wyrzuci NullPointerExceptionif którykolwiek z parametrów przeznaczonych dla pól oznaczonych @NonNullinclude null. Kolejność parametrów odpowiada kolejności, w jakiej pola pojawiają się w Twojej klasie.

Dlaczego w takim razie nie odnajduje BEANA? Dlatego, że 
 

 @EnableJpaRepositories, służy do skanowania pakietów pod kątem konfiguracji i klasy repozytorium dla Spring Data JPA.

skanowanie musi zostać określone przez Ciebie w jakim pakiecie są klasy, więc aktualnie- masz to źle skonfigurowane i skanowanie nie widzi klasy  DriverEntityRepository , więc jednocześnie dla niego taki BEAN nie istnieje.
Usunięcie rozwiązuje problem, bo wtedy korzystasz z domyślnego skanowania repozytorium, wtedy widocznosc pakietu z tym beanem jest uwzględniona i bean może zostać poprawnie załadowany. 

Podobne pytania

0 głosów
1 odpowiedź 405 wizyt
pytanie zadane 31 lipca 2019 w PHP przez r.mar Początkujący (470 p.)
0 głosów
1 odpowiedź 1,423 wizyt
pytanie zadane 16 października 2020 w Java przez Stararara Początkujący (300 p.)

93,382 zapytań

142,382 odpowiedzi

322,539 komentarzy

62,740 pasjonatów

Motyw:

Akcja Pajacyk

Pajacyk od wielu lat dożywia dzieci. Pomóż klikając w zielony brzuszek na stronie. Dziękujemy! ♡

Oto polecana książka warta uwagi.
Pełną listę książek znajdziesz tutaj

VMware Cloud PRO - przenieś swoją infrastrukturę IT do chmury
...