2

アーキテクチャに関する質問があります。私はグラスフィッシュアプ​​リサーバーで実行されるウィケット Web アプリを開発しています。ejb モジュールなどがあります。チャットパネルを作成するには、Apache ActiveMQ などのある種の JMS を使用して、継続的なポーリングを回避したいと考えています。2種類のハンドラSenderReceiver. どちらにも ConnectionFactory、Connecton、Session があります。チャット パネルはチャット ルームを表し、各チャット ルームはトピックです。(「ルーム」を選択してチャット パネルを開くと、指定されたトピックを論理的にサブスクライブします。) パネルは MessageListener インターフェイスを実装するため、パネルは Receiver オブジェクトのコンシューマーのリスナーです。

そのため、パネルは Sender オブジェクト内のトピックにメッセージを送信し、Receiver オブジェクトを介してメッセージをリッスンします。(ええ、すべてのパネルにはSenderReceiverオブジェクトもあります)

このように、2 つの接続/パネルがあり、誰もそれらの接続を閉じることをまったく気にしません。:(

activemq を使用するのは良い方法ではないと思います。この機能を実装するには、アドバイスが必要です。専門家はどのようにこれを行うのか、私にいくつかの指示をお願いできますか?それとも、どちらの方向に行かなければなりませんか?

建築

(ps、AMQ は完全にスタンドアロンで実行されています)

送信者、

public class Sender {

    private String user = ActiveMQConnection.DEFAULT_USER;
    private String password = ActiveMQConnection.DEFAULT_PASSWORD;
    private String url = "failover://(tcp://0.0.0.0:61616)?randomize=false";

    private Destination destination;
    private Connection connection = null;
    private Session session = null;
    private ActiveMQConnectionFactory connectionFactory;
    private MessageProducer producer;

    public Sender(String topicId) {
        try {
            connectionFactory = new ActiveMQConnectionFactory(user, password, url);
            connectionFactory.setDispatchAsync(false);

            connection = connectionFactory.createTopicConnection(user, password);
            connection.start();
            session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
            destination = session.createTopic(topicId);

            producer = session.createProducer(destination);
        } catch (JMSException ex) {
            Logger.getLogger(Sender.class.getName()).log(Level.SEVERE, null, ex);
            System.out.println(ex.toString());
        }
    }

    public void sendMessage(String message) {
        try {
            BytesMessage message = session.createBytesMessage();
            message.setLongProperty("text", message);
            producer.setDeliveryMode(DeliveryMode.NON_PERSISTENT);
            producer.send(destination, message);
        } catch (JMSException ex) {
            Logger.getLogger(Sender.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

    public void close() {
        try {
            producer.close();
            session.close();
            connection.close();
        } catch (JMSException ex) {
            Logger.getLogger(Sender.class.getName()).log(Level.SEVERE, null, ex);
        }
    }
}

受信機、

public class Receiver {
    private String url = "failover://(tcp://0.0.0.0:61616)?randomize=false";

    private ActiveMQConnectionFactory connectionFactory;
    private Connection connection;
    private Session session = null;
    private Topic destination = null;
    private TopicSubscriber consumer;
    private IdGenerator clientIdGenerator = new IdGenerator();

    public Receiver(String topicId, MessageListener listener) {
        try {
            connectionFactory = new ActiveMQConnectionFactory(url);
            connectionFactory.setDispatchAsync(false);

            connection = connectionFactory.createTopicConnection();
            connection.setClientID(clientIdGenerator.generateId());
            connection.start();
            session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);

            destination = session.createTopic(topicId);
            consumer = session.createDurableSubscriber(destination, "subscriber");
            consumer.setMessageListener(listener);
        } catch (JMSException ex) {
            Logger.getLogger(Receiver.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

    public void close() {
        try {
            consumer.close();
            session.close();
            connection.close();
        } catch (JMSException ex) {
            onException(ex);
            Logger.getLogger(Receiver.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

}
4

1 に答える 1

0

チャット パネルを作成するには、Apache ActiveMQ などのある種の JMS を使用して、継続的なポーリングを回避したいと考えています。

あなたが説明するセットアップには、継続的なポーリングが必要です! ChatPanels はサーバー側の Wicket コンポーネントです。サーバー側の Wicket コンポーネントからクライアント (ブラウザー) にチャット データを取得する必要があり、これには Javascript による継続的なポーリングが必要です。まさにそれを行う独自の Wicket 動作を実装できますが、それでもポーリングです。

継続的なポーリングを完全に回避したい場合は、WebSocket を使用する必要があります。Wicket には、Websocket サポート用の実験的モジュールがあります ( https://cwiki.apache.org/confluence/display/WICKET/Wicket+Native+WebSockets )。ただし、websocket は古いブラウザーでは機能しません。

于 2013-06-28T18:51:00.167 に答える