Spring MockMvc 웹 응용 프로그램 컨텍스트에 모의 주입
저는 스프링 부트를 사용하여 REST 서비스 어댑터(JUNit4 및 Spring MockMvc를 통해)를 테스트하는 작업을 하고 있습니다.어댑터는 다른 REST 서비스(사용자 지정 사용)로 요청을 전달합니다.RestTemplate
)을 클릭하고 응답에 추가 데이터를 추가합니다.
달리고 싶습니다MockMvc
컨트롤러 통합 테스트를 수행하기 위한 테스트, 그러나 오버라이드(override)를 원합니다.RestTemplate
제3자 REST 응답을 미리 정의하고 각 테스트 중에 해당 응답이 발생하지 않도록 하기 위한 모의가 있는 컨트롤러에서.저는 이것을 인스턴스화함으로써 달성할 수 있었습니다.MockMvcBuilders.standAloneSetup()
그리고 이 게시물에 나열된 것과 같이 주입된 모의 실험으로 테스트할 컨트롤러(및 아래의 내 설정)를 통과하지만, 나는 다음을 사용하여 동일한 작업을 수행할 수 없습니다.MockMvcBuilders.webAppContextSetup()
.
저는 몇 개의 다른 게시물들을 살펴보았지만, 그 중 어느 것도 이것이 어떻게 달성될 수 있는지에 대한 질문에 답하지 않았습니다.저는 애플리케이션이 성장할 가능성이 높기 때문에 격차를 방지하기 위해 독립 실행형이 아닌 실제 Spring 애플리케이션 컨텍스트를 테스트에 사용하고 싶습니다.
편집: 저는 모키토를 조롱의 틀로 사용하고 있으며 그 중 하나를 맥락에 주입하려고 합니다.만약 이것이 필요하지 않다면, 더욱 좋습니다.
컨트롤러:
@RestController
@RequestMapping(Constants.REQUEST_MAPPING_PATH)
public class Controller{
@Autowired
private DataProvider dp;
@Autowired
private RestTemplate template;
@RequestMapping(value = Constants.REQUEST_MAPPING_RESOURCE, method = RequestMethod.GET)
public Response getResponse(
@RequestParam(required = true) String data,
@RequestParam(required = false, defaultValue = "80") String minScore
) throws Exception {
Response resp = new Response();
// Set the request params from the client request
Map<String, String> parameters = new HashMap<String, String>();
parameters.put(Constants.PARAM_DATA, data);
parameters.put(Constants.PARAM_FORMAT, Constants.PARAMS_FORMAT.JSON);
resp = template.getForObject(Constants.RESTDATAPROVIDER_URL, Response.class, parameters);
if(resp.getError() == null){
resp.filterScoreLessThan(new BigDecimal(minScore));
new DataHandler(dp).populateData(resp.getData());
}
return resp;
}
}
테스트 클래스:
@RunWith(SpringJUnit4ClassRunner.class)
@WebAppConfiguration
@SpringApplicationConfiguration(classes = MainSpringBootAdapter.class)
@TestPropertySource("/application-junit.properties")
public class WacControllerTest {
private static String controllerURL = Constants.REQUEST_MAPPING_PATH + Constants.REQUEST_MAPPING_RESOURCE + compressedParams_all;
private static String compressedParams_all = "?data={data}&minScore={minScore}";
@Autowired
private WebApplicationContext wac;
private MockMvc mockMvc;
@InjectMocks
private Controller Controller;
@Mock
private RestTemplate rt;
@Value("${file}")
private String file;
@Spy
private DataProvider dp;
@Before
public void setup() throws Exception {
dp = new DataProvider(file);
MockitoAnnotations.initMocks(this);
this.mockMvc = MockMvcBuilders.standaloneSetup(controller).build();
}
@Test
public void testGetResponse() throws Exception {
String[] strings = {"requestData", "100"};
Mockito.when(
rt.getForObject(Mockito.<String> any(), Mockito.<Class<Object>> any(), Mockito.<Map<String, ?>> any()))
.thenReturn(populateTestResponse());
mockMvc.perform(get(controllerURL, strings)
.accept(Constants.APPLICATION_JSON_UTF8))
.andDo(MockMvcResultHandlers.print());
Mockito.verify(rt, Mockito.times(1)).getForObject(Mockito.<String> any(), Mockito.<Class<?>> any(), Mockito.<Map<String, ?>> any());
}
private Response populateTestResponse() {
Response resp = new Response();
resp.setScore(new BigDecimal(100));
resp.setData("Some Data");
return resp;
}
}
스프링스MockRestServiceServer
그게 바로 당신이 찾고 있는 것입니다.
클래스의 javadoc에 대한 간단한 설명:
클라이언트 측 REST 테스트를 위한 주 진입점.RestTemplate의 직접 또는 간접(클라이언트 코드를 통해) 사용과 관련된 테스트에 사용됩니다.RestTemplate를 통해 수행될 요청에 대해 세부적인 기대치를 설정하는 방법과 실제 실행 중인 서버의 필요성을 제거하여 다시 보낼 응답을 정의하는 방법을 제공합니다.
테스트를 다음과 같이 설정합니다.
@WebAppConfiguration
@ContextConfiguration(classes = {YourSpringConfig.class})
@RunWith(SpringJUnit4ClassRunner.class)
public class ExampleResourceTest {
private MockMvc mockMvc;
private MockRestServiceServer mockRestServiceServer;
@Autowired
private WebApplicationContext wac;
@Autowired
private RestOperations restOperations;
@Before
public void setUp() throws Exception {
mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).build();
mockRestServiceServer = MockRestServiceServer.createServer((RestTemplate) restOperations);
}
@Test
public void testMyApiCall() throws Exception {
// Following line verifies that our code behind /api/my/endpoint made a REST PUT
// with expected parameters to remote service successfully
expectRestCallSuccess();
this.mockMvc.perform(MockMvcRequestBuilders.get("/api/my/endpoint"))
.andExpect(status().isOk());
}
private void expectRestCallSuccess() {
mockRestServiceServer.expect(
requestTo("http://remote.rest.service/api/resource"))
.andExpect(method(PUT))
.andRespond(withSuccess("{\"message\": \"hello\"}", APPLICATION_JSON));
}
}
여기 또 다른 해결책이 있습니다.간단히 말해서, 그것은 단지 새로운 것을 창조할 뿐입니다.RestTemplate
bean 및 이미 등록된 것을 재정의합니다.
@mzc answer와 동일한 기능을 수행하지만 Mockito를 사용하여 응답 및 검증 매칭을 조금 더 쉽게 만들 수 있습니다.
몇 줄 이상의 코드라는 것은 아니지만, 변환하기 위해 코드를 추가해야 하는 것을 방지합니다.Response
의 " 대한문에대반대한자열"에에 대한 입니다.mockRestServiceServer.expect().andRespond(<String>)
메소드의 arg.
@RunWith(SpringJUnit4ClassRunner.class)
@WebAppConfiguration
@SpringApplicationConfiguration(classes = MainSpringBootAdapter.class)
@TestPropertySource("/application-junit.properties")
public class WacControllerTest {
private static String Controller_URL = Constants.REQUEST_MAPPING_PATH + Constants.REQUEST_MAPPING_RESOURCE + compressedParams_all;
@Configuration
static class Config {
@Bean
@Primary
public RestTemplate restTemplateMock() {
return Mockito.mock(RestTemplate.class);
}
}
@Autowired
private WebApplicationContext wac;
private MockMvc mockMvc;
@InjectMocks
private Controller Controller;
@Mock
private RestTemplate rt;
@Value("${file}")
private String file;
@Spy
private DataProvider dp;
@Before
public void setup() throws Exception {
dp = new DataProvider(file);
MockitoAnnotations.initMocks(this);
this.mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).build();
this.rt = (RestTemplate) this.wac.getBean("restTemplateMock");
}
@Test
public void testGetResponse() throws Exception {
String[] strings = {"request", "100"};
//Set the request params from the client request
Map<String, String> parameters = new HashMap<String, String>();
parameters.put(Constants.PARAM_SINGLELINE, strings[0]);
parameters.put(Constants.PARAM_FORMAT, Constants.PARAMS_FORMAT.JSON);
Mockito.when(
rt.getForObject(Mockito.<String> any(), Mockito.<Class<Object>> any(), Mockito.<Map<String, ?>> any()))
.thenReturn(populateTestResponse());
mockMvc.perform(get(Controller_URL, strings)
.accept(Constants.APPLICATION_JSON_UTF8))
.andDo(MockMvcResultHandlers.print());
Mockito.verify(rt, Mockito.times(1)).getForObject(Mockito.<String> any(), Mockito.<Class<?>> any(), Mockito.<Map<String, ?>> any());
}
private Response populateTestResponse() {
Response resp = new Response();
resp.setScore(new BigDecimal(100));
resp.setData("Some Data");
return resp;
}
}
org.springframework.boot.test.spring.testito.springtitoMockBean @MockBean이 저를 도와줬습니다.
언급URL : https://stackoverflow.com/questions/31819375/inject-mock-into-spring-mockmvc-webapplicationcontext
'programing' 카테고리의 다른 글
파이썬에서 문자열을 타이틀 케이스로 변환하는 방법은 무엇입니까? (0) | 2023.07.19 |
---|---|
예외를 발생시키는 람다 식 정의 (0) | 2023.07.19 |
python을 딕트하기 위한 URL 쿼리 매개 변수 (0) | 2023.07.19 |
날짜/시간별 판다 데이터 프레임 그룹 (0) | 2023.07.19 |
내측 조인 대 내측 조인(선택. 시작) (0) | 2023.07.19 |