ActiveMQ

概述
什么是MQ?

MQ:Message Queue,消息队列。
MQ常见产品有ActiveMQ、RabbitMQ、RocketMQ、Kafka。

为什么会出现MQ?(MQ作用)
  • 削峰填谷(主要):没有MQ时,大量请求到来时,系统只能拒绝请求保护自己,MQ可以在中间起到“水库”的作用,洪峰到来时,可以储存一部分水(请求),在河道(下游系统)水位降低后再排水。
  • 解耦:MQ在消息发送方和接收方之间起“媒婆”的作用,避免了发送方和接收方的直接交流,防止尴尬。接收方不在线时,MQ可存储消息,等待接收方的上线。
系统引入MQ后有什么新问题?(MQ缺点)
  • 增加系统复杂性:系统引入任何一个组件都会增加系统复杂性。复杂性的增加往往降低了系统的可靠性、可维护性等其他质量属性。
  • 只能异步调用:MQ增加了系统调用耗时,为了可以削峰填谷,也必须异步调用。所以,MQ更适合耗时较高的业务调用,同时消息发送方必须做业务的异步化。
模式
  • 队列(queue)模式:点对点模式,一条消息只能被一个消费者消费。
  • 主题(topic)模式:发布/订阅模式,一条消息可以同时被多个消费者消费。
Java API
测试框架(队列模式)
public class JmsTest {
    private Connection connection;
    private Session session;
    private Destination destination;

    @Before
    public void init() throws JMSException {
        ConnectionFactory connectionFactory = new ActiveMQConnectionFactory();
        this.connection = connectionFactory.createConnection();

        this.session = this.connection.createSession(false, Session.AUTO_ACKNOWLEDGE);

        this.destination = this.session.createQueue("test-queue");
//        this.destination = this.session.createTopic("test-topic");
    }

    @After
    public void destroy() throws JMSException {
        this.session.close();
        this.connection.close();
    }
}
发送消息
@Test
public void testSend() throws JMSException {
    MessageProducer producer = session.createProducer(destination);

    Message message = new ActiveMQTextMessage() {{
        this.setText("Hello, MQ!");
        this.setJMSType("String");
    }};

    producer.send(message);

    producer.close();
}
接收消息
@Test
public void testReceive() throws JMSException {
    MessageConsumer consumer = session.createConsumer(destination);
    connection.start();

    TextMessage message = (TextMessage) consumer.receive();
    String text = message.getText();
    System.out.println(text);

    consumer.close();
}
消息监听器
@Test
public void testListener() throws JMSException, IOException {
    MessageConsumer consumer = session.createConsumer(destination);
    connection.start();

    consumer.setMessageListener((message) -> {
        TextMessage textMessage = (TextMessage) message;
        try {
            System.out.println(textMessage.getText());
        } catch (JMSException e) {
            e.printStackTrace();
        }
    });
    
    System.in.read();
    consumer.close();
}
JMS
JMS是什么

JMS:Java Message Service,Java消息服务,定义了消息中间接的API标准。
JMS编程模型

  • ConnectionFactory:连接工厂,负责创建Connection连接,其维护了创建连接的配置参数。
  • Connection:连接,封装了与JMS Provider的连接。
  • Session:用于生产和消费消息的单线程上下文。
  • MessageProducer:消息生产者。
  • MessageConsumer:消息消费者。
  • Destination:目标。细分为QueueTopic
消息(Message)
  • 消息头
消息头解释设置方
JMSDestination目的地send
JMSDeliveryMode发送模式(持久化)send
JMSMessageID消息IDsend
JMSTimestamp发送时间send
JMSCorrelationID关联的消息IDclient
JMSReplyTo消息回复的目的地client
JMSRedelivered是否重复发送provider
JMSType消息类型client
JMSExpiration过期时间(ms)send
JMSPriority优先级(0-4普通、5-9高)send
  • 消息体
类型解释
TextMessage文本消息
ObjectMessage对象消息(对象需实现Serializable接口)
BytesMessage字节消息
StreamMessage流消息
MapMessage键值对消息
  • 消息属性
持久化
  • queue默认持久化,是否持久化取决于生产者,通过以下代码设置。
// 注意:手动设置``Message.setJMSDeliveryMode``无效。
producer.setDeliveryMode(DeliveryMode.NON_PERSISTENT); // 设置非持久化
producer.setDeliveryMode(DeliveryMode.PERSISTENT); // 设置持久化
  • topic模式默认非持久订阅,是否持久化取决于消费者,通过以下代码设置。
Session.createDurableSubscriber(topic, name); // JMS 1.x 设置持久订阅
Session.createDurableConsumer(topic, name); // JMS 2.x 设置持久订阅
Session.unsubscribe(name); // 取消持久订阅
事务(transacted)
  • 事务下的消息是原子性的,要么同时生产/消费成功,要么同时生成/消费失败。
  • 事务对消息生产者和消息消费者都有效。
  • 事务通过创建Session时的参数指定,代码如下。
Connection.createSession(true, Session.AUTO_ACKNOWLEDGE); // 第一个参数代表是否启用事务
  • 启用事务时,需要通过Session提交或回滚完成事务,代码如下。
Session.commit(); // 提交事务
Session.rollback(); // 回滚事务
签收(acknowledge)
  • 签收针对消息消费者,消息消费者通过签收消息的动作表示消息已被消费。
  • 签收模式
    AUTO_ACKNOWLEDGE:自动签收。
    CLIENT_ACKNOWLEDGE:手动签收。
    DUPS_OK_ACKNOWLEDGE:自动批量签收。
    SESSION_TRANSACTED:事务签收,事务提交时自动签收,事务回滚时不签收。
  • 消息通过如下代码签收。
Message.acknowledge(); // 签收消息
Spring、Spring Boot整合JMS
  • Spring定义了JmsTemplate,通过JmsTemplate操作。
  • Spring Boot通过spring-boot-starter-activemq整合。
ActiveMQ
ActiveMQ Broker(Embed ActiveMQ)

Broker:内嵌的ActiveMQ。

BrokerService brokerService = new BrokerService();
brokerService.setUseJmx(true);
brokerService.addConnector("tcp://localhost:61616");
brokerService.start();
System.in.read();
ActiveMQ协议

TCP、NIO、UDP、SSL、HTTP(S)、VM等。

ActiveMQ持久化

KahaDB(默认)、LevelDB、JDBC。

ActiveMQ集群
  • Broker集群
    • Broker集群中所有单点同时提供服务。
  • 主从(Master Slave)
    • 该模式提供了高可用的ActiveMQ集群。
    • 主从的基本原则是共享持久化存储,分为“共享文件系统”、“JDBC共享数据库”和“自我复制的Level DB”三种方式。
    • Slave不对外提供服务,Master宕机后,Slave自动升级为Master,开始对外提供服务。
ActiveMQ高级特性
  • 异步发送(Async Sends):Producer不等待Broker的确认,直接返回发送成功。可能丢失消息,所以需要手动确认(可以接收回调),必要时补偿消息。
  • 延时/定时投递(Delay and Schedule Message Delivery)
  • 重投递策略(Redelivery Policy):投递失败后会间隔指定时间发送多次重新投递,总是投递失败的放到死信队列(DLQ)中
  • 死信队列(Dead-Letter Queue,DLQ)
  • more…
### ActiveMQ 使用指南和配置教程 ActiveMQ 是一个功能强大的消息中间件,广泛应用于分布式系统中。以下是关于 ActiveMQ 的安装、配置及使用方法的详细说明。 #### 1. 安装与启动 ActiveMQ 的安装过程相对简单。首先需要下载并解压 ActiveMQ 的二进制文件[^2]。完成解压后,进入 `bin` 目录,根据操作系统选择合适的启动脚本: ```bash # 在 Linux 或 macOS 上 ./activemq start # 在 Windows 上 activemq.bat start ``` 启动后,可以通过访问默认管理界面 `http://localhost:8161/admin/` 来验证是否成功运行。 #### 2. 配置文件详解 ActiveMQ 的核心配置文件为 `activemq.xml`,位于安装目录下的 `conf` 文件夹中[^5]。以下是一些常见的配置项: - **持久化存储**:ActiveMQ 支持多种持久化机制,如 KahaDB 和 LevelDB。默认使用 KahaDB,其配置如下: ```xml <persistenceAdapter> <kahaDB directory="${activemq.data}/kahadb"/> </persistenceAdapter> ``` 如果需要切换到 LevelDB,可以修改为: ```xml <persistenceAdapter> <levelDB directory="${activemq.data}/leveldb"/> </persistenceAdapter> ``` - **日志存储路径**:日志文件通常存储在 `%activemq安装目录%/data/kahadb` 中[^5]。 #### 3. 使用方法 ActiveMQ 提供了多种使用模式,包括点对点(Point-to-Point)和发布/订阅(Publish/Subscribe)。具体操作步骤可参考相关文档[^4]。 以下是一个简单的 Java 示例代码,展示如何向队列发送消息: ```java import javax.jms.*; import org.apache.activemq.ActiveMQConnectionFactory; public class Producer { public static void main(String[] args) throws JMSException { ConnectionFactory connectionFactory = new ActiveMQConnectionFactory("tcp://localhost:61616"); Connection connection = connectionFactory.createConnection(); connection.start(); Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE); Destination destination = session.createQueue("TEST.QUEUE"); MessageProducer producer = session.createProducer(destination); TextMessage message = session.createTextMessage("Hello ActiveMQ!"); producer.send(message); session.close(); connection.close(); } } ``` #### 4. 管理控制台 ActiveMQ 提供了一个基于 Web 的管理控制台,用于监控和管理消息队列及主题。可以通过以下方式访问控制台[^3]: - 打开浏览器并输入地址:`http://localhost:8161/admin/` - 默认用户名和密码为 `admin/admin` #### 5. 常见问题解决 如果在使用过程中遇到问题,可以参考以下建议: - **无法连接到服务器**:确保 ActiveMQ 服务已正确启动,并检查防火墙设置。 - **日志文件过大**:调整日志级别或清理旧的日志文件[^5]。 ---
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值