Routing队列
交换机类型设为为direct 发送的消息上附加路由(routingKey)如图所示的error、info、warning。消费者绑定路由。 消息生产后就会路由到指定队列 。 因为没做交换机持久化 和消息持久化 ,代码运行的顺序应该为生产者然后两个消费者,最后再运行一次生产者。
public class RoutingProvider {
private static final String EXCHANGE_NAME = "test_exchange_routing";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
Channel channel = connection.createChannel();
String type = "direct";
channel.exchangeDeclare(EXCHANGE_NAME,type);
String msg = "provider exchange type = error and routingKey = error";
//发送一条toutingKey为error的消息
channel.basicPublish(EXCHANGE_NAME,"error",null,msg.getBytes());
RabbitMQUtil.close(connection,channel);
}
}
public class RoutingConsumerOne {
private static final String QUEUE_NAME = "test_queue_routing_error";
private static final String EXCHANGE_NAME = "test_exchange_routing";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
final Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,false,false,false,null);
//绑定路由
channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"error");
channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"successful");
channel.basicQos(1);
DefaultConsumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String msg = new String(body, "utf-8");
System.out.println("consumer error[] :"+msg);
channel.basicAck(envelope.getDeliveryTag(),false);
}
};
boolean autoAck = false;
channel.basicConsume(QUEUE_NAME,autoAck,consumer);
}
}
public class RoutingCosumerTwo {
private static final String QUEUE_NAME = "test_queue_routing_successful";
private static final String EXCHANGE_NAME = "test_exchange_routing";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
final Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,false,false,false,null);
channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"successful");
//channel.queueBind() 方法能同时存在多句 绑定多个routingKey
// channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"info");
channel.basicQos(1);
DefaultConsumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String msg = new String(body, "utf-8");
System.out.println("consumer successful[] :"+msg);
channel.basicAck(envelope.getDeliveryTag(),false);
}
};
boolean autoAck = false;
channel.basicConsume(QUEUE_NAME,autoAck,consumer);
}
}
Topic 队列
Topic 队列与RoutingKey队列区别不大,只是增加了个模糊匹配的功能。* 代表后面可连接1个字符或字符串,# 表示后面可连接多个字符或字符串 . 可以分割字符字符串 。虽然变化不大,但仍然需要将交换机类型变更为 topic 。因为没做交换机持久化 和消息持久化 ,代码运行的顺序应该为生产者然后两个消费者,最后再运行一次生产者。
public class TopicExchangeProvider {
private static final String EXCHANGE_NAME = "test_exchange_topic";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
Channel channel = connection.createChannel();
channel.exchangeDeclare(EXCHANGE_NAME, BuiltinExchangeType.TOPIC);
String msg = "增添的商品信息。。。。";
String routingKey = "good.add";
channel.basicPublish(EXCHANGE_NAME,routingKey,null,msg.getBytes());
RabbitMQUtil.close(connection,channel);
}
}
public class TopicExchangeConsumerOne {
private static final String QUEUE_NAME = "test_queue_topic_goods_add";
private static final String EXCHANGE_NAME = "test_exchange_topic";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
final Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,false,false,false,null);
channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"good.add");
channel.basicQos(1);
DefaultConsumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String msg = new String(body, "utf-8");
System.out.println("consumer one add[] :"+msg);
channel.basicAck(envelope.getDeliveryTag(),false);
}
};
boolean autoAck = false;
channel.basicConsume(QUEUE_NAME,autoAck,consumer);
}
}
public class TopicExchangeConsumerTwo {
private static final String QUEUE_NAME = "test_queue_topic_goods";
private static final String EXCHANGE_NAME = "test_exchange_topic";
public static void main(String[] args) throws IOException, TimeoutException {
Connection connection = RabbitMQUtil.getConnection();
final Channel channel = connection.createChannel();
channel.queueDeclare(QUEUE_NAME,false,false,false,null);
channel.queueBind(QUEUE_NAME,EXCHANGE_NAME,"good.#");
channel.basicQos(1);
DefaultConsumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String msg = new String(body, "utf-8");
System.out.println("consumer two select[] :"+msg);
channel.basicAck(envelope.getDeliveryTag(),false);
}
};
boolean autoAck = false;
channel.basicConsume(QUEUE_NAME,autoAck,consumer);
}
}
代码运行的正确结果应该是两个消费者都收到消息。