Выпуск CDI для инъекций Websocket Bean
Я не понимаю, почему использование инъекций CDI не работает с websockets, используя undertow.
Ниже приведен код для простой конечной точки веб-сокета.
@ServerEndpoint("/")
public class TestWebSocketEndpoint {
@Inject
private RetrieveAccessor retrieveAccessor;
private final Logger logger = Logger.getLogger(this.getClass().getName());
@OnOpen
public void onConnectionOpen(Session session) {
logger.info("Connection opened ... " + session.getId());
}
@OnMessage
public String onMessage(String message) {
if (!message.isEmpty()) {
return message;
}
System.out.println("RETRIEVE BEAN -> " + retrieveAccessor);
if (retrieveAccessor != null) {
return "BEAN NOT NULL";
}
return ":(";
}
@OnClose
public void onConnectionClose(Session session) {
logger.info("Connection close .... " + session.getId());
}
}
Конечно, проблема в том, что введенное свойство имеет значение null. Конечно, у меня нет проблем с использованием остальной части вещей для этого развертывания и внедрения bean-компонента без состояния, описанного ниже. Есть ли обходной путь для этого, с какими проблемами я мог бы столкнуться, если бы я просто инициировал нужные мне свойства, которые являются бобами? Потому что это определенно работает.
RetrieveAccessor retrieveAccessor = new.... {code}
2 ответа
Простой способ заставить внедрение работать с вашими аннотированными классами @ServerEndpoint - это установить пользовательский конфигуратор, который обрабатывает создание вашего экземпляра конечной точки, переопределив метод getEndpointInstance(Class endpointClass) для создания экземпляра с помощью CDI.
https://tyrus.java.net/documentation/1.13/user-guide.html
Аннотированная конечная точка:
@ServerEndpoint(value = "/", configurator = CDIEndpointConfigurator.class)
public class TestWebSocketEndpoint {
...
}
Пользовательский конфигуратор:
public class CDIEndpointConfigurator extends ServerEndpointConfig.Configurator {
@Override
public <T> T getEndpointInstance(Class<T> endpointClass) throws InstantiationException {
return CDI.current().select(endpointClass).get();
}
}
Undertow является только контейнером сервлетов. Weld (или OWB) обеспечивает поддержку CDI. Я не уверен, как вы создаете экземпляр Undertow, но вам нужно использовать Weld (или какую-то другую реализацию CDI).
Вот один пример, как это сделать. Используйте расширение CDI, чтобы найти конечные точки, и как только вы их получите, вы можете зарегистрировать их в Undertow
Не стесняйтесь использовать гамак для этого.