Axon 4 - ProcessingGroup 注释 类 在配置注入时未检测到

Axon 4 - ProcessingGroup annotated classes not detected at configuration injection

(最初登录 GitHub 但我想我会把它移到这里以供有相同问题的任何人使用并帮助开发团队将问题保留在同一个地方。)

我不确定这是我对框架的无知还是实际问题,请耐心等待,因为我在 Axon 4 上找到的关于事件重放的文档很少。

场景:

@Component
@ProcessingGroup("projections")
public class AddEventHandler {

    @EventHandler
    public void on(AddEvent addEvent, ReplayStatus replayStatus){
    }

    @ResetHandler
    public void onReset() { // will be called before replay starts
        // do pre-reset logic, like clearing out the Projection table for a clean slate
       // this does not get executed
    }
}

@Configuration
public class AxonConfig {

    @Autowired
    private EventProcessingModule eventProcessingModule;

    @Autowired
    public void configureProcessors(EventProcessingConfiguration configuration) {
        configuration
                .eventProcessorByProcessingGroup("projections",
                        TrackingEventProcessor.class)
                .ifPresent(trackingEventProcessor -> {
                    trackingEventProcessor.shutDown();
                    trackingEventProcessor.resetTokens();
                    trackingEventProcessor.start();
                });
    }
}

这取自Replaying Events Documentation

应用程序启动时永远不会执行 ifPresent 内容,因此永远不会重置令牌。我可以通过删除令牌手动强制重播事件。上面提到的配置是我更改的唯一配置,其他所有配置都是运行关闭自动配置。

令牌存储是 Microsoft SQL 服务器,我在那里看到的所有交互似乎都很好(事件持久化,令牌所有权在应用程序停止时更新等)。

在 运行 时间检查 EventProcessingConfiguration 时,eventProcessors 属性 和 processingGroupAssignments 属性 一样是空的,这让我相信 ProcessingGroup 注释是在自动装配配置之后处理的有 运行,因此 ifPresent 永远不会执行上面定义的代码。

版本信息:Spring Boot Starter:2.1.2,Axon Starter:4.0.3

完整答案在这里: https://github.com/AxonFramework/AxonFramework/issues/1006

引用答案:

Now to resolve the issue you're having - it seems that you want to reset some of your query models at start up of the application. You are however hitting a configuration order problem in this scenario, where the TrackingEventProcessor have not been started yet, whilst the configuration file you've created is already being called.

Note that we have plans to be more specific on the ordering when specific beans are created (potentially with Spring application events if you'd ask me) - we are however no there yet, so please bear with us until this rework has been performed.

For now, the simplest approach you can take, is have a dedicated replay service. You'd than wire this ResetService/ReplayService with the EventProcessingConfiguration and have it contain a void resetProjectors() method. I'd suggest calling this method at a point in time where you're certain the application has been completely wired up (for example by handling some of the Spring application events).

再次感谢 Axon 开发团队。