Search code examples
javaspringspring-boottcpspring-integration

Failed to publish TcpConnectionOpenEvent Or TcpConnectionOpenEvent, Dispatcher failed to deliver Message


In spring integration i am using event Listener to handle TcpConnectionOpenEvent or TcpConnectionCloseEvent.

When i use code blog below, i can handle connection open close application event but i am receiving Warning log like

2020-08-11 11:15:46.857 WARN 7104 --- [ XNIO-1 task-1] o.s.i.i.tcp.connection.TcpNetConnection : Failed to publish TcpConnectionOpenEvent [SOME DETAIL] OPENED:Dispatcher failed to deliver Message; nested exception is java.lang.NullPointerException

@Bean
public MessageChannel connectionStatusChannel() {
    DirectChannel directChannel = new DirectChannel();
    directChannel.subscribe(new ServerConnectionStatusHandler());
    return directChannel;
}

@EventListener
public void listen(TcpConnectionOpenEvent event) {
    String eventName = "TcpConnectionOpenEvent";
    String destination = event.getConnectionFactoryName();
    connectionStatusChannel().send(new GenericMessage<>(eventName + "-" + destination));
}

@Component
public class ServerConnectionStatusHandler implements MessageHandler {

    private final Logger log = LoggerFactory.getLogger(ServerConnectionStatusHandler.class);

    @Autowired
    private SimpMessageSendingOperations messagingTemplate;

    public ServerConnectionStatusHandler() {
    }

    @Override
    public void handleMessage(Message<?> message) throws MessagingException {
        log.debug("ServerConnectionStatusHandler # handleMessage message : {} ", message.getPayload());
        messagingTemplate.convertAndSend("/topic/agent/connection/tracker", message.getPayload());
    }
}

This does not break my flow but i want to understand why i am taking this warnig and how can i clear it. Without @EventListener it disappers...

Thanks for helping


Solution

  • You can’t say new if you would like to get access to some bean in the application context.

    I mean this:

    directChannel.subscribe(new ServerConnectionStatusHandler());
    

    So you create a non-managed instance if your class. Meanwhile you need to auto wire existing bean:

    @Bean
    public MessageChannel connectionStatusChannel(ServerConnectionStatusHandler handler) {
        DirectChannel directChannel = new DirectChannel();
        directChannel.subscribe(handler);
        return directChannel;
    }