springmvc+activeMQ简单实用


1.下载activeMQ

地址:http://activemq.apache.org

选择linux版本。(最新的不一定能下载。我下载的时候最新的无法下载,选择了一个比较新的)

2.在linux上部署

1.首先保证linux上有java环境

2.命令输入 hostname 保证  主机名不能有下划线,否则会失败

如:

这是我第一台服务器。没有下划线的,可以启动成功

[root@localhost ~]# hostname
localhost

第二台服务器,带下划线,启动失败

[root@VM_206_200_centos ~]# hostname
VM_206_200_centos

失败日志:

java.lang.IllegalStateException: LifecycleProcessor not initialized - call 'refresh' before invoking lifecycle methods via the context:

org.apache.activemq.xbean.XBeanBrokerFactory$1@731bf584: startup date [Thu Nov 09 11:31:11 CST 2017];root of context hierarchy

注:解决办法:修改主机名。(百度下)

3.把下载下载的 apache-activemq-5.14.0-bin.tar.gz   放到linux服务器上面解压。然后进入目录:

cd apache-activemq-5.14.0/bin/linux-x86-64 

启动:  ./activemq start &

日志路径:cd apache-activemq-5.14.0/data

查看日志:tail -f activemq.log

4.无异常,linux 部署完成。出错检查主机名 和是否有java环境

部署成功后,可输入 :

ps -ef|grep activemq

结果如下:

访问:http://ip:8161/admin

用户名:admin

密码:admin

-------------------------------------------------到此linux上工作结束-------------------------------------------------

java端:

注:我做的是两个应用之间的通信,A 应用是生产者(发送消息),B 应用是消费者(接受消息)

1.配置文件:

##################activeMQ##################
activeMq.brokerURL=tcp://192.168.1.162:61616
activeMq.userName=admin
activeMq.password=admin
activeMq.queueName=news

2.A应用spring 配置(生产者):

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:amq="http://activemq.apache.org/schema/core"
       xmlns:jms="http://www.springframework.org/schema/jms"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       http://www.springframework.org/schema/jms
       http://www.springframework.org/schema/jms/spring-jms.xsd
       http://activemq.apache.org/schema/core
       http://activemq.apache.org/schema/core/activemq-core.xsd
       http://www.springframework.org/schema/context
       http://www.springframework.org/schema/context/spring-context.xsd">

    <!-- 加载配置文件 -->
    <context:property-placeholder location="classpath:activeMQ.properties" ignore-unresolvable="true"/>

    <amq:connectionFactory id="amqConnectionFactory"
                           brokerURL="${activeMq.brokerURL}"
                           userName="${activeMq.userName}"
                           password="${activeMq.password}" />

    <!-- 配置JMS连接工长 -->
    <bean id="mqConnectionFactory"
          class="org.springframework.jms.connection.CachingConnectionFactory">
        <constructor-arg ref="amqConnectionFactory" />
        <property name="sessionCacheSize" value="100" />
    </bean>

    <!-- Spring提供的JMS工具类,它可以进行消息发送、接收等 -->
    <bean id="internalJmsTemplate" class="org.springframework.jms.core.JmsTemplate">
        <property name="connectionFactory" ref="mqConnectionFactory" />
    </bean>

    <!-- 推送给用户信息  创建一个Queue-->
    <bean id="newsServiceQueue" class="org.apache.activemq.command.ActiveMQQueue">
        <constructor-arg>
            <value>${activeMq.queueName}</value>
        </constructor-arg>
    </bean>
</beans>

2.java 接口代码(生产者)

 

public interface PushService {
    public void push(String info);
}

3.java接口实现代码(生产者)

@Service
public class NewsPushServiceImpl implements PushService {
    @Autowired
    private JmsTemplate jmsTemplate;

    /**
     * 这里是根据MQ配置文件定义的queue来注入的,也就是这里将会把不同的内容推送到不同的queue中
     */
    @Autowired
    @Qualifier("newsServiceQueue")
    private Destination destination;
    @Override
    public void push(String info) {
        jmsTemplate.send(destination, new MessageCreator() {
            public Message createMessage(Session session) throws JMSException {
                return session.createTextMessage(info);
            }
        });
    }
}
4.java Controller实现,web 端调用推送消息(生产者)

@Controller
@RequestMapping("/importSend")
public class MqDemo {

    private PushService newsPushService;

    @RequestMapping("/test")
    public @ResponseBody String abtestSend() throws Exception {

        String msg="今天一直阴着!2017年11月8日14:09:07(news)";
        newsPushService.push(msg);
        return "OK";
    }
}

注:调用下接口就会向消息队列发送

---------------------------------------------------A应用(生产者)完成--------------------------------------------------------------

3.B应用spring配置(消费者)

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:amq="http://activemq.apache.org/schema/core"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
       http://www.springframework.org/schema/beans/spring-beans.xsd
       
       
       http://activemq.apache.org/schema/core
       http://activemq.apache.org/schema/core/activemq-core.xsd">



    <amq:connectionFactory id="amqConnectionFactory"
                           brokerURL="${activeMq.brokerURL}"
                           userName="${activeMq.userName}"
                           password="${activeMq.password}" />

    <!-- 配置JMS连接工长 -->
    <bean id="mqConnectionFactory"
          class="org.springframework.jms.connection.CachingConnectionFactory">
        <constructor-arg ref="amqConnectionFactory" />
        <property name="sessionCacheSize" value="100" />
    </bean>

    <!-- 定义消息队列(Queue) -->
    <bean id="newsQueueDestination" class="org.apache.activemq.command.ActiveMQQueue">
        <!-- 设置消息队列的名字 -->
        <constructor-arg>
            <value>${activeMq.queueName}</value>
        </constructor-arg>
    </bean>

    <!--第二个消息队列-->
    <bean id="userQueueDestination" class="org.apache.activemq.command.ActiveMQQueue">
        <!-- 设置消息队列的名字 -->
        <constructor-arg>
            <value>${activeMq.queueUser}</value>
        </constructor-arg>
    </bean>


    <!-- 配置JMS模板(Queue),Spring提供的JMS工具类,它发送、接收消息。 -->
    <bean id="jmsTemplate" class="org.springframework.jms.core.JmsTemplate">
        <property name="connectionFactory" ref="mqConnectionFactory" />
      <!--  <property name="defaultDestination" ref="demoQueueDestination" />
        <property name="receiveTimeout" value="10000" />-->
        <!-- true是topic,false是queue,默认是false,此处显示写出false -->
       <!-- <property name="pubSubDomain" value="false" />-->
    </bean>

    <!-- 配置消息队列监听者(Queue) -->
    <bean id="queueMessageListener" class="com.fh.job.jms.QueueMessageListener" />

    <!-- 第二个监听器 -->
    <bean id="userqueueMessageListener" class="com.fh.job.jms.userQueueMessageListener" />

    <!-- 显示注入消息监听容器(Queue),配置连接工厂,监听的目标是demoQueueDestination,监听器是上面定义的监听器 -->
    <bean id="queueListenerContainer" class="org.springframework.jms.listener.DefaultMessageListenerContainer">
        <property name="connectionFactory" ref="mqConnectionFactory" />
        <property name="destination" ref="newsQueueDestination" />
        <property name="messageListener" ref="queueMessageListener" />
    </bean>

    <!--第二个监听容器-->
    <bean id="userQueueListenerContainer" class="org.springframework.jms.listener.DefaultMessageListenerContainer">
        <property name="connectionFactory" ref="mqConnectionFactory" />
        <property name="destination" ref="userQueueDestination" />
        <property name="messageListener" ref="userqueueMessageListener" />
    </bean>
</beans>
注: 消费者 可手动获取消息队列中 生产者 推送的消息。但是使用监听,自动获取是最好的。这里,我配置了两个监听,spring里面就需要复写,同时一个监听对应一个类。还有一种实现是在代码里面判断消息队列名字,不断的写if...。本人不知道还有没有其他方式,如果有欢迎提出,在此拜谢!(RabbitMQ 有一个路由机制。不需要这么麻烦,但是我没研究这个东西)


监听的java代码实现:

package com.fh.job.jms;

import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageListener;
import javax.jms.TextMessage;

/**
 * Created by GS on 2017/11/7.
 */
public class QueueMessageListener implements MessageListener {
    @Override
    public void onMessage(Message message) {
        TextMessage tm = (TextMessage) message;
        try {
            System.out.println("JOB----QueueMessageListener监听到了文本消息:\t" + tm.getText());
            //do something ...
        } catch (JMSException e) {
            e.printStackTrace();
        }
    }
}

:配置完成后,B应用会自动监听 队列名称相同的 消息。有新消息的时候回自动执行监听方法,也就是你可以在监听方法里面调Service 做业务处理等操作!

额外提醒

1.如果生产者和消费者都在一个应用里面,那么把上面两个spring配置融合下就可以了。

2.如果生产者发送了消息,消费者没监听到,查看下linux上面的avtiveMQ 服务是否开启。 (使用 :ps -ef|grepp activemq 查看下)

3.如果没有linux环境,Windows上也能安装activeMQ服务。

4.最关心的问题,如果消费者那台服务器挂掉了。 生产者发出的消息,消费者就不会及时的消费,那么这些消息会丢失吗?不会!

这些消息的状态是未被消费。因为activeMQ有持久化机制,所以会默认存在一个文件里面,文件最大好像默认只能存 32M 吧。

当然,可以配置它持久化的方式,比如存Mysql,Oracle。(但是如果数据库挂掉了,这个风险更大,还是觉得写文件保险点)(持久化不需要配置,它默认配置存在一个文件里面)

配置持久化的方式,都是修改安装目录下conf/acticvemq.xml文件 

 ---------------------------------linux、SpringMVC、avtiveMQ 配置 与应用到此结束-------------------------------------------

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Sun_逸圣

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值