Подписчик темы не получил сообщение

#java #jms #activemq #jms-topic

#java #jms #activemq #jms-тема

Вопрос:

Я недавно работаю с темой в jms, и у меня проблема. Мой TopicSubscriber не получил сообщение от издателя, и я не понимаю, почему.

Вот мой TopicPublisher:

 public class Publisher
{
    private static final String CONNECTION_URL = "tcp://localhost:61616";

    public static void main(String[] args) throws Exception
    {
        BrokerService service = BrokerFactory.createBroker(new URI("broker:("   CONNECTION_URL   ")"));
        service.start();
        TopicConnectionFactory connectionFactory = new ActiveMQConnectionFactory(CONNECTION_URL);

        // create a topic connection
        TopicConnection topicConn = connectionFactory.createTopicConnection();

        // create a topic session
        TopicSession topicSession = topicConn.createTopicSession(false,
                Session.AUTO_ACKNOWLEDGE);

        // lookup the topic object
        Topic topic = topicSession.createTopic("test");

        // create a topic publisher
        TopicPublisher topicPublisher = topicSession.createPublisher(topic);
        topicPublisher.setDeliveryMode(DeliveryMode.NON_PERSISTENT);

        // create the "Hello World" message
        TextMessage message = topicSession.createTextMessage();
        message.setText("Hello World");

        // publish the messages
        topicPublisher.publish(message);

        // print what we did
        System.out.println("Message published: "   message.getText());

        // close the topic connection
        topicConn.close();
    }
}
 

Мой подписчик темы:

 public class Subscriber
{
    private static final String CONNECTION_URL = "tcp://localhost:61616";

    public static void main(String[] args) throws Exception
    {
        TopicConnectionFactory connectionFactory = new ActiveMQConnectionFactory(CONNECTION_URL);

        // create a topic connection
        TopicConnection topicConn = connectionFactory.createTopicConnection();

        // create a topic session
        TopicSession topicSession = topicConn.createTopicSession(false,
                Session.AUTO_ACKNOWLEDGE);


        Topic topic = topicSession.createTopic("test");

        // create a topic subscriber
        TopicSubscriber topicSubscriber = topicSession.createSubscriber(topic);

        // start the connection
        topicConn.start();

        // receive the message
        TextMessage message = (TextMessage) topicSubscriber.receiveNoWait();

        // print the message
        System.out.println("Message received: "   message.getText());

        // close the topic connection
        topicConn.close();
    }
}
 

В моем подписчике у меня есть указатель NULL на message.getText()
В чем эта проблема? Что я делаю не так и как это можно исправить?

Комментарии:

1. Вы уверены NullPointerException , что включен topicSubscriber.receiveNoWait() ? Это указывало topicSubscriber бы на is null . Кажется более вероятным, что NullPointerException это происходит из message.getText() -за того, что message есть null . Пожалуйста, подтвердите.

2. Да, я имею в виду, что message.getText() имеет значение null. Но это потому, что подписчик не получил сообщение. И я не понимаю, почему

Ответ №1:

Похоже, что вы отправляете сообщение перед созданием подписки. Темы JMS используют семантику публикации-подписки, где любое опубликованное сообщение распространяется на все подписки. Если подписок нет, сообщение отбрасывается.

Кроме того, поскольку вы используете receiveNoWait() , вы сильно снижаете вероятность того, что ваш клиент когда-либо получит сообщение. Для того, чтобы ваш клиент действительно получил сообщение, сообщение должно быть отправлено между временем, когда вы звоните createSubscriber(topic) , и временем, когда вы звоните receiveNoWait() . Поскольку эти 2 вызова происходят очень близко друг к другу, интервал времени очень мал.

Если вы действительно хотите, чтобы ваш подписчик получил сообщение Subscriber , сначала запустите и используйте receive() receiveNoWait() , а не затем запустите Publisher . Это гарантирует, что подписка существует при отправке сообщения и что клиент ожидает получения сообщения перед завершением.