I wanted to do so custom logic(Record the request and response) on some routes. Based on some research I came decided to use AnnotationBased RequestInterceptor. This is my code for interceptor.
public class CustomInterceptor extends HandlerInterceptorAdapter {
@Override
public void afterCompletion(final HttpServletRequest request,
final HttpServletResponse response,
final Object handler,
final Exception ex) {
if (handler != null && handler instanceof HandlerMethod) {
HandlerMethod handlerMethod = (HandlerMethod) handler;
CustomRecord annotation = AnnotationUtils.getAnnotation(handlerMethod.getMethod(), CustomRecord.class);
if (annotation != null) {
// Record Request and Response in a File.
}
}
Now this class is working as expected but I was unable to unit test this function.
Second I tried to use PowerMokito. This was my test code:
@RunWith(PowerMockRunner.class)
@PrepareForTest(CustomInterceptor.class)
@PowerMockIgnore("javax.management.*")
public class CustomInterceptorTest {
@Test
public void restAnnotationRecording_negetivecase() {
HandlerMethod mockHandler = mock(HandlerMethod.class);
PowerMockito.mockStatic(AnnotationUtils.class);
when(AnnotationUtils.getAnnotation(mockHandler.getMethod(),
CustomRecord.class).thenReturn(null);
// Verify file is not saved
}
// A spy is stubbed using when(spy.foo()).then() syntax. It is safer to stub spies - - with doReturn|Throw() family of methods. More in javadocs for Mockito.spy() methodcannot be saved.
@Test
public void restAnnotationRecording_happycase() {
HandlerMethod mockHandler = mock(HandlerMethod.class);
PowerMockito.mockStatic(AnnotationUtils.class);
when(AnnotationUtils.getAnnotation(mockHandler.getMethod(), CustomRecord.class).thenReturn(mockAnnotation);
// Verify file is saved
}
}
I wanted to check if there is any method to test the Interceptor. I am a newbie in Java, thanks for help.
You can easily create your own HandlerMethod
without mocking. There's a constructor that accepts an Object (the controller) and a Method
(the controller method). The easiest way to get a Method
is to simply call Class.getMethod()
. What you want to do is just create a dummy controller class, and then use that class to get the method. For example
class TestController {
@Custom
public void testMethod() {}
}
Method method = TestController.class.getMethod("testMethod");
TestController controller = new TestController();
HandlerMethod handlerMethod = new HandlerMethod(controller, method);
Custom annotation = handlerMethod.getMethodAnnotation(Custom.class);
It's that easy. Below is a complete test.
public class HandlerInterceptorTest {
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
private @interface Custom {
}
private static class MyHandlerInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest req, HttpServletResponse res, Object handler) {
if (handler instanceof HandlerMethod) {
HandlerMethod handlerMethod = (HandlerMethod) handler;
Custom annotation = handlerMethod.getMethodAnnotation(Custom.class);
if (annotation != null) {
return true;
}
}
return false;
}
}
private static class TestController {
@Custom
public void testMethodWithAnnotation() {}
public void testMethodWithoutAnnotation() {}
}
@Test
public void testMethodWithAnnotation() throws Exception {
Method method = TestController.class.getMethod("testMethodWithAnnotation");
TestController controller = new TestController();
HandlerMethod handlerMethod = new HandlerMethod(controller, method);
MyHandlerInterceptor interceptor = new MyHandlerInterceptor();
boolean result = interceptor.preHandle(null, null, handlerMethod);
assertTrue(result);
}
@Test
public void testMethodWithoutAnnotation() throws Exception {
Method method = TestController.class.getMethod("testMethodWithoutAnnotation");
TestController controller = new TestController();
HandlerMethod handlerMethod = new HandlerMethod(controller, method);
MyHandlerInterceptor interceptor = new MyHandlerInterceptor();
boolean result = interceptor.preHandle(null, null, handlerMethod);
assertFalse(result);
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With