/* * ***************************************************************************** * Cloud Foundry * Copyright (c) [2009-2015] Pivotal Software, Inc. All Rights Reserved. * This product is licensed to you under the Apache License, Version 2.0 (the "License"). * You may not use this product except in compliance with the License. * * This product includes a number of subcomponents with * separate copyright notices and license terms. Your use of these * subcomponents is subject to the terms and conditions of the * subcomponent's license, as noted in the LICENSE file. * ***************************************************************************** */ package org.cloudfoundry.identity.client.integration; import org.cloudfoundry.identity.client.UaaContextFactory; import org.springframework.http.HttpEntity; import org.springframework.http.HttpHeaders; import org.springframework.http.HttpMethod; import org.springframework.http.HttpStatus; import org.springframework.http.ResponseEntity; import org.springframework.security.oauth2.common.util.RandomValueStringGenerator; import org.springframework.util.LinkedMultiValueMap; import org.springframework.util.MultiValueMap; import org.springframework.util.StringUtils; import org.springframework.web.client.RestTemplate; import java.util.Arrays; import java.util.regex.Matcher; import java.util.regex.Pattern; import static org.cloudfoundry.identity.client.UaaContextFactory.getNoValidatingClientHttpRequestFactory; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; import static org.springframework.http.HttpMethod.POST; import static org.springframework.http.MediaType.APPLICATION_FORM_URLENCODED; import static org.springframework.http.MediaType.APPLICATION_JSON; import static org.springframework.http.MediaType.TEXT_HTML; public class ClientIntegrationTestUtilities { public static final String DEFAULT_CSRF_COOKIE_NAME = "X-Uaa-Csrf"; public static String UAA_URI = "http://localhost:8080/uaa"; public static RandomValueStringGenerator GENERATOR = new RandomValueStringGenerator(); public static String extractCookieCsrf(String body) { String pattern = "\\<input type=\\\"hidden\\\" name=\\\""+DEFAULT_CSRF_COOKIE_NAME+"\\\" value=\\\"(.*?)\\\""; Pattern linkPattern = Pattern.compile(pattern); Matcher matcher = linkPattern.matcher(body); if (matcher.find()) { return matcher.group(1); } return null; } public static String getPasscode(String baseUrl, HttpHeaders headers) { headers.setAccept(Arrays.asList(APPLICATION_JSON)); RestTemplate template = new RestTemplate(); ResponseEntity<String> passcode = template.exchange(baseUrl+"/passcode", HttpMethod.GET, new HttpEntity<>(headers), String.class); return passcode.getBody().replace('"',' ').trim(); } public static String getAuthorizationCode(String authorizeUrl, String clientId, String redirectUri, HttpHeaders headers) { headers.setAccept(Arrays.asList(TEXT_HTML)); RestTemplate template = new RestTemplate(); template.setRequestFactory(UaaContextFactory.getNoValidatingClientHttpRequestFactory(false)); String url = String.format(authorizeUrl+"?scope=openid&client_id=%s&response_type=code&redirect_uri=%s&state=%s", clientId, redirectUri, new RandomValueStringGenerator().generate()); ResponseEntity<Void> redirect = template.exchange(url, HttpMethod.GET, new HttpEntity<>(headers), Void.class); assertEquals(HttpStatus.FOUND, redirect.getStatusCode()); String location = redirect.getHeaders().get("Location").get(0); return extractCodeFromLocation(location); } public static String extractCodeFromLocation(String location) { return location.split("code=")[1].split("&")[0]; } public static HttpHeaders performFormLogin(String baseUrl, String username, String password) throws Exception { HttpHeaders headers = new HttpHeaders(); headers.setAccept(Arrays.asList(TEXT_HTML)); RestTemplate template = new RestTemplate(); template.setRequestFactory(getNoValidatingClientHttpRequestFactory()); ResponseEntity<String> loginPage = template.exchange(baseUrl+"/login", HttpMethod.GET, new HttpEntity<>(headers), String.class); String csrfValue = extractCookieCsrf(loginPage.getBody()); HttpHeaders combined = extractAndSetCookies(loginPage); assertTrue(loginPage.getBody().contains("/login.do")); assertTrue(loginPage.getBody().contains("username")); assertTrue(loginPage.getBody().contains("password")); MultiValueMap<String,String> formData = new LinkedMultiValueMap<>(); formData.add("username", username); formData.add("password", password); formData.add(DEFAULT_CSRF_COOKIE_NAME, csrfValue); headers.setContentType(APPLICATION_FORM_URLENCODED); // Should be redirected to the original URL, but now authenticated ResponseEntity<String> loggedInPage = template.exchange(baseUrl+"/login.do", POST, new HttpEntity<>(formData, headers), String.class); assertEquals(HttpStatus.FOUND, loggedInPage.getStatusCode()); HttpHeaders newHeaders = extractAndSetCookies(loggedInPage); for (String c : newHeaders.get("Cookie")) { combined.add("Cookie", c); } return combined; } protected static HttpHeaders extractAndSetCookies(ResponseEntity<String> response) { HttpHeaders result = new HttpHeaders(); if (response.getHeaders().containsKey("Set-Cookie")) { for (String cookie : response.getHeaders().get("Set-Cookie")) { if (StringUtils.hasText(cookie)) { result.add("Cookie", cookie); } } } return result; } protected static String extractAndSetCookies(ResponseEntity<String> response, HttpHeaders headers, String findCookie) { String result = null; if (response.getHeaders().containsKey("Set-Cookie")) { for (String cookie : response.getHeaders().get("Set-Cookie")) { if (StringUtils.hasText(cookie)) { headers.add("Cookie", cookie); if (cookie.toLowerCase().contains(findCookie.toLowerCase())) { result = cookie; } } } } return result; } }