Stack sampling profiler: add fire-and-forget interface
[chromium-blink-merge.git] / components / signin / core / browser / account_tracker_service_unittest.cc
blob9fd403e2fbb7e204030d5dfa31c626f6c1eeb358
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include <algorithm>
6 #include <vector>
8 #include "base/prefs/pref_registry_simple.h"
9 #include "base/prefs/scoped_user_pref_update.h"
10 #include "base/prefs/testing_pref_service.h"
11 #include "base/strings/stringprintf.h"
12 #include "components/signin/core/browser/account_fetcher_service.h"
13 #include "components/signin/core/browser/account_tracker_service.h"
14 #include "components/signin/core/browser/fake_account_fetcher_service.h"
15 #include "components/signin/core/browser/test_signin_client.h"
16 #include "components/signin/core/common/signin_pref_names.h"
17 #include "google_apis/gaia/fake_oauth2_token_service.h"
18 #include "google_apis/gaia/gaia_oauth_client.h"
19 #include "net/http/http_status_code.h"
20 #include "net/url_request/test_url_fetcher_factory.h"
21 #include "net/url_request/url_fetcher_delegate.h"
22 #include "net/url_request/url_request_test_util.h"
23 #include "testing/gtest/include/gtest/gtest.h"
25 namespace {
27 const std::string kTokenInfoResponseFormat =
28 "{ \
29 \"id\": \"%s\", \
30 \"email\": \"%s\", \
31 \"hd\": \"\", \
32 \"name\": \"%s\", \
33 \"given_name\": \"%s\", \
34 \"locale\": \"%s\", \
35 \"picture\": \"%s\" \
36 }";
38 const std::string kTokenInfoIncompleteResponseFormat =
39 "{ \
40 \"id\": \"%s\", \
41 \"email\": \"%s\", \
42 \"hd\": \"\", \
43 }";
45 enum TrackingEventType {
46 UPDATED,
47 REMOVED,
50 std::string AccountIdToEmail(const std::string account_id) {
51 return account_id + "@gmail.com";
54 std::string AccountIdToGaiaId(const std::string account_id) {
55 return "gaia-" + account_id;
58 std::string AccountIdToFullName(const std::string account_id) {
59 return "full-name-" + account_id;
62 std::string AccountIdToGivenName(const std::string account_id) {
63 return "given-name-" + account_id;
66 std::string AccountIdToLocale(const std::string account_id) {
67 return "locale-" + account_id;
70 std::string AccountIdToPictureURL(const std::string account_id) {
71 return "picture_url-" + account_id;
74 void CheckAccountDetails(const std::string account_id,
75 const AccountTrackerService::AccountInfo& info) {
76 EXPECT_EQ(account_id, info.account_id);
77 EXPECT_EQ(AccountIdToGaiaId(account_id), info.gaia);
78 EXPECT_EQ(AccountIdToEmail(account_id), info.email);
79 EXPECT_EQ(AccountTrackerService::kNoHostedDomainFound,
80 info.hosted_domain);
81 EXPECT_EQ(AccountIdToFullName(account_id), info.full_name);
82 EXPECT_EQ(AccountIdToGivenName(account_id), info.given_name);
83 EXPECT_EQ(AccountIdToLocale(account_id), info.locale);
86 void FakeUserInfoFetchSuccess(FakeAccountFetcherService* fetcher,
87 const std::string& account_id) {
88 fetcher->FakeUserInfoFetchSuccess(
89 account_id, AccountIdToEmail(account_id), AccountIdToGaiaId(account_id),
90 AccountTrackerService::kNoHostedDomainFound,
91 AccountIdToFullName(account_id), AccountIdToGivenName(account_id),
92 AccountIdToLocale(account_id), AccountIdToPictureURL(account_id));
95 class TrackingEvent {
96 public:
97 TrackingEvent(TrackingEventType type,
98 const std::string& account_id,
99 const std::string& gaia_id)
100 : type_(type),
101 account_id_(account_id),
102 gaia_id_(gaia_id) {}
104 TrackingEvent(TrackingEventType type,
105 const std::string& account_id)
106 : type_(type),
107 account_id_(account_id),
108 gaia_id_(AccountIdToGaiaId(account_id)) {}
110 bool operator==(const TrackingEvent& event) const {
111 return type_ == event.type_ && account_id_ == event.account_id_ &&
112 gaia_id_ == event.gaia_id_;
115 std::string ToString() const {
116 const char * typestr = "INVALID";
117 switch (type_) {
118 case UPDATED:
119 typestr = "UPD";
120 break;
121 case REMOVED:
122 typestr = "REM";
123 break;
125 return base::StringPrintf("{ type: %s, account_id: %s, gaia: %s }",
126 typestr,
127 account_id_.c_str(),
128 gaia_id_.c_str());
131 private:
132 friend bool CompareByUser(TrackingEvent a, TrackingEvent b);
134 TrackingEventType type_;
135 std::string account_id_;
136 std::string gaia_id_;
139 bool CompareByUser(TrackingEvent a, TrackingEvent b) {
140 return a.account_id_ < b.account_id_;
143 std::string Str(const std::vector<TrackingEvent>& events) {
144 std::string str = "[";
145 bool needs_comma = false;
146 for (std::vector<TrackingEvent>::const_iterator it =
147 events.begin(); it != events.end(); ++it) {
148 if (needs_comma)
149 str += ",\n ";
150 needs_comma = true;
151 str += it->ToString();
153 str += "]";
154 return str;
157 class AccountTrackerObserver : public AccountTrackerService::Observer {
158 public:
159 AccountTrackerObserver() {}
160 ~AccountTrackerObserver() override {}
162 void Clear();
163 void SortEventsByUser();
165 testing::AssertionResult CheckEvents();
166 testing::AssertionResult CheckEvents(const TrackingEvent& e1);
167 testing::AssertionResult CheckEvents(const TrackingEvent& e1,
168 const TrackingEvent& e2);
169 testing::AssertionResult CheckEvents(const TrackingEvent& e1,
170 const TrackingEvent& e2,
171 const TrackingEvent& e3);
173 private:
174 // AccountTrackerService::Observer implementation
175 void OnAccountUpdated(const AccountTrackerService::AccountInfo& ids) override;
176 void OnAccountRemoved(const AccountTrackerService::AccountInfo& ids) override;
178 testing::AssertionResult CheckEvents(
179 const std::vector<TrackingEvent>& events);
181 std::vector<TrackingEvent> events_;
184 void AccountTrackerObserver::OnAccountUpdated(
185 const AccountTrackerService::AccountInfo& ids) {
186 events_.push_back(TrackingEvent(UPDATED, ids.account_id, ids.gaia));
189 void AccountTrackerObserver::OnAccountRemoved(
190 const AccountTrackerService::AccountInfo& ids) {
191 events_.push_back(TrackingEvent(REMOVED, ids.account_id, ids.gaia));
194 void AccountTrackerObserver::Clear() {
195 events_.clear();
198 void AccountTrackerObserver::SortEventsByUser() {
199 std::stable_sort(events_.begin(), events_.end(), CompareByUser);
202 testing::AssertionResult AccountTrackerObserver::CheckEvents() {
203 std::vector<TrackingEvent> events;
204 return CheckEvents(events);
207 testing::AssertionResult AccountTrackerObserver::CheckEvents(
208 const TrackingEvent& e1) {
209 std::vector<TrackingEvent> events;
210 events.push_back(e1);
211 return CheckEvents(events);
214 testing::AssertionResult AccountTrackerObserver::CheckEvents(
215 const TrackingEvent& e1,
216 const TrackingEvent& e2) {
217 std::vector<TrackingEvent> events;
218 events.push_back(e1);
219 events.push_back(e2);
220 return CheckEvents(events);
223 testing::AssertionResult AccountTrackerObserver::CheckEvents(
224 const TrackingEvent& e1,
225 const TrackingEvent& e2,
226 const TrackingEvent& e3) {
227 std::vector<TrackingEvent> events;
228 events.push_back(e1);
229 events.push_back(e2);
230 events.push_back(e3);
231 return CheckEvents(events);
234 testing::AssertionResult AccountTrackerObserver::CheckEvents(
235 const std::vector<TrackingEvent>& events) {
236 std::string maybe_newline = (events.size() + events_.size()) > 2 ? "\n" : "";
237 testing::AssertionResult result(
238 (events_ == events)
239 ? testing::AssertionSuccess()
240 : (testing::AssertionFailure()
241 << "Expected " << maybe_newline << Str(events) << ", "
242 << maybe_newline << "Got " << maybe_newline << Str(events_)));
243 events_.clear();
244 return result;
247 } // namespace
249 class AccountTrackerServiceTest : public testing::Test {
250 public:
251 AccountTrackerServiceTest() {}
253 ~AccountTrackerServiceTest() override {}
255 void SetUp() override {
256 fake_oauth2_token_service_.reset(new FakeOAuth2TokenService());
258 pref_service_.registry()->RegisterListPref(
259 AccountTrackerService::kAccountInfoPref);
260 pref_service_.registry()->RegisterIntegerPref(
261 prefs::kAccountIdMigrationState,
262 AccountTrackerService::MIGRATION_NOT_STARTED);
263 pref_service_.registry()->RegisterInt64Pref(
264 AccountFetcherService::kLastUpdatePref, 0);
265 signin_client_.reset(new TestSigninClient(&pref_service_));
266 signin_client_.get()->SetURLRequestContext(
267 new net::TestURLRequestContextGetter(message_loop_.task_runner()));
269 account_tracker_.reset(new AccountTrackerService());
270 account_tracker_->Initialize(signin_client_.get());
272 account_fetcher_.reset(new AccountFetcherService());
273 account_fetcher_->Initialize(signin_client_.get(),
274 fake_oauth2_token_service_.get(),
275 account_tracker_.get(), nullptr);
277 account_fetcher_->EnableNetworkFetches();
280 void TearDown() override {
281 account_fetcher_->Shutdown();
282 account_tracker_->Shutdown();
285 void SimulateTokenAvailable(const std::string& account_id) {
286 fake_oauth2_token_service_->AddAccount(account_id);
289 void SimulateTokenRevoked(const std::string& account_id) {
290 fake_oauth2_token_service_->RemoveAccount(account_id);
293 // Helpers to fake access token and user info fetching
294 void IssueAccessToken(const std::string& account_id) {
295 fake_oauth2_token_service_->IssueAllTokensForAccount(
296 account_id, "access_token-" + account_id, base::Time::Max());
299 std::string GenerateValidTokenInfoResponse(const std::string& account_id) {
300 return base::StringPrintf(
301 kTokenInfoResponseFormat.c_str(),
302 AccountIdToGaiaId(account_id).c_str(),
303 AccountIdToEmail(account_id).c_str(),
304 AccountIdToFullName(account_id).c_str(),
305 AccountIdToGivenName(account_id).c_str(),
306 AccountIdToLocale(account_id).c_str(),
307 AccountIdToPictureURL(account_id).c_str());
310 std::string GenerateIncompleteTokenInfoResponse(
311 const std::string& account_id) {
312 return base::StringPrintf(
313 kTokenInfoIncompleteResponseFormat.c_str(),
314 AccountIdToGaiaId(account_id).c_str(),
315 AccountIdToEmail(account_id).c_str());
317 void ReturnOAuthUrlFetchSuccess(const std::string& account_id);
318 void ReturnOAuthUrlFetchSuccessIncomplete(const std::string& account_id);
319 void ReturnOAuthUrlFetchFailure(const std::string& account_id);
321 net::TestURLFetcherFactory* test_fetcher_factory() {
322 return &test_fetcher_factory_;
324 AccountFetcherService* account_fetcher() { return account_fetcher_.get(); }
325 AccountTrackerService* account_tracker() { return account_tracker_.get(); }
326 OAuth2TokenService* token_service() {
327 return fake_oauth2_token_service_.get();
329 SigninClient* signin_client() { return signin_client_.get(); }
331 private:
332 void ReturnOAuthUrlFetchResults(int fetcher_id,
333 net::HttpStatusCode response_code,
334 const std::string& response_string);
336 base::MessageLoopForIO message_loop_;
337 net::TestURLFetcherFactory test_fetcher_factory_;
338 scoped_ptr<FakeOAuth2TokenService> fake_oauth2_token_service_;
339 TestingPrefServiceSimple pref_service_;
340 scoped_ptr<AccountFetcherService> account_fetcher_;
341 scoped_ptr<AccountTrackerService> account_tracker_;
342 scoped_ptr<TestSigninClient> signin_client_;
345 void AccountTrackerServiceTest::ReturnOAuthUrlFetchResults(
346 int fetcher_id,
347 net::HttpStatusCode response_code,
348 const std::string& response_string) {
349 net::TestURLFetcher* fetcher =
350 test_fetcher_factory_.GetFetcherByID(fetcher_id);
351 ASSERT_TRUE(fetcher);
352 fetcher->set_response_code(response_code);
353 fetcher->SetResponseString(response_string);
354 fetcher->delegate()->OnURLFetchComplete(fetcher);
357 void AccountTrackerServiceTest::ReturnOAuthUrlFetchSuccess(
358 const std::string& account_id) {
359 IssueAccessToken(account_id);
360 ReturnOAuthUrlFetchResults(gaia::GaiaOAuthClient::kUrlFetcherId,
361 net::HTTP_OK,
362 GenerateValidTokenInfoResponse(account_id));
365 void AccountTrackerServiceTest::ReturnOAuthUrlFetchSuccessIncomplete(
366 const std::string& account_id) {
367 IssueAccessToken(account_id);
368 ReturnOAuthUrlFetchResults(gaia::GaiaOAuthClient::kUrlFetcherId,
369 net::HTTP_OK,
370 GenerateIncompleteTokenInfoResponse(account_id));
373 void AccountTrackerServiceTest::ReturnOAuthUrlFetchFailure(
374 const std::string& account_id) {
375 IssueAccessToken(account_id);
376 ReturnOAuthUrlFetchResults(
377 gaia::GaiaOAuthClient::kUrlFetcherId, net::HTTP_BAD_REQUEST, "");
380 TEST_F(AccountTrackerServiceTest, Basic) {
383 TEST_F(AccountTrackerServiceTest, TokenAvailable) {
384 AccountTrackerObserver observer;
385 account_tracker()->AddObserver(&observer);
386 SimulateTokenAvailable("alpha");
387 ASSERT_FALSE(account_fetcher()->IsAllUserInfoFetched());
388 ASSERT_TRUE(observer.CheckEvents());
389 account_tracker()->RemoveObserver(&observer);
392 TEST_F(AccountTrackerServiceTest, TokenAvailable_Revoked) {
393 AccountTrackerObserver observer;
394 account_tracker()->AddObserver(&observer);
395 SimulateTokenAvailable("alpha");
396 SimulateTokenRevoked("alpha");
397 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
398 ASSERT_TRUE(observer.CheckEvents());
399 account_tracker()->RemoveObserver(&observer);
402 TEST_F(AccountTrackerServiceTest, TokenAvailable_UserInfo) {
403 AccountTrackerObserver observer;
404 account_tracker()->AddObserver(&observer);
405 SimulateTokenAvailable("alpha");
406 ReturnOAuthUrlFetchSuccess("alpha");
407 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
408 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha")));
409 account_tracker()->RemoveObserver(&observer);
412 TEST_F(AccountTrackerServiceTest, TokenAvailable_UserInfo_Revoked) {
413 AccountTrackerObserver observer;
414 account_tracker()->AddObserver(&observer);
415 SimulateTokenAvailable("alpha");
416 ReturnOAuthUrlFetchSuccess("alpha");
417 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
418 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha")));
419 SimulateTokenRevoked("alpha");
420 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(REMOVED, "alpha")));
421 account_tracker()->RemoveObserver(&observer);
424 TEST_F(AccountTrackerServiceTest, TokenAvailable_UserInfoFailed) {
425 AccountTrackerObserver observer;
426 account_tracker()->AddObserver(&observer);
427 SimulateTokenAvailable("alpha");
428 ReturnOAuthUrlFetchFailure("alpha");
429 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
430 ASSERT_TRUE(observer.CheckEvents());
431 account_tracker()->RemoveObserver(&observer);
434 TEST_F(AccountTrackerServiceTest, TokenAvailableTwice_UserInfoOnce) {
435 AccountTrackerObserver observer;
436 account_tracker()->AddObserver(&observer);
437 SimulateTokenAvailable("alpha");
438 ReturnOAuthUrlFetchSuccess("alpha");
439 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
440 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha")));
442 SimulateTokenAvailable("alpha");
443 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
444 ASSERT_TRUE(observer.CheckEvents());
445 account_tracker()->RemoveObserver(&observer);
448 TEST_F(AccountTrackerServiceTest, TokenAlreadyExists) {
449 SimulateTokenAvailable("alpha");
450 AccountTrackerService tracker;
451 AccountTrackerObserver observer;
452 AccountFetcherService fetcher;
454 tracker.AddObserver(&observer);
455 tracker.Initialize(signin_client());
457 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
458 fetcher.EnableNetworkFetches();
459 ASSERT_FALSE(fetcher.IsAllUserInfoFetched());
460 ASSERT_TRUE(observer.CheckEvents());
461 tracker.RemoveObserver(&observer);
462 tracker.Shutdown();
463 fetcher.Shutdown();
466 TEST_F(AccountTrackerServiceTest, TwoTokenAvailable_TwoUserInfo) {
467 AccountTrackerObserver observer;
468 account_tracker()->AddObserver(&observer);
469 SimulateTokenAvailable("alpha");
470 SimulateTokenAvailable("beta");
471 ReturnOAuthUrlFetchSuccess("alpha");
472 ReturnOAuthUrlFetchSuccess("beta");
473 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
474 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha"),
475 TrackingEvent(UPDATED, "beta")));
476 account_tracker()->RemoveObserver(&observer);
479 TEST_F(AccountTrackerServiceTest, TwoTokenAvailable_OneUserInfo) {
480 AccountTrackerObserver observer;
481 account_tracker()->AddObserver(&observer);
482 SimulateTokenAvailable("alpha");
483 SimulateTokenAvailable("beta");
484 ReturnOAuthUrlFetchSuccess("beta");
485 ASSERT_FALSE(account_fetcher()->IsAllUserInfoFetched());
486 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "beta")));
487 ReturnOAuthUrlFetchSuccess("alpha");
488 ASSERT_TRUE(account_fetcher()->IsAllUserInfoFetched());
489 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha")));
490 account_tracker()->RemoveObserver(&observer);
493 TEST_F(AccountTrackerServiceTest, GetAccounts) {
494 SimulateTokenAvailable("alpha");
495 SimulateTokenAvailable("beta");
496 SimulateTokenAvailable("gamma");
497 ReturnOAuthUrlFetchSuccess("alpha");
498 ReturnOAuthUrlFetchSuccess("beta");
499 ReturnOAuthUrlFetchSuccess("gamma");
501 std::vector<AccountTrackerService::AccountInfo> infos =
502 account_tracker()->GetAccounts();
504 EXPECT_EQ(3u, infos.size());
505 CheckAccountDetails("alpha", infos[0]);
506 CheckAccountDetails("beta", infos[1]);
507 CheckAccountDetails("gamma", infos[2]);
510 TEST_F(AccountTrackerServiceTest, GetAccountInfo_Empty) {
511 AccountTrackerService::AccountInfo info =
512 account_tracker()->GetAccountInfo("alpha");
513 ASSERT_EQ("", info.account_id);
516 TEST_F(AccountTrackerServiceTest, GetAccountInfo_TokenAvailable) {
517 SimulateTokenAvailable("alpha");
518 AccountTrackerService::AccountInfo info =
519 account_tracker()->GetAccountInfo("alpha");
520 ASSERT_EQ("alpha", info.account_id);
521 ASSERT_EQ("", info.gaia);
522 ASSERT_EQ("", info.email);
525 TEST_F(AccountTrackerServiceTest, GetAccountInfo_TokenAvailable_UserInfo) {
526 SimulateTokenAvailable("alpha");
527 ReturnOAuthUrlFetchSuccess("alpha");
528 AccountTrackerService::AccountInfo info =
529 account_tracker()->GetAccountInfo("alpha");
530 CheckAccountDetails("alpha", info);
533 TEST_F(AccountTrackerServiceTest, GetAccountInfo_TokenAvailable_EnableNetwork) {
534 // Shutdown the network-enabled tracker built into the test case.
535 TearDown();
537 // Create an account tracker and an account fetcher service but do not enable
538 // network fetches.
539 AccountTrackerService tracker;
540 tracker.Initialize(signin_client());
542 AccountFetcherService fetcher_service;
543 fetcher_service.Initialize(signin_client(), token_service(), &tracker,
544 nullptr);
546 SimulateTokenAvailable("alpha");
547 IssueAccessToken("alpha");
548 // No fetcher has been created yet.
549 net::TestURLFetcher* fetcher = test_fetcher_factory()->GetFetcherByID(
550 gaia::GaiaOAuthClient::kUrlFetcherId);
551 ASSERT_FALSE(fetcher);
553 // Enable the network to create the fetcher then issue the access token.
554 fetcher_service.EnableNetworkFetches();
556 // Fetcher was created and executes properly.
557 ReturnOAuthUrlFetchSuccess("alpha");
559 AccountTrackerService::AccountInfo info =
560 tracker.GetAccountInfo("alpha");
561 CheckAccountDetails("alpha", info);
562 fetcher_service.Shutdown();
563 tracker.Shutdown();
566 TEST_F(AccountTrackerServiceTest, FindAccountInfoByGaiaId) {
567 SimulateTokenAvailable("alpha");
568 ReturnOAuthUrlFetchSuccess("alpha");
570 std::string gaia_id = AccountIdToGaiaId("alpha");
571 AccountTrackerService::AccountInfo info =
572 account_tracker()->FindAccountInfoByGaiaId(gaia_id);
573 ASSERT_EQ("alpha", info.account_id);
574 ASSERT_EQ(gaia_id, info.gaia);
576 gaia_id = AccountIdToGaiaId("beta");
577 info = account_tracker()->FindAccountInfoByGaiaId(gaia_id);
578 ASSERT_EQ("", info.account_id);
581 TEST_F(AccountTrackerServiceTest, FindAccountInfoByEmail) {
582 SimulateTokenAvailable("alpha");
583 ReturnOAuthUrlFetchSuccess("alpha");
585 std::string email = AccountIdToEmail("alpha");
586 AccountTrackerService::AccountInfo info =
587 account_tracker()->FindAccountInfoByEmail(email);
588 ASSERT_EQ("alpha", info.account_id);
589 ASSERT_EQ(email, info.email);
591 // Should also work with "canonically-equal" email addresses.
592 info = account_tracker()->FindAccountInfoByEmail("Alpha@Gmail.COM");
593 ASSERT_EQ("alpha", info.account_id);
594 ASSERT_EQ(email, info.email);
595 info = account_tracker()->FindAccountInfoByEmail("al.pha@gmail.com");
596 ASSERT_EQ("alpha", info.account_id);
597 ASSERT_EQ(email, info.email);
599 email = AccountIdToEmail("beta");
600 info = account_tracker()->FindAccountInfoByEmail(email);
601 ASSERT_EQ("", info.account_id);
604 TEST_F(AccountTrackerServiceTest, Persistence) {
605 // Create a tracker and add two accounts. This should cause the accounts
606 // to be saved to persistence.
608 AccountTrackerService tracker;
609 tracker.Initialize(signin_client());
610 SimulateTokenAvailable("alpha");
611 ReturnOAuthUrlFetchSuccess("alpha");
612 SimulateTokenAvailable("beta");
613 ReturnOAuthUrlFetchSuccess("beta");
614 tracker.Shutdown();
617 // Create a new tracker and make sure it loads the accounts correctly from
618 // persistence.
620 AccountTrackerService tracker;
621 AccountTrackerObserver observer;
622 tracker.AddObserver(&observer);
623 tracker.Initialize(signin_client());
624 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "alpha"),
625 TrackingEvent(UPDATED, "beta")));
626 tracker.RemoveObserver(&observer);
628 std::vector<AccountTrackerService::AccountInfo> infos =
629 tracker.GetAccounts();
630 ASSERT_EQ(2u, infos.size());
631 CheckAccountDetails("alpha", infos[0]);
632 CheckAccountDetails("beta", infos[1]);
634 FakeAccountFetcherService fetcher;
635 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
636 fetcher.EnableNetworkFetches();
637 // Remove an account.
638 // This will allow testing removal as well as child accounts which is only
639 // allowed for a single account.
640 SimulateTokenRevoked("alpha");
641 fetcher.FakeSetIsChildAccount("beta", true);
643 fetcher.Shutdown();
644 tracker.Shutdown();
647 // Create a new tracker and make sure it loads the single account from
648 // persistence. Also verify it is a child account.
650 AccountTrackerService tracker;
651 tracker.Initialize(signin_client());
653 std::vector<AccountTrackerService::AccountInfo> infos =
654 tracker.GetAccounts();
655 ASSERT_EQ(1u, infos.size());
656 CheckAccountDetails("beta", infos[0]);
657 ASSERT_TRUE(infos[0].is_child_account);
658 tracker.Shutdown();
662 TEST_F(AccountTrackerServiceTest, SeedAccountInfo) {
663 std::vector<AccountTrackerService::AccountInfo> infos =
664 account_tracker()->GetAccounts();
665 EXPECT_EQ(0u, infos.size());
667 const std::string gaia_id = AccountIdToGaiaId("alpha");
668 const std::string email = AccountIdToEmail("alpha");
669 const std::string account_id =
670 account_tracker()->PickAccountIdForAccount(gaia_id, email);
671 account_tracker()->SeedAccountInfo(gaia_id, email);
673 infos = account_tracker()->GetAccounts();
674 EXPECT_EQ(1u, infos.size());
675 EXPECT_EQ(account_id, infos[0].account_id);
676 EXPECT_EQ(gaia_id, infos[0].gaia);
677 EXPECT_EQ(email, infos[0].email);
680 TEST_F(AccountTrackerServiceTest, UpgradeToFullAccountInfo) {
681 // Start by simulating an incomplete account info and let it be saved to
682 // prefs.
684 AccountTrackerService tracker;
685 tracker.Initialize(signin_client());
686 AccountFetcherService fetcher;
687 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
688 fetcher.EnableNetworkFetches();
689 SimulateTokenAvailable("incomplete");
690 ReturnOAuthUrlFetchSuccessIncomplete("incomplete");
691 tracker.Shutdown();
692 fetcher.Shutdown();
696 AccountTrackerService tracker;
697 tracker.Initialize(signin_client());
698 AccountFetcherService fetcher;
699 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
700 // Validate that the loaded AccountInfo from prefs is considered invalid.
701 std::vector<AccountTrackerService::AccountInfo> infos =
702 tracker.GetAccounts();
703 ASSERT_EQ(1u, infos.size());
704 ASSERT_FALSE(infos[0].IsValid());
706 // Enable network fetches and simulate the same account getting a refresh
707 // token containing all the info.
708 fetcher.EnableNetworkFetches();
709 SimulateTokenAvailable("incomplete");
710 ReturnOAuthUrlFetchSuccess("incomplete");
712 // Validate that the account is now considered valid.
713 infos = tracker.GetAccounts();
714 ASSERT_EQ(1u, infos.size());
715 ASSERT_TRUE(infos[0].IsValid());
717 tracker.Shutdown();
718 fetcher.Shutdown();
721 // Reinstantiate a tracker to validate that the AccountInfo saved to prefs is
722 // now the upgraded one, considered valid.
724 AccountTrackerService tracker;
725 AccountTrackerObserver observer;
726 tracker.AddObserver(&observer);
727 tracker.Initialize(signin_client());
728 AccountFetcherService fetcher;
729 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
731 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, "incomplete")));
732 // Enabling network fetches shouldn't cause any actual fetch since the
733 // AccountInfos loaded from prefs should be valid.
734 fetcher.EnableNetworkFetches();
736 std::vector<AccountTrackerService::AccountInfo> infos =
737 tracker.GetAccounts();
738 ASSERT_EQ(1u, infos.size());
739 ASSERT_TRUE(infos[0].IsValid());
740 // Check that no network fetches were made.
741 ASSERT_TRUE(observer.CheckEvents());
743 tracker.RemoveObserver(&observer);
744 tracker.Shutdown();
745 fetcher.Shutdown();
749 TEST_F(AccountTrackerServiceTest, TimerRefresh) {
750 // Start by creating a tracker and adding a couple accounts to be persisted to
751 // prefs.
753 AccountTrackerService tracker;
754 tracker.Initialize(signin_client());
755 AccountFetcherService fetcher;
756 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
757 fetcher.EnableNetworkFetches();
758 SimulateTokenAvailable("alpha");
759 ReturnOAuthUrlFetchSuccess("alpha");
760 SimulateTokenAvailable("beta");
761 ReturnOAuthUrlFetchSuccess("beta");
762 tracker.Shutdown();
763 fetcher.Shutdown();
766 // Rewind the time by half a day, which shouldn't be enough to trigger a
767 // network refresh.
768 base::Time fake_update = base::Time::Now() - base::TimeDelta::FromHours(12);
769 signin_client()->GetPrefs()->SetInt64(
770 AccountFetcherService::kLastUpdatePref,
771 fake_update.ToInternalValue());
773 // Instantiate a new ATS, making sure the persisted accounts are still there
774 // and that no network fetches happen.
776 AccountTrackerService tracker;
777 tracker.Initialize(signin_client());
778 AccountFetcherService fetcher;
779 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
781 ASSERT_TRUE(fetcher.IsAllUserInfoFetched());
782 std::vector<AccountTrackerService::AccountInfo> infos =
783 tracker.GetAccounts();
784 ASSERT_EQ(2u, infos.size());
785 ASSERT_TRUE(infos[0].IsValid());
786 ASSERT_TRUE(infos[1].IsValid());
788 fetcher.EnableNetworkFetches();
789 ASSERT_TRUE(fetcher.IsAllUserInfoFetched());
790 tracker.Shutdown();
791 fetcher.Shutdown();
794 // Rewind the last updated time enough to trigger a network refresh.
795 fake_update = base::Time::Now() - base::TimeDelta::FromHours(25);
796 signin_client()->GetPrefs()->SetInt64(
797 AccountFetcherService::kLastUpdatePref,
798 fake_update.ToInternalValue());
800 // Instantiate a new tracker and validate that even though the AccountInfos
801 // are still valid, the network fetches are started.
803 AccountTrackerService tracker;
804 tracker.Initialize(signin_client());
805 AccountFetcherService fetcher;
806 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
808 ASSERT_TRUE(fetcher.IsAllUserInfoFetched());
809 std::vector<AccountTrackerService::AccountInfo> infos =
810 tracker.GetAccounts();
811 ASSERT_EQ(2u, infos.size());
812 ASSERT_TRUE(infos[0].IsValid());
813 ASSERT_TRUE(infos[1].IsValid());
815 fetcher.EnableNetworkFetches();
816 ASSERT_FALSE(fetcher.IsAllUserInfoFetched());
817 tracker.Shutdown();
818 fetcher.Shutdown();
822 TEST_F(AccountTrackerServiceTest, LegacyDottedAccountIds) {
823 // Start by creating a tracker and adding an account with a dotted account id
824 // because of an old bug in token service. The token service would also add
825 // a correct non-dotted account id for the same account.
827 AccountTrackerService tracker;
828 tracker.Initialize(signin_client());
829 AccountFetcherService fetcher;
830 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
831 fetcher.EnableNetworkFetches();
832 SimulateTokenAvailable("foo.bar@gmail.com");
833 SimulateTokenAvailable("foobar@gmail.com");
834 ReturnOAuthUrlFetchSuccess("foo.bar@gmail.com");
835 ReturnOAuthUrlFetchSuccess("foobar@gmail.com");
836 tracker.Shutdown();
837 fetcher.Shutdown();
840 // Remove the bad account now from the token service to simulate that it
841 // has been "fixed".
842 SimulateTokenRevoked("foo.bar@gmail.com");
844 // Instantiate a new tracker and validate that it has only one account, and
845 // it is the correct non dotted one.
847 AccountTrackerService tracker;
848 tracker.Initialize(signin_client());
849 AccountFetcherService fetcher;
850 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
852 ASSERT_TRUE(fetcher.IsAllUserInfoFetched());
853 std::vector<AccountTrackerService::AccountInfo> infos =
854 tracker.GetAccounts();
855 ASSERT_EQ(1u, infos.size());
856 ASSERT_STREQ("foobar@gmail.com", infos[0].account_id.c_str());
857 tracker.Shutdown();
858 fetcher.Shutdown();
862 TEST_F(AccountTrackerServiceTest, MigrateAccountIdToGaiaId) {
863 if (account_tracker()->GetMigrationState() !=
864 AccountTrackerService::MIGRATION_NOT_STARTED) {
865 AccountTrackerService tracker;
866 TestingPrefServiceSimple pref;
867 AccountTrackerService::AccountInfo account_info;
869 std::string email_alpha = AccountIdToEmail("alpha");
870 std::string gaia_alpha = AccountIdToGaiaId("alpha");
871 std::string email_beta = AccountIdToEmail("beta");
872 std::string gaia_beta = AccountIdToGaiaId("beta");
874 pref.registry()->RegisterListPref(AccountTrackerService::kAccountInfoPref);
875 pref.registry()->RegisterIntegerPref(
876 prefs::kAccountIdMigrationState,
877 AccountTrackerService::MIGRATION_NOT_STARTED);
879 ListPrefUpdate update(&pref, AccountTrackerService::kAccountInfoPref);
881 base::DictionaryValue* dict = new base::DictionaryValue();
882 update->Append(dict);
883 dict->SetString("account_id", base::UTF8ToUTF16(email_alpha));
884 dict->SetString("email", base::UTF8ToUTF16(email_alpha));
885 dict->SetString("gaia", base::UTF8ToUTF16(gaia_alpha));
887 dict = new base::DictionaryValue();
888 update->Append(dict);
889 dict->SetString("account_id", base::UTF8ToUTF16(email_beta));
890 dict->SetString("email", base::UTF8ToUTF16(email_beta));
891 dict->SetString("gaia", base::UTF8ToUTF16(gaia_beta));
893 scoped_ptr<TestSigninClient> client;
894 client.reset(new TestSigninClient(&pref));
895 tracker.Initialize(client.get());
897 ASSERT_EQ(tracker.GetMigrationState(),
898 AccountTrackerService::MIGRATION_IN_PROGRESS);
900 account_info = tracker.GetAccountInfo(gaia_alpha);
901 ASSERT_EQ(account_info.account_id, gaia_alpha);
902 ASSERT_EQ(account_info.gaia, gaia_alpha);
903 ASSERT_EQ(account_info.email, email_alpha);
905 account_info = tracker.GetAccountInfo(gaia_beta);
906 ASSERT_EQ(account_info.account_id, gaia_beta);
907 ASSERT_EQ(account_info.gaia, gaia_beta);
908 ASSERT_EQ(account_info.email, email_beta);
910 std::vector<AccountTrackerService::AccountInfo> accounts =
911 tracker.GetAccounts();
912 ASSERT_EQ(2u, accounts.size());
916 TEST_F(AccountTrackerServiceTest, CanNotMigrateAccountIdToGaiaId) {
917 if ((account_tracker()->GetMigrationState() !=
918 AccountTrackerService::MIGRATION_NOT_STARTED)) {
919 AccountTrackerService tracker;
920 TestingPrefServiceSimple pref;
921 AccountTrackerService::AccountInfo account_info;
923 std::string email_alpha = AccountIdToEmail("alpha");
924 std::string gaia_alpha = AccountIdToGaiaId("alpha");
925 std::string email_beta = AccountIdToEmail("beta");
927 pref.registry()->RegisterListPref(AccountTrackerService::kAccountInfoPref);
928 pref.registry()->RegisterIntegerPref(
929 prefs::kAccountIdMigrationState,
930 AccountTrackerService::MIGRATION_NOT_STARTED);
932 ListPrefUpdate update(&pref, AccountTrackerService::kAccountInfoPref);
934 base::DictionaryValue* dict = new base::DictionaryValue();
935 update->Append(dict);
936 dict->SetString("account_id", base::UTF8ToUTF16(email_alpha));
937 dict->SetString("email", base::UTF8ToUTF16(email_alpha));
938 dict->SetString("gaia", base::UTF8ToUTF16(gaia_alpha));
940 dict = new base::DictionaryValue();
941 update->Append(dict);
942 dict->SetString("account_id", base::UTF8ToUTF16(email_beta));
943 dict->SetString("email", base::UTF8ToUTF16(email_beta));
944 dict->SetString("gaia", base::UTF8ToUTF16(std::string()));
946 scoped_ptr<TestSigninClient> client;
947 client.reset(new TestSigninClient(&pref));
948 tracker.Initialize(client.get());
950 ASSERT_EQ(tracker.GetMigrationState(),
951 AccountTrackerService::MIGRATION_NOT_STARTED);
953 account_info = tracker.GetAccountInfo(email_alpha);
954 ASSERT_EQ(account_info.account_id, email_alpha);
955 ASSERT_EQ(account_info.gaia, gaia_alpha);
956 ASSERT_EQ(account_info.email, email_alpha);
958 account_info = tracker.GetAccountInfo(email_beta);
959 ASSERT_EQ(account_info.account_id, email_beta);
960 ASSERT_EQ(account_info.email, email_beta);
962 std::vector<AccountTrackerService::AccountInfo> accounts =
963 tracker.GetAccounts();
964 ASSERT_EQ(2u, accounts.size());
968 TEST_F(AccountTrackerServiceTest, GaiaIdMigrationCrashInTheMiddle) {
969 if (account_tracker()->GetMigrationState() !=
970 AccountTrackerService::MIGRATION_NOT_STARTED) {
971 AccountTrackerService tracker;
972 TestingPrefServiceSimple pref;
973 AccountTrackerService::AccountInfo account_info;
975 std::string email_alpha = AccountIdToEmail("alpha");
976 std::string gaia_alpha = AccountIdToGaiaId("alpha");
977 std::string email_beta = AccountIdToEmail("beta");
978 std::string gaia_beta = AccountIdToGaiaId("beta");
980 pref.registry()->RegisterListPref(AccountTrackerService::kAccountInfoPref);
981 pref.registry()->RegisterIntegerPref(
982 prefs::kAccountIdMigrationState,
983 AccountTrackerService::MIGRATION_IN_PROGRESS);
985 ListPrefUpdate update(&pref, AccountTrackerService::kAccountInfoPref);
987 base::DictionaryValue* dict = new base::DictionaryValue();
988 update->Append(dict);
989 dict->SetString("account_id", base::UTF8ToUTF16(email_alpha));
990 dict->SetString("email", base::UTF8ToUTF16(email_alpha));
991 dict->SetString("gaia", base::UTF8ToUTF16(gaia_alpha));
993 dict = new base::DictionaryValue();
994 update->Append(dict);
995 dict->SetString("account_id", base::UTF8ToUTF16(email_beta));
996 dict->SetString("email", base::UTF8ToUTF16(email_beta));
997 dict->SetString("gaia", base::UTF8ToUTF16(gaia_beta));
999 // Succeed miggrated account.
1000 dict = new base::DictionaryValue();
1001 update->Append(dict);
1002 dict->SetString("account_id", base::UTF8ToUTF16(gaia_alpha));
1003 dict->SetString("email", base::UTF8ToUTF16(email_alpha));
1004 dict->SetString("gaia", base::UTF8ToUTF16(gaia_alpha));
1006 scoped_ptr<TestSigninClient> client;
1007 client.reset(new TestSigninClient(&pref));
1008 tracker.Initialize(client.get());
1010 ASSERT_EQ(tracker.GetMigrationState(),
1011 AccountTrackerService::MIGRATION_IN_PROGRESS);
1013 account_info = tracker.GetAccountInfo(gaia_alpha);
1014 ASSERT_EQ(account_info.account_id, gaia_alpha);
1015 ASSERT_EQ(account_info.gaia, gaia_alpha);
1016 ASSERT_EQ(account_info.email, email_alpha);
1018 account_info = tracker.GetAccountInfo(gaia_beta);
1019 ASSERT_EQ(account_info.account_id, gaia_beta);
1020 ASSERT_EQ(account_info.gaia, gaia_beta);
1021 ASSERT_EQ(account_info.email, email_beta);
1023 std::vector<AccountTrackerService::AccountInfo> accounts =
1024 tracker.GetAccounts();
1025 ASSERT_EQ(2u, accounts.size());
1027 tracker.SetMigrationDone();
1028 tracker.Shutdown();
1029 tracker.Initialize(client.get());
1031 ASSERT_EQ(tracker.GetMigrationState(),
1032 AccountTrackerService::MIGRATION_DONE);
1034 account_info = tracker.GetAccountInfo(gaia_alpha);
1035 ASSERT_EQ(account_info.account_id, gaia_alpha);
1036 ASSERT_EQ(account_info.gaia, gaia_alpha);
1037 ASSERT_EQ(account_info.email, email_alpha);
1039 account_info = tracker.GetAccountInfo(gaia_beta);
1040 ASSERT_EQ(account_info.account_id, gaia_beta);
1041 ASSERT_EQ(account_info.gaia, gaia_beta);
1042 ASSERT_EQ(account_info.email, email_beta);
1044 accounts.clear();
1045 accounts = tracker.GetAccounts();
1046 ASSERT_EQ(2u, accounts.size());
1050 TEST_F(AccountTrackerServiceTest, ChildAccountBasic) {
1051 AccountTrackerService tracker;
1052 tracker.Initialize(signin_client());
1053 FakeAccountFetcherService fetcher;
1054 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
1055 fetcher.EnableNetworkFetches();
1056 AccountTrackerObserver observer;
1057 tracker.AddObserver(&observer);
1058 std::string child_id("child");
1060 // Responses are processed iff there is a single account with a valid token
1061 // and the response is for that account.
1062 fetcher.FakeSetIsChildAccount(child_id, true);
1063 ASSERT_TRUE(observer.CheckEvents());
1066 SimulateTokenAvailable(child_id);
1067 IssueAccessToken(child_id);
1068 fetcher.FakeSetIsChildAccount(child_id, true);
1069 // Response was processed but observer is not notified as the account state
1070 // is invalid.
1071 ASSERT_TRUE(observer.CheckEvents());
1072 AccountTrackerService::AccountInfo info = tracker.GetAccountInfo(child_id);
1073 ASSERT_TRUE(info.is_child_account);
1074 SimulateTokenRevoked(child_id);
1076 tracker.RemoveObserver(&observer);
1077 fetcher.Shutdown();
1078 tracker.Shutdown();
1081 TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedAndRevoked) {
1082 AccountTrackerService tracker;
1083 tracker.Initialize(signin_client());
1084 FakeAccountFetcherService fetcher;
1085 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
1086 fetcher.EnableNetworkFetches();
1087 AccountTrackerObserver observer;
1088 tracker.AddObserver(&observer);
1089 std::string child_id("child");
1091 SimulateTokenAvailable(child_id);
1092 IssueAccessToken(child_id);
1093 fetcher.FakeSetIsChildAccount(child_id, false);
1094 FakeUserInfoFetchSuccess(&fetcher, child_id);
1095 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id)));
1096 AccountTrackerService::AccountInfo info = tracker.GetAccountInfo(child_id);
1097 ASSERT_FALSE(info.is_child_account);
1098 SimulateTokenRevoked(child_id);
1099 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(REMOVED, child_id)));
1101 tracker.RemoveObserver(&observer);
1102 fetcher.Shutdown();
1103 tracker.Shutdown();
1106 TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedAndRevokedWithUpdate) {
1107 AccountTrackerService tracker;
1108 tracker.Initialize(signin_client());
1109 FakeAccountFetcherService fetcher;
1110 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
1111 fetcher.EnableNetworkFetches();
1112 AccountTrackerObserver observer;
1113 tracker.AddObserver(&observer);
1114 std::string child_id("child");
1116 SimulateTokenAvailable(child_id);
1117 IssueAccessToken(child_id);
1118 fetcher.FakeSetIsChildAccount(child_id, true);
1119 FakeUserInfoFetchSuccess(&fetcher, child_id);
1120 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id)));
1121 AccountTrackerService::AccountInfo info = tracker.GetAccountInfo(child_id);
1122 ASSERT_TRUE(info.is_child_account);
1123 SimulateTokenRevoked(child_id);
1124 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id),
1125 TrackingEvent(REMOVED, child_id)));
1127 tracker.RemoveObserver(&observer);
1128 fetcher.Shutdown();
1129 tracker.Shutdown();
1132 TEST_F(AccountTrackerServiceTest, ChildAccountUpdatedTwiceThenRevoked) {
1133 AccountTrackerService tracker;
1134 tracker.Initialize(signin_client());
1135 FakeAccountFetcherService fetcher;
1136 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
1137 fetcher.EnableNetworkFetches();
1138 AccountTrackerObserver observer;
1139 tracker.AddObserver(&observer);
1140 std::string child_id("child");
1142 SimulateTokenAvailable(child_id);
1143 IssueAccessToken(child_id);
1144 // Observers notified the first time.
1145 FakeUserInfoFetchSuccess(&fetcher, child_id);
1146 // Since the account state is already valid, this will notify the
1147 // observers for the second time.
1148 fetcher.FakeSetIsChildAccount(child_id, true);
1149 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id),
1150 TrackingEvent(UPDATED, child_id)));
1151 SimulateTokenRevoked(child_id);
1152 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id),
1153 TrackingEvent(REMOVED, child_id)));
1155 tracker.RemoveObserver(&observer);
1156 fetcher.Shutdown();
1157 tracker.Shutdown();
1160 TEST_F(AccountTrackerServiceTest, ChildAccountGraduation) {
1161 AccountTrackerService tracker;
1162 tracker.Initialize(signin_client());
1163 FakeAccountFetcherService fetcher;
1164 fetcher.Initialize(signin_client(), token_service(), &tracker, nullptr);
1165 fetcher.EnableNetworkFetches();
1166 AccountTrackerObserver observer;
1167 tracker.AddObserver(&observer);
1168 std::string child_id("child");
1170 SimulateTokenAvailable(child_id);
1171 IssueAccessToken(child_id);
1173 // Set and verify this is a child account.
1174 fetcher.FakeSetIsChildAccount(child_id, true);
1175 AccountTrackerService::AccountInfo info = tracker.GetAccountInfo(child_id);
1176 ASSERT_TRUE(info.is_child_account);
1177 FakeUserInfoFetchSuccess(&fetcher, child_id);
1178 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id)));
1180 // Now simulate child account graduation.
1181 fetcher.FakeSetIsChildAccount(child_id, false);
1182 info = tracker.GetAccountInfo(child_id);
1183 ASSERT_FALSE(info.is_child_account);
1184 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(UPDATED, child_id)));
1186 SimulateTokenRevoked(child_id);
1187 ASSERT_TRUE(observer.CheckEvents(TrackingEvent(REMOVED, child_id)));
1189 tracker.RemoveObserver(&observer);
1190 fetcher.Shutdown();
1191 tracker.Shutdown();