WebSocket 정리

Dal col·2025년 4월 13일

WebSocket

목록 보기
3/6

WebSocketConfig

코드

@Configuration
@EnableWebSocketMessageBroker
public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {
	@Override
	public void configureMessageBroker(MessageBrokerRegistry config) {
		config.enableSimpleBroker("/topic");
		config.setApplicationDestinationPrefixes("/app");
	}

	@Override
	public void registerStompEndpoints(StompEndpointRegistry registry) {
		registry.addEndpoint("/gs-guide-websocket");
	}

}

@Configuration

@Configuration은 해당 클래스가 설정 클래스임을 의미합니다. 내부에 정의된 @Bean 메서드들을 스프링 컨테이너에 등록해줍니다. WebSocketConfig는 웹소켓 설정을 위한 설정 클래스로 사용됩니다.

@EnableWebSocketMessageBroker

@EnableWebSocketMessageBroker는 STOMP 기반의 메시지 브로커를 사용한 WebSocket 메시지 처리를 활성화합니다. 이를 통해 @MessageMapping과 같은 어노테이션 기반 메시지 핸들링이 가능해집니다.

WebSocketMessageBrokerConfigurer

WebSocketMessageBrokerConfigurer는 웹소켓 메시지 브로커의 설정을 커스터마이징할 수 있는 인터페이스입니다. 이 인터페이스를 구현하면 메시지 브로커 구성, 엔드포인트 등록 등 다양한 설정을 오버라이딩할 수 있습니다.

주요 메서드:

  • configureMessageBroker() : 메시지 브로커 설정
  • registerStompEndpoints() : STOMP 엔드포인트 설정

configureMessageBroker(MessageBrokerRegistry config)

  • enableSimpleBroker("/topic"):
    간단한 메모리 기반 메시지 브로커를 활성화합니다. 클라이언트는 /topic/채널명에 subscribe하여 서버로부터 메시지를 받을 수 있습니다. 일반적으로 @SendTo("/topic/xxx")와 함께 사용됩니다.

  • setApplicationDestinationPrefixes("/app"):
    클라이언트가 서버에 메시지를 보낼 때 prefix를 설정합니다. 예를 들어 클라이언트가 /app/hello로 메시지를 보내면, 서버의 @MessageMapping("/hello") 메서드가 이를 처리합니다.

registerStompEndpoints(StompEndpointRegistry registry)

클라이언트가 처음으로 WebSocket 연결을 맺을 때 사용하는 엔드포인트입니다.
예: ws://localhost:8080/gs-guide-websocket

보안 또는 호환성을 위해 .withSockJS() 옵션을 추가할 수도 있습니다:

registry.addEndpoint("/gs-guide-websocket").withSockJS();
  • STOMP란?
    STOMP(Simple Text Oriented Messaging Protocol)는 WebSocket 위에서 동작하는 메시징 프로토콜입니다.
    이를 사용하면 pub-sub 방식으로 메시지를 보낼 수 있으며, 클라이언트와 서버 간의 메시지를 topic 기반으로 관리할 수 있습니다.

Controller

코드

@Controller
public class GreetingController {


	@MessageMapping("/hello")
	@SendTo("/topic/greetings")
	public Greeting greeting(HelloMessage message) throws Exception {
		Thread.sleep(1000); // simulated delay
		return new Greeting("Hello, " + HtmlUtils.htmlEscape(message.getName()) + "!");
	}

}

@MessageMapping

  • 클라이언트가 보낸 메시지를 처리하는 핸들러 메서드입니다.

  • 클라이언트는 /app/hello 주소로 메시지를 전송하고, 이 메시지는 @MessageMapping("/hello")가 붙은 메서드에서 처리됩니다.

  • @RequestMapping의 WebSocket 버전이라고 이해하면 좋습니다.

@SendTo

  • 해당 메서드가 처리한 결과 메시지를 브로드캐스트할 대상 주소입니다.

  • 이 경로를 구독하고 있는 클라이언트들에게 메시지를 전송합니다.

  • 예: 클라이언트가 /topic/greetings를 구독하고 있다면, 이 메서드의 리턴 값이 해당 클라이언트들에게 전달됩니다.

    브로드캐스트란
    여러 클라이언트에 동시에 메시지를 보내는 방식

topic/greeting에 구독하고 있는 사람들은 메시지 하나가 올라오면 그걸 동시에 모든 사람들이 메시지를 받습니다.

@SendToUser

한 명의 사용자에게만 메시지를 보내고 싶을 때 사용합니다.

@Configuration
@EnableWebSocketMessageBroker
public class WebSocketConfig implements WebSocketMessageBrokerConfigurer {

    @Override
    public void configureMessageBroker(MessageBrokerRegistry config) {
        config.enableSimpleBroker("/topic", "/queue");

        config.setApplicationDestinationPrefixes("/app");

        config.setUserDestinationPrefix("/user");
    }

    @Override
    public void registerStompEndpoints(StompEndpointRegistry registry) {
        registry.addEndpoint("/gs-guide-websocket").withSockJS(); // SockJS fallback도 추가하면 좋아
    }
}

/queue

클라이언트가 구독하는 목적지이며 queue는 개인용으로 사용합니다.

config.setUserDestinationPrefix("/user")

@SendToUser가 사용하는 대상 경로 prefix를 /user로 설정한것입니다.

@MessageMapping("/hello")
@SendToUser("/queue/reply")
public String replyToUser(String name) {
    return "안녕, " + name + "님!";
}

이로 인해 @SendToUser은 user/queue/reply를 통해 구독을 하면 app/hello을 통해 메시지를 보낼 수 있습니다.

profile
백엔드 개발자가 되기까지의 과정

0개의 댓글