Посмотрел этот пост , где @ slim дал решение, близкое к тому, о чем я спрашиваю. Я пытаюсь написать модульный тест по классу ниже. Я вытаскиваю идентификатор сессии. ( ищите String sessId внутри метода doFilterInternal )
@Component
public class AppLoggingFilter extends OncePerRequestFilter {
private AppLoggingMDCService mdcService;
@Inject
public AppLoggingFilter(AppLoggingMDCService appLoggingMDCService) {
Assert.notNull(appLoggingMDCService, "AppLoggingMDCService must not be null");
this.mdcService = appLoggingMDCService;
}
@Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) throws ServletException, IOException {
Principal principal = request.getUserPrincipal();
String sessId = DigestUtils.sha256Hex(request.getSession().getId());
if (principal != null) {
String userId = principal.getName();
mdcService.put(AppLoggingMDCService.LOG_KEY_USER_ID, userId);
}
mdcService.put(AppLoggingMDCService.LOG_KEY_SESSION_ID, sessId);
try {
filterChain.doFilter(request, response);
} finally {
mdcService.removeAll();
}
}
Естественно, что приведенный ниже тест не пройден, потому что у меня нет действительного сеанса. Очевидно, что я получаю исключение нулевого указателя всякий раз, когда я вызываю filter.doFilterInternal (request, response, filterChain); . В тестовом классе «mock-session» не настроен и не имеет идентификатора. В моем модульном тесте у меня есть это.
@RunWith(SpringJUnit4ClassRunner.class)
@ActiveProfiles(value = {"test"})
public class AppLoggingFilterUnitTest {
@Mock
AppLoggingMDCService mdcService;
@Mock
MockHttpServletRequest request;
@Mock
MockHttpServletResponse response;
@Mock
MockFilterChain filterChain;
@Mock
MockHttpSession session;
@InjectMocks
AppLoggingFilter filter;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
request.setSession(session);
}
@Test
public void testCustomerIdHasBeenLogged() throws Exception {
String customerId = "1234";
when(request.getHeader(AuthorizationConstants.CUSTOMER_KEY)).thenReturn(customerId);
filter.doFilterInternal(request, response, filterChain);
verify(mdcService, times(1)).put(AppLoggingMDCService.LOG_KEY_CUST_ID,customerId);
}
}
Итак, возвращаясь к моему вопросу, как имитировать как действительный макет "MockHttpSession", чтобы другие мои тесты не провалились?
ОБНОВЛЕНИЕ Итак, я добавил сессию в свой тестовый класс следующим образом. В моем методе настройки, где я сказал, чтобы вернуть «Mocked» сеанс. Тест проходит только когда я звоню String sessId = request.getSession().getId();
. если я попытаюсь сделать DigestUtils.sha256Hex как String sessId = DigestUtils.sha256Hex(request.getSession().getId());
, все тесты не пройдут из-за нулевого указателя. Я не уверен почему. Mocking DigestUtils не имеет особого смысла.
@Mock
AppLoggingMDCService mdcService;
@Mock
HttpServletRequest request;
@Mock
HttpServletResponse response;
@Mock
FilterChain filterChain;
@Mock
HttpSession session;
@InjectMocks
AppLoggingFilter filter;
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
when(request.getSession()).thenReturn(this.session);
}