ActiveMQ(一)

写在前面:

终于终于学到了ActiveMQ,和之前的Nginx一样。对ActiveMQ也保持着极高的兴趣。听说过没用过,学完Nginx就开始了ActiveMQ。

一、安装

①官网下载Linux版

②tar–zxcf apache-activemq-5.15.13-bin.tar.gz到/opt目录下

③复制到根目录 /mycativeMQ。cp –r apache-activemq-5.15.13/myactiveMQ

二、启动

在bin目录下。

启动 ./activemq start带运行日志启动./activemq start > /myactiveMQ/run_activemq.log

关闭 ./activemq stop

重载 ./activemq reload

默认后台端口 6161

默认前台(管理控制台)端口 8161默认用户名/密码 admin/admin

*查看后台进程的3种方式

ps–ef | grep activemq | grep –v grep

netstat–anp | grep 61616

lsof–i:61616

三、JMS开发的基本步骤

生产者-队列

public class JmsProduce {


    private static final String ACTIVEMQ_URL = "tcp://192.168.91.130:61616";
    private static final String QUEUE_NAME = "queue01";


    public static void main(String[] args) throws JMSException {
        //1.创建连接工厂。按照给定的url地址,采用默认用户名和密码
        ActiveMQConnectionFactory activeMQConnection = new ActiveMQConnectionFactory(ACTIVEMQ_URL);


        //2.通过连接工厂,获得连接connection并启动访问
        Connection connection = activeMQConnection.createConnection();
        connection.start();


        //3.创建会话Session
        //有两个参数 第一个叫事务、第二个叫签收
        Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);


        //4.创建目的地(具体是队列还是主题topic)
        Queue queue = session.createQueue(QUEUE_NAME); //Collections collection = new ArrayList() == Destination destination = session.createQueue(QUEUE_NAME);
        //5.创建消息的生产者
        MessageProducer messageProducer = session.createProducer(queue);
        //6.通过使用messageProducer生产3条消息发送到MQ的队列里
        for (int i = 0; i < 3; i++) {
            //7.创建消息
            TextMessage textMessage = session.createTextMessage("msg----" + i);
            //8.通过messageProducer发送给MQ
            messageProducer.send(textMessage);
        }


        //9.关闭资源
        messageProducer.close();
        session.close();
        connection.close();


        System.out.println("***********消息发布到MQ完成");
    }
}

消费者-队列-消费方式1 receive()

MessageConsumer messageConsumer = session.createConsumer(queue);


//同步阻塞式  receive()来消费消息
while (true){
    TextMessage textMessage = (TextMessage)messageConsumer.receive(5000L);
    if(null != textMessage){
        System.out.println("*********消费者接收到消息:"+textMessage.getText());
    }else {
        break;
    }
}
messageConsumer.close();
session.close();
connection.close();

消费者-队列-消费方式2(listener)

MessageConsumer messageConsumer = session.createConsumer(queue);


//异步非阻塞式 通过监听的方式来消费消息
messageConsumer.setMessageListener(new MessageListener() {
    public void onMessage(Message message) {
        if(null != message && message instanceof TextMessage){
            TextMessage textMessage = (TextMessage) message;
            try {
                System.out.println("*********消费者接收到消息:"+textMessage.getText());
            } catch (JMSException e) {
                e.printStackTrace();
            }
        }
    }
});
System.in.read();   //保证控制台灯不灭
messageConsumer.close();
session.close();
connection.close();

*消费顺序-队列

先创造2个消费者。再生产4条消息。

每个消费者轮询的获取每条消息。

目的地

在点对点的消息传递域中,目的地被称为队列(queue)

在发布订阅消息传递域中,目的地被称为主题(topic)

先消费(订阅)再生产(发布)

生产者-主题

其余和生产者-队列的保持一致。唯独创建目的地

Topic topic = session.createTopic("topic01");

消费者-主题

其余和消费者-队列的保持一致。唯独创建目的地

Topic topic = session.createTopic("topic01");
MessageConsumer messageConsumer = session.createConsumer(topic);
messageConsumer.setMessageListener((message)->{
    if(null != message && message instanceof TextMessage){
        TextMessage textMessage = (TextMessage)message;
        try {
            System.out.println("*********Topic消费者接收到消息:"+textMessage.getText());
        } catch (JMSException e) {
            e.printStackTrace();
        }
    }
});

先消费(订阅)再生产(发布).

队列VS主题

队列

主题

“负载均衡”模式。

“订阅-发布“模式。

即使没有消费者,消息也不会丢弃。

没有消费者,消息会丢弃

一条消息对应一个消费者。

有多个订阅者,每个订阅者都会收到消息。

四、JMS的组成结构和特点

JMS(Java Message Server)主要由消息头消息体消息属性组成。

消息头

①setJMSDestination(Destination destination)设置目的地

②setDeliveryMode(DeliveryMode.PERSISTENT);设置持久模式

DeliveryMode.PERSISTENT:JMS发送出现故障,该消息不会消失,服务恢复之后再次传递。

DeliveryMode.NON_PERSISTENT:最多传递一次,意味着服务出现故障,消息永远丢失。

③ setJMSExpiration(long tinmeToLive)设置消息过期时间

④ setJMSPriority(int)设置优先级

从0-9十个级别,0-4普通级别,5-9加急消息。默认4级,加急消息优先于普通消息。

⑤ setJMSMessageID()设置消息ID

唯一标识每个消息的标识,由MQ产生。

消息体

TextMessage textMessage1 = session.createTextMessage();
textMessage1.setText("String s");
MapMessage mapMessage1 = session.createMapMessage();
mapMessage1.setString("k1","v1");


session.createBytesMessage();
session.createObjectMessage();
session.createStreamMessage();

消息属性

去重、标识、重点标注(对消息头的补充)

textMessage.setStringProperty("property_name","property_value");
textMessage.getStringProperty("property_name");

五、JMS的可靠性

可靠性(持久性、事务、签收)

持久性

队列:

默认持久化messageProducer.setDeliveryMode(DeliveryMode.PERSISTENT);
DeliveryMode.PERSISTENT:JMS发送出现故障,该消息不会消失,服务恢复之后再次传递。
DeliveryMode.NON_PERSISTENT:最多传递一次,意味着服务出现故障,消息永远丢失。

主题:

connection.setClientID("z4");   //向MQ注册一个自己身份ID识别号
TopicSubscriber topicSubscriber = session.createDurableSubscriber(topic, "备注");//创造持久化订阅者

一定要先运行一次消费者(等于向MQ注册)。

然后再运行生产者发送消息。

此时,无论消费者是否在线,都会接收到。如果不在线,下次连接时会把没有接收到的消息接收下来。

事务(偏生产者)

//有两个参数 第一个叫事务、第二个叫签收
Session session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);

 

开启事务:

connection.createSession(true,Session.AUTO_ACKNOWLEDGE);

session.commit();//提交事务

session.rollback();//回滚

 

消费者:开启了事务也要commit()避免消息重复消费

签收(偏消费者)

自动签收(默认)Session.AUTO_ACKNOWLEDGE
手动签收Session.CLIENT_ACKNOWLEDGE

 

没开启事务(手动签收)

connection.createSession(false,Session.CLIENT_ACKNOWLEDGE)

textMessage.acknowledge();//手动签收

 

事务VS签收

开启事务:当一个事务被成功提交则消息被自动签收。如果事务回滚,则消息被再次传送。

关闭事务:消息何时被确认,取决于创建会话时的应答模式(acknowledge

六、JMS点对点总结

①点对点模型是基于队列的。生产者发送消息到队列,消费者从队列接收到消息。实现了“异步传输”。

②如果Session关闭时,有部分消息已被收到但还没签收acknowledged那当消费者下次连接到相同队列时,消息还会被再次接收(消息重复)

③队列可以长久保存消息直到消费者收到消息。消费者不用担心,消息会丢失而时刻和队列保持激活的连接状态。

七、JMS发布、订阅总结

主题被认为是消息的传输中介,发布者publisher发布消息到主题,订阅者subscribler从主题订阅消息。

②主题使得消息订阅者和消息发布者保持互相独立,不需要接触即可消息传达。

未完待续。。。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值