1 package com.atlassian.plugins.rest.common.validation; 2 3 import com.atlassian.plugins.rest.common.interceptor.MethodInvocation; 4 import com.atlassian.sal.api.message.I18nResolver; 5 import com.sun.jersey.api.core.HttpContext; 6 import com.sun.jersey.api.core.HttpResponseContext; 7 import com.sun.jersey.api.model.AbstractResourceMethod; 8 import com.sun.jersey.api.model.Parameter; 9 import org.junit.Before; 10 import org.junit.Test; 11 import org.mockito.ArgumentCaptor; 12 13 import javax.validation.MessageInterpolator; 14 import javax.validation.constraints.NotNull; 15 import javax.validation.constraints.Size; 16 import javax.ws.rs.core.Response; 17 import java.lang.reflect.InvocationTargetException; 18 import java.util.Collections; 19 20 import static junit.framework.Assert.assertTrue; 21 import static org.junit.Assert.assertEquals; 22 import static org.junit.Assert.assertNotNull; 23 import static org.mockito.Matchers.anyObject; 24 import static org.mockito.Matchers.eq; 25 import static org.mockito.Mockito.mock; 26 import static org.mockito.Mockito.never; 27 import static org.mockito.Mockito.times; 28 import static org.mockito.Mockito.verify; 29 import static org.mockito.Mockito.when; 30 31 public class ValidationInterceptorTest 32 { 33 private I18nResolver resolver; 34 private ValidationInterceptor interceptor; 35 private MethodInvocation methodInvocation; 36 private AbstractResourceMethod method; 37 private ArgumentCaptor<Response> responseCaptor; 38 private HttpResponseContext response; 39 40 @Before 41 public void setUp() 42 { 43 resolver = mock(I18nResolver.class); 44 interceptor = new ValidationInterceptor(resolver); 45 methodInvocation = mock(MethodInvocation.class); 46 HttpContext httpContext = mock(HttpContext.class); 47 response = mock(HttpResponseContext.class); 48 method = mock(AbstractResourceMethod.class); 49 50 51 when(httpContext.getResponse()).thenReturn(response); 52 when(methodInvocation.getHttpContext()).thenReturn(httpContext); 53 when(methodInvocation.getMethod()).thenReturn(method); 54 55 responseCaptor = ArgumentCaptor.forClass(Response.class); 56 } 57 58 @Test 59 public void testInterceptPass() throws IllegalAccessException, InvocationTargetException 60 { 61 ValidatableObject obj = new ValidatableObject("jim"); 62 63 when(methodInvocation.getParameters()).thenReturn(new Object[] {obj}); 64 Parameter parameter = mock(Parameter.class); 65 when(parameter.getSource()).thenReturn(Parameter.Source.ENTITY); 66 when(method.getParameters()).thenReturn(Collections.<Parameter>singletonList(parameter)); 67 68 interceptor.intercept(methodInvocation); 69 verify(methodInvocation, times(1)).invoke(); 70 71 verify(response, never()).getEntity(); 72 } 73 74 @Test 75 public void testInterceptPassNoAnnotations() throws IllegalAccessException, InvocationTargetException 76 { 77 when(methodInvocation.getParameters()).thenReturn(new Object[] {new Object()}); 78 Parameter parameter = mock(Parameter.class); 79 when(parameter.getSource()).thenReturn(Parameter.Source.ENTITY); 80 when(method.getParameters()).thenReturn(Collections.<Parameter>singletonList(parameter)); 81 82 interceptor.intercept(methodInvocation); 83 84 verify(response, never()).getEntity(); 85 } 86 87 @Test 88 public void testInterceptPassParametersButNoEntity() throws IllegalAccessException, InvocationTargetException 89 { 90 when(methodInvocation.getParameters()).thenReturn(new Object[] {new Object()}); 91 Parameter parameter = mock(Parameter.class); 92 when(parameter.getSource()).thenReturn(Parameter.Source.PATH); 93 when(method.getParameters()).thenReturn(Collections.<Parameter>singletonList(parameter)); 94 95 interceptor.intercept(methodInvocation); 96 97 verify(response, never()).getEntity(); 98 } 99 100 @Test 101 public void testInterceptPassNoEntityParameter() throws IllegalAccessException, InvocationTargetException 102 { 103 when(methodInvocation.getParameters()).thenReturn(new Object[0]); 104 when(method.getParameters()).thenReturn(Collections.<Parameter>emptyList()); 105 106 interceptor.intercept(methodInvocation); 107 108 verify(response, never()).getEntity(); 109 } 110 111 @Test 112 public void testInterceptFail() throws IllegalAccessException, InvocationTargetException 113 { 114 when(resolver.getText("notnull")).thenReturn("Not Null"); 115 ValidatableObject obj = new ValidatableObject(null); 116 117 when(methodInvocation.getParameters()).thenReturn(new Object[] {obj}); 118 Parameter parameter = mock(Parameter.class); 119 when(parameter.getSource()).thenReturn(Parameter.Source.ENTITY); 120 when(method.getParameters()).thenReturn(Collections.<Parameter>singletonList(parameter)); 121 122 interceptor.intercept(methodInvocation); 123 verify(methodInvocation, never()).invoke(); 124 verify(response).setResponse(responseCaptor.capture()); 125 126 assertNotNull(responseCaptor.getValue()); 127 assertEquals(400, responseCaptor.getValue().getStatus()); 128 129 Object entity = responseCaptor.getValue().getEntity(); 130 assertTrue(entity instanceof ValidationErrors); 131 ValidationErrors errors = (ValidationErrors) entity; 132 assertEquals(1, errors.getErrors().size()); 133 assertEquals("Not Null", errors.getErrors().get(0).getMessage()); 134 } 135 136 @Test 137 public void testInterceptFailWithCustomMessageInterpolator() throws IllegalAccessException, InvocationTargetException 138 { 139 MessageInterpolator messageInterpolator = mock(MessageInterpolator.class); 140 when(messageInterpolator.interpolate(eq("notnull"), (MessageInterpolator.Context) anyObject())).thenReturn("Bar"); 141 interceptor = new ValidationInterceptor(messageInterpolator); 142 143 ValidatableObject obj = new ValidatableObject(null); 144 145 when(methodInvocation.getParameters()).thenReturn(new Object[] {obj}); 146 Parameter parameter = mock(Parameter.class); 147 when(parameter.getSource()).thenReturn(Parameter.Source.ENTITY); 148 when(method.getParameters()).thenReturn(Collections.<Parameter>singletonList(parameter)); 149 150 interceptor.intercept(methodInvocation); 151 verify(methodInvocation, never()).invoke(); 152 verify(response).setResponse(responseCaptor.capture()); 153 154 assertNotNull(responseCaptor.getValue()); 155 assertEquals(400, responseCaptor.getValue().getStatus()); 156 157 Object entity = responseCaptor.getValue().getEntity(); 158 assertTrue(entity instanceof ValidationErrors); 159 ValidationErrors errors = (ValidationErrors) entity; 160 assertEquals(1, errors.getErrors().size()); 161 assertEquals("Bar", errors.getErrors().get(0).getMessage()); 162 } 163 164 static class ValidatableObject 165 { 166 @NotNull(message = "notnull") 167 @Size(min = 2, max = 10, message = "size") 168 private String name; 169 170 public ValidatableObject(String name) 171 { 172 this.name = name; 173 } 174 175 public String getName() 176 { 177 return name; 178 } 179 } 180 }