java - 在 SpringBoot 应用之外使用 MockMVC

标签 java rest spring-mvc mockito spring-test-mvc

我有一个应用程序使用 Spring MVC 来运行 REST 服务(没有 Spring Boot)。上下文主要是从父级加载的。 我有一个 Controller ,我想通过 MockMvc 测试它。

我曾尝试手动设置本地测试上下文,但这不足以运行测试。我想,应该还有我没有设置的额外 bean。

我的 Controller 是:

@RestController
public class ProrertyEditorController extends AbstractPropertyEditorController {
     
    @Autowired
    protected PropertyEditorService prorertyEditorService;

    @RequestMapping(method = RequestMethod.DELETE, value = "/{dataType}/deletewithcontent")
    @ResponseStatus(value = HttpStatus.OK)
    public void deleteWithContent(@PathVariable("dataType") String dataType, @RequestParam("deleteall") boolean deleteAllContent, @RequestBody String node) {
        try {
            JSONArray itemsToDelete = new JSONArray(node);
            prorertyEditorService.deleteItemsWithContent(dataType, itemsToDelete, deleteAllContent);
        } catch (Exception e) {
        //handling exception
        }
    }
}

到目前为止, Controller 的测试如下所示:

@RunWith(SpringJUnit4ClassRunner.class)
@WebAppConfiguration
@ContextConfiguration("classpath*:configBeans1.xml")
public class ProrertyEditorControllerTest{
    private MockMvc mockMvc;

    @Mock
    private PropertyEditorService mockService;
    @InjectMocks
    private ProrertyEditorController controller;

    @Before
    public void setup() {
        mockMvc = MockMvcBuilders.standaloneSetup(new ProrertyEditorController()).build();
    }

    @Test
    public void deleteWithContentTest() throws Exception {
        mockMvc.perform(delete("/full/path/{dataType}/deletewithcontent", type)
                .param("deleteall", "true")
                .param("node", "[{\"test key1\":\"test value1\"}, {\"test keys2\":\"test value2\"}]"));

        verify(mockService, times(1)).deleteItemsWithContent(eq("promotion"), eq(new JSONArray("[{\"test key1\":\"test value1\"}, {\"test keys2\": \"test value2\"}]")), eq(true));
    }
}

不幸的是,由于 Failed to load ApplicationContext 并且没有创建 bean,它无法工作。

PS有一个选项可以使用

MockHttpServletRequest request = new MockHttpServletRequest();
MockHttpServletResponse response = new MockHttpServletResponse();

然而,它可能需要重构 Controller 方法。

最佳答案

事实证明,完全可以做到。启动它只需要一些配置。

  1. 您的 pom.xml 中需要 spring-test:

     <dependency>
         <groupId>org.springframework</groupId>
         <artifactId>spring-test</artifactId>
         <scope>test</scope>
     </dependency>
    
  2. 创建一个 testContext.xml 文件。就我而言,它实际上是空的:

     <?xml version="1.0" encoding="UTF-8"?>
     <beans xmlns="http://www.springframework.org/schema/beans"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://www.springframework.org/schema/beans 
     http://www.springframework.org/schema/beans/spring-beans.xsd">
    
     </beans>
    

    尽管如此,它仍然是必需的,否则 MockMVC 将不会启动,因为没有上下文。

  3. 使用以下注释配置您的 ControllerTest 类:

     @RunWith(SpringJUnit4ClassRunner.class)
     @ContextConfiguration(locations = "classpath*:testContextConfig.xml")
     @WebAppConfiguration
     public class ControllerTest {        ...    }
    

    如果没有 @ContextConfigurationMockMVC 将无法工作。

  4. @Before方法中创建一个MockMVC实例:

     private MockMvc mockMvc;
    
     @Mock
     private Service mockService;
    
     @Before
     public void setup() {
         MockitoAnnotations.initMocks(this);
         mockMvc = MockMvcBuilders.standaloneSetup(new Controller(mockService))
                 .setHandlerExceptionResolvers(exceptionResolver()) //crucial for standaloneSetup of MockMVC
                 .build();
     }
    

    据我所知,setHandlerExceptionResolversmockMVC 设置的关键部分。

关于java - 在 SpringBoot 应用之外使用 MockMVC,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43145408/

相关文章:

使用 @RequestHeader 的 Spring : How do I know where a query comes from? (值 = "User-Agent")

java - 调用birt报告时不支持请求方法 'POST'

java - 如何让我的按钮切换而不循环?

java - Spring Data MongoDB 错误

java - JAX-RS 多态 POST 请求 : how should I write my JSON?

c# - C# 中的 REST Web 服务

java - 当我将代码从一个应用程序移动到另一个应用程序时,用于编辑 Google 电子表格的 Android 应用程序崩溃

java - 如何在我的小程序中加载并显示远程 jar 小程序?

java - 如何使用 String 的 Controller 和 RestTemplate 设置多个参数?

java - 最佳选择 - Spring XML 解析以读取某些元素