面试复盘:Junit 小白入门指南——从面试题到单测实践

面试复盘:Junit 小白入门指南------从面试题到单测实践

在最近一次后端面试中,面试官问了我三个问题:"什么是 Junit?在 Spring Boot 项目中用到了 Junit 吗?你能写一段代码模拟一个接口的单测吗?"作为一名后端开发者,我顺利回答并写出了代码,但事后复盘时发现,有些细节对新手来说可能不太好理解,比如 MockBeanwhen().thenReturn()mockMvc.perform().andExpect() 是啥?这次我就以小白视角,详细复盘这些问题和代码,帮你从零基础搞懂 Junit 单测!

问题 1:什么是 Junit?

简单回答: Junit 是一个专门帮我们测试 Java 代码的工具。就像老师批改作业一样,它能检查你的代码是不是按预期工作。写代码时,我们用 Junit 写"测试用例",运行后就能知道哪里对了,哪里错了。

小白理解

  • 比如你写了个计算器程序,想确认"2 + 2"是不是等于 4,就可以用 Junit 写个测试,自动跑一遍,结果不对就报错。
  • 它靠一些"标记"(注解,比如 @Test)告诉电脑哪些是测试代码,还能用 assertEquals 这种方法检查结果。

面试改进: 面试时我说 Junit 是"单元测试框架",其实可以加一句:"它是 Java 程序员的好帮手,能自动化验证代码,还跟 Spring Boot 配合得特别好!"


问题 2:在 Spring Boot 项目中用到了 Junit 吗?

简单回答: 用到了!Spring Boot 项目里,Junit 是默认的测试工具。我用它测过接口、业务逻辑和数据库操作。

小白理解

  • Spring Boot 是一个开发网站的框架,里面有很多"零件"(比如 Controller、Service),Junit 帮我们检查这些零件单独或一起工作时有没有问题。
  • Spring Boot 自带了个 spring-boot-starter-test 的包,里面就包含 Junit 和其他测试工具,像个"测试套装"。

面试改进: 我会补充:"在 Spring Boot 里,我用 Junit 测试过接口有没有返回正确数据,比如查用户信息时,能不能返回正确的名字和 ID。"


问题 3:写一段代码模拟接口开发的单测

面试要求: 假设我开发了一个查询用户信息的接口,怎么用 Junit 写单测?

代码示例: 我写了一个简单的接口和测试代码,下面是完整版,后面会一步步拆解关键点。

java 复制代码
// UserController.java(接口代码)
@RestController
@RequestMapping("/api/users")
public class UserController {
    private final UserService userService;

    public UserController(UserService userService) {
        this.userService = userService;
    }

    @GetMapping("/{id}")
    public ResponseEntity<User> getUserById(@PathVariable Long id) {
        User user = userService.findUserById(id);
        if (user == null) {
            return ResponseEntity.notFound().build();
        }
        return ResponseEntity.ok(user);
    }
}

// User.java(用户类)
public class User {
    private Long id;
    private String name;

    public User(Long id, String name) {
        this.id = id;
        this.name = name;
    }
    // Getters 和 Setters 省略
}

// UserService.java(服务类)
@Service
public class UserService {
    public User findUserById(Long id) {
        return new User(id, "User-" + id); // 模拟查询
    }
}

// UserControllerTest.java(测试代码)
@SpringBootTest
@AutoConfigureMockMvc
public class UserControllerTest {

    @Autowired
    private MockMvc mockMvc;

    @MockBean
    private UserService userService;

    @Test
    public void testGetUserById_Success() throws Exception {
        Long userId = 1L;
        User mockUser = new User(userId, "User-1");

        when(userService.findUserById(userId)).thenReturn(mockUser);

        mockMvc.perform(get("/api/users/{id}", userId))
               .andExpect(status().isOk())
               .andExpect(jsonPath("$.id").value(userId))
               .andExpect(jsonPath("$.name").value("User-1"));
    }

    @Test
    public void testGetUserById_NotFound() throws Exception {
        Long userId = 999L;
        when(userService.findUserById(userId)).thenReturn(null);

        mockMvc.perform(get("/api/users/{id}", userId))
               .andExpect(status().isNotFound());
    }
}

小白拆解:关键概念详解 这代码里有几个"魔法"操作,新手可能会懵,下面我逐一解释。

1. @MockBean 是什么?

小白理解

  • 想象一下,UserService 是去数据库找数据的"工人"。但测试时,我们不想真去数据库(太麻烦,还可能没数据),怎么办?@MockBean 就像雇了个"假工人",假装干活,实际啥也不干,全听你指挥。
  • 在代码里,@MockBean private UserService userService 告诉 Spring Boot:"别用真的 UserService,给我个假的,我要控制它!"

技术解释

  • @MockBean 是 Spring Boot 测试里的注解,用来创建"模拟对象"(Mock),由 Mockito(一个模拟工具)支持。
  • 它会替换掉 Spring 容器里真正的 UserService,让你自由定义它的行为。

为什么用它

  • 测试接口时,只关心接口逻辑,不想依赖数据库或其他服务,用 @MockBean 隔离依赖。

2. when().thenReturn() 是什么?

小白理解

  • 这个是给"假工人"下指令。比如 when(userService.findUserById(1L)).thenReturn(mockUser),意思是:"嘿,假的 UserService,如果有人问你 ID 是 1 的用户是谁,你就回答这个 mockUser,别干别的!"
  • 就像提前录好答案,测试时直接用。

技术解释

  • when().thenReturn() 是 Mockito 的语法,用来设置模拟对象的行为。
  • when(条件) 定义触发条件,thenReturn(结果) 指定返回值。
  • 比如:when(userService.findUserById(1L)).thenReturn(new User(1L, "User-1")),表示调用 findUserById(1L) 时返回假数据。

为什么用它

  • 控制测试环境,确保每次输入固定值时,输出是我们想要的,方便验证接口逻辑。

3. mockMvc.perform().andExpect() 在做什么?

小白理解

  • MockMvc 就像一个"假浏览器",能假装访问你的接口。
  • perform() 是"发送请求",比如 get("/api/users/1") 就是访问 http://localhost/api/users/1
  • andExpect() 是"检查结果",比如 status().isOk() 确认返回状态是 200,jsonPath("$.name").value("User-1") 检查返回的 JSON 里 name 是不是 "User-1"。

技术解释

  • MockMvc 是 Spring 提供的一个测试工具,用来模拟 HTTP 请求,不用真的启动服务器。
  • perform() 执行请求,andExpect() 链式调用检查响应。
  • 常用检查:
    • status().isOk():状态码 200。
    • status().isNotFound():状态码 404。
    • jsonPath("$.字段").value(值):验证 JSON 数据。

代码例子解析

java 复制代码
mockMvc.perform(get("/api/users/{id}", userId))
       .andExpect(status().isOk())
       .andExpect(jsonPath("$.id").value(userId))
       .andExpect(jsonPath("$.name").value("User-1"));
  • 这段代码假装访问 /api/users/1,然后检查:
    1. 状态码是不是 200(成功)。
    2. 返回的 JSON 里 id 是不是 1。
    3. name 是不是 "User-1"。

为什么用它

  • 测试接口时,模拟真实请求,检查返回结果是不是我们想要的,比直接调用方法更贴近用户体验。

复盘与新手建议

面试表现反思

  • 我回答了 Junit 的基本概念,也写出了代码,但没解释清楚这些"魔法"工具。对新手来说,这些细节很重要。
  • 改进版回答:"Junit 是测试代码的工具,在 Spring Boot 里我用它测接口。像上面代码,我用 @MockBean 造了个假服务,用 when().thenReturn() 控制返回值,再用 MockMvc 假装访问接口,最后检查结果。"

给小白的建议

  1. 从简单开始 :先写个 @Test 方法,用 assertEquals 测试加法,跑通了再试复杂点的。
  2. 理解 Mock :把 @MockBean 想象成"替身演员",帮你省去麻烦的依赖。
  3. 多练 MockMvc :写个小接口,用 perform()andExpect() 测几次,熟悉检查状态码和 JSON。
  4. 工具配合:Junit 常跟 Mockito 和 Spring Test 一起用,别怕,慢慢学。

完整学习路径

  • 下载个 Spring Boot 项目,加 spring-boot-starter-test 依赖。
  • 照着上面代码改改,跑跑看,熟悉报错和成功的感觉。

总结

这次面试让我意识到,Junit 不只是个工具,它背后还有很多"小助手"(像 Mockito 和 MockMvc)。对新手来说,理解 @MockBean 是造假对象、when().thenReturn() 是定规则、mockMvc.perform().andExpect() 是发请求检查结果,就能轻松上手单测。希望这篇博客能帮你搞懂 Junit,下次面试不慌!

相关推荐
uzong2 小时前
技术故障复盘模版
后端
GetcharZp2 小时前
基于 Dify + 通义千问的多模态大模型 搭建发票识别 Agent
后端·llm·agent
桦说编程3 小时前
Java 中如何创建不可变类型
java·后端·函数式编程
IT毕设实战小研3 小时前
基于Spring Boot 4s店车辆管理系统 租车管理系统 停车位管理系统 智慧车辆管理系统
java·开发语言·spring boot·后端·spring·毕业设计·课程设计
wyiyiyi3 小时前
【Web后端】Django、flask及其场景——以构建系统原型为例
前端·数据库·后端·python·django·flask
阿华的代码王国4 小时前
【Android】RecyclerView复用CheckBox的异常状态
android·xml·java·前端·后端
Jimmy4 小时前
AI 代理是什么,其有助于我们实现更智能编程
前端·后端·ai编程
AntBlack5 小时前
不当韭菜V1.1 :增强能力 ,辅助构建自己的交易规则
后端·python·pyqt
bobz9655 小时前
pip install 已经不再安全
后端
寻月隐君6 小时前
硬核实战:从零到一,用 Rust 和 Axum 构建高性能聊天服务后端
后端·rust·github