使用op-rabbit时如何设置TTL并捕获异常?

时间:2018-02-14 19:12:47

标签: scala rabbitmq akka

我有一些op-rabbit代码,如下所示:

val subscriptionRef: SubscriptionRef = Subscription.run(rabbitControl) {
  val directive = body(UTF8StringMarshaller) & routingKey
  channel(qos = MAX_CONCURRENT_MSGS) {
    consume(topic(queue(inputQueue), List(inputKey))) {
      directive((s, key) => {
        processMessage(s, key)
        ack
      })
    }
  }
}

它在某些应用程序中运行良好,但在我的最新应用程序中,我在几分钟内就在日志中得到了5GB的错误。我正在试图找出处理异常的位置。错误的原因似乎是队列的TTL(30分钟或1800000毫秒)不匹配,以及应用程序期望的内容(显然没有)。我想指定TTL,如果有问题,我想记录它然后立即关闭。我不希望文件系统填充堆栈跟踪,如下所示:

18:39:08.518 [such-system-akka.actor.default-dispatcher-9] ERROR com.spingo.op_rabbit.SubscriptionActor - Connection related error while trying to re-bind a consumer to EXCHANGE.QUEUE. Waiting in anticipating of a new channel.
java.io.IOException: null
    at com.rabbitmq.client.impl.AMQChannel.wrap(AMQChannel.java:105) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.wrap(AMQChannel.java:101) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.exnWrappingRpc(AMQChannel.java:123) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.ChannelN.queueDeclare(ChannelN.java:948) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.ChannelN.queueDeclare(ChannelN.java:50) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.spingo.op_rabbit.QueueConcrete.declare(Queue.scala:31) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at com.spingo.op_rabbit.Binding$$anon$2.declare(Binding.scala:79) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at com.spingo.op_rabbit.SubscriptionActor.doSubscribe(SubscriptionActor.scala:222) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at com.spingo.op_rabbit.SubscriptionActor$$anonfun$8.applyOrElse(SubscriptionActor.scala:170) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at com.spingo.op_rabbit.SubscriptionActor$$anonfun$8.applyOrElse(SubscriptionActor.scala:157) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at scala.runtime.AbstractPartialFunction.apply(AbstractPartialFunction.scala:34) ~[scala-library-2.12.4.jar:?]
    at akka.actor.FSM.$anonfun$handleTransition$1(FSM.scala:608) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM.$anonfun$handleTransition$1$adapted(FSM.scala:608) ~[akka-actor_2.12-2.5.4.jar:?]
    at scala.collection.immutable.List.foreach(List.scala:389) ~[scala-library-2.12.4.jar:?]
    at akka.actor.FSM.handleTransition(FSM.scala:608) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM.makeTransition(FSM.scala:690) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM.makeTransition$(FSM.scala:683) ~[akka-actor_2.12-2.5.4.jar:?]
    at com.spingo.op_rabbit.SubscriptionActor.makeTransition(SubscriptionActor.scala:11) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at akka.actor.FSM.applyState(FSM.scala:675) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM.applyState$(FSM.scala:673) ~[akka-actor_2.12-2.5.4.jar:?]
    at com.spingo.op_rabbit.SubscriptionActor.applyState(SubscriptionActor.scala:11) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at akka.actor.FSM.processEvent(FSM.scala:670) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM.processEvent$(FSM.scala:662) ~[akka-actor_2.12-2.5.4.jar:?]
    at com.spingo.op_rabbit.SubscriptionActor.akka$actor$LoggingFSM$$super$processEvent(SubscriptionActor.scala:11) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at akka.actor.LoggingFSM.processEvent(FSM.scala:801) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.LoggingFSM.processEvent$(FSM.scala:783) ~[akka-actor_2.12-2.5.4.jar:?]
    at com.spingo.op_rabbit.SubscriptionActor.processEvent(SubscriptionActor.scala:11) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at akka.actor.FSM.akka$actor$FSM$$processMsg(FSM.scala:659) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.FSM$$anonfun$receive$1.applyOrElse(FSM.scala:653) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.Actor.aroundReceive(Actor.scala:514) ~[akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.Actor.aroundReceive$(Actor.scala:512) ~[akka-actor_2.12-2.5.4.jar:?]
    at com.spingo.op_rabbit.SubscriptionActor.aroundReceive(SubscriptionActor.scala:11) ~[op-rabbit-core_2.12-2.0.0.jar:2.0.0]
    at akka.actor.ActorCell.receiveMessage(ActorCell.scala:527) [akka-actor_2.12-2.5.4.jar:?]
    at akka.actor.ActorCell.invoke(ActorCell.scala:496) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.Mailbox.processMailbox(Mailbox.scala:257) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.Mailbox.run(Mailbox.scala:224) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.Mailbox.exec(Mailbox.scala:234) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.forkjoin.ForkJoinTask.doExec(ForkJoinTask.java:260) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.forkjoin.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1339) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.forkjoin.ForkJoinPool.runWorker(ForkJoinPool.java:1979) [akka-actor_2.12-2.5.4.jar:?]
    at akka.dispatch.forkjoin.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:107) [akka-actor_2.12-2.5.4.jar:?]
Caused by: com.rabbitmq.client.ShutdownSignalException: channel error; protocol method: #method<channel.close>(reply-code=406, reply-text=PRECONDITION_FAILED - inequivalent arg 'x-message-ttl' for queue 'EXCHANGE.QUEUE' in vhost '/': received none but current is the value '1800000' of type 'long', class-id=50, method-id=10)
    at com.rabbitmq.utility.ValueOrException.getValue(ValueOrException.java:66) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.utility.BlockingValueOrException.uninterruptibleGetValue(BlockingValueOrException.java:32) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel$BlockingRpcContinuation.getReply(AMQChannel.java:366) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.privateRpc(AMQChannel.java:229) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.exnWrappingRpc(AMQChannel.java:117) ~[amqp-client-4.0.0.jar:4.0.0]
    ... 38 more
Caused by: com.rabbitmq.client.ShutdownSignalException: channel error; protocol method: #method<channel.close>(reply-code=406, reply-text=PRECONDITION_FAILED - inequivalent arg 'x-message-ttl' for queue 'EXCHANGE.QUEUE' in vhost '/': received none but current is the value '1800000' of type 'long', class-id=50, method-id=10)
    at com.rabbitmq.client.impl.ChannelN.asyncShutdown(ChannelN.java:505) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.ChannelN.processAsync(ChannelN.java:336) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.handleCompleteInboundCommand(AMQChannel.java:143) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQChannel.handleFrame(AMQChannel.java:90) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQConnection.readFrame(AMQConnection.java:634) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQConnection.access$300(AMQConnection.java:47) ~[amqp-client-4.0.0.jar:4.0.0]
    at com.rabbitmq.client.impl.AMQConnection$MainLoop.run(AMQConnection.java:572) ~[amqp-client-4.0.0.jar:4.0.0]
    at java.lang.Thread.run(Thread.java:748) ~[?:1.8.0_144]
18:39:08.534 [such-system-akka.actor.default-dispatcher-9] ERROR com.spingo.op_rabbit.SubscriptionActor - Connection related error while trying to re-bind a consumer to EXCHANGE.QUEUE. Waiting in anticipating of a new channel.

1 个答案:

答案 0 :(得分:1)

您正尝试使用零x-message-ttl的值重新声明队列。首先删除队列,然后可以用你想要的代码声明它。

  

频道错误;协议方法:#method(reply-code = 406,reply-text = PRECONDITION_FAILED - 不相等的arg&#39; x-message-ttl&#39;用于队列&#39; EXCHANGE.QUEUE&#39;在vhost&#39; /&#39;:收到没有,但是当前的值为&#39; 1800000&#39;类型&#39; long&#39;,class-id = 50,method-id = 10

要完全清楚,这是每条消息TTL ,而不是每个队列的TTL。存在差异,这可能是您的问题。

否则,代码将继续尝试执行相同的操作,并且代理将继续拒绝该操作。