diff --git a/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketConfig.java b/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketConfig.java new file mode 100644 index 0000000000..5218140d2c --- /dev/null +++ b/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketConfig.java @@ -0,0 +1,23 @@ +package com.baeldung.rawwebsocket; + +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.web.socket.WebSocketHandler; +import org.springframework.web.socket.config.annotation.EnableWebSocket; +import org.springframework.web.socket.config.annotation.WebSocketConfigurer; +import org.springframework.web.socket.config.annotation.WebSocketHandlerRegistry; + +@Configuration +@EnableWebSocket +public class ServerWebSocketConfig implements WebSocketConfigurer { + + @Override + public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) { + registry.addHandler(webSocketHandler(), "/websocket"); + } + + @Bean + public WebSocketHandler webSocketHandler() { + return new ServerWebSocketHandler(); + } +} diff --git a/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketHandler.java b/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketHandler.java new file mode 100644 index 0000000000..ed1ac8edc3 --- /dev/null +++ b/spring-websockets/src/main/java/com/baeldung/rawwebsocket/ServerWebSocketHandler.java @@ -0,0 +1,72 @@ +package com.baeldung.rawwebsocket; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.scheduling.annotation.Scheduled; +import org.springframework.web.socket.CloseStatus; +import org.springframework.web.socket.SubProtocolCapable; +import org.springframework.web.socket.TextMessage; +import org.springframework.web.socket.WebSocketSession; +import org.springframework.web.socket.handler.TextWebSocketHandler; +import org.springframework.web.util.HtmlUtils; + +import java.io.IOException; +import java.time.LocalTime; +import java.util.Collections; +import java.util.List; +import java.util.Set; +import java.util.concurrent.CopyOnWriteArraySet; + +public class ServerWebSocketHandler extends TextWebSocketHandler implements SubProtocolCapable { + + private static final Logger logger = LoggerFactory.getLogger(ServerWebSocketHandler.class); + + private final Set sessions = new CopyOnWriteArraySet<>(); + + @Override + public void afterConnectionEstablished(WebSocketSession session) throws Exception { + logger.info("Server connection opened"); + sessions.add(session); + + TextMessage message = new TextMessage("one-time message from server"); + logger.info("Server sends: {}", message); + session.sendMessage(message); + } + + @Override + public void afterConnectionClosed(WebSocketSession session, CloseStatus status) { + logger.info("Server connection closed: {}", status); + sessions.remove(session); + } + + @Scheduled(fixedRate = 10000) + void sendPeriodicMessages() throws IOException { + for (WebSocketSession session : sessions) { + if (session.isOpen()) { + String broadcast = "server periodic message " + LocalTime.now(); + logger.info("Server sends: {}", broadcast); + session.sendMessage(new TextMessage(broadcast)); + } + } + } + + @Override + public void handleTextMessage(WebSocketSession session, TextMessage message) throws Exception { + String request = message.getPayload(); + logger.info("Server received: {}", request); + + String response = String.format("response from server to '%s'", HtmlUtils.htmlEscape(request)); + logger.info("Server sends: {}", response); + session.sendMessage(new TextMessage(response)); + } + + @Override + public void handleTransportError(WebSocketSession session, Throwable exception) { + logger.info("Server transport error: {}", exception.getMessage()); + } + + @Override + public List getSubProtocols() { + return Collections.singletonList("subprotocol.demo.websocket"); + } +}