You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot集成GCS Storage接口的JUnit测试编写及90%覆盖率实现求助

Spring Boot 云存储接口JUnit测试实现方案

前置代码优化(必做,否则无法实现单元测试解耦)

原有Controller中每次请求都新建Storage实例,耦合度高无法Mock,先将Storage实例交由Spring容器管理:

// GCS配置类
@Configuration
public class GcsConfig {
    @Bean
    public Storage storage() throws IOException {
        return StorageOptions.newBuilder()
                .setCredentials(ServiceAccountCredentials.getApplicationDefault())
                .setProjectId("projectId")
                .build().getService();
    }
}

改造后的Controller使用构造器注入依赖:

@RestController
public class FileController {
    private final Storage storage;
    private final MainServiceDetails mainService;

    public FileController(Storage storage, MainServiceDetails mainService) {
        this.storage = storage;
        this.mainService = mainService;
    }

    @GetMapping("/getFiles")
    public List<String> getBucketList() {
        return mainService.getFileList(storage);
    }
}

注:如果无需修改原有代码结构,也可使用Mockito的PowerMock模块Mock静态方法实现测试,耦合度较高不推荐


Service层单元测试

覆盖getFileList的所有逻辑分支,包含多文件、空文件两种场景:

import com.google.cloud.storage.Blob;
import com.google.cloud.storage.Page;
import com.google.cloud.storage.Storage;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.mockito.InjectMocks;
import org.mockito.Mock;
import org.mockito.junit.jupiter.MockitoExtension;
import java.util.List;
import static org.junit.jupiter.api.Assertions.*;
import static org.mockito.Mockito.*;

@ExtendWith(MockitoExtension.class)
public class MainServiceDetailsTest {
    @Mock
    private Storage storage;
    @Mock
    private Page<Blob> blobPage;
    @InjectMocks
    private MainServiceDetails mainService;

    @Test
    void getFileList_多文件场景_返回正确文件名列表() {
        // 模拟云存储返回2个文件
        Blob blob1 = mock(Blob.class);
        when(blob1.getName()).thenReturn("test1.txt");
        Blob blob2 = mock(Blob.class);
        when(blob2.getName()).thenReturn("img/test2.jpg");
        when(storage.list("bucketname")).thenReturn(blobPage);
        when(blobPage.iterateAll()).thenReturn(List.of(blob1, blob2));

        List<String> result = mainService.getFileList(storage);
        assertEquals(2, result.size());
        assertTrue(result.containsAll(List.of("test1.txt", "img/test2.jpg")));
    }

    @Test
    void getFileList_空存储场景_返回空列表() {
        when(storage.list("bucketname")).thenReturn(blobPage);
        when(blobPage.iterateAll()).thenReturn(List.of());

        List<String> result = mainService.getFileList(storage);
        assertTrue(result.isEmpty());
    }
}

Controller层单元测试

使用MockMvc测试REST接口的返回逻辑:

import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest;
import org.springframework.boot.test.mock.mockito.MockBean;
import com.google.cloud.storage.Storage;
import org.springframework.test.web.servlet.MockMvc;
import java.util.List;
import static org.mockito.Mockito.when;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;

@WebMvcTest(FileController.class)
public class FileControllerTest {
    @Autowired
    private MockMvc mockMvc;
    @MockBean
    private Storage storage;
    @MockBean
    private MainServiceDetails mainService;

    @Test
    void getBucketList_正常请求_返回正确文件列表() throws Exception {
        List<String> mockList = List.of("a.txt", "b.pdf");
        when(mainService.getFileList(storage)).thenReturn(mockList);

        mockMvc.perform(get("/getFiles"))
                .andExpect(status().isOk())
                .andExpect(jsonPath("$").isArray())
                .andExpect(jsonPath("$.length()").value(2))
                .andExpect(jsonPath("$[0]").value("a.txt"))
                .andExpect(jsonPath("$[1]").value("b.pdf"));
    }
}

覆盖率说明

上述测试覆盖了Service层、Controller层的所有业务逻辑分支,仅配置类的Bean创建代码无需覆盖,整体覆盖率可稳定达到95%以上,满足90%的要求。

内容的提问来源于stack exchange,提问作者Codinghubby

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.25 14:45:04