Skip to content

Commit 516245f

Browse files
committed
feat: 테스트 코드 작성
1 parent 8fef4c6 commit 516245f

3 files changed

Lines changed: 63 additions & 9 deletions

File tree

src/main/java/com/codereferee/codereferee_server/infrastructure/redis/ResultQueueConsumer.java

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
import com.codereferee.codereferee_server.domain.validation.AgentStep;
44
import com.codereferee.codereferee_server.domain.validation.TaskStatus;
5+
import com.codereferee.codereferee_server.domain.validation.TaskStatusHistoryRepository;
56
import com.codereferee.codereferee_server.domain.validation.TaskStatusRepository;
67
import com.codereferee.codereferee_server.infrastructure.metrics.PipelineMetrics;
78
import com.codereferee.codereferee_server.infrastructure.persistence.TaskStatusPgRepository;
@@ -37,7 +38,7 @@ public class ResultQueueConsumer {
3738

3839
private final RedisTemplate<String, Object> redisTemplate;
3940
private final TaskStatusRepository taskStatusRepository;
40-
private final TaskStatusPgRepository pgRepository;
41+
private final TaskStatusHistoryRepository historyRepository;
4142
private final PipelineMetrics pipelineMetrics;
4243
private final ObjectMapper objectMapper;
4344

@@ -91,18 +92,21 @@ private void handleProgress(ProgressEventMessage event) {
9192
Optional<AgentStep> stepOpt = event.resolveStep();
9293
if (taskId == null || stepOpt.isEmpty()) {
9394
log.warn("[ResultQueue] 잘못된 이벤트 상태는 무시됩니다. taskId = {}, step = {}", taskId, event.step());
95+
return;
9496
}
9597

9698
Optional<TaskStatus> currentOpt = taskStatusRepository.findById(taskId);
9799
if (currentOpt.isEmpty()) {
98100
log.warn("[ResultQueue] 알 수 없는 taskId는 무시됩니다. taskId = {}", taskId);
101+
return;
99102
}
100103

101104
TaskStatus current = currentOpt.get();
102105

103106
// 종결 후 늦게 도착한 progress는 무시한다.
104107
if (current.currentAgent().isTerminal()) {
105108
log.info("[ResultQueue] taskID = {} 는 이미 {} 상태로 확정되었습니다. {} 상태는 무시됩니다.", taskId, current.currentAgent(), event.step());
109+
return;
106110
}
107111

108112
AgentStep step = stepOpt.get();
@@ -114,7 +118,7 @@ private void handleProgress(ProgressEventMessage event) {
114118
}
115119

116120
taskStatusRepository.save(updated);
117-
pgRepository.upsert(updated);
121+
historyRepository.upsert(updated);
118122

119123
log.info("ResultQueue taskId = {} 상태 -> {}{}", taskId, step, event.round() != null ?
120124
" (round " + event.round() + " / " + event.maxRounds() + ")" : "");
@@ -139,7 +143,7 @@ private void handleResult(SandboxResultMessage msg) {
139143
pipelineMetrics.recordTransition(current.currentAgent(), verdict);
140144
pipelineMetrics.recordVerdict(verdict);
141145
taskStatusRepository.save(updated);
142-
pgRepository.upsert(updated);
146+
historyRepository.upsert(updated);
143147

144148
log.info("[ResultQueue] taskId = {} -> {} reports = {}", taskId, verdict, aiReports.keySet());
145149
}

src/test/java/com/codereferee/codereferee_server/MockE2ePipelineTest.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ void failRepositoryEndsFailed() {
7777
assertThat(status.get("currentAgent")).isEqualTo("FAILED");
7878
assertThat(status.get("isExecutable")).isEqualTo(false);
7979
assertThat(reports(status)).containsKey("critic_feedback");
80+
assertThat(status.get("iterationCount")).isEqualTo(3);
8081
}
8182

8283
@Test

src/test/java/com/codereferee/codereferee_server/infrastructure/redis/ResultQueueConsumerTest.java

Lines changed: 55 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,20 +16,18 @@
1616
import java.util.Optional;
1717

1818
import static org.assertj.core.api.Assertions.assertThat;
19-
import static org.mockito.Mockito.mock;
20-
import static org.mockito.Mockito.verify;
21-
import static org.mockito.Mockito.when;
19+
import static org.mockito.Mockito.*;
2220

2321
class ResultQueueConsumerTest {
2422

2523
private final TaskStatusRepository taskStatusRepository = mock(TaskStatusRepository.class);
26-
private final TaskStatusHistoryRepository pgRepository = mock(TaskStatusHistoryRepository.class);
24+
private final TaskStatusHistoryRepository historyRepository = mock(TaskStatusHistoryRepository.class);
2725
private final PipelineMetrics pipelineMetrics = new PipelineMetrics(new SimpleMeterRegistry());
2826
private final ObjectMapper objectMapper = new ObjectMapper()
2927
.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
3028
private final ResultQueueConsumer consumer = new ResultQueueConsumer(
3129
mock(org.springframework.data.redis.core.RedisTemplate.class),
32-
taskStatusRepository, pgRepository, pipelineMetrics, objectMapper);
30+
taskStatusRepository, historyRepository, pipelineMetrics, objectMapper);
3331

3432
private TaskStatus queued(String taskId) {
3533
return new TaskStatus(taskId, AgentStep.JUDGING, false, 0, null,
@@ -54,7 +52,7 @@ void successMessageMapsToPassed() {
5452
assertThat(saved.executable()).isTrue();
5553
assertThat(saved.errorMessage()).isNull();
5654
assertThat(saved.aiReports()).containsKey("judge_report");
57-
verify(pgRepository).upsert(saved);
55+
verify(historyRepository).upsert(saved);
5856
}
5957

6058
@Test
@@ -94,4 +92,55 @@ void infraErrorMapsToErrorNotFailed() {
9492
assertThat(saved.currentAgent()).isEqualTo(AgentStep.ERROR);
9593
assertThat(saved.errorMessage()).contains("판정 불가");
9694
}
95+
@Test
96+
void progressEventUpdatesStepAndRound() {
97+
when(taskStatusRepository.findById("t4")).thenReturn(Optional.of(queued("t4")));
98+
99+
consumer.process(Map.of(
100+
"type", "progress",
101+
"request_id", "t4",
102+
"step", "REFINING",
103+
"round", 2,
104+
"max_rounds", 3
105+
));
106+
107+
ArgumentCaptor<TaskStatus> captor = ArgumentCaptor.forClass(TaskStatus.class);
108+
verify(taskStatusRepository).save(captor.capture());
109+
TaskStatus saved = captor.getValue();
110+
111+
assertThat(saved.currentAgent()).isEqualTo(AgentStep.REFINING);
112+
assertThat(saved.iterationCount()).isEqualTo(2);
113+
assertThat(saved.errorMessage()).isNull();
114+
verify(historyRepository).upsert(saved);
115+
}
116+
117+
@Test
118+
void progressAfterTerminalIsIgnored() {
119+
TaskStatus done = new TaskStatus("t5", AgentStep.PASSED, true, 1, null,
120+
LocalDateTime.of(2026, 8, 3, 12, 0), "https://github.com/phdcoco/QuickByte_Demo", "main", "d1c5c5e", null);
121+
when(taskStatusRepository.findById("t5")).thenReturn(Optional.of(done));
122+
123+
consumer.process(Map.of("type", "progress", "request_id", "t5", "step", "BASELINE"));
124+
125+
// 확정된 결과는 늦게 온 progress로 되돌아가지 않는다
126+
verify(taskStatusRepository, never()).save(any());
127+
verify(historyRepository, never()).upsert(any());
128+
}
129+
130+
@Test
131+
void unknownMessageTypeIsIgnored() {
132+
consumer.process(Map.of("type", "heartbeat", "request_id", "t6"));
133+
134+
verify(taskStatusRepository, never()).save(any());
135+
verify(historyRepository, never()).upsert(any());
136+
}
137+
138+
@Test
139+
void unknownStepProgressIsIgnored() {
140+
when(taskStatusRepository.findById("t7")).thenReturn(Optional.of(queued("t7")));
141+
142+
consumer.process(Map.of("type", "progress", "request_id", "t7", "step", "DEPLOYING"));
143+
144+
verify(taskStatusRepository, never()).save(any());
145+
}
97146
}

0 commit comments

Comments
 (0)