Тестирование сопоставлений аннотаций Spring MVC - PullRequest
19 голосов
/ 14 мая 2009

В Spring MVC вы можете указать, что определенный URL-адрес будет обрабатываться определенным методом, и вы можете указать, что конкретные параметры будут сопоставляться с определенными аргументами, например:

@Controller
public class ImageController {

   @RequestMapping("/getImage")
   public String getImage( @RequestParam("imageId") int imageId, Map<String,Object> model ) {
      model.put("image",ImageService.getImage(imageId));
   }

}

Это все хорошо, но теперь я хочу проверить, что http-запрос с параметром imageId правильно вызовет этот метод. Другими словами, мне нужен тест, который будет нарушен, если я удалю или изменю любую из аннотаций. Есть ли способ сделать это?

Легко проверить, что getImage работает правильно. Я мог бы просто создать ImageController и вызвать getImage с соответствующими аргументами. Однако это только одна половина теста. Другая половина теста должна заключаться в том, будет ли getImage () вызываться средой Spring при поступлении соответствующего HTTP-запроса. Мне кажется, что мне также нужен тест для этой части, особенно когда мои @RequestMapping аннотации становятся более сложными вызвать сложные условия параметра.

Не могли бы вы показать мне тест, который сломается, если я уберу строку 4, @RequestMapping("getImage")?

Ответы [ 2 ]

13 голосов
/ 15 мая 2009

Вы можете использовать AnnotationMethodHandlerAdapter и его метод handle программно. Это разрешит метод для данного запроса и выполнит его. К сожалению, это немного косвенно. На самом деле в AMHA есть закрытый класс с именем ServletHandlerMethodResolver, который отвечает только за разрешение метода для данного запроса. Я только что подал запрос на улучшение по этой теме, поскольку я действительно хотел бы, чтобы это тоже было возможно.

Тем временем вы можете использовать, например, EasyMock , чтобы создать макет вашего класса контроллера, ожидать, что данный метод будет вызван, и передать это макет handle.

Контроллер:

@Controller
public class MyController {

  @RequestMapping("/users")
  public void foo(HttpServletResponse response) {

    // your controller code
  }
}

Тест:

public class RequestMappingTest {

  private MockHttpServletRequest request;
  private MockHttpServletResponse response;
  private MyController controller;
  private AnnotationMethodHandlerAdapter adapter;


  @Before
  public void setUp() {

    controller = EasyMock.createNiceMock(MyController.class);

    adapter = new AnnotationMethodHandlerAdapter();
    request = new MockHttpServletRequest();
    response = new MockHttpServletResponse();
  }


  @Test
  public void testname() throws Exception {

    request.setRequestURI("/users");

    controller.foo(response);
    EasyMock.expectLastCall().once();
    EasyMock.replay(controller);

    adapter.handle(request, response, controller);

    EasyMock.verify(controller);
  }
}

С уважением, Олли

7 голосов
/ 16 марта 2010

Решение Олли охватывает тестирование конкретного примера аннотации, но как насчет более широкого вопроса о том, как протестировать все другие различные аннотации Spring MVC. Мой подход (который можно легко распространить на другие аннотации) был бы

import static org.springframework.test.web.ModelAndViewAssert.*;

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration({/* include live config here
    e.g. "file:web/WEB-INF/application-context.xml",
    "file:web/WEB-INF/dispatcher-servlet.xml" */})
public class MyControllerIntegrationTest {

    @Inject
    private ApplicationContext applicationContext;

    private MockHttpServletRequest request;
    private MockHttpServletResponse response;
    private HandlerAdapter handlerAdapter;
    private MyController controller;

    @Before
    public void setUp() {
       request = new MockHttpServletRequest();
       response = new MockHttpServletResponse();
       handlerAdapter = applicationContext.getBean(HandlerAdapter.class);
       // I could get the controller from the context here
       controller = new MyController();
    }

    @Test
    public void testFoo() throws Exception {
       request.setRequestURI("/users");
       final ModelAndView mav = handlerAdapter.handle(request, response, 
           controller);
       assertViewName(mav, null);
       assertAndReturnModelAttributeOfType(mav, "image", Image.class);
    }
}

Я также написал запись в блоге об интеграционном тестировании аннотаций Spring MVC .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...