I'm using a #PostCostruct annotation to get an initializing method to run code at startup of my Sprin Boot application.
#Service("jobManager")
public class JobManager {
#Autowired
SchedulerFactoryBean scheduler;
#Autowired
InterruttoreService interruttoreService;
#PostConstruct
public void createInitialJobs() throws SchedulerException {
List<Interruttore> interruttori = interruttoreService.findAllSwitches();
for (int i = 0; i < interruttori.size(); i++) {
Interruttore interruttore = interruttori.get(i);
interruttoreService.toggleSwitchOnStartup(interruttore);
}
}
interruttoreService.toggleSwitchOnStartup(interruttore)
is in a service class and is the following (job manager is auto wired in the this class)
#Override
public void toggleSwitchOnStartup(Interruttore interruttore) {
Date nextTimeout = interruttore.getTimeoutDate();
Date date = new Date();
Date now = new Timestamp(date.getTime());
if (nextTimeout == null) {
nextTimeout = now;
}
int idInterruttore = interruttore.getIdInterruttore();
if(nextTimeout.after(now)){ //c'รจ un timeout futuro
try { lightOn(idInterruttore);
jobManager.createJob(interruttore, nextTimeout);
} catch (SchedulerException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
} else {
shutDown(idInterruttore);
}
}
I'm getting a NullPointerException when calling jobManager from this method, don't know why if the bean was created during #PostCostruct...
This is the stack trace of the error
Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'interruttoreService': Unsatisfied dependency expressed through field 'jobManager'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'jobManager': Invocation of init method failed; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:569)
at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:349)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1219)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:543)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:482)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202)
at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:207)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1128)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1056)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:566)
... 53 more
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'jobManager': Invocation of init method failed; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.annotation.InitDestroyAnnotationBeanPostProcessor.postProcessBeforeInitialization(InitDestroyAnnotationBeanPostProcessor.java:136)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyBeanPostProcessorsBeforeInitialization(AbstractAutowireCapableBeanFactory.java:408)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1575)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:545)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:482)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202)
at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:207)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1128)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1056)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:566)
... 66 more
Caused by: java.lang.NullPointerException
at it.besmart.service.InterruttoreServiceImpl.toggleSwitchOnStartup(InterruttoreServiceImpl.java:112)
at it.besmart.service.InterruttoreServiceImpl$$FastClassBySpringCGLIB$$907e162e.invoke(<generated>)
at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204)
at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:720)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:157)
at org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:99)
at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:281)
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:96)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:179)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:655)
at it.besmart.service.InterruttoreServiceImpl$$EnhancerBySpringCGLIB$$e2a6ab4b.toggleSwitchOnStartup(<generated>)
at it.besmart.quartz.JobManager.createInitialJobs(JobManager.java:47)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:497)
at org.springframework.beans.factory.annotation.InitDestroyAnnotationBeanPostProcessor$LifecycleElement.invoke(InitDestroyAnnotationBeanPostProcessor.java:365)
at org.springframework.beans.factory.annotation.InitDestroyAnnotationBeanPostProcessor$LifecycleMetadata.invokeInitMethods(InitDestroyAnnotationBeanPostProcessor.java:310)
at org.springframework.beans.factory.annotation.InitDestroyAnnotationBeanPostProcessor.postProcessBeforeInitialization(InitDestroyAnnotationBeanPostProcessor.java:133)
... 78 more
interruttoreService is auto wired correctly because just after the startup it starts working as usual.
Rergarding jobManager, i simply #Autowire it in InterruttoreService.class in this way
#Service("interruttoreService")
#Transactional
public class InterruttoreServiceImpl implements InterruttoreService {
#Autowired
JobManager jobManager;
....
....
This is tightly coupled code (you have InterruttoreService injected into JobManager and at the same time JobManager injected into InterruttoreService).
Why don't you remove InterruttoreService injection from JobManager and let toggleSwitchOnStartup() complete within a #PostCostruct annotated method all in InterruttoreService directly where JobManager is already wired-up.
The problem is a small typo with your service name
You have in your service
#Service("jobManager")//first j lowercase
public class JobManager {
#Autowired //In your Autowired if you dont say a qualifier name will try to find names as "JobManager" first J uppercase
JobManager jobManager;
Solution:
Remove the name in your service an keep only
#Service
public class JobManager {
Add a qualifier
#Autowired
#Qualifier("jobManager")
JobManager jobManager;
Related
Here is my code, I don't know why my bean MouvementToMapItemProcessor is not injected, it's always null in constructor
#Autowired
private MouvementToMapItemProcessor mvts;
private Iterator it;
public InMemoryMouvementReader() {
it = mvts.getMouvmentFileRowMap().entrySet().iterator();
}
Here is my configuration class:
#Configuration
#EnableBatchProcessing
public class BatchConfiguration {
public BatchConfiguration() {
}
#Bean
public ItemReader<MouvementFileRow> mouvementMapReader() {
return new InMemoryMouvementReader();
}
#Bean
public ItemProcessor<MouvementFileRow, MouvementFileRow> mouvementMapProcessor() {
return new MouvementToMapItemProcessor();
}
#Bean
public Step generateDemmandeCommunication() {
return stepBuilderFactory.get("generateDemmandeCommunication")
.<MouvementFileRow, DemandeCommunication>chunk(10)
.faultTolerant().skipLimit(Integer.MAX_VALUE).skip(CustomReaderSkipException.class)
.reader(mouvementMapReader())
.processor(mouvementProcessor())
.writer(demandeCommunicationItemWriter())
.listener(customStepListener())
.build();
}
public class InMemoryMouvementReader implements ItemReader<MouvementFileRow> {
#Autowired
private MouvementToMapItemProcessor mvts;
private Iterator it;
public InMemoryMouvementReader() {
it = mvts.getMouvmentFileRowMap().entrySet().iterator();
}
private void initialize() {
}
#Override
public MouvementFileRow read() throws Exception {
if (it.hasNext()) {
return mvts.getMouvmentFileRowMap().get(it.next());
} else return null;
}
}
#Component
public class MouvementToMapItemProcessor implements ItemProcessor<MouvementFileRow, MouvementFileRow> {
private static final Logger log = LoggerFactory.getLogger(MouvementToMapItemProcessor.class);
private Map<Long, MouvementFileRow> mouvmentFileRowMap;
public MouvementToMapItemProcessor() {
mouvmentFileRowMap = new HashMap<Long, MouvementFileRow>();
}
#Override
public MouvementFileRow process(final MouvementFileRow mouvement) throws Exception {
........
return null;
}
public Map<Long, MouvementFileRow> getMouvmentFileRowMap() {
return mouvmentFileRowMap;
}
My stack trace
Error starting ApplicationContext. To display the auto-configuration report re-run your application with 'debug' enabled.
11:55:29.139 [restartedMain] ERROR o.s.boot.SpringApplication - Application startup failed
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'mouvementMapReader' defined in class path resource [fr/gouv/justice/spark/fileToBaseBatch/BatchConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.batch.item.ItemReader]: Factory method 'mouvementMapReader' threw exception; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:599)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1173)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1067)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:513)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:761)
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:867)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:543)
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:693)
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:360)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:303)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1118)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1107)
at fr.gouv.justice.spark.fileToBaseBatch.Application.main(Application.java:18)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.springframework.boot.devtools.restart.RestartLauncher.run(RestartLauncher.java:49)
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.batch.item.ItemReader]: Factory method 'mouvementMapReader' threw exception; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:189)
at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:588)
... 22 common frames omitted
Caused by: java.lang.NullPointerException: null
at fr.gouv.justice.spark.fileToBaseBatch.readers.InMemoryMouvementReader.(InMemoryMouvementReader.java:19)
at fr.gouv.justice.spark.fileToBaseBatch.BatchConfiguration.mouvementMapReader(BatchConfiguration.java:74)
at fr.gouv.justice.spark.fileToBaseBatch.BatchConfiguration$$EnhancerBySpringCGLIB$$e3e5804e.CGLIB$mouvementMapReader$34()
at fr.gouv.justice.spark.fileToBaseBatch.BatchConfiguration$$EnhancerBySpringCGLIB$$e3e5804e$$FastClassBySpringCGLIB$$8f516405.invoke()
at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:228)
at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:358)
at fr.gouv.justice.spark.fileToBaseBatch.BatchConfiguration$$EnhancerBySpringCGLIB$$e3e5804e.mouvementMapReader()
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:162)
... 23 common frames omitted
Your MouvementToMapItemProcessor is not injected into InMemoryMouvementReader until after it is constructed, which is what causes the constructor to fail with a NullPointerException. Use constructor injection instead:
#Autowired
public InMemoryMouvementReader(MouvementToMapItemProcessor mvts) {
this.mvts = mvts;
it = mvts.getMouvmentFileRowMap().entrySet().iterator();
}
and
#Bean
public ItemReader<MouvementFileRow> mouvementMapReader(MouvementToMapItemProcessor mvts) {
return new InMemoryMouvementReader(mvts);
}
and
#Bean
public Step generateDemmandeCommunication(InMemoryMouvementReader reader, MouvementToMapItemProcessor mvts) {
return stepBuilderFactory.get("generateDemmandeCommunication")
.<MouvementFileRow, DemandeCommunication>chunk(10)
.faultTolerant().skipLimit(Integer.MAX_VALUE).skip(CustomReaderSkipException.class)
.reader(reader)
.processor(mvts)
.writer(demandeCommunicationItemWriter())
.listener(customStepListener())
.build();
}
I am newbie in spring boot and mongoDB please help.
I am getting unsatified dependcy expressed through mongoTemplate, I am unable to find the root cause of it. Below is the stack trace of it.
"org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'gmailPullHandler': Unsatisfied dependency expressed through field 'gmailPullService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'gmailPullService': Unsatisfied dependency expressed through field 'gmailMailDataRepository'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'gmailMailDataRepositoryImpl': Unsatisfied dependency expressed through field 'mongoTemplate'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'mongoTemplate' defined in class path resource [org/springframework/boot/autoconfigure/data/mongo/MongoDataAutoConfiguration.class]: Unsatisfied dependency expressed through method 'mongoTemplate' parameter 1; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'mappingMongoConverter' defined in class path resource [org/springframework/boot/autoconfigure/data/mongo/MongoDataAutoConfiguration.class]: Unsatisfied dependency expressed through method 'mappingMongoConverter' parameter 1; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'mongoMappingContext' defined in class path resource [org/springframework/boot/autoconfigure/data/mongo/MongoDataAutoConfiguration.class]: Invocation of init method failed; nested exception is java.lang.StackOverflowError
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588)
at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:761)
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:866)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:542)
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:122)
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:737)
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:370)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:314)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1162)
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1151)
at com.plash.configurator.Application.main(Application.java:38)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:498)
at org.springframework.boot.loader.MainMethodRunner.run(MainMethodRunner.java:48)
at org.springframework.boot.loader.Launcher.launch(Launcher.java:87)
at org.springframework.boot.loader.Launcher.launch(Launcher.java:50)
at org.springframework.boot.loader.JarLauncher.main(JarLauncher.java:51)
Since there are three unsatisfied dependency which one is causing error, i am unable to find it.
NOTE: gmailMailDataRepository class is extended by MongoRepository, GmailMailDataRepositoryCustom
gmailMailDataRepository :
#Repository
public interface GmailMailDataRepository extends MongoRepository<GmailMailData, String>, GmailMailDataRepositoryCustom {
{'threadidslist.threadid':?1}{'useremail':?2}")
List<GmailMailData> getListByThreadidmMsgidEmailid(String messagid, String threadid, String useremail);
void saveObjectToMsgList(GmailMessages gm, String useremailid, String threadid, String prospectemailid);
}
Below is GmailMailDataRepositoryCustom and GmailMailDataRepositoryImpl:
GmailMailDataRepositoryCustom:
public interface GmailMailDataRepositoryCustom {
void saveObjectToMsgList(GmailMessages g, String useremailid, String threadid, String prospectemailid);
}
GmailMailDataRepositoryImpl:
public class GmailMailDataRepositoryImpl implements GmailMailDataRepositoryCustom {
// private final MongoOperations operations;
#Autowired
private MongoTemplate mongoTemplate;
Update update = new Update();
#Override
public void saveObjectToMsgList(GmailMessages gm, String useremailid, String threadid, String prospectemailid) {
Query query = new Query(Criteria.where("useremail").is(useremailid).and("prospectemailid").is(prospectemailid).and("threadidslist.threadid").is(threadid));
update.push("threadidslist.$.messagelist", gm);
mongoTemplate.updateFirst(query, update, GmailMailData.class);
}
Application.properities configuration for mongo is as following:
spring.data.mongodb.host=localhost
spring.data.mongodb.password=#########
spring.data.mongodb.port=27017
spring.data.mongodb.repositories.enabled=true
build.gradle:
compile("org.springframework.boot:spring-boot-starter-data-mongodb")
Issue resolved. It was model level error.
List casting was wrong.
#Data
#Document(collection = "GmailOtherMailData")
public class GmailOtherMailData {
#Id
private String id;
private String useremail;
private List<GmailOtherThreads> threadidslist;
}
I supposed to cast GmailOtherThreads object in List but i was using some other object. Because of wrong casting i was getting error everywhere in code.
I am new to building web services and I started using spring boot to build one. I created the following controller class
package controller;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import model.Time;
import service.FeedService;
#RestController
public class FeedController extends ScheduledThreadPoolExecutor{
public FeedController(int corePoolSize) {
super(corePoolSize);
// TODO Auto-generated constructor stub
}
int difference;
int a;
boolean schedule;
//static as the variable is accessed across multiple threads
#Autowired
static FeedService fs;
#RequestMapping(value="/test")
public String test(){
return "test";
}
#RequestMapping(value = "/schedule", method = RequestMethod.GET)
public int ScheduleFeed(#RequestParam(value = "difference",required = false) String y) throws InterruptedException, ExecutionException{
// if(y != null){
// difference = Integer.parseInt(y);
difference = 0;
NewScheduledThreadPoolTest.mymethod(difference);
return difference;
// }else{
// return -1;
// }
}
#RequestMapping(value = "/inquireSchedule", method = RequestMethod.GET)
public ResponseEntity<Time> RequestFeed(){
if(schedule == true){
schedule = fs.setFalse();
return new ResponseEntity<Time>(HttpStatus.OK);
}
return new ResponseEntity<Time>(HttpStatus.BAD_REQUEST);
}
//schedule the task to happen after a certain number of times
static class NewScheduledThreadPoolTest {
public static void mymethod(int difference, final String... args) throws InterruptedException, ExecutionException {
// creates thread pool with 1 thread
System.out.println("hello world");
final ScheduledExecutorService schExService = Executors.newScheduledThreadPool(2);
// Object creation of runnable thread.
final Runnable ob = new NewScheduledThreadPoolTest().new myclass();
// Thread scheduling ie run it after "difference" hours before and then after every 24 hours later on
schExService.scheduleWithFixedDelay(ob, difference, 24, TimeUnit.SECONDS);
// waits for termination for 30 seconds only
schExService.awaitTermination(30, TimeUnit.SECONDS);
// shutdown now.
schExService.shutdownNow();
System.out.println("Shutdown Complete");
}
class myclass implements Runnable{
#Override
public void run() {
try{
// the mechanism to give a positive feedback to the arduino service
fs.setTrue();
System.out.println("hello world");
}catch(Exception e){
System.out.println("task failed");
e.printStackTrace();
}
}}
}
}
Trying to run my web service causes it to throw the following exception:
org.springframework.beans.factory.UnsatisfiedDependencyException:
Error creating bean with name 'feedController' defined in file
[D:\Rishit\Java
workspaces\FeedNemo\target\classes\controller\FeedController.class]:
Unsatisfied dependency expressed through constructor parameter 0: No
qualifying bean of type [int] found for dependency [int]: expected at
least 1 bean which qualifies as autowire candidate for this
dependency. Dependency annotations: {}; nested exception is
org.springframework.beans.factory.NoSuchBeanDefinitionException: No
qualifying bean of type [int] found for dependency [int]: expected at
least 1 bean which qualifies as autowire candidate for this
dependency. Dependency annotations: {} at
org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:749)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:189)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1143)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1046)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:510)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:482)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:776)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:861)
~[spring-context-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:541)
~[spring-context-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:122)
~[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
org.springframework.boot.SpringApplication.refresh(SpringApplication.java:759)
[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:369)
[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:313)
[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:1185)
[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
org.springframework.boot.SpringApplication.run(SpringApplication.java:1174)
[spring-boot-1.4.0.RELEASE.jar:1.4.0.RELEASE] at
com.example.DemoApplication.main(DemoApplication.java:17)
[classes/:na] Caused by:
org.springframework.beans.factory.NoSuchBeanDefinitionException: No
qualifying bean of type [int] found for dependency [int]: expected at
least 1 bean which qualifies as autowire candidate for this
dependency. Dependency annotations: {} at
org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoMatchingBeanFound(DefaultListableBeanFactory.java:1406)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1057)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1019)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:835)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] at
org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741)
~[spring-beans-4.3.2.RELEASE.jar:4.3.2.RELEASE] ... 19 common frames
omitted
However, If I remove the "ScheduledThreadPoolExecutor" and the constructor, it runs fine. Can someone please explain what is the problem with extending the class?
Note:
1) Extending the class was suggested in the below mentioned post as a solution to my initial problem. Initially, my runnable was not running without any sort of notification or error message
2) The below post makes use of abusive language. However this was the only one that provided a solution to my initial problem. The initial problem is specified just to give a clarity of why I extended the above class and may not be directly related to my current problem. Please do not open if you find such language offensive.
http://code.nomad-labs.com/2011/12/09/mother-fk-the-scheduledexecutorservice/
Do not make bean members static. The fact that they're referenced from multiple threads is irrelevant; it's Spring's job to make sure that the dependencies are populated.
Also, prefer constructor injection to field injection; it makes these sorts of issues dramatically less likely.
I create simple news system with comments using Spring Boot and MongoDB. I would like to focus on code quality. I create service using generic to save data from class.
My code:
Dao.java
#Repository
public interface Dao<T, ID extends Serializable> extends MongoRepository<T, ID>{
}
DaoService.java
#Service
public class DaoService<T> extends AbstractService<T, Long> {
#Autowired
public DaoService(Dao<T, Long> dao) {
super(dao);
}
}
Service.java
#org.springframework.stereotype.Service
public interface Service<T, ID extends Serializable> {
T save(T entity);
}
AbstractService.java
public abstract class AbstractService<T, ID extends Serializable> implements
Service<T, ID> {
protected final Logger logger = LoggerFactory.getLogger(getClass());
protected Dao<T, ID> dao;
public AbstractService(Dao<T, ID> dao) {
this.dao = dao;
}
#Override
public T save(T entity) {
this.logger.debug("Create a new {} with information: {}", entity.getClass(),
entity.toString());
return this.dao.save(entity);
}
}
and 2 repo
#Repository
public interface CommentDao extends Dao<Comment, Long> {
}
and
#Repository
public interface NewsDao extends Dao<News, Long> {
}
My controller:
#RestController
#RequestMapping("/news")
public class NewsController {
private final DaoService<News> newsService;
private final DaoService<Comment> commentDaoService;
public NewsController(DaoService<News> newsService, DaoService<Comment> commentDaoService) {
this.newsService = newsService;
this.commentDaoService = commentDaoService;
}
#RequestMapping(method = RequestMethod.GET)
public void save(){
newsService.save(new News("elo","a","c"));
commentDaoService.save(new Comment("iss","we"));
}
}
error:
2016-03-02 23:22:30.265 WARN 6100 --- [ main] ationConfigEmbeddedWebApplicationContext : Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'daoService' defined in file [C:\Users\Lukasz\IdeaProjects\NewsSystem_REST\build\classes\main\com\newssystem\lab\dao\DaoService.class]: Unsatisfied dependency expressed through constructor argument with index 0 of type [com.newssystem.lab.dao.Dao]: : No qualifying bean of type [com.newssystem.lab.dao.Dao] is defined: expected single matching bean but found 2: newsDao,commentDao; nested exception is org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type [com.newssystem.lab.dao.Dao] is defined: expected single matching bean but found 2: newsDao,commentDao
2016-03-02 23:22:30.273 INFO 6100 --- [ main] o.apache.catalina.core.StandardService : Stopping service Tomcat
2016-03-02 23:22:30.296 ERROR 6100 --- [ main] o.s.boot.SpringApplication : Application startup failed
org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'daoService' defined in file [C:\Users\Lukasz\IdeaProjects\NewsSystem_REST\build\classes\main\com\newssystem\lab\dao\DaoService.class]: Unsatisfied dependency expressed through constructor argument with index 0 of type [com.newssystem.lab.dao.Dao]: : No qualifying bean of type [com.newssystem.lab.dao.Dao] is defined: expected single matching bean but found 2: newsDao,commentDao; nested exception is org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type [com.newssystem.lab.dao.Dao] is defined: expected single matching bean but found 2: newsDao,commentDao
at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:749) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:185) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1143) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1046) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:510) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:482) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:197) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:772) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:839) ~[spring-context-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:538) ~[spring-context-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:118) ~[spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:766) [spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at org.springframework.boot.SpringApplication.createAndRefreshContext(SpringApplication.java:361) [spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:307) [spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1191) [spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1180) [spring-boot-1.3.2.RELEASE.jar:1.3.2.RELEASE]
at com.newssystem.lab.NewsSystemApplication.main(NewsSystemApplication.java:18) [main/:na]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_25]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_25]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_25]
at java.lang.reflect.Method.invoke(Method.java:483) ~[na:1.8.0_25]
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:144) [idea_rt.jar:na]
Caused by: org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type [com.newssystem.lab.dao.Dao] is defined: expected single matching bean but found 2: newsDao,commentDao
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1126) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1014) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:813) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741) ~[spring-beans-4.2.4.RELEASE.jar:4.2.4.RELEASE]
... 24 common frames omitted
You must use the qualifier annotation to define which bean will be injected into your service. On Spring an interface can have many implementations, but if none of those implementations has the primary annotation defined Spring does not know which one to pick automatically.
#Autowired
#Qualifier("bean-name")
Originaly, we've had #Service and #Repository on single class (called DbHome), doing just CRUD operations. Each operation was mrked #Transactional, which is obviously slow.
So I want to move #Transactional to the class (called Db) where are more logical operations (like, getUsers, or getDevices). But I've read that #Transactional can only be used in #Service. So I moved #Service from DbHome to Db class.
But now I get the following exception:
SEVERE: Exception sending context initialized event to listener instance of class org.springframework.web.context.ContextLoaderListener
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'db' defined in file [/home/pitel/tomcat/wtpwebapps/anna_controller/WEB-INF/classes/cz/master/anna/controller/dao/Db.class]: Instantiation of bean failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [cz.master.anna.controller.dao.Db]: Constructor threw exception; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateBean(AbstractAutowireCapableBeanFactory.java:1093)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1038)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476)
at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:303)
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:299)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:762)
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:757)
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:480)
at org.springframework.web.context.ContextLoader.configureAndRefreshWebApplicationContext(ContextLoader.java:403)
at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:306)
at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:106)
at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4994)
at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5492)
at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1575)
at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1565)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [cz.master.anna.controller.dao.Db]: Constructor threw exception; nested exception is java.lang.NullPointerException
at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:163)
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:89)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateBean(AbstractAutowireCapableBeanFactory.java:1086)
... 22 more
Caused by: java.lang.NullPointerException
at cz.master.anna.controller.dao.Db.<init>(Db.java:68)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:422)
at org.springframework.beans.BeanUtils.instantiateClass(BeanUtils.java:147)
... 24 more
The start of the Db class:
#Service
public class Db {
public static synchronized Db getInstance() {
if (instance == null) {
instance = new Db();
}
return instance;
}
private static Db instance = null;
#Autowired
private ApplicationContext appContext;
private DbHome dbHome = null;
private Db() {
dbHome = (DbHome) ControllerConfig.getInstance().getAppContext().getBean("dbHome");
}
// Normal methods are here
}
And the DbHome class:
#Repository("dbHome")
public class DbHome {
#Autowired(required=true)
private SessionFactory sessionFactory;
// CRUD methods are here
}
I'm new to the Spring stuff, so can you please help me?
Issue is here:
#Autowired
private ApplicationContext appContext;
This bean appContext is not going to initialize until and unless this (DB) object is fully constructed and you are trying to access it from constructor and hence you end up with null pointer exception.
If you need to run some initialization code, you should pull the code from constructor into a method, and annotate that method with #PostConstruct
NullPointerException occured at
ControllerConfig.getInstance().getAppContext().getBean("dbHome")
Check that your application context is not null.
The best practice is, don't create instace on application context inside constructor create it using #Autowiring.