復習日記

勤務時間内で理解できなかったことやつまづいたことをまとめていく予定。

wildflyでActiveMQを使ってみる

前回のつづき。

Wildfly埋め込みのJMSのHornetQではなくて、ActiveMQを使ってみます。

HornetQを使う場合は、何も設定いらず直接使えたんですが、

ActiveMQを使う場合は、HornetQをブリッジしてActiveMQResource Adapterというのを経由して、ActiveMQにアクセスしたらできました。(汗

参考サイト)

http://blog.c2b2.co.uk/2014/01/connecting-jboss-wildfly-7-to-activemq.html

http://activemq.apache.org/download.html

apache-activemq-5.9.1-bin.zipをダウンロードして解凍。

binディレクトリにあるactivemq.batを実行

(ローカルでActiveMQが起動します。)

 INFO | Apache ActiveMQ 5.9.1 (localhost, ID:game-PC-59019-1416632735373-0:1) started
 INFO | For help or more information please see: http://activemq.apache.org
 INFO | ActiveMQ WebConsole available at http://localhost:8161/
 INFO | Initializing Spring FrameworkServlet 'dispatcher'
 INFO | jolokia-agent: No access restrictor found at classpath:/jolokia-access.xml, access to all MBeans is allowed

http://localhost:8161/ にアクセス

f:id:raimus0904:20141122141726j:plain

ActiveMQがちゃんと動いているようなのでOK

なお、デフォルトではActiveMQResource Adapterと、ポート:61616でやり取りするようです。

  • ActiveMQResource Adapterの設定

http://repo1.maven.org/maven2/org/apache/activemq/activemq-rar/

activemq-rar-5.9.1.rarをダウンロード

wildflyのmoduleとして登録する。

mkdir %JBOSS_HOME%\modules\system\layers\base\org\apache\activemq\main 

上記フォルダにactivemq-rar-5.9.1.rarを解凍し、module.xmlを以下の内容で作成。

Wildflyでは、modules配下にディレクトリを作成してそこにjarと一緒にmodules.xmlというファイルを作ることで、Wildflyにロードさせることができるようになるそうです。

<?xml version="1.0" encoding="UTF-8"?>
<module xmlns="urn:jboss:module:1.3" name="org.apache.activemq">
  <resources>
    <resource-root path="."/>
    <resource-root path="activemq-broker-5.9.1.jar"/>
    <resource-root path="activemq-client-5.9.1.jar"/>
    <resource-root path="activemq-jms-pool-5.9.1.jar"/>
    <resource-root path="activemq-kahadb-store-5.9.1.jar"/>
    <resource-root path="activemq-openwire-legacy-5.9.1.jar"/>
    <resource-root path="activemq-pool-5.9.1.jar"/>
    <resource-root path="activemq-protobuf-1.1.jar"/>
    <resource-root path="activemq-ra-5.9.1.jar"/>
    <resource-root path="activemq-spring-5.9.1.jar"/>
    <resource-root path="aopalliance-1.0.jar"/>
    <resource-root path="commons-pool-1.6.jar"/>
    <resource-root path="geronimo-j2ee-management_1.1_spec-1.0.1.jar"/>
    <resource-root path="commons-logging-1.1.3.jar"/>
    <resource-root path="hawtbuf-1.9.jar"/>
    <resource-root path="spring-aop-3.2.5.RELEASE.jar"/>
    <resource-root path="spring-beans-3.2.5.RELEASE.jar"/>
    <resource-root path="spring-context-3.2.5.RELEASE.jar"/>
    <resource-root path="spring-core-3.2.5.RELEASE.jar"/>
    <resource-root path="spring-expression-3.2.5.RELEASE.jar"/>
    <resource-root path="xbean-spring-3.15.jar"/>
  </resources>
  <exports>
    <exclude path="org/springframework/**"/>
    <exclude path="org/apache/xbean/**"/>
    <exclude path="org/apache/commons/**"/>
    <exclude path="org/aopalliance/**"/>
    <exclude path="org/fusesource/**"/>
  </exports>
  <dependencies>
    <module name="javax.api"/>
    <module name="org.slf4j"/>
    <module name="javax.resource.api"/>
    <module name="javax.jms.api"/>
    <module name="javax.management.j2ee.api"/>
  </dependencies>
</module>

落としてきたactivemq-rar-5.9.1.rarは、参考サイトのrarよりバージョンが新しかったので、そこは変えています。

wildflyのstandalone-full.xmlを編集します

mdbのresource-adapter-nameにactivemq-rarを指定

        <subsystem xmlns="urn:jboss:domain:ejb3:2.0">
            <mdb>
                <resource-adapter-ref resource-adapter-name="activemq-rar"/>
                <bean-instance-pool-ref pool-name="mdb-strict-max-pool"/>
            </mdb>

hornetq-serverのjms-destinationsにJMSBridgeSourceQueueを追加

jms-bridgeの設定を追加

        <subsystem xmlns="urn:jboss:domain:messaging:2.0">
            <hornetq-server>

                <jms-destinations>
                    <jms-queue name="ExpiryQueue">
                        <entry name="java:/jms/queue/ExpiryQueue"/>
                    </jms-queue>
                    <jms-queue name="DLQ">
                        <entry name="java:/jms/queue/DLQ"/>
                    </jms-queue>
                    <jms-queue name="JMSBridgeSourceQueue">
                        <entry name="java:/queue/JMSBridgeSourceQ"/>
                        <entry name="java:jboss/exported/jms/queue/JMSBridgeSourceQ"/>
                    </jms-queue>
                </jms-destinations>
            </hornetq-server>
            <jms-bridge name="simple-jms-bridge">
                <source>
                    <connection-factory name="ConnectionFactory"/>
                    <destination name="queue/JMSBridgeSourceQ"/>
                </source>
                <target>
                    <connection-factory name="AMQConnectionFactory"/>
                    <destination name="queue/JMSBridgeTargetQ"/>
                </target>
                <quality-of-service>AT_MOST_ONCE</quality-of-service>
                <failure-retry-interval>1000</failure-retry-interval>
                <max-retries>-1</max-retries>
                <max-batch-size>10</max-batch-size>
                <max-batch-time>100</max-batch-time>
            </jms-bridge>
        </subsystem>

resource-adaptersサブシステムの設定

        <subsystem xmlns="urn:jboss:domain:resource-adapters:2.0">
            <resource-adapters>
                <resource-adapter id="activemq-rar.rar">
                    <module slot="main" id="org.apache.activemq"/>
                    <transaction-support>NoTransaction</transaction-support>
                    <config-property name="ServerUrl">
                        tcp://localhost:61616
                    </config-property>
                    <connection-definitions>
                        <connection-definition class-name="org.apache.activemq.ra.ActiveMQManagedConnectionFactory" jndi-name="java:/AMQConnectionFactory" enabled="true" use-java-context="true" pool-name="AMQConnectionFactory"/>
                    </connection-definitions>
                    <admin-objects>
                        <admin-object class-name="org.apache.activemq.command.ActiveMQQueue" jndi-name="java:/queue/JMSBridgeTargetQ" use-java-context="true" pool-name="target_queue">
                            <config-property name="PhysicalName">
                                JMSBridgeTargetQ
                            </config-property>
                        </admin-object>
                    </admin-objects>
                </resource-adapter>
            </resource-adapters>
        </subsystem>

キューの送信側(サーブレット

package org.jboss.as.quickstarts.servlet;

import java.io.IOException;
import java.io.PrintWriter;
import javax.annotation.Resource;
import javax.inject.Inject;
import javax.jms.ConnectionFactory;
import javax.jms.Destination;
import javax.jms.JMSContext;
import javax.jms.Queue;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet("/HelloWorldMDBServletClient")
public class HelloWorldMDBServletClient extends HttpServlet {

    private static final long serialVersionUID = -8314035702649252239L;

    private static final int MSG_COUNT = 5;

    @Inject
    private JMSContext context;

    @Resource(mappedName = "java:jboss/DefaultJMSConnectionFactory") 
    private ConnectionFactory cf;  
    
    @Resource(lookup  = "java:/queue/JMSBridgeSourceQ")
    private Queue queue;

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        resp.setContentType("text/html");
        PrintWriter out = resp.getWriter();
        out.write("<h1>Quickstart: Example demonstrates the use of <strong>JMS 2.0</strong> and <strong>EJB 3.2 Message-Driven Bean</strong> in WildFly 8.</h1>");
        try {
            final Destination destination = queue;

            out.write("<p>Sending messages to <em>" + destination + "</em></p>");
            out.write("<h2>Following messages will be send to the destination:</h2>");
            for (int i = 0; i < MSG_COUNT; i++) {
                String text = "This is message " + (i + 1);
                context.createProducer().send(destination, text);
                out.write("Message (" + i + "): " + text + "</br>");
            }
            out.write("<p><i>Go to your WildFly Server console or Server log to see the result of messages processing</i></p>");
        } finally {
            if (out != null) {
                out.close();
            }
        }
    }
}

キューの取り出し側(MDB)

package org.jboss.as.quickstarts.mdb;

import java.util.logging.Logger;
import javax.ejb.ActivationConfigProperty;
import javax.ejb.MessageDriven;
import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageListener;
import javax.jms.TextMessage;

@MessageDriven(name = "HelloWorldQueueMDB", activationConfig = {
        @ActivationConfigProperty(propertyName = "destination", propertyValue = "JMSBridgeTargetQ"),
        @ActivationConfigProperty(propertyName = "destinationType", propertyValue = "javax.jms.Queue"),
        @ActivationConfigProperty(propertyName = "acknowledgeMode", propertyValue = "Auto-acknowledge") })
public class HelloWorldQueueMDB implements MessageListener {

    private final static Logger LOGGER = Logger.getLogger(HelloWorldQueueMDB.class.toString());

    public void onMessage(Message rcvMessage) {
        TextMessage msg = null;
        try {
            if (rcvMessage instanceof TextMessage) {
                msg = (TextMessage) rcvMessage;
                LOGGER.info("Received Message from queue: " + msg.getText());
            } else {
                LOGGER.warning("Message of wrong type: " + rcvMessage.getClass().getName());
            }
        } catch (JMSException e) {
            throw new RuntimeException(e);
        }
    }
}

wildflyを起動

%JBOSS_HOME%\bin\standalone.bat -c standalone-full.xml

サーブレットにアクセスして、送信の動作確認

http://localhost:8080/wildfly-helloworld-mdb/HelloWorldMDBServletClient

f:id:raimus0904:20141122223217j:plain

server.logから、キューの受信ができたことを確認

2014-11-22 23:12:28,221 INFO  [org.jboss.as.messaging] (ServerService Thread Pool -- 59) JBAS011601: Bound messaging object to jndi name java:jboss/exported/jms/queue/JMSBridgeSourceQ
2014-11-22 23:12:28,222 INFO  [org.jboss.as.messaging] (ServerService Thread Pool -- 59) JBAS011601: Bound messaging object to jndi name java:/queue/JMSBridgeSourceQ
2014-11-22 23:12:28,222 INFO  [org.hornetq.core.server] (ServerService Thread Pool -- 58) HQ221003: trying to deploy queue jms.queue.ExpiryQueue
2014-11-22 23:12:28,222 INFO  [org.jboss.as.messaging] (ServerService Thread Pool -- 58) JBAS011601: Bound messaging object to jndi name java:/jms/queue/ExpiryQueue
2014-11-22 23:12:28,222 INFO  [org.hornetq.core.server] (ServerService Thread Pool -- 57) HQ221003: trying to deploy queue jms.queue.DLQ
2014-11-22 23:12:28,223 INFO  [org.jboss.as.messaging] (ServerService Thread Pool -- 57) JBAS011601: Bound messaging object to jndi name java:/jms/queue/DLQ
2014-11-22 23:12:28,231 INFO  [org.jboss.as.connector.deployment] (MSC service thread 1-13) JBAS010406: Registered connection factory java:/JmsXA
2014-11-22 23:12:28,242 INFO  [org.hornetq.ra] (MSC service thread 1-13) HornetQ resource adaptor started
2014-11-22 23:12:28,242 INFO  [org.jboss.as.connector.services.resourceadapters.ResourceAdapterActivatorService$ResourceAdapterActivator] (MSC service thread 1-13) IJ020002: Deployed: file://RaActivatorhornetq-ra
2014-11-22 23:12:28,243 INFO  [org.jboss.as.connector.deployment] (MSC service thread 1-6) JBAS010401: Bound JCA ConnectionFactory [java:/JmsXA]
2014-11-22 23:12:28,243 INFO  [org.jboss.as.messaging] (MSC service thread 1-3) JBAS011601: Bound messaging object to jndi name java:jboss/DefaultJMSConnectionFactory
2014-11-22 23:12:28,246 INFO  [org.jboss.weld.deployer] (MSC service thread 1-11) JBAS016008: Starting weld service for deployment wildfly-helloworld-mdb.war
2014-11-22 23:12:28,266 INFO  [org.jboss.as.ejb3] (MSC service thread 1-7) JBAS014142: Started message driven bean 'HelloWorldQueueMDB' with 'activemq-rar' resource adapter
2014-11-22 23:12:28,458 INFO  [org.jboss.messaging] (ServerService Thread Pool -- 59) JBAS011610: Started JMS Bridge simple-jms-bridge
2014-11-22 23:12:28,734 INFO  [org.apache.activemq.ra.ActiveMQEndpointWorker] (ServerService Thread Pool -- 59) Starting
2014-11-22 23:12:28,740 INFO  [org.apache.activemq.ra.ActiveMQEndpointWorker] (default-threads - 1) Establishing connection to broker [tcp://localhost:61616]
2014-11-22 23:12:28,745 INFO  [org.apache.activemq.ra.ActiveMQEndpointWorker] (default-threads - 1) Successfully established connection to broker [tcp://localhost:61616]
2014-11-22 23:12:28,833 INFO  [org.wildfly.extension.undertow] (MSC service thread 1-11) JBAS017534: Registered web context: /wildfly-helloworld-mdb
2014-11-22 23:12:28,864 INFO  [org.jboss.as.server] (ServerService Thread Pool -- 31) JBAS018559: Deployed "wildfly-helloworld-mdb.war" (runtime-name : "wildfly-helloworld-mdb.war")
2014-11-22 23:12:28,974 INFO  [org.jboss.as] (Controller Boot Thread) JBAS015961: Http management interface listening on http://127.0.0.1:9990/management
2014-11-22 23:12:28,975 INFO  [org.jboss.as] (Controller Boot Thread) JBAS015951: Admin console listening on http://127.0.0.1:9990
2014-11-22 23:12:28,975 INFO  [org.jboss.as] (Controller Boot Thread) JBAS015874: WildFly 8.1.0.CR2 "Kenny" started in 3029ms - Started 346 of 398 services (102 services are lazy, passive or on-demand)
2014-11-22 23:12:49,563 INFO  [class org.jboss.as.quickstarts.mdb.HelloWorldQueueMDB] (default-threads - 3) Received Message from queue: This is message 2
2014-11-22 23:12:49,563 INFO  [class org.jboss.as.quickstarts.mdb.HelloWorldQueueMDB] (default-threads - 2) Received Message from queue: This is message 1
2014-11-22 23:12:49,563 INFO  [class org.jboss.as.quickstarts.mdb.HelloWorldQueueMDB] (default-threads - 4) Received Message from queue: This is message 3
2014-11-22 23:12:49,563 INFO  [class org.jboss.as.quickstarts.mdb.HelloWorldQueueMDB] (default-threads - 5) Received Message from queue: This is message 4
2014-11-22 23:12:49,563 INFO  [class org.jboss.as.quickstarts.mdb.HelloWorldQueueMDB] (default-threads - 6) Received Message from queue: This is message 5

ActiveMQの管理画面から確認してみる

http://localhost:8161/

f:id:raimus0904:20141122223816j:plain

OK。