I am working on spring batch with spring boot 2.X application, actually its existing code i am checked out from git. While running the application it fails due to below error only for me and same code is working for others.
s.c.a.AnnotationConfigApplicationContext : Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'inputItemReader' defined in file [C:\Users\XYZ\git\main\batch\CBatchProcessing\target\classes\com\main\batchprocessing\batch\reader\InputItemReader.class]: Unsatisfied dependency expressed through **constructor parameter 0; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'java.lang.String' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations**: {} Error starting ApplicationContext. To display the conditions report re-run your application with 'debug' enabled. 2018-10-16 23:23:37.411 ERROR 2384 --- [ main] o.s.b.d.LoggingFailureAnalysisReporter : *************************** APPLICATION FAILED TO START *************************** Description: **Parameter 0 of constructor in com.main.batchprocessing.batch.reader.InputItemReader required a bean of type 'java.lang.String' that could not be found.** Action: Consider defining a bean of type 'java.lang.String' in your configuration. I have checked below
- All Spring components are correctly annotated with @Component, @Service, @Controller,@Repository, etc...
- @ComponentScan & @EnableAutoCOnfiguration is also provided.
- Tried giving "java.lang.String" in declarations.
Code:
import java.util.Map; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.batch.core.ExitStatus; import org.springframework.batch.core.StepExecution; import org.springframework.batch.core.StepExecutionListener; import org.springframework.batch.item.file.FlatFileItemReader; import org.springframework.batch.item.file.mapping.JsonLineMapper; import org.springframework.batch.item.file.separator.JsonRecordSeparatorPolicy; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.core.io.FileSystemResource; import org.springframework.stereotype.Component; @Component public class InputItemReader extends FlatFileItemReader<Map<String, Object>> implements StepExecutionListener { @Autowired private InputFileHeaderValidator inputFileHeaderValidator; @Autowired private FileAuditService fileAuditService; private final Logger log = LoggerFactory.getLogger(InputItemReader.class); private java.lang.String inputFilePath; public InputItemReader(String inputFilePath) { setLineMapper(new JsonLineMapper()); setRecordSeparatorPolicy(new JsonRecordSeparatorPolicy()); setResource(new FileSystemResource(inputFilePath)); this.inputFilePath = inputFilePath; } } 631 Answers
Since you do not provide the public default constructor and you added your own non-default constructor the instantiation will fail. I would suggest you to define the input file path as property like @Value("${inputFilePath}"). If you need further initialization in your bean define a void method and annotate it with @PostConstruct and do the initialization within.
Add a public default constructor in your class. For example.
public User() { } 2Make sure you are using spring-boot-starter-data-jpa
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> </dependency> 1For me, it was because of using @AllArgsConstructor annotation of the lombok. My code was like this:
@Service @AllArgsConstructor public class SampleService { @Value("${search.page.size}") private Integer pageSize; private final SampleRepository sampleRepository; And then, I removed @AllArgsConstructor and added @RequiredArgsConstructor annotation. The problem was solved.
@Service @RequiredArgsConstructor public class SampleService { @Value("${search.page.size}") private Integer pageSize; private final BatchRepository batchRepository; 1You defined something like this:
@Component public class InputItemReader{ public InputItemReader(String input){ ... } } The name of your class suggest that your object is not a bean, just a simple object. You should try to use it in classic way:
new InputItemReader(myString); or to have a static method to process the input String.
Explanation: Spring IoC container will try to instantiate a new InputItemReader object like this :
new InputItemReader( -- WHAT TO PUT HERE? --) and will fail to call your constructor, because it will not know what you do actually expect and input string.
UPDATE: Your problem can be solved by removing @Component annotation and defining the bean in a configuration like this:
@Bean public InputItemReader inputItemReader(InputFileHeaderValidator inputFileHeaderValidator, FileAuditService fileAuditService){ InputItemReader inputItemReader = new InputItemReader("--HERE SHOULD BE ACTUAL PATH---"); // set the required service, a cleaner approach would be to send them via constructor inputItemReader.setFilteAuditService(fileAuditService); inputItemReader.setInputFileHeaderValidator(inputFileHeaderValidator); return inputItemReader; } 2I had the same error but the error was generated by Feign Client. If you have this error using feign client you must add @EnableFeignClients on your main class:
@SpringCloudApplication @EnableFeignClients public class Application { ... } I was also having the same problem, for me following solution worked perfectly fine:
I had annotated my class as @AllArgsConstructor by importing import lombok.AllArgsConstructor
I had just removed this annotation and the code starts working.
I also had the same error:
*************************** APPLICATION FAILED TO START *************************** Description: Field repository in com.example.controller.CampaignController required a bean of type 'com.example.data.CustomerRepository' that could not be found. Action: Consider defining a bean of type 'com.example.data.CustomerRepository' in your configuration.de here I solved this issue by adding @EnableMongoRepositories annotation in the main class:
@SpringBootApplication @EnableMongoRepositories(basePackageClasses = CustomerRepository.class) public class CampaignAPI { public static void main(String[] args) { SpringApplication.run(CampaignAPI.class, args); } } 1Even after following the above solutions, if the problem still exists then please check your import statements.
In my case it was the wrong import of @service annotation.
In my case I missed the @Service annotation so once I placed it works.
The issue in my case was a redundant @Autowired, I initially added a dependency using @Autowired, by eventually commenting it out, however, I forgot to comment on the annotation, due to which the method next to @Autowired was considered as some sort of setter.
On removing the redundant annotation it is working fine.
In my case annotating fields with lombok @NonNull was causing the trouble.
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
@Service @RequiredArgsConstructor @Transactional @Slf4j public class UserServiceImp implements UserService, UserDetailsService { .... } I had this problem while testing with JUnit. It was that I forgot to create @MockBean annotation, that's why the bean was missing.
3Not related to the above issue but if you have the same error of bean creation in a spring boot application and you are getting the same above error please check whether you have added the class path in @ComponentScan( of the main spring booth application launching class.
For it to work I had to add this @RequiredArgsConstructor annotation to my class, and then added this @Value("${inputFilePath}") annotation to access the variable. See below:
@Component @RequiredArgsConstructor public class InputItemReader extends FlatFileItemReader<Map<String, Object>> implements StepExecutionListener { @Value("${inputFilePath}") private inputFilePath; //... } In my case, removing the @EnableJpaRepositories annotation from my config fixed the issue. The repositories are still wired correctly.
Before:
@Configuration @EnableTransactionManagement @EnableJpaRepositories @EnableJpaAuditing public class PersistenceConfig { After:
@Configuration @EnableTransactionManagement @EnableJpaAuditing public class PersistenceConfig { Check if the application.properties file is written correctly.
For some reason my application was spring.profiles.on=test in the application.properties file.
When i change it to the proper value of spring.profiles.active=test it worked.
Generate Constructor from Superclass. It worked for me.
e.g.
public UserModel() { super(); // TODO Auto-generated constructor stub } If you want to add beans to your context that are defined in some external library then use @Import annotation and pass the class file name/bean name. Add @Import to your main configuration file having @SpringBootApplication annotation
Use:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-mongodb</artifactId> </dependency> instead of:
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-data-mongodb</artifactId> </dependency> This issue will also occurs when by mistake method is @Autowired in place of @Override but this is a rare case.
General Case:
- Missing Bean Definition (Service or any component should be anotated properly)
- Component Scan Make sure that the package containing your class is included in Spring's component scan.
- Bean Configuration: Verify that you have a bean definition (for Instance you are trying to autowire) in your Spring configuration.
- @Autowired Annotation: Ensure that the @Autowired annotation is correctly used.
This issue occurred when using spring boot 3.
I used below dependency for sql connecto. Replaced javax with Jakarta for @Table and @Entity. This resolved my issue.
<dependency> <groupId>com.mysql</groupId> <artifactId>mysql-connector-j</artifactId> <version>8.1.0</version> </dependency> In my case, I had to use RequiredArgsContructor annotation and removed final keyword for the variable blobContainerName. In the end, it looks like this.
@Service @RequiredArgsConstructor public class AzureStorageServiceImpl implements StorageService { @Value("${spring.cloud.azure.storage.blob.container-name}") private String blobContainerName; Adding to the "services" block of my application-default.yml & application-kubernetes.yml fixed the issue for me.
0I was facing the same issue and it got fixed by removing Constructors from my Model class. Adding sample snippet below:
Map<String, ServiceDefinition> serviceDefinitionMapper = new HashMap<>(); A def; B serviceCharacter; @Autowired public Scan(Map<String, ServiceDefinition> serviceDefinitionMapper, A def, B serviceCharacter) { super(); this.serviceDefinitionMapper = serviceDefinitionMapper; this.def = def; this.serviceCharacter = serviceCharacter; } Please Note: Do not keep any Constructor/@AllArgsConstructor in your Model class unless it is very much needed to be declared.
In my case, the issue was way different.
@SpringBootApplication @EnableNeo4jRepositories("com.digital.api.repositories") // <-- This was non-existent. public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); } } Look at the @EnableNeo4jRepositories annotation. The package defined, was non-existent. Try defining that package, and be careful that the Repository interfaces are based there. Otherwise, Spring will not find the repositories classes that it should load up!
In my case I had this problem but it was because of I added an annotation of @Component in my Exception code which I shouldn't because we don't want it to be scanned really we're just using it to handle an exception in our service or I don't know try to delete the annotation in your built-in exception.
Worked on my machine.
I faced the same issue but with my own created interface repository that could not be found. The answer for me was that Spring 2.6.3 has bugs with Java 8. After I switched to the Java 11 version everything goes correctly.
More info about this kind of problems I found here
I had a similar issue in a different scenario. I had everything perfectly working until I found that the main Application method has several annotations along with @EnableAutoConfiguration.
Also, make sure the services and their classes are @Overriding and @Autowired as needed.
I removed all the unwanted annotations, and it worked like a charm!!
From:
@EntityScan(basePackages = {"com.some.*"}) //removed @EnableJpaRepositories(basePackages = {"com.some.*"}) //removed @EnableAutoConfiguration @EnableAsync @ComponentScan(basePackages = {"com.some.*"}) //removed to:
@SpringBootApplication //this will ask Spring to do scanning, if your package structure is good, you can just use this @Controller MyController { //has Autowired dependency @Autowired private MyService myservice; //using myService.someMethod(String parameter); } Removed the
[12Dec2023 14:40:32.65]WARN
o.s.b.w.s.c.AnnotationConfigServletWebServerApplicationContext - Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'myController': Unsatisfied dependency expressed through field 'myService': Error creating bean with name 'myServiceImpl': Unsatisfied dependency expressed through method 'someMethod' parameter 0: No qualifying bean of type 'java.lang.String' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {} Description:
Parameter 0 of method someMethod in com.service.MyServiceImpl required a bean of type 'java.lang.String' that could not be found.
The injection point has the following annotations: - @org.springframework.beans.factory.annotation.Autowired(required=true)