feat(files): complete v2 upload sessions

This commit is contained in:
yoyuzh
2026-04-08 15:18:09 +08:00
parent 7ddef9bddb
commit 35b0691188
7 changed files with 129 additions and 1 deletions

View File

@@ -87,6 +87,22 @@ class UploadSessionV2ControllerTest {
.andExpect(jsonPath("$.data.status").value("CREATED"));
}
@Test
void shouldCompleteUploadSessionWithV2Envelope() throws Exception {
User user = createUser(7L);
UploadSession session = createSession(user);
session.setStatus(UploadSessionStatus.COMPLETED);
when(userDetailsService.loadDomainUser("alice")).thenReturn(user);
when(uploadSessionService.completeOwnedSession(user, "session-1")).thenReturn(session);
mockMvc.perform(post("/api/v2/files/upload-sessions/session-1/complete")
.with(user(userDetails())))
.andExpect(status().isOk())
.andExpect(jsonPath("$.code").value(0))
.andExpect(jsonPath("$.data.sessionId").value("session-1"))
.andExpect(jsonPath("$.data.status").value("COMPLETED"));
}
private UserDetails userDetails() {
return org.springframework.security.core.userdetails.User
.withUsername("alice")

View File

@@ -6,6 +6,7 @@ import com.yoyuzh.config.FileStorageProperties;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.ArgumentCaptor;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
@@ -18,7 +19,9 @@ import java.util.Optional;
import static org.assertj.core.api.Assertions.assertThat;
import static org.assertj.core.api.Assertions.assertThatThrownBy;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.when;
import static org.mockito.Mockito.verify;
@ExtendWith(MockitoExtension.class)
class UploadSessionServiceTest {
@@ -27,6 +30,8 @@ class UploadSessionServiceTest {
private UploadSessionRepository uploadSessionRepository;
@Mock
private StoredFileRepository storedFileRepository;
@Mock
private FileService fileService;
private UploadSessionService uploadSessionService;
@@ -37,6 +42,7 @@ class UploadSessionServiceTest {
uploadSessionService = new UploadSessionService(
uploadSessionRepository,
storedFileRepository,
fileService,
properties,
Clock.fixed(Instant.parse("2026-04-08T06:00:00Z"), ZoneOffset.UTC)
);
@@ -91,6 +97,39 @@ class UploadSessionServiceTest {
)).isInstanceOf(BusinessException.class);
}
@Test
void shouldCompleteOwnedSessionThroughLegacyFileCommitPath() {
User user = createUser(7L);
UploadSession session = createSession(user);
when(uploadSessionRepository.findBySessionIdAndUserId("session-1", 7L))
.thenReturn(Optional.of(session));
when(uploadSessionRepository.save(any(UploadSession.class))).thenAnswer(invocation -> invocation.getArgument(0));
UploadSession result = uploadSessionService.completeOwnedSession(user, "session-1");
assertThat(result.getStatus()).isEqualTo(UploadSessionStatus.COMPLETED);
assertThat(result.getUpdatedAt()).isEqualTo(LocalDateTime.of(2026, 4, 8, 6, 0));
ArgumentCaptor<CompleteUploadRequest> requestCaptor = ArgumentCaptor.forClass(CompleteUploadRequest.class);
verify(fileService).completeUpload(eq(user), requestCaptor.capture());
assertThat(requestCaptor.getValue().path()).isEqualTo("/docs");
assertThat(requestCaptor.getValue().filename()).isEqualTo("movie.mp4");
assertThat(requestCaptor.getValue().storageName()).isEqualTo("blobs/session-1");
assertThat(requestCaptor.getValue().contentType()).isEqualTo("video/mp4");
assertThat(requestCaptor.getValue().size()).isEqualTo(20L);
}
@Test
void shouldRejectCompletingCancelledSession() {
User user = createUser(7L);
UploadSession session = createSession(user);
session.setStatus(UploadSessionStatus.CANCELLED);
when(uploadSessionRepository.findBySessionIdAndUserId("session-1", 7L))
.thenReturn(Optional.of(session));
assertThatThrownBy(() -> uploadSessionService.completeOwnedSession(user, "session-1"))
.isInstanceOf(BusinessException.class);
}
private User createUser(Long id) {
User user = new User();
user.setId(id);
@@ -100,4 +139,23 @@ class UploadSessionServiceTest {
user.setCreatedAt(LocalDateTime.now());
return user;
}
private UploadSession createSession(User user) {
UploadSession session = new UploadSession();
session.setSessionId("session-1");
session.setUser(user);
session.setTargetPath("/docs");
session.setFilename("movie.mp4");
session.setContentType("video/mp4");
session.setSize(20L);
session.setObjectKey("blobs/session-1");
session.setChunkSize(8L * 1024 * 1024);
session.setChunkCount(1);
session.setUploadedPartsJson("[]");
session.setStatus(UploadSessionStatus.CREATED);
session.setCreatedAt(LocalDateTime.of(2026, 4, 8, 6, 0));
session.setUpdatedAt(LocalDateTime.of(2026, 4, 8, 6, 0));
session.setExpiresAt(LocalDateTime.of(2026, 4, 9, 6, 0));
return session;
}
}