Невозможно создать производителя для отправки сообщений в ActiveMQ - PullRequest
3 голосов
/ 01 августа 2020

Я изучаю JMS и различные типы брокеров. В настоящее время я использую ActiveMQ (Artemis) для фиктивного проекта.

Сейчас у меня Artemis работает с настройками по умолчанию. Я могу go перейти в консоль управления и посмотреть очереди и темы. Сейчас я создаю 2 Java приложения на основе Spring; один для производства и один для потребления. Я видел несколько руководств, но я получаю NPE, в котором я не уверен - почему, поскольку я считаю, что я правильно подключаю bean-компонент.

Это мои классы:

Основной класс:

@SpringBootApplication
public class SpringJmsApplication {

  public static void main(String[] args) {
    SpringApplication.run(SpringJmsApplication.class, args);

    SendMessage send = new SendMessage("This is the test message");
  }
}

Отправитель:

public class Sender {

  private static final Logger LOGGER =
      LoggerFactory.getLogger(Sender.class);

  @Autowired
  private JmsTemplate jmsTemplate;

  public void send(String message) {
    LOGGER.info("sending message='{}'", message);
    jmsTemplate.convertAndSend("helloworld.q", message);
  }
}

Конфигурация отправителя:

@Configuration
public class SenderConfig {

  @Value("${artemis.broker-url}")
  private String brokerUrl;

  @Bean
  public ActiveMQConnectionFactory senderActiveMQConnectionFactory() {
    return new ActiveMQConnectionFactory(brokerUrl);
  }

  @Bean
  public CachingConnectionFactory cachingConnectionFactory() {
    return new CachingConnectionFactory(
        senderActiveMQConnectionFactory());
  }

  @Bean
  public JmsTemplate jmsTemplate() {
    return new JmsTemplate(cachingConnectionFactory());
  }

  @Bean
  public Sender sender() {
    return new Sender();
  }
}

Служба SendMessage:

public class SendMessage {  
    @Autowired
    Sender sender;

    public SendMessage(String message){
        this.sender.send(message);
    }
}

Итак по сути, ошибка возникает из класса SendMessage, он не может автоматически подключать bean-компонент отправителя, но я не уверен, почему эта ошибка возникает, потому что bean-компонент Sender создается в классе SenderConfig, поэтому, безусловно, Spring должен был добавить его к нему Spring контейнер / фабрика компонентов / контекст приложения?

Это трассировка стека:

Exception in thread "main" java.lang.NullPointerException
    at com.codenotfound.jms.SendMessage.<init>(SendMessage.java:11)
    at com.codenotfound.SpringJmsApplication.main(SpringJmsApplication.java:16)

Ответы [ 2 ]

1 голос
/ 01 августа 2020

Ваша проблема не связана с классом SendMessage, этот класс кажется нормальным.

Ваш NPE вызван тем, как вы получаете экземпляр класса SendMessage, а именно, вы не совсем получение @Bean, управляемое Spring Container; скорее, вы создаете его вручную с помощью ключевого слова new, например:

SendMessage send = new SendMessage("This is the test message");

Это полностью выделяет объект new в куче, который не будет в конечном итоге в контейнере Spring, следовательно → не будет управляться Spring, следовательно → его поле sender не будет @Autowired.

1 голос
/ 01 августа 2020

Вот и виноват ваш основной класс.

SendMessage send = new SendMessage("This is the test message");

Вы создаете объект самостоятельно, а не получаете его из контекста, Spring DI не будет применяться к объектам, созданным нами самим.

Решение состоит в том, чтобы пометить SendMessage как управляемый Spring bean-объект, аннотируя @Component, и получить его из контекста.

...