Spring没有检测到@Scheduled方法

时间:2013-05-28 15:42:58

标签: spring

我正在运行Spring 3.2.3.RELEASE,我在@Service装饰类中有几个方法,它们是计划任务,因此用@Scheduled注释进行修饰。

在容器中检测并实例化所有Spring bean,但永远不会调用@Scheduled注释。

我有几个应用程序上下文,但主文件如下所述:

  <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:task="http://www.springframework.org/schema/task"
    xsi:schemaLocation="http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task-3.2.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd">

    <import resource="classpath:core-properties.xml" />
    <import resource="classpath:core-datasource.xml" />
    <import resource="classpath:core-task-scheduler.xml" />

    <context:component-scan base-package="com.atlaschase.project.core">
        <context:exclude-filter type="regex"
            expression="com.atlaschase.project.core.services.jms.*" />
        <context:exclude-filter type="regex"
            expression="com.atlaschase.project.core.services.processor.*" />
        <context:exclude-filter type="regex"
            expression="com.atlaschase.project.core.services.remote.*" />
        <context:exclude-filter type="regex"
            expression="com.atlaschase.project.core.bootstrap.populators.*" />
    </context:component-scan>

    <bean id="bufferPopulator" class="com.atlaschase.project.core.services.jms.buffer.BufferPopulator"/>

    <bean id="eventBuffer" class="com.atlaschase.project.core.services.jms.buffer.EventBuffer"/>

    <bean id="processorEventHandler" class="com.atlaschase.project.core.services.jms.buffer.ProcessorEventHandler"/>

另一个重要文件导入为“core-task-scheduler.xml”。配置如下:

    <?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:p="http://www.springframework.org/schema/p"
    xmlns:task="http://www.springframework.org/schema/task"
    xsi:schemaLocation="http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task-3.2.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">

    <task:annotation-driven executor="myExecutor" scheduler="myScheduler"/>

    <task:executor id="myExecutor" pool-size="1"/>

    <task:scheduler id="myScheduler" pool-size="5"/>

</beans>

最初,执行程序引用(上面)是在主应用程序上下文中定义的,但在阅读其他类似问题以这种方式解决后,我将其拆分为导入。不幸的是,这没有帮助。我也已经移动了导入声明,但这似乎没有效果。

在Spring Application Context中声明计划方法直接正常工作 - 但是我非常希望使用注释。

以下是带注释的类:

**
 * Service that batches the saving of position updates into a periodically executed
 * process. 
 */
@Service
public class PositionAggregatorService {

    static Logger logger = Logger.getLogger(AircraftPositionAggregatorService.class);

    // The service will not execute within 1 minute of a previous batch attempt.
    // This paramater is updated by a message from another node indicating that
    // they are commencing a batch save of position updates.
    private DateTime blockingTime; 

    private Map<Long, List<Position>> positions;

    @Autowired
    private PositionDao positionDao;

    @Autowired
    private InternalPublisher internalEventPublisher;

    @PostConstruct
    private void initialise(){
        positions = new ConcurrentHashMap<Long, List<Position>>();
    }

    /*
     * Scheduled to execute every 10 minutes as long current time is not
     * before the blocking time threshold.
     * 
     * */
    @Scheduled(fixedRate=6000)
    public void batchSavePositionUpdates(){

        if(blockingTime != null){
            if(DateTime.now(DateTimeZone.UTC).isBefore(blockingTime)){
                return;
            }
        }

        PositionPersistStartedNotification started = new PositionPersistStartedNotification(DateTime.now(DateTimeZone.UTC), DateTime.now(DateTimeZone.UTC).plusMinutes(2));
        internalEventPublisher.publishPositionPersistStartedNotification(started);

        DateTime mostRecentUpdateTime = null;

        List<Position> positionsToSave = new ArrayList<Position>();

        for(Long flightId : positions.keySet()){

            List<Position> positionList = positions.get(flightId);

            for(Position position : positionList){
                if(mostRecentUpdateTime == null){
                    mostRecentUpdateTime = new DateTime(position.getTime());
                }
                else{
                    DateTime positionTime = new DateTime(position.getTime());
                    if(positionTime.isAfter(mostRecentUpdateTime)){
                        mostRecentUpdateTime = positionTime;
                    }
                }
                positionsToSave.add(position);
            }
        }

        Boolean successfulSave = false;

        try{
            positionDao.save(positionsToSave);
            successfulSave = true;
            logger.info(positionsToSave.size() + " Position Updates saved successfully");
        }catch(Exception exception){
            logger.error("Failed to persist latest position updates to database");
            logger.error(exception);
        }


        if(successfulSave){
            removeSavedPositions(mostRecentUpdateTime);
            PositionPersistEndedNotification ended = new PositionPersistEndedNotification(DateTime.now(DateTimeZone.UTC), mostRecentUpdateTime);
            internalEventPublisher.publishPositionPersistEndedNotification(ended);
        }

    }
}

任何帮助都将不胜感激。

2 个答案:

答案 0 :(得分:2)

Spring上下文是否在运行时成功加载?我发现在命名空间定义中存在一些不一致的地方,其中各种版本在xsd(3.0和3.2)中共存。您可以尝试在这些命名空间中始终使用相同的版本并重试吗?

答案 1 :(得分:0)

通过侦听要加载的上下文然后在 ContextRefreshedEvent 上执行方法来启动应用程序。

当我从应用程序中删除此ApplicationEventListener并简单地调用bean上的公共方法来启动服务(而不是依赖于ApplicationEventListener)时,应用程序随后正常启动,所有@Scheduled注释按预期工作。