클라이언트(Sender)가 메세지를 보내면 STOMP 통신으로 서버에 메세지가 전달된다.
Controller의 @MessageMapping에 의해 메세지를 받는다.
Controller의 @SendTo로 특정 topic을(/1) 구독(/room) 하는 클라이언트에게 메세지를 보낸다.
(구독은 /room 으로 보면되고 특정 topic은 채팅방 id인 /1로 보면된다. -> /room/1)
https://blog.naver.com/qjawnswkd/222283176175
implementation'org.springframework.boot:spring-boot-starter-websocket'implementation'org.webjars:webjars-locator-core'implementation'org.webjars:sockjs-client:1.0.2'implementation'org.webjars:stomp-websocket:2.3.3'implementation'org.webjars:bootstrap:3.3.7'implementation'org.webjars:jquery:3.1.1-1'@Configuration@RequiredArgsConstructor@EnableWebSocketMessageBrokerpublicclassWebSocketConfigimplementsWebSocketMessageBrokerConfigurer {
@OverridepublicvoidconfigureMessageBroker(MessageBrokerRegistryregistry) {
registry.setApplicationDestinationPrefixes("/send"); //클라이언트에서 보낸 메세지를 받을 prefixregistry.enableSimpleBroker("/room"); //해당 주소를 구독하고 있는 클라이언트들에게 메세지 전달
}
@OverridepublicvoidregisterStompEndpoints(StompEndpointRegistryregistry) {
registry.addEndpoint("/ws-stomp") //SockJS 연결 주소
.withSockJS(); //버전 낮은 브라우저에서도 적용 가능// 주소 : ws://localhost:8080/ws-stomp
}
}@Controller@RequiredArgsConstructorpublicclassChatController {
privatefinalChatServicechatService;
@MessageMapping("/{roomId}") //여기로 전송되면 메서드 호출 -> WebSocketConfig prefixes 에서 적용한건 앞에 생략@SendTo("/room/{roomId}") //구독하고 있는 장소로 메시지 전송 (목적지) -> WebSocketConfig Broker 에서 적용한건 앞에 붙어줘야됨publicChatMessagetest(@DestinationVariableLongroomId, ChatMessagemessage) {
//채팅 저장Chatchat = chatService.createChat(roomId, message.getSender(), message.getMessage());
returnChatMessage.builder()
.roomId(roomId)
.sender(chat.getSender())
.message(chat.getMessage())
.build();
}
}<scriptth:inline="javascript">
var stompClient = null;
var roomId = [[${roomId}]];
var chatList = [[${chatList}]];
function setConnected(connected) {$("#connect").prop("disabled",connected);$("#disconnect").prop("disabled",!connected);if(connected){$("#conversation").show();}
else {$("#conversation").hide();}
$("#chatting").html("");
}functionconnect(){varsocket=newSockJS('/ws-stomp');stompClient=Stomp.over(socket);stompClient.connect({},function(frame){setConnected(true);console.log('Connected: '+frame);loadChat(chatList)//저장된 채팅 불러오기//구독stompClient.subscribe('/room/'+roomId,function(chatMessage){showChat(JSON.parse(chatMessage.body));});});}
function disconnect() {if(stompClient!==null){stompClient.disconnect();}
setConnected(false);
console.log("Disconnected");
}//html 에서 입력값, roomId 를 받아서 Controller 로 전달functionsendChat(){stompClient.send("/send/"+roomId,{},JSON.stringify({'sender': $("#sender").val(),'message' : $("#message").val()}));}
//저장된 채팅 불러오기
function loadChat(chatList){if(chatList!=null){for(chatinchatList){$("#chatting").append("<tr><td>"+"["+chatList[chat].sender+"]"+chatList[chat].message+"</td></tr>");}}}//보낸 채팅 보기functionshowChat(chatMessage){$("#chatting").append("<tr><td>"+"["+chatMessage.sender+"]"+chatMessage.message+"</td></tr>");}
$(function () {$("form").on('submit',function(e){e.preventDefault();});$("#connect").click(function(){connect();});$("#disconnect").click(function(){disconnect();});$("#send").click(function(){sendChat();});});
</script><script>//창 키면 바로 연결window.onload=function(){connect();}window.BeforeUnloadEvent=function(){disconnect();}</script>채팅 로그 Redis에 저장
