官方文档中对于rabbitmq消息模型的分类有七种,第一种和第二种差别不大,几乎完全一样。
Rabbit的send和receive代码层面几乎一样,第一种说的是一个sender和一个receiver,
而第二个说的是一个send和多个receiver(消息轮流发给多个receiver,每个receiver得到的消息数是均匀分配的),
两种消息模型在代码层面上都没有用到exchange。
第七种和第六种忽略掉。剩下的三种(3,4,5)就是在代码中提到了exchange的消息模型,这三种都属于订阅模式。
在此对比一下work queue和direct exchange的sender代码的区别。
Work queue:
// 生产者
public class Send {
private final static String QUEUE_NAME = "test_work_queue";
public static void main(String[] argv) throws Exception {
// 获取到连接
Connection connection = ConnectionUtil.getConnection();
// 获取通道
Channel channel = connection.createChannel();
// 声明队列
channel.queueDeclare(QUEUE_NAME, false, false, false, null);
// 循环发布任务
for (int i = 0; i < 50; i++) {
// 消息内容
String message = "task .. " + i;
channel.basicPublish("", QUEUE_NAME, null, message.getBytes());
System.out.println(" [x] Sent '" + message + "'");
Thread.sleep(i * 2);
}
// 关闭通道和连接
channel.close();
connection.close();
}
}
Direct exchange:
/**
* 生产者,模拟为商品服务
*/
public class Send {
private final static String EXCHANGE_NAME = "direct_exchange_test";
public static void main(String[] argv) throws Exception {
// 获取到连接
Connection connection = ConnectionUtil.getConnection();
// 获取通道
Channel channel = connection.createChannel();
// 声明exchange,指定类型为direct
channel.exchangeDeclare(EXCHANGE_NAME, "direct");
// 消息内容
String message = "商品删除了, id = 1001";
// 发送消息,并且指定routing key 为:insert ,代表新增商品
channel.basicPublish(EXCHANGE_NAME, "delete", null, message.getBytes());
System.out.println(" [商品服务:] Sent '" + message + "'");
channel.close();
connection.close();
}
}
两者的区别在于,work queue声明队列是这样的:
// 声明队列
channel.queueDeclare(QUEUE_NAME, false, false, false, null);
direct exchange声明队列是这样的:
// 声明exchange,指定类型为direct
channel.exchangeDeclare(EXCHANGE_NAME, "direct");
queueDeclare和exchangeDeclare都是channel里的方法,但两者返回值不同,
第一个返回AMPQ这个类中的内部类queue类 中的内部接口 DeclareOk接口 。
第二个返回的是