Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(2665)

Unified Diff: chrome/browser/supervised_user/child_accounts/family_info_fetcher_unittest.cc

Issue 783083002: Add support for child accounts. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: remove CrOS for now Created 6 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/browser/supervised_user/child_accounts/family_info_fetcher_unittest.cc
diff --git a/chrome/browser/supervised_user/child_accounts/family_info_fetcher_unittest.cc b/chrome/browser/supervised_user/child_accounts/family_info_fetcher_unittest.cc
new file mode 100644
index 0000000000000000000000000000000000000000..0d4d0938d1125ec00f136ff726676c0c7171ad90
--- /dev/null
+++ b/chrome/browser/supervised_user/child_accounts/family_info_fetcher_unittest.cc
@@ -0,0 +1,322 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <string>
+#include <vector>
+
+#include "base/json/json_writer.h"
+#include "base/memory/scoped_ptr.h"
+#include "base/message_loop/message_loop.h"
+#include "base/message_loop/message_loop_proxy.h"
+#include "base/values.h"
+#include "chrome/browser/signin/fake_profile_oauth2_token_service.h"
+#include "chrome/browser/supervised_user/child_accounts/family_info_fetcher.h"
+#include "net/url_request/test_url_fetcher_factory.h"
+#include "net/url_request/url_request_test_util.h"
+#include "testing/gmock/include/gmock/gmock.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+const char kAccountId[] = "user@gmail.com";
+const char kDifferentAccountId[] = "some_other_user@gmail.com";
+const int kFamilyInfoFetcherURLFetcherID = 0;
+
+bool operator==(const FamilyInfoFetcher::FamilyProfile& family1,
+ const FamilyInfoFetcher::FamilyProfile& family2) {
+ return family1.id == family2.id &&
+ family1.name == family2.name;
+}
+
+bool operator==(const FamilyInfoFetcher::FamilyMember& account1,
+ const FamilyInfoFetcher::FamilyMember& account2) {
+ return account1.obfuscated_gaia_id == account2.obfuscated_gaia_id &&
+ account1.role == account2.role &&
+ account1.display_name == account2.display_name &&
+ account1.email == account2.email &&
+ account1.profile_url == account2.profile_url &&
+ account1.profile_image_url == account2.profile_image_url;
+}
+
+namespace {
+
+std::string BuildGetFamilyProfileResponse(
+ const FamilyInfoFetcher::FamilyProfile& family) {
+ base::DictionaryValue dict;
+ base::DictionaryValue* family_dict = new base::DictionaryValue;
+ family_dict->SetStringWithoutPathExpansion("familyId", family.id);
+ base::DictionaryValue* profile_dict = new base::DictionaryValue;
+ profile_dict->SetStringWithoutPathExpansion("name", family.name);
+ family_dict->SetWithoutPathExpansion("profile", profile_dict);
+ dict.SetWithoutPathExpansion("family", family_dict);
+ std::string result;
+ base::JSONWriter::Write(&dict, &result);
+ return result;
+}
+
+std::string BuildEmptyGetFamilyProfileResponse() {
+ base::DictionaryValue dict;
+ base::DictionaryValue* family_dict = new base::DictionaryValue;
+ dict.SetWithoutPathExpansion("family", family_dict);
+ std::string result;
+ base::JSONWriter::Write(&dict, &result);
+ return result;
+}
+
+std::string BuildGetFamilyMembersResponse(
+ const std::vector<FamilyInfoFetcher::FamilyMember>& members) {
+ base::DictionaryValue dict;
+ base::ListValue* list = new base::ListValue;
+ for (size_t i = 0; i < members.size(); i++) {
+ const FamilyInfoFetcher::FamilyMember& member = members[i];
+ base::DictionaryValue* member_dict = new base::DictionaryValue;
+ member_dict->SetStringWithoutPathExpansion("userId",
+ member.obfuscated_gaia_id);
+ member_dict->SetStringWithoutPathExpansion(
+ "role", FamilyInfoFetcher::RoleToString(member.role));
+ if (!member.display_name.empty() ||
+ !member.email.empty() ||
+ !member.profile_url.empty() ||
+ !member.profile_image_url.empty()) {
+ base::DictionaryValue* profile_dict = new base::DictionaryValue;
+ if (!member.display_name.empty())
+ profile_dict->SetStringWithoutPathExpansion("displayName",
+ member.display_name);
+ if (!member.email.empty())
+ profile_dict->SetStringWithoutPathExpansion("email",
+ member.email);
+ if (!member.profile_url.empty())
+ profile_dict->SetStringWithoutPathExpansion("profileUrl",
+ member.profile_url);
+ if (!member.profile_image_url.empty())
+ profile_dict->SetStringWithoutPathExpansion("profileImageUrl",
+ member.profile_image_url);
+
+ member_dict->SetWithoutPathExpansion("profile", profile_dict);
+ }
+ list->Append(member_dict);
+ }
+ dict.SetWithoutPathExpansion("members", list);
+ std::string result;
+ base::JSONWriter::Write(&dict, &result);
+ return result;
+}
+
+} // namespace
+
+class FamilyInfoFetcherTest : public testing::Test,
+ public FamilyInfoFetcher::Consumer {
+ public:
+ FamilyInfoFetcherTest()
+ : request_context_(new net::TestURLRequestContextGetter(
+ base::MessageLoopProxy::current())),
+ fetcher_(this, kAccountId, &token_service_, request_context_.get()) {
+ }
+
+ MOCK_METHOD1(OnGetFamilyProfileSuccess,
+ void(const FamilyInfoFetcher::FamilyProfile& family));
+ MOCK_METHOD1(OnGetFamilyMembersSuccess,
+ void(const std::vector<FamilyInfoFetcher::FamilyMember>&
+ members));
+ MOCK_METHOD1(OnFailure, void(FamilyInfoFetcher::ErrorCode error));
+
+ protected:
+ void IssueRefreshToken() {
+ token_service_.UpdateCredentials(kAccountId, "refresh_token");
+ }
+
+ void IssueRefreshTokenForDifferentAccount() {
+ token_service_.UpdateCredentials(kDifferentAccountId, "refresh_token");
+ }
+
+ void IssueAccessToken() {
+ token_service_.IssueAllTokensForAccount(
+ kAccountId,
+ "access_token",
+ base::Time::Now() + base::TimeDelta::FromHours(1));
+ }
+
+ net::TestURLFetcher* GetURLFetcher() {
+ net::TestURLFetcher* url_fetcher =
+ url_fetcher_factory_.GetFetcherByID(
+ kFamilyInfoFetcherURLFetcherID);
+ EXPECT_TRUE(url_fetcher);
+ return url_fetcher;
+ }
+
+ void SendResponse(net::URLRequestStatus::Status status,
+ const std::string& response) {
+ net::TestURLFetcher* url_fetcher = GetURLFetcher();
+ url_fetcher->set_status(net::URLRequestStatus(status, 0));
+ url_fetcher->set_response_code(net::HTTP_OK);
+ url_fetcher->SetResponseString(response);
+ url_fetcher->delegate()->OnURLFetchComplete(url_fetcher);
+ }
+
+ void SendValidGetFamilyProfileResponse(
+ const FamilyInfoFetcher::FamilyProfile& family) {
+ SendResponse(net::URLRequestStatus::SUCCESS,
+ BuildGetFamilyProfileResponse(family));
+ }
+
+ void SendValidGetFamilyMembersResponse(
+ const std::vector<FamilyInfoFetcher::FamilyMember>& members) {
+ SendResponse(net::URLRequestStatus::SUCCESS,
+ BuildGetFamilyMembersResponse(members));
+ }
+
+ void SendInvalidGetFamilyProfileResponse() {
+ SendResponse(net::URLRequestStatus::SUCCESS,
+ BuildEmptyGetFamilyProfileResponse());
+ }
+
+ void SendFailedResponse() {
+ SendResponse(net::URLRequestStatus::CANCELED, std::string());
+ }
+
+ base::MessageLoop message_loop_;
+ FakeProfileOAuth2TokenService token_service_;
+ scoped_refptr<net::TestURLRequestContextGetter> request_context_;
+ net::TestURLFetcherFactory url_fetcher_factory_;
+ FamilyInfoFetcher fetcher_;
+};
+
+
+TEST_F(FamilyInfoFetcherTest, GetFamilyProfileSuccess) {
+ IssueRefreshToken();
+
+ fetcher_.StartGetFamilyProfile();
+
+ // Since a refresh token is already available, we should immediately get a
+ // request for an access token.
+ EXPECT_EQ(1U, token_service_.GetPendingRequests().size());
+
+ IssueAccessToken();
+
+ FamilyInfoFetcher::FamilyProfile family("test", "My Test Family");
+ EXPECT_CALL(*this, OnGetFamilyProfileSuccess(family));
+ SendValidGetFamilyProfileResponse(family);
+}
+
+TEST_F(FamilyInfoFetcherTest, GetFamilyMembersSuccess) {
+ IssueRefreshToken();
+
+ fetcher_.StartGetFamilyMembers();
+
+ // Since a refresh token is already available, we should immediately get a
+ // request for an access token.
+ EXPECT_EQ(1U, token_service_.GetPendingRequests().size());
+
+ IssueAccessToken();
+
+ std::vector<FamilyInfoFetcher::FamilyMember> members;
+ members.push_back(
+ FamilyInfoFetcher::FamilyMember("someObfuscatedGaiaId",
+ FamilyInfoFetcher::HEAD_OF_HOUSEHOLD,
+ "Homer Simpson",
+ "homer@simpson.com",
+ "http://profile.url/homer",
+ "http://profile.url/homer/image"));
+ members.push_back(
+ FamilyInfoFetcher::FamilyMember("anotherObfuscatedGaiaId",
+ FamilyInfoFetcher::PARENT,
+ "Marge Simpson",
+ std::string(),
+ "http://profile.url/marge",
+ std::string()));
+ members.push_back(
+ FamilyInfoFetcher::FamilyMember("obfuscatedGaiaId3",
+ FamilyInfoFetcher::CHILD,
+ "Lisa Simpson",
+ "lisa@gmail.com",
+ std::string(),
+ "http://profile.url/lisa/image"));
+ members.push_back(
+ FamilyInfoFetcher::FamilyMember("obfuscatedGaiaId4",
+ FamilyInfoFetcher::CHILD,
+ "Bart Simpson",
+ "bart@bart.bart",
+ std::string(),
+ std::string()));
+ members.push_back(
+ FamilyInfoFetcher::FamilyMember("obfuscatedGaiaId5",
+ FamilyInfoFetcher::MEMBER,
+ std::string(),
+ std::string(),
+ std::string(),
+ std::string()));
+
+ EXPECT_CALL(*this, OnGetFamilyMembersSuccess(members));
+ SendValidGetFamilyMembersResponse(members);
+}
+
+
+TEST_F(FamilyInfoFetcherTest, SuccessAfterWaitingForRefreshToken) {
+ fetcher_.StartGetFamilyProfile();
+
+ // Since there is no refresh token yet, we should not get a request for an
+ // access token at this point.
+ EXPECT_EQ(0U, token_service_.GetPendingRequests().size());
+
+ IssueRefreshToken();
+
+ // Now there is a refresh token and we should have got a request for an
+ // access token.
+ EXPECT_EQ(1U, token_service_.GetPendingRequests().size());
+
+ IssueAccessToken();
+
+ FamilyInfoFetcher::FamilyProfile family("test", "My Test Family");
+ EXPECT_CALL(*this, OnGetFamilyProfileSuccess(family));
+ SendValidGetFamilyProfileResponse(family);
+}
+
+TEST_F(FamilyInfoFetcherTest, NoRefreshToken) {
+ fetcher_.StartGetFamilyProfile();
+
+ IssueRefreshTokenForDifferentAccount();
+
+ // Credentials for a different user should be ignored, i.e. not result in a
+ // request for an access token.
+ EXPECT_EQ(0U, token_service_.GetPendingRequests().size());
+
+ // After all refresh tokens have been loaded, there is still no token for our
+ // user, so we expect a token error.
+ EXPECT_CALL(*this, OnFailure(FamilyInfoFetcher::TOKEN_ERROR));
+ token_service_.IssueAllRefreshTokensLoaded();
+}
+
+TEST_F(FamilyInfoFetcherTest, GetTokenFailure) {
+ IssueRefreshToken();
+
+ fetcher_.StartGetFamilyProfile();
+
+ // On failure to get an access token we expect a token error.
+ EXPECT_CALL(*this, OnFailure(FamilyInfoFetcher::TOKEN_ERROR));
+ token_service_.IssueErrorForAllPendingRequestsForAccount(
+ kAccountId,
+ GoogleServiceAuthError(GoogleServiceAuthError::INVALID_GAIA_CREDENTIALS));
+}
+
+TEST_F(FamilyInfoFetcherTest, InvalidResponse) {
+ IssueRefreshToken();
+
+ fetcher_.StartGetFamilyProfile();
+
+ IssueAccessToken();
+
+ // Invalid response data should result in a service error.
+ EXPECT_CALL(*this, OnFailure(FamilyInfoFetcher::SERVICE_ERROR));
+ SendInvalidGetFamilyProfileResponse();
+}
+
+TEST_F(FamilyInfoFetcherTest, FailedResponse) {
+ IssueRefreshToken();
+
+ fetcher_.StartGetFamilyProfile();
+
+ IssueAccessToken();
+
+ // Failed API call should result in a network error.
+ EXPECT_CALL(*this, OnFailure(FamilyInfoFetcher::NETWORK_ERROR));
+ SendFailedResponse();
+}

Powered by Google App Engine
This is Rietveld 408576698