P:生产者,也就是要发送消息的程序,但是不再发送到队列中,而是发给X (交换机)
C:消费者,消息的接收者,会-直等待消息到来
Queue: 消息队列,接收消息、缓存消息
Exchange: 交换机(X) 。- -方面,接收生产者发送的消息。另- -方面,知道如何处理消息,例如递交给某个特别队列、递交给所有队列、或是将消息丢弃。到底如何操作,取决于Exchange的类型。Exchange有 常见以下3种类型:
Fanout: 广播将消息交给所有绑定到交换机的队列
Direct: 定向,把消息交给符合指定routing key的队列
Topic: 通配符,把消息交给符合routing pattern (路由模式)的队列
Exchange (交换机)只负责转发消息,不具备存储消息的能力,因此如果没有任何队列与Exchange绑定,或者没有符合路由规则的队列,那么消息将会丢失。
生产者:
package com.sx.producer;
import com.rabbitmq.client.BuiltinExchangeType;
import com.rabbitmq.client.Channel;
import com.rabbitmq.client.Connection;
import com.rabbitmq.client.ConnectionFactory;
import java.io.IOException;
import java.util.concurrent.TimeoutException;
/**
* 发送消息
*/
public class Producer_PubSub {
public static void main(String[] args) throws IOException, TimeoutException {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("192.168.1.3");
factory.setPort(5672);
factory.setVirtualHost("/sx");
factory.setUsername("sx");
factory.setPassword("123456");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
//创建交换机
/**
* public DeclareOk exchangeDeclare(String exchange, BuiltinExchangeType type, boolean durable, boolean autoDelete, boolean internal, Map arguments) throws IOException {
* return this.exchangeDeclare(exchange, type.getType(), durable, autoDelete, internal, arguments);
* }
* exchange:交换机名称
* type:交换机类型
* DIRECT("direct"),定向
* FANOUT("fanout"),广播,发送消息到每一个与之绑定的队列
* TOPIC("topic"),通配符
* HEADERS("headers");参数匹配
* durable:是否持久化
* autoDelete:是否自动删除
* internal:内部使用,false
* arguments:参数
*/
String exchangeName = "test_fanout";
channel.exchangeDeclare(exchangeName, BuiltinExchangeType.FANOUT, true, false, false, null);
//创建队列 2个
String queue1 = "test_fanout_queue1";
String queue2 = "test_fanout_queue2";
channel.queueDeclare(queue1, true, false, false, null);
channel.queueDeclare(queue2, true, false, false, null);
//绑定队列和交换机
/**
* public com.rabbitmq.client.AMQP.Queue.BindOk queueBind(String queue,
* String exchange, String routingKey) throws IOException {
* return this.queueBind(queue, exchange, routingKey, (Map)null);
* }
* queue:队列名称
* exchange:交换机名称
* routingKey:路由键,绑定规则
* 交换机类型为fanout,routingKey设置为""
*/
channel.queueBind(queue1, exchangeName, "");
channel.queueBind(queue2, exchangeName, "");
String body = "log";
//发送消息
channel.basicPublish(exchangeName, "", null, body.getBytes());
//释放资源
channel.close();
connection.close();
}
}
消费者C1
package com.sx.consumer;
import com.rabbitmq.client.*;
import java.io.IOException;
import java.util.concurrent.TimeoutException;
public class Consumer_PubSubC1 {
public static void main(String[] args) throws IOException, TimeoutException {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("192.168.1.3");
factory.setPort(5672);
factory.setVirtualHost("/sx");
factory.setUsername("sx");
factory.setPassword("123456");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
Consumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
System.out.println("body = " + new String(body));
System.out.println("完成事件A");
}
};
channel.basicConsume("test_fanout_queue1", true, consumer);
}
}
消费者C2
package com.sx.consumer;
import com.rabbitmq.client.*;
import java.io.IOException;
import java.util.concurrent.TimeoutException;
public class Consumer_PubSubC2 {
public static void main(String[] args) throws IOException, TimeoutException {
ConnectionFactory factory = new ConnectionFactory();
factory.setHost("192.168.1.3");
factory.setPort(5672);
factory.setVirtualHost("/sx");
factory.setUsername("sx");
factory.setPassword("123456");
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
Consumer consumer = new DefaultConsumer(channel) {
@Override
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
System.out.println("body = " + new String(body));
System.out.println("完成事件B");
}
};
channel.basicConsume("test_fanout_queue2", true, consumer);
}
}