LoginFilter implements Filter { @Override public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { final HttpServletRequest httpReq = (HttpServletRequest) request; final HttpServletResponse httpResp = (HttpServletResponse) response; if (requestFilter.shouldSkip(httpReq)) { chain.doFilter(request, response); return; } final String method = httpReq.getMethod(); final String clientUrl = clientUrlExtractor.getClientUrl(httpReq); if ("GET".equals(method) && httpReq.getParameter("login") != null) { UriBuilder redirectUrlParameter = UriBuilder.fromUri(httpReq.getRequestURL().toString()) .replaceQuery(httpReq.getQueryString()); redirectUrlParameter.replaceQueryParam("login"); String redirectUrl = UriBuilder.fromUri(loginPageUrl) .queryParam("redirect_url", encode(redirectUrlParameter.build().toString(), "UTF-8")) .queryParam("client_url", encode(clientUrl, "UTF-8")) .build() .toString(); LOG.debug("Redirect to login {} ", redirectUrl); httpResp.sendRedirect(redirectUrl); } else { String token = tokenExtractor.getToken(httpReq); HttpSession session; if (token != null) { session = sessionStore.getSession(token); if (session == null) { session = httpReq.getSession(); sessionStore.saveSession(token, session); } final SsoClientPrincipal principal = getPrincipal(session, token, clientUrl); if (principal == null) { tokenHandler.handleBadToken(httpReq, httpResp, chain, token); } else { tokenHandler.handleValidToken(httpReq, httpResp, chain, session, principal); } } else { if (httpReq.getParameter("cookiePresent") != null) { httpResp.sendRedirect(cookiesDisabledErrorPageUrl); } else { tokenHandler.handleMissingToken(httpReq, httpResp, chain); } } } }  @Override void init(FilterConfig config); @Override void doFilter(ServletRequest request, ServletResponse response, FilterChain chain); @Override void destroy();  }
@Test public void shouldRedirectToSsoServerIfSessionDoesntContainsPrincipalOnGet() throws IOException, ServletException, URISyntaxException { HttpServletRequest request = new MockHttpServletRequest("http: when(clientUrlExtractor.getClientUrl(eq(request))) .thenReturn("http: setFieldValue( filter, "tokenHandler", new RecoverableTokenHandler(requestWrapper, clientUrlExtractor, true)); filter.doFilter(request, response, chain); verify(response) .sendRedirect( eq( "/api/internal/sso/server/refresh?" + "redirect_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmyworkspace" + "&client_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmyworkspace&" + "allowAnonymous=true")); }
@Test public void shouldRedirectToSsoServerAnonymousIsNotAllowed() throws IOException, ServletException, URISyntaxException { setFieldValue(filter, "attemptToGetNewTokenIfNotExist", true); HttpServletRequest request = new MockHttpServletRequest("http: when(clientUrlExtractor.getClientUrl(eq(request))) .thenReturn("http: setFieldValue( filter, "tokenHandler", new RecoverableTokenHandler(requestWrapper, clientUrlExtractor, false)); filter.doFilter(request, response, chain); verify(response) .sendRedirect( eq( "/api/internal/sso/server/refresh?" + "redirect_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmyworkspace" + "&client_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmyworkspace" + "&allowAnonymous=false")); }
@Test public void shouldRedirectToSsoServerWithCorrectRedirectAndClientUrl() throws IOException, ServletException, URISyntaxException { HttpServletRequest request = new MockHttpServletRequest( "http: when(clientUrlExtractor.getClientUrl(eq(request))) .thenReturn("http: setFieldValue( filter, "tokenHandler", new RecoverableTokenHandler(requestWrapper, clientUrlExtractor, false)); filter.doFilter(request, response, chain); verify(response) .sendRedirect( eq( "/api/internal/sso/server/refresh?" + "redirect_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmypersonal.Workspace" + "&client_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fmypersonal.Workspace" + "&allowAnonymous=false")); }
@Test public void shouldPutPrincipalInSession() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest("http: when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), nullable(String.class))) .thenReturn(createSubject("user@domain")); filter.doFilter(request, response, chain); SsoClientPrincipal actual = (SsoClientPrincipal) request.getSession().getAttribute("principal"); assertEquals(actual.getName(), "user@domain"); verify(chain).doFilter(any(ServletRequest.class), eq(response)); }
@Test public void shouldBeAbleToReplaceAnonymousWithCorrectUserPrincipal() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest("http: when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())) .thenReturn(createSubject("user@domain")); when(ssoServerClient.getSubject(eq("t12f"), anyString())) .thenReturn(createSubject("Anonymous123@domain")); when(clientUrlExtractor.getClientUrl(eq(request))).thenReturn("http: SsoClientPrincipal anonymous = new SsoClientPrincipal( "t12f", "http: request.getSession().setAttribute("principal", anonymous); filter.doFilter(request, response, chain); ArgumentCaptor<ServletRequest> captor = ArgumentCaptor.forClass(ServletRequest.class); verify(chain).doFilter(captor.capture(), eq(response)); assertEquals( ((HttpServletRequest) captor.getValue()).getUserPrincipal().getName(), "user@domain"); }
@Test public void shouldRedirectToRefreshTokenIfTokenIsInvalidAndRecoverConfigured() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest("http: when(clientUrlExtractor.getClientUrl(eq(request))).thenReturn("http: when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())).thenReturn(null); setFieldValue( filter, "tokenHandler", new RecoverableTokenHandler(requestWrapper, clientUrlExtractor, false)); filter.doFilter(request, response, chain); verify(response) .sendRedirect( eq( "/api/internal/sso/server/refresh?" + "redirect_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fws" + "&client_url=http%3A%2F%2Flocalhost%3A8080%2Fws%2Fws" + "&allowAnonymous=false")); }
@Test public void shouldWrapPrincipalInRequest() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest("http: when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())) .thenReturn(createSubject("user@domain")); when(clientUrlExtractor.getClientUrl(eq(request))).thenReturn("http: SsoClientPrincipal principal = new SsoClientPrincipal("t13f", "http: request.getSession().setAttribute("principal", principal); filter.doFilter(request, response, chain); ArgumentCaptor<HttpServletRequest> captor = ArgumentCaptor.forClass(HttpServletRequest.class); verify(chain).doFilter(captor.capture(), any(ServletResponse.class)); HttpServletRequest actual = captor.getValue(); Assert.assertNotEquals(actual, request); assertEquals(actual.getRemoteUser(), "user@domain"); }
@Test public void shouldWrappedPrincipalShouldNotBeTheSameAsInRequest() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest("http: when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())) .thenReturn(createSubject("user@domain")); when(clientUrlExtractor.getClientUrl(eq(request))).thenReturn("http: SsoClientPrincipal principal = new SsoClientPrincipal("t13f", "http: request.getSession().setAttribute("principal", principal); filter.doFilter(request, response, chain); ArgumentCaptor<HttpServletRequest> captor = ArgumentCaptor.forClass(HttpServletRequest.class); verify(chain).doFilter(captor.capture(), any(ServletResponse.class)); HttpServletRequest actual = captor.getValue(); Principal actualUserPrincipal = actual.getUserPrincipal(); Assert.assertNotEquals(actualUserPrincipal, principal); }
@Test public void shouldReuseSessionAssociatedWithToken() throws IOException, ServletException { HttpServletRequest request = spy( new MockHttpServletRequest( "http: HttpSession session1 = mock(HttpSession.class); SsoClientPrincipal principal = mock(SsoClientPrincipal.class); when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(request.getSession()).thenReturn(session); when(session1.getAttribute(eq("principal"))).thenReturn(principal); when(principal.getToken()).thenReturn("t13f"); when(sessionStore.getSession(eq("t13f"))).thenReturn(session1); request.getSession().setAttribute("principal", principal); filter.doFilter(request, response, chain); ArgumentCaptor<HttpServletRequest> captor = ArgumentCaptor.forClass(HttpServletRequest.class); verify(chain).doFilter(captor.capture(), any(ServletResponse.class)); HttpServletRequest actual = captor.getValue(); assertEquals(actual.getSession(), session1); Assert.assertNotEquals(actual.getSession(), session); verify(sessionStore).getSession(eq("t13f")); verifyNoMoreInteractions(sessionStore); }
@Test public void shouldRespond401IfPostRequestHasNoToken() throws IOException, ServletException { ByteArrayOutputStream bos = new ByteArrayOutputStream(); PrintWriter writer = new PrintWriter(bos); when(response.getWriter()).thenReturn(writer); HttpServletRequest request = spy(new MockHttpServletRequest("http: filter.doFilter(request, response, chain); verify(response).setStatus(HttpServletResponse.SC_UNAUTHORIZED); assertEquals( new String(bos.toByteArray()), "{\"message\":\"User not authorized to call this method.\"}"); }
@Test public void shouldRespond401IfGetRequestHasNoToken() throws IOException, ServletException { HttpServletRequest request = spy(new MockHttpServletRequest("http: ByteArrayOutputStream bos = new ByteArrayOutputStream(); PrintWriter writer = new PrintWriter(bos); when(response.getWriter()).thenReturn(writer); setFieldValue(filter, "tokenHandler", new NoUserInteractionTokenHandler(requestWrapper)); filter.doFilter(request, response, chain); verify(response).setStatus(HttpServletResponse.SC_UNAUTHORIZED); assertEquals( new String(bos.toByteArray()), "{\"message\":\"User not authorized to call this method.\"}"); }
@Test public void shouldRedirectToCookieErrorPageIfNotTokenInRequestButCookiesCheckRequested() throws IOException, ServletException { HttpServletRequest request = spy( new MockHttpServletRequest( "http: filter.doFilter(request, response, chain); verify(response).sendRedirect(eq("/site/cookiesDisabledErrorPageUrl")); }
@Test public void shouldRespond403ForPostRequestWithInvalidToken() throws ServletException, IOException { ByteArrayOutputStream bos = new ByteArrayOutputStream(); PrintWriter writer = new PrintWriter(bos); HttpServletRequest request = new MockHttpServletRequest("http: setFieldValue(filter, "attemptToGetNewTokenIfInvalid", false); when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())).thenReturn(null); when(response.getWriter()).thenReturn(writer); setFieldValue(filter, "tokenHandler", new NoUserInteractionTokenHandler(requestWrapper)); filter.doFilter(request, response, chain); verify(response).setStatus(HttpServletResponse.SC_FORBIDDEN); assertEquals(new String(bos.toByteArray()), "{\"message\":\"Provided token t13f is invalid\"}"); Assert.assertTrue(bos.size() > 0); }
@Test public void shouldRespond403ForGetRequestWithInvalidToken() throws ServletException, IOException { ByteArrayOutputStream bos = new ByteArrayOutputStream(); PrintWriter writer = new PrintWriter(bos); HttpServletRequest request = new MockHttpServletRequest("http: setFieldValue(filter, "attemptToGetNewTokenIfInvalid", false); when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), anyString())).thenReturn(null); when(response.getWriter()).thenReturn(writer); setFieldValue(filter, "tokenHandler", new NoUserInteractionTokenHandler(requestWrapper)); filter.doFilter(request, response, chain); verify(response).setStatus(HttpServletResponse.SC_FORBIDDEN); assertEquals(new String(bos.toByteArray()), "{\"message\":\"Provided token t13f is invalid\"}"); Assert.assertTrue(bos.size() > 0); }
@Test public void shouldRemoveCookiePresentParamFromValidGetRequestWithTokenAndRedirect() throws IOException, ServletException { HttpServletRequest request = new MockHttpServletRequest( "http: null, 0, "GET", null); when(tokenExtractor.getToken(eq(request))).thenReturn("t13f"); when(ssoServerClient.getSubject(eq("t13f"), nullable(String.class))) .thenReturn(createSubject("user@domain")); filter.doFilter(request, response, chain); verify(response).sendRedirect(eq("http: }
@Test public void shouldSkipRequestByFilter() throws IOException, ServletException, URISyntaxException { HttpServletRequest request = new MockHttpServletRequest("http: when(requestFilter.shouldSkip(eq(request))).thenReturn(true); filter.doFilter(request, response, chain); verify(chain).doFilter(request, response); verifyNoMoreInteractions(sessionStore, tokenExtractor, clientUrlExtractor, ssoServerClient); }