I have a problem with Spring's annotation based task scheduler - I can't get it working, I don't see any problem here...
application-context.xml
<task:scheduler id="taskScheduler" />
<task:executor id="taskExecutor" pool-size="1" />
<task:annotation-driven executor="taskExecutor" scheduler="taskScheduler" />
bean
#Service
public final class SchedulingTest {
private static final Logger logger = Logger.getLogger(SchedulingTest.class);
#Scheduled(fixedRate = 1000)
public void test() {
logger.debug(">>> Scheduled test service <<<");
}
}
Spring #Configuration (non-xml configuration) for annotation-driven tasks
Just add #EnableScheduling on your WebMvcConfig class
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.web.servlet.config.annotation.EnableWebMvc;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
#Configuration
#EnableWebMvc
#EnableAsync
#EnableScheduling
public class WebMvcConfig implements WebMvcConfigurer {
/** Annotations config Stuff ... **/
}
If you want to use task:annotation-driven approach and your #Scheduled annotation is not working, then you most probably missed context:component-scan in your context xml.
Without this line, spring cannot guess where to search for your annotations.
<context:component-scan base-package="..." />
This is happening because by default Spring lazy initializes the beans.
Disable lazy initialization for the bean by placing this annotation
#Lazy(false)
on top of your #Component.
For me the solution that worked in Spring 5 was that I had to add #Component to the class having #Scheduled annotated methods.
After configuring the Schedulers, add #EnableScheduling in your main class.
I finally found a solution.
application-context.xml
<bean id="schedulingTest" class="...SchedulingTest" />
<task:scheduled-tasks>
<task:scheduled ref="schedulingTest" method="test" cron="* * * * * ?"/>
</task:scheduled-tasks>
and the test() method without the annotation. This runs the method every second and works perfectly.
if you have dispatcher-servlet.xml move your configuration there. it worked for me and i have left a comment in this article:
https://stackoverflow.com/a/11632536/546130
The solution for me was to add in the applicationContext.xml:
<task:annotation-driven/>
with the following schemaLocation:
http://www.springframework.org/schema/task
http://www.springframework.org/schema/task/spring-task-3.0.xsd
You should also check lazy-init to be false for that bean or use default-lazy-init="false" in beans.
That solved my problem.
I had to update my dispatcher-servlet.xml with
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:task="http://www.springframework.org/schema/task"
xsi:schemaLocation="http://www.springframework.org/schema/task
http://www.springframework.org/schema/task/spring-task-4.3.xsd"></beans>
Bean definition below:
<bean id="scheduledTasks" class="com.vish.services.scheduler.ScheduledTasks"></bean>
We had the following reason:
Service needed an interface (due to Transaction annotation) - IDE added this tx annotation also to interface. But #Scheduled was in implementing service class - and Spring ignored it since it thought that only annotations exist on the interface. So be careful to only have annotations on implementing classes!
Just add #EnableScheduling at any spring boot configuration class annotated with #Configuration and for the method that run the schedule job add #Scheduled annotation.
Maybe it will be useful for someone. I ran into similar issue when I had a bean that did a long processing job in PostConstruct method. Thus, Spring Boot application didn't start (because PostConstruct method was in progress) and that's why my scheduled jobs didn't run (they start running after application startup).
If you are using Grails with Spring Scheduler you will need to add to the top of your class.
static lazyInit = false
Source
I have a Spring Config which is working fine. My Spring Config uses multiple security:http sections.
When you define a security:http section, certain operations happen automagically, such as some bean definitions. One of these beans that get defined automatically, is a SessionAuthenticationStrategy -implementing bean.
Question: how can you identify which is which? For example I need to reference from code, via #Autowired, a specific authentication strategy, defined in a specific http:security tag; how can I accomplish this?
One way to have the same SessionAuthenticationStrategy instance in your custom bean and inside <sec:http>-spawned machinery is to go in the opposite direction: define SessionAuthenticationStrategy explicitly and inject it wherever you want, including http configuration:
<bean id="fancySessionAuthStrategy" class="com.fancy.FancySessionAuthStrategy">
...
</bean>
<sec:http ...>
<sec:session-management session-authentication-strategy-ref="fancySessionAuthStrategy"/>
...
</sec:http>
The only problem here is that you will have to manually build that strategy bean definition.
An example can be found in the documentation: http://docs.spring.io/spring-security/site/docs/current/reference/html/session-mgmt.html
I have defined various scheduler in my configuration file as follows:
<task:executor id="xxxxxExecutor" pool-size="${async.executor.pool.size}"/>
<task:scheduler id="xxxxwwwScheduler" pool-size="1" />
<task:scheduler id="qqqqSchedular" pool-size="1" />
<task:scheduler id="lastScheduler" pool-size="1" />
My controller has been annotated via #Controller annotation. How do I specify a particular Scheduler in #Scheduled annotation in Spring?
p.s. I am trying to schedule a method in a controller using #Scheduled annotation.
Using multiple schedulers and pointing to them via the #Scheduled annotation is unfortunately not possible.
However, if you really do need that flexibility, you can define the jobs in XML:
<task:scheduled-tasks scheduler="myScheduler">
<task:scheduled ref="beanA" method="methodA" fixed-delay="5000"/>
</task:scheduled-tasks>
That allows you to specify the exact id of the scheduler you need to use, and then simply reference the actual task.
Hope this helps.
I was reading below article to implement executor and scheduler.
http://docs.spring.io/spring/docs/current/spring-framework-reference/html/scheduling.html#scheduling-enable-annotation-support
Can any one please tell me which executor and scheduler does it use when we specify below xml entry
<task:annotation-driven executor="myExecutor" scheduler="myScheduler"/>
<task:executor id="myExecutor" pool-size="5"/>
<task:scheduler id="myScheduler" pool-size="10"/>
Internally spring uses org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor for namespace of task:executor and org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler for task:scheduler. Refer respective API docs here and here
specify the package
any classes inside that package which have the annotation #Configuration, #EnableScheduling and method with #Scheduled(cron="") will be scheduled on the mentioned time in the cron expression.
Right now I have one bean with a #Scheduled method working fine; it's declared in my applicationContext.xml.
<!-- some JPA stuff -->
<bean id="aWorkingBean" class="some.package.WorkingBean">
<property name="someDAO" ref="someDAO" />
</bean>
<task:annotation-driven scheduler="myScheduler" />
<task:scheduler id="myScheduler" pool-size="10" />
What I'm trying to do is programmatically schedule another method (e.g. loading some annotated class and inject its dependencies) upon request. Something like:
WebApplicationContext ctx = ContextLoader.getCurrentWebApplicationContext();
BeanDefinitionBuilder builder = BeanDefinitionBuilder.rootBeanDefinition(NonWorkingBean.class);
// add DAO references...
ctx.registerBeanDefinition("nonWorkingBean", builder.getBeanDefinition()); // <-- this doesn't work
Obviously it doesn't work because the XmlWebApplicationContext is read-only and has no registerBeanDefinition method. Is there any other way to achieve this?
I'm using Tomcat 6.0.29 and Spring 3.0.4
<task:scheduler> and #Scheduled is really just a convenience approach to scheduling static tasks. It's not really suitable for dynamic scheduling. Yes, you can make it work, but it's going to be awkward.
When you put <task:scheduler id="myScheduler"> into your config, Spring creates a TaskScheduler bean called myScheduler. This can be injected into your own beans, and can be invoked programmatically in order to schedule new tasks. You'll need to create a Runnable to pass to the TaskScheduler, but that should be simple enough.
There are several ways to do that, but you would usually use an AutowireCapableBeanFactory.
Here's one way to do it:
final WebApplicationContext ctx =
ContextLoader.getCurrentWebApplicationContext();
// create the object yourself
// and inject the dependenices you want manually
final Object existingBean = initializeYourObjectHere();
AutowireCapableBeanFactory beanFactory = ctx.getAutowireCapableBeanFactory();
// now autowire it, injecting the remaining dependencies
beanFactory.autowireBeanProperties(
existingBean, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
// run post processors and register bean under this name
beanFactory.initializeBean(existingBean, "newBeanName");