最簡單接受MQ消息的方法-annotation

一 簡單定義

用一個註解就能夠接受MQ了,而不用定義交換機,定義隊列啥的,簡簡單單,一句話搞定ui

@Component
public class MyService {

@RabbitListener(queues = "myQueue")
public void processOrder(String data) {
    ...
}
}

二 再複雜一點

一個默認隊列怎麼能知足要求能,固然是要實用點的code

@Component
public class MyService {
  //定義隊列名稱,交換機名稱,以及routingkey名稱
  @RabbitListener(bindings = @QueueBinding(
        value = @Queue(value = "myQueue", durable = "true"),
        exchange = @Exchange(value = "auto.exch", ignoreDeclarationExceptions = "true"),
        key = "orderRoutingKey")
  )
  public void processOrder(Order order) {
    ...
  }
  
  //定義一個默認隊列,監聽全部的bindingkey
  @RabbitListener(bindings = @QueueBinding(
        value = @Queue,
        exchange = @Exchange(value = "auto.exch"),
        key = "invoiceRoutingKey")
  )
  public void processInvoice(Invoice invoice) {
    ...
  }
  
  //queue是個變量了,能夠從配置文件中取到
  @RabbitListener(queuesToDeclare = @Queue(name = "${my.queue}", durable = "true"))
  public String handleWithSimpleDeclare(String data) {
      ...
  }  
}

咱們還能夠加入更多的參數,好比死信隊列隊列

@RabbitListener(
        bindings = @QueueBinding(
            value = @Queue(value = "annoQueue", durable = "true",
                    arguments = {
                        @Argument(name = "x-dead-letter-exchange", value = "dlx.exchange"),
                        @Argument(name = "x-dead-letter-routing-key", value = "dlx.routing.key")
            }),
            exchange = @Exchange(value = "annoExch", ignoreDeclarationExceptions = "true"),
            key = "annoKey"
      )
)
public void processOrder(Message msgStr, Channel channel, @Header(AmqpHeaders.DELIVERY_TAG) long ta) throws Exception {
...
}

上述代碼不只定義了一個隊列,並在argument中加入了死信隊列,來接受失敗消息
同時,咱們在接受參數時 傳入了 channel以及 tag, 這樣能夠很方便的進行消息回傳了,好比: channel.baskAck(...)get

三 元註解

有時候咱們實在嫌寫註解太麻煩了,能夠定義一個元註解it

@Target({ElementType.TYPE, ElementType.METHOD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@RabbitListener(bindings = @QueueBinding(
        value = @Queue,
        exchange = @Exchange(value = "metaFanout", type = ExchangeTypes.FANOUT)))
public @interface MyAnonFanoutListener {
}

public class MetaListener {

    @MyAnonFanoutListener
    public void handle1(String foo) {
        ...
    }

    @MyAnonFanoutListener
    public void handle2(String foo) {
        ...
    }

}

四 默認監聽鏈接工廠

有一點忘記說了,你若是確實想用@RabbitListener必須在@Configuration註解加上@EnableRabbit註解,好比這樣io

@Configuration
@EnableRabbit
public class AppConfig {

    @Bean
    public SimpleRabbitListenerContainerFactory rabbitListenerContainerFactory() {
        SimpleRabbitListenerContainerFactory factory = new SimpleRabbitListenerContainerFactory();
        factory.setConnectionFactory(connectionFactory());
        factory.setConcurrentConsumers(3);
        factory.setMaxConcurrentConsumers(10);
        return factory;
    }
}

其中SimpleRabbitListenerContainerFactory是監聽器的factory,若是你不指定,boot會自動生成一個出來,固然仍是本身指定一個比較好。class

五 連環發送

當你收到消息後想發到另外一個隊列該怎麼辦呢?能夠用sendto註解變量

@RabbitListener(destination = "myQueue")
@SendTo("status")
public Message<OrderStatus> processOrder(Order order) {
    // order processing
    return MessageBuilder
        .withPayload(status)
        .setHeader("code", 1234)
        .build();
}
相關文章
相關標籤/搜索