UnsatisfiedDependencyException: Error creating bean with name
Asked Answered
R

27

113

For several days I have been trying to create a Spring CRUD application. I'm confused. I can't solve these errors.

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'clientController': Unsatisfied dependency expressed through method 'setClientService' parameter 0; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'clientService': Unsatisfied dependency expressed through field 'clientRepository'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.kopylov.repository.ClientRepository' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}

And this:

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'clientService': Unsatisfied dependency expressed through field 'clientRepository'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.kopylov.repository.ClientRepository' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}

ClientController

@Controller
public class ClientController {
    private ClientService clientService;

    @Autowired
    @Qualifier("clientService")
    public void setClientService(ClientService clientService) {
        this.clientService = clientService;
    }

    @RequestMapping(value = "registration/add", method = RequestMethod.POST)
    public String addUser(@ModelAttribute Client client) {
        this.clientService.addClient(client);
        return "home";
    }
}

ClientServiceImpl

@Service("clientService")
public class ClientServiceImpl implements ClientService {

    private ClientRepository clientRepository;

    @Autowired
    @Qualifier("clientRepository")
    public void setClientRepository(ClientRepository clientRepository) {
        this.clientRepository = clientRepository;
    }

    @Transactional
    public void addClient(Client client) {
        clientRepository.saveAndFlush(client);
    }
}

ClientRepository

public interface ClientRepository extends JpaRepository<Client, Integer> {

}

I looked through a lot of similar questions, but not one answer to them helps me.

Runnerup answered 6/1, 2017 at 17:57 Comment(3)
Where is the implementation class of ClientRepository?Expellee
@Arpit I create an instance of ClientRepository only in ClientServiceImpl. It's my first experience this Spring Data JPA and i don't know how do correctly. So I followed exampleRunnerup
@Arpit Please look at my project on github (i add link)Runnerup
A
56

The ClientRepository should be annotated with @Repository tag. With your current configuration Spring will not scan the class and have knowledge about it. At the moment of booting and wiring will not find the ClientRepository class.

EDIT If adding the @Repository tag doesn't help, then I think that the problem might be now with the ClientService and ClientServiceImpl.

Try to annotate the ClientService (interface) with @Service. As you should only have a single implementation for your service, you don't need to specify a name with the optional parameter @Service("clientService"). Spring will autogenerate it based on the interface' name.

Also, as Bruno mentioned, the @Qualifier is not needed in the ClientController as you only have a single implementation for the service.

ClientService.java

@Service
public interface ClientService {

    void addClient(Client client);
}

ClientServiceImpl.java (option 1)

@Service
public class ClientServiceImpl implements ClientService{

    private ClientRepository clientRepository;

    @Autowired
    public void setClientRepository(ClientRepository clientRepository){
        this.clientRepository=clientRepository;
    }

    @Transactional
    public void addClient(Client client){
        clientRepository.saveAndFlush(client);
    }
}

ClientServiceImpl.java (option 2/preferred)

@Service
public class ClientServiceImpl implements ClientService{

    @Autowired
    private ClientRepository clientRepository;

    @Transactional
    public void addClient(Client client){
        clientRepository.saveAndFlush(client);
    }
}

ClientController.java

@Controller
public class ClientController {
    private ClientService clientService;

    @Autowired
    //@Qualifier("clientService")
    public void setClientService(ClientService clientService){
        this.clientService=clientService;
    }

    @RequestMapping(value = "registration", method = RequestMethod.GET)
    public String reg(Model model){
        model.addAttribute("client", new Client());
        return "registration";
    }

    @RequestMapping(value = "registration/add", method = RequestMethod.POST)
    public String addUser(@ModelAttribute Client client){
        this.clientService.addClient(client);
    return "home";
    }
}
Aquitaine answered 6/1, 2017 at 18:4 Comment(3)
Now I have such error: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.kopylov.repository.ClientRepository' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}Runnerup
I also had the same issue, forgot to add Service annotation in impl. Adding Service annotation fixed the issue. Thanks @AlexDiplosis
I have the same issue. It runs perfectly as a Maven based project, but fails with the same horrific error message and stacktrace when built & run as a Gradle based project. I already spent 2 days trying all the ideas posted here - to no avail. Anyone has experienced this before? Additional tips?Wiltz
D
10

I know it seems too late, but it may help others in future.

I face the same error and the problem was that spring boot did not read my services package so add:

@ComponentScan(basePackages = {"com.example.demo.Services"}) (you have to specify your own path to the services package) and in the class demoApplication (class that have main function) and for service interface must be annotated @Service and the class that implement the service interface must be annotated with @Component, then autowired the service interface.

Dissert answered 14/12, 2018 at 18:38 Comment(1)
Could you please make it more clearer to understandUncivil
S
5

Try adding @EntityScan(basePackages = "insert package name here") on top of your main class.

Smallish answered 13/3, 2018 at 8:27 Comment(1)
What about i have no main class ?Melessa
H
5

If you are using Spring Boot, your main app should be like this (just to make and understand things in simple way) -

package aaa.bbb.ccc;
@SpringBootApplication
@ComponentScan({ "aaa.bbb.ccc.*" })
public class Application {
.....

Make sure you have @Repository and @Service appropriately annotated.

Make sure all your packages fall under - aaa.bbb.ccc.*

In most cases this setup resolves these kind of trivial issues. Here is a full blown example. Hope it helps.

Hamlett answered 19/2, 2019 at 19:27 Comment(2)
this fixed mine. THanks alot. But I wonder why it doesn't automatically detect my beans/classes even though they exist. Is this some sort of a bug?. My application is all under one package anyway and I dont have any other packages.I don't get why I have to manually have the component class be declared.Palomino
Well if you are using @ SPringbootApplication annotation then you dont need @ ComponentScan . @ SpringBootApplication = @ Configuration + @ ComponentScan + @ EnableAutoConfigurationBismuthinite
B
4

That might happen because the pojos you are using lack of the precise constructor the service needs. That is, try to generate all the constructors for the pojo or objects (model object) that your serviceClient uses, so that the client can be instanced correctly. In your case,regenerate the constructors (with arguments)for your client object (taht is your model object).

Barty answered 3/4, 2018 at 8:21 Comment(0)
L
4

I was facing the same issue, and it was, as i missed marking my DAO class with Entity annotations. I tried below and error got resolved.

/**
*`enter code here`
*/
@Entity <-- was missing earlier
    public class Topic {
        @Id  
        String id;
        String name;
        String desc;

    .
    .
    .
    }
Letendre answered 19/5, 2018 at 20:51 Comment(0)
M
4

I just added the @Repository annotation to Repository interface and @EnableJpaRepositories ("domain.repositroy-package") to the main class. It worked just fine.

Middleaged answered 10/10, 2018 at 9:6 Comment(1)
im not sure if would have helped the OP, but if anyone is using SpringBoot and have @EnableAutoConfiguration(exclude = {DataSource/HibernateJpa..etc} These excludes may deny spring to auto verify the annotations declared in the CRUD classes, so the removal of the exclusions might fix it together with adding the @EnableJpaRepositories in the Main classQuadrennial
R
3

I was facing the same issue. In my Product Entity Class I had imported @Id from org.springframework.data.annotation.Id and this was causing the error.

It was fixed after I change it to import jakarta.persistence.Id;

Rheotaxis answered 5/1, 2023 at 4:5 Comment(0)
M
2

The application needs to be placed in the same directory as the scanned package:

enter image description here

Mango answered 21/4, 2018 at 12:46 Comment(0)
B
1

Add @Repository annotation to the Spring Data JPA repo

Buss answered 6/1, 2017 at 18:3 Comment(0)
F
1

Check out the table structure of Client table, if there is a mismatch between table structure in db and the entity, you would get this error..

I had this error which was coming due to datatype mismatch of primary key between db table and the entity ...

Foreboding answered 10/9, 2018 at 18:58 Comment(0)
U
1

That was the version incompatibility where their was the inclusion of lettuce. When i excluded , it worked for me.

<!--Spring-Boot 2.0.0 -->
    <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-redis</artifactId>
                <exclusions>
                    <exclusion>
                        <groupId>io.lettuce</groupId>
                        <artifactId>lettuce-core</artifactId>
                    </exclusion>
                </exclusions>    
            </dependency>
            <dependency>
                <groupId>redis.clients</groupId>
                <artifactId>jedis</artifactId>
            </dependency>
Undergird answered 30/4, 2019 at 4:18 Comment(0)
T
0

According to documentation you should set XML configuration:

<jpa:repositories base-package="com.kopylov.repository" />
Tyronetyrosinase answered 6/1, 2017 at 18:3 Comment(1)
This is I have in my appContext.xml and it doesn't helpRunnerup
I
0

Considering that your package scanning is correctly set either through XML configuration or annotation based configuration.

You will need a @Repository on your ClientRepository implementation as well to allow Spring to use it in an @Autowired. Since it's not here we can only suppose that's what's missing.

As a side note, it would be cleaner to put your @Autowired/@Qualifier directly on your member if the setter method is only used for the @Autowired.

@Autowired
@Qualifier("clientRepository")
private ClientRepository clientRepository;

Lastly, you don't need the @Qualifier is there is only one class implementing the bean definition so unless you have several implementation of ClientService and ClientRepository you can remove the @Qualifier

Interact answered 6/1, 2017 at 18:6 Comment(1)
You are just writting the same things that already have been postedLivingston
C
0

I had the exactly same issue, with a very very long stack trace. At the end of the trace I saw this:

InvalidQueryException: Keyspace 'mykeyspace' does not exist

I created the keyspace in cassandra, and solved the problem.

CREATE KEYSPACE mykeyspace
  WITH REPLICATION = { 
   'class' : 'SimpleStrategy', 
   'replication_factor' : 1 
  };
Catatonia answered 4/5, 2018 at 13:8 Comment(0)
I
0

If you describe a field as criteria in method definition ("findBy"), You must pass that parameter to the method, otherwise you will get "Unsatisfied dependency expressed through method parameter" exception.

public interface ClientRepository extends JpaRepository<Client, Integer> {
       Client findByClientId();                ////WRONG !!!!
       Client findByClientId(int clientId);    /// CORRECT 
}

*I assume that your Client entity has clientId attribute.

Inexpressible answered 24/10, 2018 at 22:35 Comment(0)
N
0

See if your <context:component-scan base-package="your package "/> is missing in either config or context xml file

Naturally answered 21/3, 2019 at 2:46 Comment(0)
H
0

Just add @Service annotation to top of the service class

Habile answered 28/7, 2019 at 19:48 Comment(0)
M
0

There is another instance still same error will shown after you doing everything above mentioned. When you change your codes accordingly mentioned solutions make sure to keep originals. So you can easily go back. So go and again check dispatcher-servelet configuration file's base package location. Is it scanning all relevant packages when you running application.

<context:component-scan base-package="your.pakage.path.here"/>
Mitis answered 2/10, 2019 at 20:23 Comment(0)
T
0

Add @Component annotation just above the component definition

Tattler answered 11/8, 2020 at 10:18 Comment(0)
E
0

This error can occur if there are syntax errors with Derived Query Methods. For example, if there are some mismatches with entity class fields and the Derived methods' names.

Elliotelliott answered 1/1, 2021 at 21:38 Comment(0)
F
0

I was facing this issue because of duplicate column name staffId and staff_id in same entity class.

    private Integer staffId;
    @ManyToOne(cascade = CascadeType.ALL, optional = false)
    @JoinColumn(name = "staff_id")
    private User user;
Fjord answered 22/9, 2021 at 5:55 Comment(0)
J
0

My issue got resolved by adding "value" & "nativeQuery" tags in @Query annotation like this:

@Query(value = "select * from employee e where e.email_address = ?1", nativeQuery = true)
Journey answered 21/3, 2022 at 14:0 Comment(0)
C
0

In my case, I was using dependency of spring boot 3 in spring boot 4. make sure you use latest dependency version.

you can find that here https://mvnrepository.com/

Conventionalism answered 25/4, 2022 at 9:26 Comment(0)
D
0

Below one may be one of the reason, I was able to solve my error by doing that.

Just make sure that the methods you have written in Dao are correct or not, means the method is unique or not.

Decaliter answered 4/3, 2023 at 17:14 Comment(0)
B
0

add the below code in your main class, springboot might not able to scan the jpa lavel pakage.

@SpringBootApplication(scanBasePackages={"com.*"})
@EntityScan( basePackages = {"com.*"} )
@EnableJpaRepositories( basePackages = {"com.*"} )

enter image description here

Botnick answered 14/8, 2023 at 11:42 Comment(0)
P
0

For me, the issue was due to the typo error in the JPQL query, which I have written in the Repository interface. @Query("SELECT em FROM Employee WHERE em.name = :name").

Updated query: @Query("SELECT em FROM Employee em WHERE em.name = :name")

Updating the query resolved the error for me.

Potpourri answered 16/2 at 15:48 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.