Skip to content

Commit 58f4b3e

Browse files
jueunk617namgigun
authored andcommitted
Test: NotificationWebSocketService 테스트 코드 작성
1 parent 9178316 commit 58f4b3e

File tree

1 file changed

+218
-0
lines changed

1 file changed

+218
-0
lines changed
Lines changed: 218 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,218 @@
1+
package com.back.domain.notification.service;
2+
3+
import static org.mockito.ArgumentMatchers.*;
4+
import static org.mockito.BDDMockito.*;
5+
import static org.mockito.Mockito.verify;
6+
7+
import com.back.domain.notification.dto.NotificationWebSocketDto;
8+
import com.back.domain.notification.entity.NotificationType;
9+
import org.junit.jupiter.api.BeforeEach;
10+
import org.junit.jupiter.api.DisplayName;
11+
import org.junit.jupiter.api.Nested;
12+
import org.junit.jupiter.api.Test;
13+
import org.junit.jupiter.api.extension.ExtendWith;
14+
import org.mockito.InjectMocks;
15+
import org.mockito.Mock;
16+
import org.mockito.junit.jupiter.MockitoExtension;
17+
import org.springframework.messaging.simp.SimpMessagingTemplate;
18+
19+
import java.time.LocalDateTime;
20+
21+
@ExtendWith(MockitoExtension.class)
22+
class NotificationWebSocketServiceTest {
23+
24+
@Mock
25+
private SimpMessagingTemplate messagingTemplate;
26+
27+
@InjectMocks
28+
private NotificationWebSocketService webSocketService;
29+
30+
private NotificationWebSocketDto notificationDto;
31+
32+
@BeforeEach
33+
void setUp() {
34+
notificationDto = NotificationWebSocketDto.from(
35+
1L,
36+
"테스트 알림",
37+
"알림 내용",
38+
NotificationType.PERSONAL,
39+
"/target",
40+
LocalDateTime.now()
41+
);
42+
}
43+
44+
@Nested
45+
@DisplayName("개인 알림 전송 테스트")
46+
class SendNotificationToUserTest {
47+
48+
@Test
49+
@DisplayName("특정 유저에게 알림 전송")
50+
void t1() {
51+
// given
52+
Long userId = 1L;
53+
String expectedDestination = "/topic/user/1/notifications";
54+
55+
// when
56+
webSocketService.sendNotificationToUser(userId, notificationDto);
57+
58+
// then
59+
verify(messagingTemplate).convertAndSend(
60+
eq(expectedDestination),
61+
eq(notificationDto)
62+
);
63+
}
64+
65+
@Test
66+
@DisplayName("전송 실패 시 예외를 로깅하고 정상 종료")
67+
void t2() {
68+
// given
69+
Long userId = 1L;
70+
willThrow(new RuntimeException("전송 실패"))
71+
.given(messagingTemplate)
72+
.convertAndSend(anyString(), any(Object.class));
73+
74+
// when & then - 예외가 발생해도 메서드는 정상 종료되어야 함
75+
webSocketService.sendNotificationToUser(userId, notificationDto);
76+
77+
verify(messagingTemplate).convertAndSend(anyString(), any(Object.class));
78+
}
79+
}
80+
81+
@Nested
82+
@DisplayName("시스템 알림 브로드캐스트 테스트")
83+
class BroadcastSystemNotificationTest {
84+
85+
@Test
86+
@DisplayName("전체 유저에게 시스템 알림 브로드캐스트")
87+
void t1() {
88+
// given
89+
String expectedDestination = "/topic/notifications/system";
90+
NotificationWebSocketDto systemDto = NotificationWebSocketDto.from(
91+
2L,
92+
"시스템 알림",
93+
"시스템 공지",
94+
NotificationType.SYSTEM,
95+
"/system",
96+
LocalDateTime.now()
97+
);
98+
99+
// when
100+
webSocketService.broadcastSystemNotification(systemDto);
101+
102+
// then
103+
verify(messagingTemplate).convertAndSend(
104+
eq(expectedDestination),
105+
eq(systemDto)
106+
);
107+
}
108+
109+
@Test
110+
@DisplayName("브로드캐스트 실패 시 예외 로깅하고 정상 종료")
111+
void t2() {
112+
// given
113+
willThrow(new RuntimeException("브로드캐스트 실패"))
114+
.given(messagingTemplate)
115+
.convertAndSend(anyString(), any(Object.class));
116+
117+
// when & then
118+
webSocketService.broadcastSystemNotification(notificationDto);
119+
120+
verify(messagingTemplate).convertAndSend(anyString(), any(Object.class));
121+
}
122+
}
123+
124+
@Nested
125+
@DisplayName("스터디룸 알림 전송 테스트")
126+
class SendNotificationToRoomTest {
127+
128+
@Test
129+
@DisplayName("스터디룸 멤버들에게 알림 전송")
130+
void t1() {
131+
// given
132+
Long roomId = 100L;
133+
String expectedDestination = "/topic/room/100/notifications";
134+
NotificationWebSocketDto roomDto = NotificationWebSocketDto.from(
135+
3L,
136+
"스터디룸 알림",
137+
"새 공지사항",
138+
NotificationType.ROOM,
139+
"/room/100",
140+
LocalDateTime.now()
141+
);
142+
143+
// when
144+
webSocketService.sendNotificationToRoom(roomId, roomDto);
145+
146+
// then
147+
verify(messagingTemplate).convertAndSend(
148+
eq(expectedDestination),
149+
eq(roomDto)
150+
);
151+
}
152+
153+
@Test
154+
@DisplayName("전송 실패 시 예외 로깅하고 정상 종료")
155+
void t2() {
156+
// given
157+
Long roomId = 100L;
158+
willThrow(new RuntimeException("룸 전송 실패"))
159+
.given(messagingTemplate)
160+
.convertAndSend(anyString(), any(Object.class));
161+
162+
// when & then
163+
webSocketService.sendNotificationToRoom(roomId, notificationDto);
164+
165+
verify(messagingTemplate).convertAndSend(anyString(), any(Object.class));
166+
}
167+
}
168+
169+
@Nested
170+
@DisplayName("destination 검증 테스트")
171+
class DestinationTest {
172+
173+
@Test
174+
@DisplayName("유저별 알림 경로 정상 생성")
175+
void t1() {
176+
// given
177+
Long userId = 12345L;
178+
179+
// when
180+
webSocketService.sendNotificationToUser(userId, notificationDto);
181+
182+
// then
183+
verify(messagingTemplate).convertAndSend(
184+
eq("/topic/user/12345/notifications"),
185+
any(Object.class)
186+
);
187+
}
188+
189+
@Test
190+
@DisplayName("스터디룸 알림 경로 정상 생성")
191+
void t2() {
192+
// given
193+
Long roomId = 99L;
194+
195+
// when
196+
webSocketService.sendNotificationToRoom(roomId, notificationDto);
197+
198+
// then
199+
verify(messagingTemplate).convertAndSend(
200+
eq("/topic/room/99/notifications"),
201+
any(Object.class)
202+
);
203+
}
204+
205+
@Test
206+
@DisplayName("시스템 알림 경로 정상 생성")
207+
void t3() {
208+
// when
209+
webSocketService.broadcastSystemNotification(notificationDto);
210+
211+
// then
212+
verify(messagingTemplate).convertAndSend(
213+
eq("/topic/notifications/system"),
214+
any(Object.class)
215+
);
216+
}
217+
}
218+
}

0 commit comments

Comments
 (0)