我在我的应用程序的控制器中运行一个单元测试,我得到了一个NullPointerException。
控制器:
@RestController
@CrossOrigin
@RequestMapping("/api/users")
public class UserMigrationController {
UserService userService;
@Value("${SOURCE_DNS}")
private String sourceDns;
@Autowired
public UserMigrationController(UserRepository userRepository, DocumentRepository documentRepository) {
userService = new UserService(userRepository, documentRepository);
}
@GetMapping(value = "/getUsers", produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<List<UserData>> getUsersForList() throws Exception {
List<UsersData> usersDataList = UserService.getUsersForList();
return new ResponseEntity<>(usersDataList, HttpStatus.OK);
}
}
UserData只是一个简单的
public record UserData(String id, String name) {
}
这是我的测试类:
@AutoConfigureMockMvc
class UserMigrationControllerTest {
@Autowired
private MockMvc mockMvc;
@MockBean
private UserService userService;
@BeforeEach
void setup() {
MockitoAnnotations.openMocks(this);
}
@Test
void should_get_users_for_list() throws Exception {
String id = "id";
String name = "name";
UserData userData = new UserData(id, name);
List<UserData> response = new ArrayList<>();
response.add(userData);
when(userService.getUsersForList())
.thenReturn(response);
mockMvc.perform(
MockMvcRequestBuilders.get("/api/users/getUsers")
.contentType(MediaType.APPLICATION_JSON)
.accept("application/json"))
.andExpect(MockMvcResultMatchers.status().isOk());
}
正如我所看到的,所有的注解都在正确的位置。但是当我运行一个测试时,我得到了如下的NullPointerException:
Cannot invoke "com.package.usersapi.service.UserService.getUsersForList()" because "this.userService" is null
2条答案
按热度按时间zpgglvta1#
我会作出以下修订:
1.在产品代码中:将UserService注入到控制器中,而不是在构造函数中创建一个:
当前您没有与您在测试中创建的mock进行交互。UserService必须是一个springbean-用
@Service
注解它应该可以完成这项工作。1.您在测试中使用了错误的注解。对于此类测试,@WebMvcTest是理想的选择:
请参阅:使用@WebMvcTest进行单元测试
注意:您不再需要调用
MockitoAnnotations.openMocks
ghg1uchk2#
事实上,我需要从Controller类的构造函数模拟存储库。测试类应该如下所示:
谢谢您的建议!