繁体   English   中英

如何在具有多个服务器的同一数据库上使用骆驼 JPA 组件?

[英]How to use camel JPA component on the same database with multiple servers?

我目前正在设置我的骆驼项目,但我无法让我的 JPA 轮询器在多个并发服务器上工作。

这是我的骆驼路线:

public class TicketPoller extends RouteBuilder {

    /** The uri. */
    private final String uri = "jpa://Ticket?consumeDelete=false&consumeLockEntity=true&consumer.SkipLockedEntity=true&consumer.query=select t from Ticket t where t.state=1";

    @Override
    public void configure() {
        from(uri).to("log:input");

    }
}

在我的 Hibernate 实体中直接轮询时,我使用 @Consumed 注释来更改票证状态:

@Entity
@Table(name = "TICKET", schema = "TEIKITEL")
public class Ticket implements Serializable {

    private static final long serialVersionUID = 1L;

    @Id
    @Column(name = "TICKET_ID")
    private String ticketId;

    @Column(name = "STATE")
    private int state;

    ...

    @Consumed
    public void changeTicketState() {
        this.state = 2;
    }

    @Override
    public String toString() {
        return "Ticket@ticketId=" + this.ticketId;
    }
}

当我从 Eclipse 的一台 Tomcat 服务器 (Tomcat 8) 上启动它时,它工作正常。

但是当我在同一个数据库上启动 2 个服务器轮询时,当我在我的 TICKET 表中插入一些行时出现这些错误:

在我的第一台服务器上,我可以看到:

Hibernate: select TICKET_ID from TEIKITEL.TICKET where TICKET_ID =? for update nowait
2016-04-05 15:04:56,796 INFO  [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] input(180) - Exchange[ExchangePattern: InOnly, BodyType: com.teikitel.model.entity.Ticket, Body: Ticket@ticketId=TICKET1]
Hibernate: select TICKET_ID from TEIKITEL.TICKET where TICKET_ID =? for update nowait
2016-04-05 15:04:56,812 INFO  [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] input(180) - Exchange[ExchangePattern: InOnly, BodyType: com.teikitel.model.entity.Ticket, Body: Ticket@ticketId=TICKET2]

在我的第二台服务器上:

Hibernate: select TICKET_ID from TEIKITEL.TICKET where TICKET_ID =? for update nowait
2016-04-05 15:04:56,859 WARN  [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] o.h.e.j.spi.SqlExceptionHelper(144) - SQL Error: 54, SQLState: 61000
2016-04-05 15:04:56,859 ERROR [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] o.h.e.j.spi.SqlExceptionHelper(146) - ORA-00054: resource busy and acquire with NOWAIT specified or timeout expired
Hibernate: select TICKET_ID from TEIKITEL.TICKET where TICKET_ID =? for update nowait
2016-04-05 15:04:56,874 WARN  [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] o.h.e.j.spi.SqlExceptionHelper(144) - SQL Error: 54, SQLState: 61000
2016-04-05 15:04:56,874 ERROR [Camel (camel-1) thread #0 - jpa://com.teikitel.model.entity.Ticket] o.h.e.j.spi.SqlExceptionHelper(146) - ORA-00054: resource busy and acquire with NOWAIT specified or timeout expired

有人遇到过同样的问题吗?

洛伊克

没有错误!

这些错误日志来自Hibernate,而不是来自Camel。

Camel执行其Job并跳过锁定在数据库中的元素(触发的日志操作仅在一个实例上执行一次)但它使用Hibernate执行其非阻塞选择请求。 Hibernate抛出异常,Camel BUT成功忽略该异常,在日志输出中打印错误。 这就是你所看到的。

我解决你的问题的方法是将Hibernate日志设置到更高的级别。

对于诸如论文(同步)之类的问题,请不要犹豫,使用骆驼中的延迟方法来更好地理解:

public class TicketPoller extends RouteBuilder {

/** The uri. */
private final String uri = "jpa://Ticket?consumeDelete=false&consumeLockEntity=true&consumer.SkipLockedEntity=true&consumer.query=select t from Ticket t where t.state=1";

@Override
public void configure() {
    from(uri).delay(10000).to("log:input"); //wait 10sec 

}

}

看起来实体已经锁定了第一台服务器上运行的其他线程。 您正在使用consumeLockEntity = true锁定单元格,并且您没有等待发布使用消费者 .SkipLockedEntity = true因此在尝试之后第二个服务器中的连接关闭而不等待。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM