http://activemq.apache.org/virtual-destinations.html

普通的 topic 是发布/订阅模式:消息会被广播发送给所有的订阅者,订阅者拿到的是全部消息,如下图:

而 virtual topic,在消息的传递过程中,多加了一个队列节点,如下图:

全量的消息先发送到队列,然后再分发给消费者。这么做有什么好处呢?

假定consumer1和consumer2分别是2个进程,2个进程共同处理消息,这算不算负载均衡呢?

其次,如果consumer1挂掉了,队列的消息还能发送给consumer2,这是不是failover呢?

示例代码:

producer

public static void main(String[] args) throws JMSException {
ActiveMQConnectionFactory factory = new ActiveMQConnectionFactory("tcp://localhost:61616");
Connection connection = factory.createConnection();
connection.start();
Session session = connection.createSession(Boolean.FALSE, Session.AUTO_ACKNOWLEDGE); // 创建virtual topic,前缀必须是"VirtualTopic.",当然这是可配置的
Topic topic = session.createTopic("VirtualTopic.bank");
MessageProducer producer = session.createProducer(topic);
producer.setDeliveryMode(DeliveryMode.NON_PERSISTENT); for (int i = 0; i < 1; i++) {
TextMessage message = session.createTextMessage();
message.setText("hello zhang");
// 发布主题消息
producer.send(message);
System.out.println("Sent message: " + message.getText());
} session.close();
connection.close();
}

consumer

public static void main(String[] args) throws JMSException {
ActiveMQConnectionFactory factory = new ActiveMQConnectionFactory("tcp://localhost:61616");
ActiveMQConnection connection = (ActiveMQConnection) factory.createConnection();
connection.start(); Session session = connection.createSession(Boolean.FALSE, Session.AUTO_ACKNOWLEDGE);
// 根据 virtual topic 创建队列。格式为 "Consumer.*.VirtualTopic.>"
Queue queueA = session.createQueue("Consumer.A.VirtualTopic.bank");
Queue queueB = session.createQueue("Consumer.B.VirtualTopic.bank"); // 队列A创建订阅
MessageConsumer consumerA1 = session.createConsumer(queueA);
consumerA1.setMessageListener(new MessageListener() {
public void onMessage(Message message) {
TextMessage tm = (TextMessage) message;
System.out.println("A1: " + tm);
}
});
MessageConsumer consumerA2 = session.createConsumer(queueA);
consumerA2.setMessageListener(new MessageListener() {
public void onMessage(Message message) {
TextMessage tm = (TextMessage) message;
System.out.println("A2: " + tm);
}
}); // 队列B创建订阅
MessageConsumer consumerB1 = session.createConsumer(queueB);
consumerB1.setMessageListener(new MessageListener() {
public void onMessage(Message message) {
TextMessage tm = (TextMessage) message;
System.out.println("B1: " + tm);
}
});
MessageConsumer consumerB2 = session.createConsumer(queueB);
consumerB2.setMessageListener(new MessageListener() {
public void onMessage(Message message) {
TextMessage tm = (TextMessage) message;
System.out.println("B2: " + tm);
}
}); // session.close();
// connection.close();
}

上面只是demo,正常情况下,consumer应该在单独的进程中。

图解ActiveMQ virtual topic的更多相关文章

  1. ActiveMQ之topic主题模式

    开发环境我们使用的是ActiveMQ 5.11.1 Release的Windows版,官网最新版是ActiveMQ 5.12.0 Release,大家可以自行下载,下载地址.需要注意的是,开发时候,要 ...

  2. 基于ActiveMQ的Topic的数据同步——消费者持久化

    前面一章中介绍了activemq的初步实现:基于ActiveMQ的Topic的数据同步——初步实现 下面来解决持久化订阅的问题: (1)使用queue,即队列时,每个消息只有一个消费者,所以,持久化很 ...

  3. JMS学习七(ActiveMQ之Topic的持久订阅)

    非持久化订阅持续到它们订阅对象的生命周期.这意味着,客户端只能在订阅者活动时看到相关主题发布的消息.如果订阅者不活动,它会错过相关主题的消息.如果花费较大的开销,订阅者可以被定义为durable(持久 ...

  4. spring +ActiveMQ 实战 topic selecter指定接收

    spring +ActiveMQ 实战 topic selecter指定接收 queue:点对点模式,一个消息只能由一个消费者接受 topic:一对多,发布/订阅模式,需要消费者都在线(可能会导致信息 ...

  5. SPRING 集成 activemq 的 topic 模式

    概要 activemq 支持两种模式: 1.队列模式 2. 发布订阅者模式,topic有一个主题可以有多个订阅者.这种情况可以将一个消息,分发到多个消费者. 比如我有这样一个案例,用户需要同步,而且需 ...

  6. ActiveMQ之Topic

    与Queue不同,Topic实现的是发布/订阅模型,在下面的例子中,启动两个消费者共同监听一个Topic,然后循环给这个Topic发送多个消息. 例子: public class TopicTest ...

  7. 基于ActiveMQ的Topic的数据同步——初步实现

    一.背景介绍 公司自成立以来,一直以做项目为主,算是经累经验吧,自去年以来,我们部门准备将以前的项目做成产品,大概细分了几个小的产品,部们下面又分了几个团队,分别负责产品的研发,而我们属于平台团队,负 ...

  8. ActiveMQ Queue vs Topic vs VirtualTopic

    之前写过一篇文章讨论VirtualTopic,但觉得不够透彻,这里再根据实验结果进行一次横向对比破除模糊和选择困难症. 文章中核心对比要素是:消息副本和负载均衡 Queue的特点和优势 ActiveM ...

  9. activemq用户手册

    1 JMS 在介绍ActiveMQ之前,首先简要介绍一下JMS规范. 1.1 JMS的基本构件 1.1.1 连接工厂 连接工厂是客户用来创建连接的对象,例如ActiveMQ提供的ActiveMQCon ...

随机推荐

  1. 《深入理解JVM虚拟机》读书笔记

    前言:<深入理解JVM虚拟机>是JAVA的经典著作之一,因为内容更偏向底层,所以之前一直没有好好的阅读过.最近因为刚好有空,又有了新目标.所以打算和<构架师的12项修炼>一起看 ...

  2. Centos7 linux下通过源码安装redis以及使用

    下载redis安装包 wget http://download.redis.io/releases/redis-5.0.3.tar.gz 解压压缩包 tar -zxvf redis-.tar.gz y ...

  3. [原][osg][QT]osg与QT界面结合的简单例子二

    //main.cpp #include "VREObliqueEditorQTWindow.h" #include <QtWidgets/QApplication> # ...

  4. ImageConverter引起的 invalid address or address of corrupt block 0xb7feab58 passed to dlfree

    虹软人脸识别,其方法要传NV21格式的byte[], github上有一个虹软的Demo,是不是虹软工作人员写的不清楚,这个Demo里bitmap转NV21格式byte[]用的是一个第三方库https ...

  5. 学习笔记36—坚果云 | Papership或Zotero使用webDAV验证服务器不成功怎么办?

    很多人都喜欢用坚果云作为Zotero的第三方云盘,从而无限扩展Zotero的存储空间.可是大家在Papership或zotero客户端中验证坚果云webDAV服务器时,会出现验证不成功的问题,相信这个 ...

  6. RTTI(运行时类型识别),typeid,dynamic_cast

    dynamic_cast注意: 1.只能应用于指针和引用的转换: 2.要转换的类型中必须包含虚函数: 3.转换成功则返回地址,如果失败则返回NULL: 参见项目:RTTI

  7. JS client(X,Y)、screen(X,Y)、page(X,Y)的区别

    clientX:光标相对于当前窗口的水平位置: clientY :光标相对于当前窗口的垂直位置: screenX :光标相对于该屏幕的水平位置: screenY:光标相对于该屏幕的垂直位置: page ...

  8. Unity中角度与弧度之间的相互转换

    弧度数 = 角度数 * Mathf.Deg2Rad角度数 = 弧度数 * Mathf.Rad2Deg

  9. PHP里面增加写日志功能

    配置项中:

  10. Python 编程快速上手 第十四章 处理 CSV 文件和 JSON 数据

    前言 这一章分为两个部分,处理 CSV 格式的数据和处理 JSON 格式个数据. 处理 CSV 理解 csv csv 的每一行代表了电子表格中的每一行,每个逗号分开两个单元格csv 的内容全部为文本, ...