我有一个发布事件的控制器
@RestController
public class Controller
{
@Autowired
private ApplicationEventPublisher publisher;
@GetMapping("/event")
public void get()
{
publisher.publishEvent(new Event());
}
}
现在,我想测试事件是否已发布。首先,我尝试@MockBean ApplicationEventPublisher并验证方法调用。但这根据https://jira.spring.io/browse/SPR-14335
不起作用所以我是这样做的:
@RunWith(SpringRunner.class)
@WebMvcTest(controllers = Controller.class)
public class ControllerTest
{
@Autowired
private MockMvc mockMvc;
@Test
public void getTest() throws Exception
{
this.mockMvc.perform(get("/").contentType(MediaType.APPLICATION_JSON)
.andExpect(status().isOk());
assertNotNull(Listener.event);
}
@TestConfiguration
static class Listener
{
public static Event event;
@EventListener
void listen ( Event incoming )
{
event = incoming;
}
}
}
这种常见用例是否有更简单的方法?
答案 0 :(得分:2)
您可以这样做
@RunWith(SpringRunner.class)
public class ControllerTest {
private MockMvc mockMvc;
@MockBean
private ApplicationEventPublisher publisher;
@Before
public void setup() {
Controller someController= new Controller(publisher);
mockMvc = MockMvcBuilders.standaloneSetup(someController).build();
}
@Test
public void getTest() throws Exception
{
ArgumentCaptor<Event> argumentCaptor = ArgumentCaptor.forClass(Event.class);
doAnswer(invocation -> {
Event value = argumentCaptor.getValue();
//assert if event is correct
return null;
}).when(publisher).publishEvent(argumentCaptor.capture());
this.mockMvc.perform(get("/").contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk());
verify(publisher, times(1)).publishEvent(any(Event.class));
}
}
并在您的控制器类中将“字段注入”更改为“构造函数注入”(这是一个好习惯)。
@RestController
public class Controller
{
private ApplicationEventPublisher publisher;
@Autowired
public Controller(ApplicationEventPublisher publisher) {
this.publisher = publisher;
}
....
}
答案 1 :(得分:0)
我面临同样的问题,现在我使用 TestConfiguration 解决了这个问题:
@SpringBootTest
class MyUseCaseIT {
@Autowired private ApplicationEventPublisher publisher;
@Autowired private MyService service;
@Test
void callUseCase() {
var event = mock(MyEvent.class);
doNothing().when(publisher).publishEvent(event);
service.useCase();
verify(publisher).publishEvent(event);
}
@TestConfiguration
static class MockitoPublisherConfiguration {
@Bean
@Primary
ApplicationEventPublisher publisher() {
return mock(ApplicationEventPublisher.class);
}
}