12

Spring MVC を使用して Rest サービスを作成しています。クラスの概要は次のとおりです。

 @Controller
 public class MyController{

     @RequestMapping(..)
     public void myMethod(...) throws NotAuthorizedException{...}

     @ExceptionHandler(NotAuthorizedException.class)
     @ResponseStatus(value=HttpStatus.UNAUTHORIZED, reason="blah")
     public void handler(...){...}
 }

ここに投稿されたデザインを使用して単体テストを作成しました。テストは基本的に次のとおりです。

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(....)
public class mytest{

    MockHttpServletRequest requestMock;
    MockHttpServletResponse responseMock;
    AnnotationMethodHandlerAdapter handlerAdapter;

@Before
public void setUp() {
    requestMock = new MockHttpServletRequest();
    requestMock.setContentType(MediaType.APPLICATION_JSON_VALUE);
    requestMock.addHeader(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE);

    responseMock = new MockHttpServletResponse();

    handlerAdapter = new AnnotationMethodHandlerAdapter();
}

@Test
public void testExceptionHandler(){
    // setup ....
    handlerAdapter.handle(...);

    // verify
    // I would like to do the following
    assertThat(responseMock.getStatus(), is(HttpStatus.UNAUTHORIZED.value()));
}

}

ただし、への呼び出しhandleNotAuthorizedException. これは、メソッドが適切な例外をスローすることを単体テストできるように設計されていることを読みましたが、フレームワークがこの例外を適切に処理していること、およびテスト対象のクラスがハンドラーを適切に実装していることを自動テストを記述したいと思います. これを行う方法はありますか?

投稿できる場所にある実際のコードにアクセスできないことに注意してください。

また、(残念な理由で) Spring 3.0.5 または 3.1.2 に制限されています。

4

3 に答える 3

8

Spring 3.2 とそのmvc-test-framework の使用を検討してください

import static org.springframework.test.web.servlet.setup.MockMvcBuilders.*;
import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.*;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.*;

@RunWith(SpringJUnit4ClassRunner.class)
@WebAppConfiguration
@ContextConfiguration("file:src/main/webapp/WEB-INF/spring/appServlet/servlet-context.xml")
public class WebMvcTest {

    @Autowired
    private WebApplicationContext wac;

    private MockMvc mockMvc;

    @Before
    public void setup() {
        this.mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).build();
    }

    @Test
    public void getFoo() throws Exception {
        this.mockMvc.perform(
            get("/testx")
            .contentType(MediaType.APPLICATION_JSON)
            .accept(MediaType.APPLICATION_JSON)
            )
            .andExpect(status().isUnauthorized());
    }
}

コントローラーコード

@Controller
public class MyController {

    public class MyException extends RuntimeException {
    };

    @RequestMapping("/testx")
    public void myMethod() {
        throw new MyException();

    }

    @ExceptionHandler(MyException.class)
    @ResponseStatus(value = HttpStatus.UNAUTHORIZED, reason = "blah")
    public void handler() {
        System.out.println("handler processed");
    }
}

この「テスト」はうまくいきます。

免責事項:現在、私はSpring MVCテストの初心者です。実際、これは私の最初のテストです。
upd: The Drakeの修正に感謝します。

于 2013-01-30T20:54:54.210 に答える
-2

@Test を次のように変更できます。

@Test(expected=NotAuthorizedException.class)

これは、内部でその例外がスローされた場合は true を返し、それ以外の場合は false を返します。

これにより、assertThat() も不要になります。NotAuthorizedException をキャッチする 2 番目のテストを作成してから、その条件下で responseMock を調べることができます。

于 2013-01-30T14:31:57.420 に答える