feat: extend operation log service and repository with pagination support
This commit is contained in:
@@ -35,6 +35,11 @@
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.projectreactor</groupId>
|
||||
<artifactId>reactor-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
<build>
|
||||
@@ -69,6 +74,26 @@
|
||||
</annotationProcessorPaths>
|
||||
</configuration>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.jacoco</groupId>
|
||||
<artifactId>jacoco-maven-plugin</artifactId>
|
||||
<version>0.8.12</version>
|
||||
<executions>
|
||||
<execution>
|
||||
<id>prepare-agent</id>
|
||||
<goals>
|
||||
<goal>prepare-agent</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
<execution>
|
||||
<id>report</id>
|
||||
<phase>verify</phase>
|
||||
<goals>
|
||||
<goal>report</goal>
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</project>
|
||||
|
||||
+1
@@ -0,0 +1 @@
|
||||
cn.novalon.manage.notify.config.WebSocketConfig
|
||||
+252
@@ -0,0 +1,252 @@
|
||||
package cn.novalon.manage.notify.handler;
|
||||
|
||||
import cn.novalon.manage.notify.core.domain.SysNotice;
|
||||
import cn.novalon.manage.notify.core.service.ISysNoticeService;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.mock.web.reactive.function.server.MockServerRequest;
|
||||
import org.springframework.web.reactive.function.server.ServerRequest;
|
||||
import org.springframework.web.reactive.function.server.ServerResponse;
|
||||
import reactor.core.publisher.Flux;
|
||||
import reactor.core.publisher.Mono;
|
||||
import reactor.test.StepVerifier;
|
||||
|
||||
import java.time.LocalDateTime;
|
||||
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.ArgumentMatchers.anyLong;
|
||||
import static org.mockito.ArgumentMatchers.anyString;
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
class SysNoticeHandlerTest {
|
||||
|
||||
@Mock
|
||||
private ISysNoticeService noticeService;
|
||||
|
||||
private SysNoticeHandler noticeHandler;
|
||||
private SysNotice testNotice;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
noticeHandler = new SysNoticeHandler(noticeService);
|
||||
|
||||
testNotice = new SysNotice();
|
||||
testNotice.setId(1L);
|
||||
testNotice.setNoticeTitle("系统维护通知");
|
||||
testNotice.setNoticeType("SYSTEM");
|
||||
testNotice.setNoticeContent("系统将于今晚进行维护");
|
||||
testNotice.setStatus("PUBLISHED");
|
||||
testNotice.setCreateBy("admin");
|
||||
testNotice.setCreatedAt(LocalDateTime.now());
|
||||
}
|
||||
|
||||
@Test
|
||||
void testGetAllNotices() {
|
||||
when(noticeService.getAllNotices()).thenReturn(Flux.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder().build();
|
||||
Mono<ServerResponse> response = noticeHandler.getAllNotices(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).getAllNotices();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testGetNoticeById() {
|
||||
when(noticeService.getNoticeById(1L)).thenReturn(Mono.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "1")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.getNoticeById(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).getNoticeById(1L);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testGetNoticeById_NotFound() {
|
||||
when(noticeService.getNoticeById(999L)).thenReturn(Mono.empty());
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "999")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.getNoticeById(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.NOT_FOUND)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).getNoticeById(999L);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testGetNoticesByStatus() {
|
||||
when(noticeService.getNoticesByStatus("PUBLISHED")).thenReturn(Flux.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("status", "PUBLISHED")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.getNoticesByStatus(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).getNoticesByStatus("PUBLISHED");
|
||||
}
|
||||
|
||||
@Test
|
||||
void testGetNoticesByStatus_Draft() {
|
||||
when(noticeService.getNoticesByStatus("DRAFT")).thenReturn(Flux.empty());
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("status", "DRAFT")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.getNoticesByStatus(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).getNoticesByStatus("DRAFT");
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateNotice() {
|
||||
SysNotice newNotice = new SysNotice();
|
||||
newNotice.setNoticeTitle("新通知");
|
||||
newNotice.setNoticeType("SYSTEM");
|
||||
newNotice.setNoticeContent("测试内容");
|
||||
newNotice.setStatus("DRAFT");
|
||||
|
||||
when(noticeService.createNotice(any(SysNotice.class))).thenReturn(Mono.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.body(Mono.just(newNotice));
|
||||
Mono<ServerResponse> response = noticeHandler.createNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).createNotice(any(SysNotice.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testCreateNotice_WithAllFields() {
|
||||
SysNotice newNotice = new SysNotice();
|
||||
newNotice.setNoticeTitle("完整通知");
|
||||
newNotice.setNoticeType("ANNOUNCEMENT");
|
||||
newNotice.setNoticeContent("完整内容");
|
||||
newNotice.setStatus("PUBLISHED");
|
||||
newNotice.setCreateBy("admin");
|
||||
|
||||
when(noticeService.createNotice(any(SysNotice.class))).thenReturn(Mono.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.body(Mono.just(newNotice));
|
||||
Mono<ServerResponse> response = noticeHandler.createNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).createNotice(any(SysNotice.class));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testUpdateNotice() {
|
||||
SysNotice updateNotice = new SysNotice();
|
||||
updateNotice.setNoticeTitle("更新后的通知");
|
||||
updateNotice.setNoticeType("SYSTEM");
|
||||
updateNotice.setNoticeContent("更新后的内容");
|
||||
updateNotice.setStatus("PUBLISHED");
|
||||
|
||||
when(noticeService.updateNotice(anyLong(), any(SysNotice.class))).thenReturn(Mono.just(testNotice));
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "1")
|
||||
.body(Mono.just(updateNotice));
|
||||
Mono<ServerResponse> response = noticeHandler.updateNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).updateNotice(1L, updateNotice);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testUpdateNotice_NotFound() {
|
||||
SysNotice updateNotice = new SysNotice();
|
||||
updateNotice.setNoticeTitle("更新后的通知");
|
||||
|
||||
when(noticeService.updateNotice(anyLong(), any(SysNotice.class))).thenReturn(Mono.empty());
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "999")
|
||||
.body(Mono.just(updateNotice));
|
||||
Mono<ServerResponse> response = noticeHandler.updateNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.NOT_FOUND)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).updateNotice(999L, updateNotice);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testDeleteNotice() {
|
||||
when(noticeService.deleteNotice(1L)).thenReturn(Mono.empty());
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "1")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.deleteNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).deleteNotice(1L);
|
||||
}
|
||||
|
||||
@Test
|
||||
void testDeleteNotice_NotFound() {
|
||||
when(noticeService.deleteNotice(999L)).thenReturn(Mono.empty());
|
||||
|
||||
ServerRequest request = MockServerRequest.builder()
|
||||
.pathVariable("id", "999")
|
||||
.build();
|
||||
Mono<ServerResponse> response = noticeHandler.deleteNotice(request);
|
||||
|
||||
StepVerifier.create(response)
|
||||
.expectNextMatches(serverResponse ->
|
||||
serverResponse.statusCode() == HttpStatus.OK)
|
||||
.verifyComplete();
|
||||
|
||||
verify(noticeService).deleteNotice(999L);
|
||||
}
|
||||
}
|
||||
+181
@@ -0,0 +1,181 @@
|
||||
package cn.novalon.manage.notify.websocket;
|
||||
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.api.extension.ExtendWith;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.junit.jupiter.MockitoExtension;
|
||||
import org.springframework.web.reactive.socket.HandshakeInfo;
|
||||
import org.springframework.web.reactive.socket.WebSocketMessage;
|
||||
import org.springframework.web.reactive.socket.WebSocketSession;
|
||||
import reactor.core.publisher.Flux;
|
||||
import reactor.core.publisher.Mono;
|
||||
import reactor.test.StepVerifier;
|
||||
|
||||
import java.net.URI;
|
||||
|
||||
import static org.mockito.Mockito.*;
|
||||
|
||||
@ExtendWith(MockitoExtension.class)
|
||||
class SysWebSocketHandlerTest {
|
||||
|
||||
@Mock
|
||||
private WebSocketSession session;
|
||||
|
||||
@Mock
|
||||
private WebSocketMessage message;
|
||||
|
||||
@Mock
|
||||
private HandshakeInfo handshakeInfo;
|
||||
|
||||
private SysWebSocketHandler webSocketHandler;
|
||||
|
||||
@BeforeEach
|
||||
void setUp() {
|
||||
webSocketHandler = new SysWebSocketHandler();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_NewConnection() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(session.receive()).thenReturn(Flux.empty());
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_WithUserId() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=123"));
|
||||
when(session.receive()).thenReturn(Flux.empty());
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_WithoutUserId() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws"));
|
||||
when(session.getId()).thenReturn("test-session-id");
|
||||
when(session.receive()).thenReturn(Flux.empty());
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_PongMessage() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(message.getPayloadAsText()).thenReturn("{\"type\":\"pong\"}");
|
||||
when(session.receive()).thenReturn(Flux.just(message));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
verify(message).getPayloadAsText();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_SubscribeMessage() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(message.getPayloadAsText()).thenReturn("{\"type\":\"subscribe\"}");
|
||||
when(session.receive()).thenReturn(Flux.just(message));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
verify(message).getPayloadAsText();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_HeartbeatMessage() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(message.getPayloadAsText()).thenReturn("{\"type\":\"heartbeat\"}");
|
||||
when(session.receive()).thenReturn(Flux.just(message));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
verify(message).getPayloadAsText();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_UnknownMessageType() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(message.getPayloadAsText()).thenReturn("{\"type\":\"unknown\"}");
|
||||
when(session.receive()).thenReturn(Flux.just(message));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
verify(message).getPayloadAsText();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_InvalidJson() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(message.getPayloadAsText()).thenReturn("invalid json");
|
||||
when(session.receive()).thenReturn(Flux.just(message));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyComplete();
|
||||
|
||||
verify(session).receive();
|
||||
verify(message).getPayloadAsText();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testHandle_SessionError() {
|
||||
when(session.getHandshakeInfo()).thenReturn(handshakeInfo);
|
||||
when(handshakeInfo.getUri()).thenReturn(URI.create("ws://localhost/ws?userId=testuser"));
|
||||
when(session.receive()).thenReturn(Flux.error(new RuntimeException("Connection error")));
|
||||
|
||||
Mono<Void> result = webSocketHandler.handle(session);
|
||||
|
||||
StepVerifier.create(result)
|
||||
.verifyError();
|
||||
|
||||
verify(session).receive();
|
||||
}
|
||||
|
||||
@Test
|
||||
void testSendMessageToUser_SessionNotFound() {
|
||||
webSocketHandler.sendMessageToUser("nonexistent", java.util.Map.of("type", "notification", "message", "test"));
|
||||
|
||||
verify(session, never()).send(any());
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user