diff options
author | sergeyu@chromium.org <sergeyu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-25 03:21:15 +0000 |
---|---|---|
committer | sergeyu@chromium.org <sergeyu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-25 03:21:15 +0000 |
commit | 607dba220110b63034c8956c4f45cc859970bf22 (patch) | |
tree | c2e376b7136f83700c6ce3fb7c87dd21bd031b9a /google_apis/gaia | |
parent | 16d1cbc6d2e4064abd2f41614ce9dfc0c8eb89af (diff) | |
download | chromium_src-607dba220110b63034c8956c4f45cc859970bf22.zip chromium_src-607dba220110b63034c8956c4f45cc859970bf22.tar.gz chromium_src-607dba220110b63034c8956c4f45cc859970bf22.tar.bz2 |
Add GetUserInfo() in GaiaOAuthClient.
The new method allows getting email of the user given an access token.
Review URL: https://chromiumcodereview.appspot.com/11226067
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@164003 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'google_apis/gaia')
-rw-r--r-- | google_apis/gaia/gaia_oauth_client.cc | 108 | ||||
-rw-r--r-- | google_apis/gaia/gaia_oauth_client.h | 5 | ||||
-rw-r--r-- | google_apis/gaia/gaia_oauth_client_unittest.cc | 31 |
3 files changed, 123 insertions, 21 deletions
diff --git a/google_apis/gaia/gaia_oauth_client.cc b/google_apis/gaia/gaia_oauth_client.cc index cd04325..41e8f96 100644 --- a/google_apis/gaia/gaia_oauth_client.cc +++ b/google_apis/gaia/gaia_oauth_client.cc @@ -8,6 +8,7 @@ #include "base/logging.h" #include "base/memory/scoped_ptr.h" #include "base/values.h" +#include "google_apis/gaia/gaia_urls.h" #include "googleurl/src/gurl.h" #include "net/base/escape.h" #include "net/http/http_status_code.h" @@ -32,7 +33,9 @@ class GaiaOAuthClient::Core : gaia_url_(gaia_url), num_retries_(0), request_context_getter_(request_context_getter), - delegate_(NULL) {} + delegate_(NULL), + request_type_(NO_PENDING_REQUEST) { + } void GetTokensFromAuthCode(const OAuthClientInfo& oauth_client_info, const std::string& auth_code, @@ -42,12 +45,23 @@ class GaiaOAuthClient::Core const std::string& refresh_token, int max_retries, GaiaOAuthClient::Delegate* delegate); + void GetUserInfo(const std::string& oauth_access_token, + int max_retries, + Delegate* delegate); // net::URLFetcherDelegate implementation. virtual void OnURLFetchComplete(const net::URLFetcher* source) OVERRIDE; private: friend class base::RefCountedThreadSafe<Core>; + + enum RequestType { + NO_PENDING_REQUEST, + TOKENS_FROM_AUTH_CODE, + REFRESH_TOKEN, + USER_INFO, + }; + virtual ~Core() {} void MakeGaiaRequest(const std::string& post_body, @@ -61,6 +75,7 @@ class GaiaOAuthClient::Core scoped_refptr<net::URLRequestContextGetter> request_context_getter_; GaiaOAuthClient::Delegate* delegate_; scoped_ptr<net::URLFetcher> request_; + RequestType request_type_; }; void GaiaOAuthClient::Core::GetTokensFromAuthCode( @@ -68,6 +83,8 @@ void GaiaOAuthClient::Core::GetTokensFromAuthCode( const std::string& auth_code, int max_retries, GaiaOAuthClient::Delegate* delegate) { + DCHECK_EQ(request_type_, NO_PENDING_REQUEST); + request_type_ = TOKENS_FROM_AUTH_CODE; std::string post_body = "code=" + net::EscapeUrlEncodedData(auth_code, true) + "&client_id=" + net::EscapeUrlEncodedData(oauth_client_info.client_id, @@ -85,6 +102,8 @@ void GaiaOAuthClient::Core::RefreshToken( const std::string& refresh_token, int max_retries, GaiaOAuthClient::Delegate* delegate) { + DCHECK_EQ(request_type_, NO_PENDING_REQUEST); + request_type_ = REFRESH_TOKEN; std::string post_body = "refresh_token=" + net::EscapeUrlEncodedData(refresh_token, true) + "&client_id=" + net::EscapeUrlEncodedData(oauth_client_info.client_id, @@ -95,6 +114,24 @@ void GaiaOAuthClient::Core::RefreshToken( MakeGaiaRequest(post_body, max_retries, delegate); } +void GaiaOAuthClient::Core::GetUserInfo(const std::string& oauth_access_token, + int max_retries, + Delegate* delegate) { + DCHECK_EQ(request_type_, NO_PENDING_REQUEST); + DCHECK(!request_.get()); + request_type_ = USER_INFO; + delegate_ = delegate; + num_retries_ = 0; + request_.reset(net::URLFetcher::Create( + 0, GURL(GaiaUrls::GetInstance()->oauth_user_info_url()), + net::URLFetcher::GET, this)); + request_->SetRequestContext(request_context_getter_); + request_->AddExtraRequestHeader( + "Authorization: OAuth " + oauth_access_token); + request_->SetMaxRetries(max_retries); + request_->Start(); +} + void GaiaOAuthClient::Core::MakeGaiaRequest( const std::string& post_body, int max_retries, @@ -141,39 +178,69 @@ void GaiaOAuthClient::Core::HandleResponse( delegate_->OnOAuthError(); return; } - std::string access_token; - std::string refresh_token; - int expires_in_seconds = 0; + + scoped_ptr<DictionaryValue> response_dict; if (source->GetResponseCode() == net::HTTP_OK) { std::string data; source->GetResponseAsString(&data); scoped_ptr<Value> message_value(base::JSONReader::Read(data)); if (message_value.get() && message_value->IsType(Value::TYPE_DICTIONARY)) { - scoped_ptr<DictionaryValue> response_dict( + response_dict.reset( static_cast<DictionaryValue*>(message_value.release())); - response_dict->GetString(kAccessTokenValue, &access_token); - response_dict->GetString(kRefreshTokenValue, &refresh_token); - response_dict->GetInteger(kExpiresInValue, &expires_in_seconds); } } - if (access_token.empty()) { + + if (!response_dict.get()) { // If we don't have an access token yet and the the error was not // RC_BAD_REQUEST, we may need to retry. - if ((-1 != source->GetMaxRetries()) && + if ((source->GetMaxRetries() != -1) && (num_retries_ > source->GetMaxRetries())) { // Retry limit reached. Give up. delegate_->OnNetworkError(source->GetResponseCode()); } else { *should_retry_request = true; } - } else if (refresh_token.empty()) { - // If we only have an access token, then this was a refresh request. - delegate_->OnRefreshTokenResponse(access_token, expires_in_seconds); - } else { - delegate_->OnGetTokensResponse(refresh_token, - access_token, - expires_in_seconds); + return; + } + + RequestType type = request_type_; + request_type_ = NO_PENDING_REQUEST; + + switch (type) { + case USER_INFO: { + std::string email; + response_dict->GetString("email", &email); + delegate_->OnGetUserInfoResponse(email); + break; + } + + case TOKENS_FROM_AUTH_CODE: + case REFRESH_TOKEN: { + std::string access_token; + std::string refresh_token; + int expires_in_seconds = 0; + response_dict->GetString(kAccessTokenValue, &access_token); + response_dict->GetString(kRefreshTokenValue, &refresh_token); + response_dict->GetInteger(kExpiresInValue, &expires_in_seconds); + + if (access_token.empty()) { + delegate_->OnOAuthError(); + return; + } + + if (type == REFRESH_TOKEN) { + delegate_->OnRefreshTokenResponse(access_token, expires_in_seconds); + } else { + delegate_->OnGetTokensResponse(refresh_token, + access_token, + expires_in_seconds); + } + break; + } + + default: + NOTREACHED(); } } @@ -185,7 +252,6 @@ GaiaOAuthClient::GaiaOAuthClient(const std::string& gaia_url, GaiaOAuthClient::~GaiaOAuthClient() { } - void GaiaOAuthClient::GetTokensFromAuthCode( const OAuthClientInfo& oauth_client_info, const std::string& auth_code, @@ -207,4 +273,10 @@ void GaiaOAuthClient::RefreshToken(const OAuthClientInfo& oauth_client_info, delegate); } +void GaiaOAuthClient::GetUserInfo(const std::string& access_token, + int max_retries, + Delegate* delegate) { + return core_->GetUserInfo(access_token, max_retries, delegate); +} + } // namespace gaia diff --git a/google_apis/gaia/gaia_oauth_client.h b/google_apis/gaia/gaia_oauth_client.h index 3dad639..a03b134 100644 --- a/google_apis/gaia/gaia_oauth_client.h +++ b/google_apis/gaia/gaia_oauth_client.h @@ -37,6 +37,8 @@ class GaiaOAuthClient { // Invoked on a successful response to the RefreshToken request. virtual void OnRefreshTokenResponse(const std::string& access_token, int expires_in_seconds) = 0; + // Invoked on a successful response to the GetUserInfo request. + virtual void OnGetUserInfoResponse(const std::string& user_email) {}; // Invoked when there is an OAuth error with one of the requests. virtual void OnOAuthError() = 0; // Invoked when there is a network error or upon receiving an invalid @@ -63,6 +65,9 @@ class GaiaOAuthClient { const std::string& refresh_token, int max_retries, Delegate* delegate); + void GetUserInfo(const std::string& oauth_access_token, + int max_retries, + Delegate* delegate); private: // The guts of the implementation live in this class. diff --git a/google_apis/gaia/gaia_oauth_client_unittest.cc b/google_apis/gaia/gaia_oauth_client_unittest.cc index 739898d..f21a395 100644 --- a/google_apis/gaia/gaia_oauth_client_unittest.cc +++ b/google_apis/gaia/gaia_oauth_client_unittest.cc @@ -104,6 +104,7 @@ class MockOAuthFetcherFactory : public net::URLFetcherFactory, const std::string kTestAccessToken = "1/fFAGRNJru1FTz70BzhT3Zg"; const std::string kTestRefreshToken = "1/6BMfW9j53gdGImsixUH6kU5RsR4zwI9lUVX-tqf8JXQ"; +const std::string kTestUserEmail = "a_user@gmail.com"; const int kTestExpiresIn = 3920; const std::string kDummyGetTokensResult = @@ -114,6 +115,9 @@ const std::string kDummyGetTokensResult = const std::string kDummyRefreshTokenResult = "{\"access_token\":\"" + kTestAccessToken + "\"," "\"expires_in\":" + base::IntToString(kTestExpiresIn) + "}"; + +const std::string kDummyUserInfoResult = + "{\"email\":\"" + kTestUserEmail + "\"}"; } namespace gaia { @@ -133,9 +137,11 @@ class MockGaiaOAuthClientDelegate : public gaia::GaiaOAuthClient::Delegate { ~MockGaiaOAuthClientDelegate() {} MOCK_METHOD3(OnGetTokensResponse, void(const std::string& refresh_token, - const std::string& access_token, int expires_in_seconds)); + const std::string& access_token, + int expires_in_seconds)); MOCK_METHOD2(OnRefreshTokenResponse, void(const std::string& access_token, - int expires_in_seconds)); + int expires_in_seconds)); + MOCK_METHOD1(OnGetUserInfoResponse, void(const std::string& user_email)); MOCK_METHOD0(OnOAuthError, void()); MOCK_METHOD1(OnNetworkError, void(int response_code)); }; @@ -243,6 +249,25 @@ TEST_F(GaiaOAuthClientTest, RefreshTokenSuccess) { client_info.redirect_uri = "test_redirect_uri"; GaiaOAuthClient auth(kGaiaOAuth2Url, profile_.GetRequestContext()); - auth.GetTokensFromAuthCode(client_info, "auth_code", -1, &delegate); + auth.RefreshToken(client_info, "refresh_token", -1, &delegate); } + +TEST_F(GaiaOAuthClientTest, GetUserInfo) { + MockGaiaOAuthClientDelegate delegate; + EXPECT_CALL(delegate, OnGetUserInfoResponse(kTestUserEmail)).Times(1); + + TestingProfile profile; + + MockOAuthFetcherFactory factory; + factory.set_results(kDummyUserInfoResult); + + OAuthClientInfo client_info; + client_info.client_id = "test_client_id"; + client_info.client_secret = "test_client_secret"; + client_info.redirect_uri = "test_redirect_uri"; + GaiaOAuthClient auth(kGaiaOAuth2Url, + profile_.GetRequestContext()); + auth.GetUserInfo("access_token", 1, &delegate); +} + } // namespace gaia |