Spring integration JpaPollingChannelAdapter是否具有与JdbcPollingChannelAdapter的UpdateSql类似的功能?

Spring integration JpaPollingChannelAdapter是否具有与JdbcPollingChannelAdapter的UpdateSql类似的功能?,spring-integration,Spring Integration,我有一个小型Spring启动应用程序,它使用Spring集成来查询Oracle数据库中的特定状态记录 最初,我有一个使用JdbcPollingChannelAdapter的工作POC,该POC还定义了一个更新语句,该语句更改了找到的记录的状态,因此它们不会被重新扫描 应用程序使用Hibernate,因此我想用JPA方法替换Jdbc实现 因此,我成功地使用JpaExecutor实现了一个JpaPollingChannelAdapter,以实体形式检索结果 我试图实现的是与Jdbc方法类似的行为,J

我有一个小型Spring启动应用程序,它使用Spring集成来查询Oracle数据库中的特定状态记录

最初,我有一个使用JdbcPollingChannelAdapter的工作POC,该POC还定义了一个更新语句,该语句更改了找到的记录的状态,因此它们不会被重新扫描

应用程序使用Hibernate,因此我想用JPA方法替换Jdbc实现

因此,我成功地使用JpaExecutor实现了一个JpaPollingChannelAdapter,以实体形式检索结果

我试图实现的是与Jdbc方法类似的行为,Jdbc方法将在与轮询器相同的事务中更新所有找到的记录

在适配器中是否有适当的方法来实现这一点,还是应该在消息处理程序中使用实体dao

希望这是有道理的

更新:

我假设我需要使用OutboundChannelAdapter或Gateway而不是InboundChannelAdapter,因为它只用于检索

我想我的问题是,如果我可以在一个处理程序中完成所有工作,或者如果我需要定义多个通道,一个用于检索,另一个用于更新实体状态,那么如何正确地连接这些通道

以下是一些基本代码:

@Configuration
public class IntegrationConfiguration {

    private final Log log = LogFactory.getLog(getClass());

    @Autowired
    private DataSource dataSource;

    @Autowired
    private EntityManager entityManager;

    @Autowired
    private Reactor rootReactor;

    @Autowired
    private RunDao runDao;

    @Bean
    @InboundChannelAdapter(channel = "notificationChannel", poller = @Poller(fixedDelay = "60000", maxMessagesPerPoll = "-1"))
    public MessageSource<?> jpaMessageSource() {
        return new JpaPollingChannelAdapter(jpaSelectExecutor());
    }

    @Bean
    @Gateway(requestChannel = "notificationChannel")
    public void updateMessageStatus() {
        JpaOutboundGateway gateway = new JpaOutboundGateway(jpaUpdateExecutor());
        gateway.setGatewayType(OutboundGatewayType.UPDATING);
    }

    @Bean
    public JpaExecutor jpaSelectExecutor() {
        JpaExecutor executor = new JpaExecutor(this.entityManager);
        executor.setJpaQuery("select R from Run R where R.notificationStatus = 'NOT_SENT' and R.runStatus.status = 'COMPLETE' and R.runConfig.notificationRecipients is not null");
        executor.setEntityClass(Run.class);
        return executor;
    }

    @Bean
    public JpaExecutor jpaUpdateExecutor() {
        JpaExecutor executor = new JpaExecutor(this.entityManager);
        executor.setJpaQuery("update Run R set R.notificationStatus = 'SENDING' where R.RunId = :RunId");
        executor.setEntityClass(Run.class);
        return executor;
    }

    @Bean
    @ServiceActivator(inputChannel = "notificationChannel")
    public MessageHandler jpaMessageHandler() {
        MessageHandler handler = new MessageHandler() {
            @Override
            public void handleMessage(Message<?> message) throws MessagingException {
                for (Run run : (ArrayList<Run>) message.getPayload()) {
                    rootReactor.notify("send-email-notification", Event.wrap(run));
                    //run.setNotificationStatus(Run.NotificationStatus.SENDING);
                    //runDao.merge(run);
                }
            }
        };

        return handler;
    }

    @Bean
    public IntegrationFlow pollingAdapterFlow() {
        return IntegrationFlows
                .from(jpaMessageSource())
                .handle(jpaMessageHandler())
                .get();
    }
}
对于JpaPollingChannelAdapter功能,JpaExecutor具有deleteAfterPoll选项

您可以在实体类上使用Hibernate@SQLDelete使用自定义更新覆盖默认删除


或者是的,您可以在同一轮询事务中单向或多次使用JpaOutboundGateway进行合并操作。但是在这种情况下,它必须是fixedDelay,而不是fixedRate,以避免任务重叠,并且不要在并行线程中轮询相同的数据。

感谢Artem,我将使用fixedDelay研究JpaOutboundGateway合并方法。只是一个后续问题。我正在尝试实现您关于使用JpaOutboundGateway的第二个建议。我是否应该用JpaOutboundGateway适配器替换上面代码中JpaPollingChannelAdapter的定义?我正在努力解决如何定义用于检索记录的select查询和更新实体状态的步骤。不,不应该。您可以使用JpaPollingChannelAdapter进行选择,并使用JpaOutboundGateway进行更新。明白了吗?好的,我两个都留着。再次为所有的问题感到抱歉。我是否应该为JpaOutboundGateway定义第二个JpaExcutor?我不知道在一个事务中连接所有内容需要哪些额外的通道/bean定义。我将用我的进度更新上面的代码。如果您使用Jpa工厂查看Java DSL,会更好: