device_oauth2_token_service_unittest.cc revision 7dbb3d5cf0c15f500944d211057644d6a2f37371
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/chromeos/settings/device_oauth2_token_service.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/message_loop.h" 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/prefs/testing_pref_service.h" 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/run_loop.h" 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/signin/oauth2_token_service_test_util.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/pref_names.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/test/base/scoped_testing_local_state.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/test/base/testing_browser_process.h" 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chromeos/cryptohome/mock_cryptohome_library.h" 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/browser_thread.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/test/test_browser_thread.h" 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "google_apis/gaia/gaia_oauth_client.h" 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/http/http_status_code.h" 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/url_request/test_url_fetcher_factory.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/url_request/url_fetcher_delegate.h" 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/url_request/url_request_test_util.h" 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gmock/include/gmock/gmock.h" 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "testing/gtest/include/gtest/gtest.h" 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using ::testing::_; 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using ::testing::AnyNumber; 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using ::testing::Return; 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using ::testing::StrEq; 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using ::testing::StrictMock; 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace chromeos { 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static const int kOAuthTokenServiceUrlFetcherId = 0; 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static const int kValidatorUrlFetcherId = gaia::GaiaOAuthClient::kUrlFetcherId; 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class TestDeviceOAuth2TokenService : public DeviceOAuth2TokenService { 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) explicit TestDeviceOAuth2TokenService(net::URLRequestContextGetter* getter, 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PrefService* local_state) 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : DeviceOAuth2TokenService(getter, local_state) { 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SetRobotAccountIdPolicyValue(const std::string& id) { 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) robot_account_id_ = id; 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Skip calling into the policy subsystem and return our test value. 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual std::string GetRobotAccountId() OVERRIDE { 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return robot_account_id_; 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string robot_account_id_; 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(TestDeviceOAuth2TokenService); 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class DeviceOAuth2TokenServiceTest : public testing::Test { 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DeviceOAuth2TokenServiceTest() 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : ui_thread_(content::BrowserThread::UI, &message_loop_), 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_testing_local_state_(TestingBrowserProcess::GetGlobal()), 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) request_context_getter_(new net::TestURLRequestContextGetter( 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) message_loop_.message_loop_proxy())), 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) oauth2_service_(request_context_getter_.get(), 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_testing_local_state_.Get()) { 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) oauth2_service_.max_refresh_token_validation_retries_ = 0; 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) oauth2_service_.set_max_authorization_token_fetch_retries_for_testing(0); 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~DeviceOAuth2TokenServiceTest() {} 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Most tests just want a noop crypto impl with a dummy refresh token value in 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Local State (if the value is an empty string, it will be ignored). 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SetUpDefaultValues() { 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) cryptohome_library_.reset(chromeos::CryptohomeLibrary::GetTestImpl()); 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) chromeos::CryptohomeLibrary::SetForTest(cryptohome_library_.get()); 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SetDeviceRefreshTokenInLocalState("device_refresh_token_4_test"); 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) oauth2_service_.SetRobotAccountIdPolicyValue("service_acct@g.com"); 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AssertConsumerTokensAndErrors(0, 0); 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<OAuth2TokenService::Request> StartTokenRequest() { 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return oauth2_service_.StartRequest(std::set<std::string>(), &consumer_); 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void TearDown() OVERRIDE { 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CryptohomeLibrary::SetForTest(NULL); 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::RunLoop().RunUntilIdle(); 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Utility method to set a value in Local State for the device refresh token 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // (it must have a non-empty value or it won't be used). 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SetDeviceRefreshTokenInLocalState(const std::string& refresh_token) { 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_testing_local_state_.Get()->SetManagedPref( 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) prefs::kDeviceRobotAnyApiRefreshToken, 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Value::CreateStringValue(refresh_token)); 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string GetValidTokenInfoResponse(const std::string email) { 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return "{ \"email\": \"" + email + "\"," 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) " \"user_id\": \"1234567890\" }"; 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // A utility method to return fake URL results, for testing the refresh token 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // validation logic. For a successful validation attempt, this method will be 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // called three times for the steps listed below (steps 1 and 2 happen in 1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // parallel). 1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Step 1a: fetch the access token for the tokeninfo API. 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Step 1b: call the tokeninfo API. 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Step 2: Fetch the access token for the requested scope 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // (in this case, cloudprint). 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void ReturnOAuthUrlFetchResults(int fetcher_id, 1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::HttpStatusCode response_code, 1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& response_string); 1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void AssertConsumerTokensAndErrors(int num_tokens, int num_errors); 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected: 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::MessageLoop message_loop_; 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) content::TestBrowserThread ui_thread_; 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ScopedTestingLocalState scoped_testing_local_state_; 1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_refptr<net::TestURLRequestContextGetter> request_context_getter_; 1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::TestURLFetcherFactory factory_; 1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) TestDeviceOAuth2TokenService oauth2_service_; 1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) TestingOAuth2TokenServiceConsumer consumer_; 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<chromeos::CryptohomeLibrary> cryptohome_library_; 1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DeviceOAuth2TokenServiceTest::ReturnOAuthUrlFetchResults( 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int fetcher_id, 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::HttpStatusCode response_code, 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& response_string) { 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::TestURLFetcher* fetcher = factory_.GetFetcherByID(fetcher_id); 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_TRUE(fetcher); 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) fetcher->set_response_code(response_code); 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) fetcher->SetResponseString(response_string); 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) fetcher->delegate()->OnURLFetchComplete(fetcher); 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DeviceOAuth2TokenServiceTest::AssertConsumerTokensAndErrors( 1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int num_tokens, 1445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int num_errors) { 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ(num_tokens, consumer_.number_of_successful_tokens_); 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ(num_errors, consumer_.number_of_errors_); 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(DeviceOAuth2TokenServiceTest, SaveEncryptedToken) { 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) StrictMock<MockCryptohomeLibrary> mock_cryptohome_library; 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CryptohomeLibrary::SetForTest(&mock_cryptohome_library); 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_CALL(mock_cryptohome_library, DecryptWithSystemSalt(StrEq(""))) 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .Times(1) 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .WillOnce(Return("")); 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_CALL(mock_cryptohome_library, 1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EncryptWithSystemSalt(StrEq("test-token"))) 1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .Times(1) 1595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .WillOnce(Return("encrypted")); 1605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) EXPECT_CALL(mock_cryptohome_library, 1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DecryptWithSystemSalt(StrEq("encrypted"))) 1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .Times(1) 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) .WillOnce(Return("test-token")); 1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ("", oauth2_service_.GetRefreshToken()); 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) oauth2_service_.SetAndSaveRefreshToken("test-token"); 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ("test-token", oauth2_service_.GetRefreshToken()); 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // This call won't invoke decrypt again, since the value is cached. 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ("test-token", oauth2_service_.GetRefreshToken()); 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TEST_F(DeviceOAuth2TokenServiceTest, RefreshTokenValidation_Success) { 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SetUpDefaultValues(); 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ReturnOAuthUrlFetchResults( 1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) kValidatorUrlFetcherId, 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::HTTP_OK, 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetValidTokenResponse("tokeninfo_access_token", 3600)); 1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ReturnOAuthUrlFetchResults( 183a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) kValidatorUrlFetcherId, 184a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) net::HTTP_OK, 185a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) GetValidTokenInfoResponse("service_acct@g.com")); 186a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) 187a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) ReturnOAuthUrlFetchResults( 1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) kOAuthTokenServiceUrlFetcherId, 1895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) net::HTTP_OK, 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) GetValidTokenResponse("scoped_access_token", 3600)); 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) AssertConsumerTokensAndErrors(1, 0); 193 194 EXPECT_EQ("scoped_access_token", consumer_.last_token_); 195} 196 197TEST_F(DeviceOAuth2TokenServiceTest, 198 RefreshTokenValidation_Failure_TokenInfoAccessTokenHttpError) { 199 SetUpDefaultValues(); 200 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 201 202 ReturnOAuthUrlFetchResults( 203 kValidatorUrlFetcherId, 204 net::HTTP_UNAUTHORIZED, 205 ""); 206 207 // TokenInfo API call skipped (error returned in previous step). 208 209 // CloudPrint access token fetch is successful, but consumer still given error 210 // due to bad refresh token. 211 ReturnOAuthUrlFetchResults( 212 kOAuthTokenServiceUrlFetcherId, 213 net::HTTP_OK, 214 GetValidTokenResponse("ignored_scoped_access_token", 3600)); 215 216 AssertConsumerTokensAndErrors(0, 1); 217} 218 219TEST_F(DeviceOAuth2TokenServiceTest, 220 RefreshTokenValidation_Failure_TokenInfoAccessTokenInvalidResponse) { 221 SetUpDefaultValues(); 222 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 223 224 ReturnOAuthUrlFetchResults( 225 kValidatorUrlFetcherId, 226 net::HTTP_OK, 227 "invalid response"); 228 229 // TokenInfo API call skipped (error returned in previous step). 230 231 ReturnOAuthUrlFetchResults( 232 kOAuthTokenServiceUrlFetcherId, 233 net::HTTP_OK, 234 GetValidTokenResponse("ignored_scoped_access_token", 3600)); 235 236 // CloudPrint access token fetch is successful, but consumer still given error 237 // due to bad refresh token. 238 AssertConsumerTokensAndErrors(0, 1); 239} 240 241TEST_F(DeviceOAuth2TokenServiceTest, 242 RefreshTokenValidation_Failure_TokenInfoApiCallHttpError) { 243 SetUpDefaultValues(); 244 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 245 246 ReturnOAuthUrlFetchResults( 247 kValidatorUrlFetcherId, 248 net::HTTP_OK, 249 GetValidTokenResponse("tokeninfo_access_token", 3600)); 250 251 ReturnOAuthUrlFetchResults( 252 kValidatorUrlFetcherId, 253 net::HTTP_INTERNAL_SERVER_ERROR, 254 ""); 255 256 ReturnOAuthUrlFetchResults( 257 kOAuthTokenServiceUrlFetcherId, 258 net::HTTP_OK, 259 GetValidTokenResponse("ignored_scoped_access_token", 3600)); 260 261 // CloudPrint access token fetch is successful, but consumer still given error 262 // due to bad refresh token. 263 AssertConsumerTokensAndErrors(0, 1); 264} 265 266TEST_F(DeviceOAuth2TokenServiceTest, 267 RefreshTokenValidation_Failure_TokenInfoApiCallInvalidResponse) { 268 SetUpDefaultValues(); 269 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 270 271 ReturnOAuthUrlFetchResults( 272 kValidatorUrlFetcherId, 273 net::HTTP_OK, 274 GetValidTokenResponse("tokeninfo_access_token", 3600)); 275 276 ReturnOAuthUrlFetchResults( 277 kValidatorUrlFetcherId, 278 net::HTTP_OK, 279 "invalid response"); 280 281 ReturnOAuthUrlFetchResults( 282 kOAuthTokenServiceUrlFetcherId, 283 net::HTTP_OK, 284 GetValidTokenResponse("ignored_scoped_access_token", 3600)); 285 286 // CloudPrint access token fetch is successful, but consumer still given error 287 // due to bad refresh token. 288 AssertConsumerTokensAndErrors(0, 1); 289} 290 291TEST_F(DeviceOAuth2TokenServiceTest, 292 RefreshTokenValidation_Failure_CloudPrintAccessTokenHttpError) { 293 SetUpDefaultValues(); 294 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 295 296 ReturnOAuthUrlFetchResults( 297 kValidatorUrlFetcherId, 298 net::HTTP_OK, 299 GetValidTokenResponse("tokeninfo_access_token", 3600)); 300 301 ReturnOAuthUrlFetchResults( 302 kValidatorUrlFetcherId, 303 net::HTTP_OK, 304 GetValidTokenInfoResponse("service_acct@g.com")); 305 306 ReturnOAuthUrlFetchResults( 307 kOAuthTokenServiceUrlFetcherId, 308 net::HTTP_BAD_REQUEST, 309 ""); 310 311 AssertConsumerTokensAndErrors(0, 1); 312} 313 314TEST_F(DeviceOAuth2TokenServiceTest, 315 RefreshTokenValidation_Failure_CloudPrintAccessTokenInvalidResponse) { 316 SetUpDefaultValues(); 317 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 318 319 ReturnOAuthUrlFetchResults( 320 kValidatorUrlFetcherId, 321 net::HTTP_OK, 322 GetValidTokenResponse("tokeninfo_access_token", 3600)); 323 324 ReturnOAuthUrlFetchResults( 325 kValidatorUrlFetcherId, 326 net::HTTP_OK, 327 GetValidTokenInfoResponse("service_acct@g.com")); 328 329 ReturnOAuthUrlFetchResults( 330 kOAuthTokenServiceUrlFetcherId, 331 net::HTTP_OK, 332 "invalid request"); 333 334 AssertConsumerTokensAndErrors(0, 1); 335} 336 337TEST_F(DeviceOAuth2TokenServiceTest, RefreshTokenValidation_Failure_BadOwner) { 338 SetUpDefaultValues(); 339 scoped_ptr<OAuth2TokenService::Request> request = StartTokenRequest(); 340 341 oauth2_service_.SetRobotAccountIdPolicyValue("WRONG_service_acct@g.com"); 342 343 // The requested token comes in before any of the validation calls complete, 344 // but the consumer still gets an error, since the results don't get returned 345 // until validation is over. 346 ReturnOAuthUrlFetchResults( 347 kOAuthTokenServiceUrlFetcherId, 348 net::HTTP_OK, 349 GetValidTokenResponse("ignored_scoped_access_token", 3600)); 350 AssertConsumerTokensAndErrors(0, 0); 351 352 ReturnOAuthUrlFetchResults( 353 kValidatorUrlFetcherId, 354 net::HTTP_OK, 355 GetValidTokenResponse("tokeninfo_access_token", 3600)); 356 AssertConsumerTokensAndErrors(0, 0); 357 358 ReturnOAuthUrlFetchResults( 359 kValidatorUrlFetcherId, 360 net::HTTP_OK, 361 GetValidTokenInfoResponse("service_acct@g.com")); 362 363 // All fetches were successful, but consumer still given error since 364 // the token owner doesn't match the policy value. 365 AssertConsumerTokensAndErrors(0, 1); 366} 367 368} // namespace chromeos 369