1 // Copyright (c) 2012 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.
4 
5 #include "chrome/browser/profiles/profile_info_cache_unittest.h"
6 
7 #include <stddef.h>
8 #include <stdint.h>
9 
10 #include <algorithm>
11 #include <set>
12 #include <vector>
13 
14 #include "base/bind.h"
15 #include "base/command_line.h"
16 #include "base/files/file_util.h"
17 #include "base/stl_util.h"
18 #include "base/strings/stringprintf.h"
19 #include "base/strings/utf_string_conversions.h"
20 #include "base/time/time.h"
21 #include "build/build_config.h"
22 #include "chrome/browser/browser_process.h"
23 #include "chrome/browser/profiles/avatar_menu.h"
24 #include "chrome/browser/profiles/profile_avatar_icon_util.h"
25 #include "chrome/browser/profiles/profile_info_cache.h"
26 #include "chrome/browser/profiles/profile_manager.h"
27 #include "chrome/common/chrome_switches.h"
28 #include "chrome/common/pref_names.h"
29 #include "chrome/test/base/testing_browser_process.h"
30 #include "components/account_id/account_id.h"
31 #include "components/prefs/testing_pref_service.h"
32 #include "components/sync_preferences/pref_service_syncable.h"
33 #include "content/public/test/browser_task_environment.h"
34 #include "content/public/test/test_utils.h"
35 #include "third_party/skia/include/core/SkBitmap.h"
36 #include "ui/base/resource/resource_bundle.h"
37 #include "ui/gfx/image/image.h"
38 #include "ui/gfx/image/image_unittest_util.h"
39 
40 #if BUILDFLAG(ENABLE_SUPERVISED_USERS)
41 #include "chrome/browser/supervised_user/supervised_user_constants.h"
42 #endif
43 
44 using base::ASCIIToUTF16;
45 using base::UTF8ToUTF16;
46 using content::BrowserThread;
47 
48 namespace {
49 
GetDefaultAvatarIconResourceIDAtIndex(int index)50 size_t GetDefaultAvatarIconResourceIDAtIndex(int index) {
51 #if defined(OS_WIN)
52   return profiles::GetOldDefaultAvatar2xIconResourceIDAtIndex(index);
53 #else
54   return profiles::GetDefaultAvatarIconResourceIDAtIndex(index);
55 #endif  // defined(OS_WIN)
56 }
57 
58 }  //  namespace
59 
ProfileNameVerifierObserver(TestingProfileManager * testing_profile_manager)60 ProfileNameVerifierObserver::ProfileNameVerifierObserver(
61     TestingProfileManager* testing_profile_manager)
62     : testing_profile_manager_(testing_profile_manager) {
63   DCHECK(testing_profile_manager_);
64 }
65 
~ProfileNameVerifierObserver()66 ProfileNameVerifierObserver::~ProfileNameVerifierObserver() {
67 }
68 
OnProfileAdded(const base::FilePath & profile_path)69 void ProfileNameVerifierObserver::OnProfileAdded(
70     const base::FilePath& profile_path) {
71   ProfileAttributesEntry* entry = nullptr;
72   GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
73   base::string16 profile_name = entry->GetName();
74   EXPECT_TRUE(profile_names_.find(profile_path) == profile_names_.end());
75   profile_names_.insert({profile_path, profile_name});
76 }
77 
OnProfileWillBeRemoved(const base::FilePath & profile_path)78 void ProfileNameVerifierObserver::OnProfileWillBeRemoved(
79     const base::FilePath& profile_path) {
80   auto it = profile_names_.find(profile_path);
81   EXPECT_TRUE(it != profile_names_.end());
82   profile_names_.erase(it);
83 }
84 
OnProfileWasRemoved(const base::FilePath & profile_path,const base::string16 & profile_name)85 void ProfileNameVerifierObserver::OnProfileWasRemoved(
86     const base::FilePath& profile_path,
87     const base::string16& profile_name) {
88   EXPECT_TRUE(profile_names_.find(profile_path) == profile_names_.end());
89 }
90 
OnProfileNameChanged(const base::FilePath & profile_path,const base::string16 & old_profile_name)91 void ProfileNameVerifierObserver::OnProfileNameChanged(
92     const base::FilePath& profile_path,
93     const base::string16& old_profile_name) {
94   ProfileAttributesEntry* entry = nullptr;
95   GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
96   base::string16 new_profile_name = entry->GetName();
97   EXPECT_TRUE(profile_names_[profile_path] == old_profile_name);
98   profile_names_[profile_path] = new_profile_name;
99 }
100 
OnProfileAvatarChanged(const base::FilePath & profile_path)101 void ProfileNameVerifierObserver::OnProfileAvatarChanged(
102     const base::FilePath& profile_path) {
103   EXPECT_TRUE(profile_names_.find(profile_path) != profile_names_.end());
104 }
105 
GetCache()106 ProfileInfoCache* ProfileNameVerifierObserver::GetCache() {
107   return testing_profile_manager_->profile_info_cache();
108 }
109 
ProfileInfoCacheTest()110 ProfileInfoCacheTest::ProfileInfoCacheTest()
111     : testing_profile_manager_(TestingBrowserProcess::GetGlobal()),
112       name_observer_(&testing_profile_manager_) {}
113 
~ProfileInfoCacheTest()114 ProfileInfoCacheTest::~ProfileInfoCacheTest() {
115 }
116 
SetUp()117 void ProfileInfoCacheTest::SetUp() {
118   ASSERT_TRUE(testing_profile_manager_.SetUp());
119   testing_profile_manager_.profile_info_cache()->AddObserver(&name_observer_);
120 }
121 
TearDown()122 void ProfileInfoCacheTest::TearDown() {
123   // Drain remaining tasks to make sure all tasks are completed. This prevents
124   // memory leaks.
125   content::RunAllTasksUntilIdle();
126 }
127 
GetCache()128 ProfileInfoCache* ProfileInfoCacheTest::GetCache() {
129   return testing_profile_manager_.profile_info_cache();
130 }
131 
GetProfilePath(const std::string & base_name)132 base::FilePath ProfileInfoCacheTest::GetProfilePath(
133     const std::string& base_name) {
134   return testing_profile_manager_.profile_manager()->user_data_dir().
135       AppendASCII(base_name);
136 }
137 
ResetCache()138 void ProfileInfoCacheTest::ResetCache() {
139   testing_profile_manager_.DeleteProfileInfoCache();
140 }
141 
GetConcatenation(const base::string16 & gaia_name,const base::string16 profile_name)142 base::string16 ProfileInfoCacheTest::GetConcatenation(
143     const base::string16& gaia_name,
144     const base::string16 profile_name) {
145   base::string16 name_to_display(gaia_name);
146   name_to_display.append(base::UTF8ToUTF16(" ("));
147   name_to_display.append(profile_name);
148   name_to_display.append(base::UTF8ToUTF16(")"));
149   return name_to_display;
150 }
151 
TEST_F(ProfileInfoCacheTest,AddProfiles)152 TEST_F(ProfileInfoCacheTest, AddProfiles) {
153   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
154   // Avatar icons not used on Android.
155 #if !defined(OS_ANDROID)
156   ui::ResourceBundle& rb = ui::ResourceBundle::GetSharedInstance();
157 #endif
158 
159   for (uint32_t i = 0; i < 4; ++i) {
160     base::FilePath profile_path =
161         GetProfilePath(base::StringPrintf("path_%ud", i));
162     base::string16 profile_name =
163         ASCIIToUTF16(base::StringPrintf("name_%ud", i));
164 #if !defined(OS_ANDROID)
165 
166     size_t icon_id = GetDefaultAvatarIconResourceIDAtIndex(i);
167     const SkBitmap* icon = rb.GetImageNamed(icon_id).ToSkBitmap();
168 
169 #endif  // !defined(OS_ANDROID)
170     std::string supervised_user_id;
171 #if BUILDFLAG(ENABLE_SUPERVISED_USERS)
172     if (i == 3)
173       supervised_user_id = supervised_users::kChildAccountSUID;
174 #endif
175 
176     GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
177                                   base::string16(), false, i,
178                                   supervised_user_id, EmptyAccountId());
179 
180     ProfileAttributesEntry* entry = nullptr;
181     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
182     entry->SetBackgroundStatus(true);
183     base::string16 gaia_name = ASCIIToUTF16(base::StringPrintf("gaia_%ud", i));
184     entry->SetGAIAName(gaia_name);
185 
186     EXPECT_EQ(i + 1, GetCache()->GetNumberOfProfiles());
187     base::string16 expected_profile_name =
188         GetConcatenation(gaia_name, profile_name);
189 
190     EXPECT_EQ(expected_profile_name, entry->GetName());
191 
192     EXPECT_EQ(profile_path, GetCache()->GetPathOfProfileAtIndex(i));
193 #if !defined(OS_ANDROID)
194     const SkBitmap* actual_icon = entry->GetAvatarIcon().ToSkBitmap();
195     EXPECT_EQ(icon->width(), actual_icon->width());
196     EXPECT_EQ(icon->height(), actual_icon->height());
197 #endif
198 #if BUILDFLAG(ENABLE_SUPERVISED_USERS)
199     EXPECT_EQ(i == 3, entry->IsSupervised());
200     EXPECT_EQ(i == 3, entry->IsOmitted());
201 #else
202     EXPECT_FALSE(entry->IsSupervised());
203     EXPECT_FALSE(entry->IsOmitted());
204 #endif  // BUILDFLAG(ENABLE_SUPERVISED_USERS)
205     EXPECT_EQ(supervised_user_id, entry->GetSupervisedUserId());
206   }
207 
208   // Reset the cache and test the it reloads correctly.
209   ResetCache();
210 
211   EXPECT_EQ(4u, GetCache()->GetNumberOfProfiles());
212   for (uint32_t i = 0; i < 4; ++i) {
213     base::FilePath profile_path =
214           GetProfilePath(base::StringPrintf("path_%ud", i));
215     int index = GetCache()->GetIndexOfProfileWithPath(profile_path);
216     ProfileAttributesEntry* entry = nullptr;
217     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
218     base::string16 profile_name =
219         ASCIIToUTF16(base::StringPrintf("name_%ud", index));
220     base::string16 gaia_name = ASCIIToUTF16(base::StringPrintf("gaia_%ud", i));
221     base::string16 expected_profile_name =
222         GetConcatenation(gaia_name, profile_name);
223     EXPECT_EQ(expected_profile_name, entry->GetName());
224 #if !defined(OS_ANDROID)
225     EXPECT_EQ(i, GetCache()->GetAvatarIconIndexOfProfileAtIndex(index));
226 #endif
227     EXPECT_EQ(true, entry->GetBackgroundStatus());
228     EXPECT_EQ(gaia_name, entry->GetGAIAName());
229   }
230 }
231 
TEST_F(ProfileInfoCacheTest,GAIAName)232 TEST_F(ProfileInfoCacheTest, GAIAName) {
233   base::FilePath profile_path_1 = GetProfilePath("path_1");
234   GetCache()->AddProfileToCache(profile_path_1, ASCIIToUTF16("Person 1"),
235                                 std::string(), base::string16(), false, 0,
236                                 std::string(), EmptyAccountId());
237   ProfileAttributesEntry* entry_1 = nullptr;
238   GetCache()->GetProfileAttributesWithPath(profile_path_1, &entry_1);
239   base::string16 profile_name(ASCIIToUTF16("Person 2"));
240   base::FilePath profile_path_2 = GetProfilePath("path_2");
241   GetCache()->AddProfileToCache(GetProfilePath("path_2"), profile_name,
242                                 std::string(), base::string16(), false, 0,
243                                 std::string(), EmptyAccountId());
244   ProfileAttributesEntry* entry_2 = nullptr;
245   GetCache()->GetProfileAttributesWithPath(profile_path_2, &entry_2);
246 
247   // Sanity check.
248   EXPECT_TRUE(entry_1->GetGAIAName().empty());
249   EXPECT_TRUE(entry_2->GetGAIAName().empty());
250 
251   // Set GAIA name.
252   base::string16 gaia_name(ASCIIToUTF16("Pat Smith"));
253   entry_2->SetGAIAName(gaia_name);
254   // Since there is a GAIA name, we use that as a display name.
255   EXPECT_TRUE(entry_1->GetGAIAName().empty());
256   EXPECT_EQ(gaia_name, entry_2->GetGAIAName());
257   EXPECT_EQ(gaia_name, entry_2->GetName());
258 
259   base::string16 custom_name(ASCIIToUTF16("Custom name"));
260   entry_2->SetLocalProfileName(custom_name);
261   entry_2->SetIsUsingDefaultName(false);
262 
263   base::string16 expected_profile_name =
264       GetConcatenation(gaia_name, custom_name);
265   EXPECT_EQ(expected_profile_name, entry_2->GetName());
266   EXPECT_EQ(gaia_name, entry_2->GetGAIAName());
267 }
268 
TEST_F(ProfileInfoCacheTest,ConcatenateGaiaNameAndProfileName)269 TEST_F(ProfileInfoCacheTest, ConcatenateGaiaNameAndProfileName) {
270   // We should only append the profile name to the GAIA name if:
271   // - The user has chosen a profile name on purpose.
272   // - Two profiles has the sama GAIA name and we need to show it to
273   //   clear ambiguity.
274   // If one of the two conditions hold, we will show the profile name in this
275   // format |GAIA name (Profile local name)|
276   // Single profile.
277   GetCache()->AddProfileToCache(
278       GetProfilePath("path_1"), ASCIIToUTF16("Person 1"), std::string(),
279       base::string16(), false, 0, std::string(), EmptyAccountId());
280   ProfileAttributesEntry* entry_1 = nullptr;
281   GetCache()->GetProfileAttributesWithPath(GetProfilePath("path_1"), &entry_1);
282   EXPECT_EQ(ASCIIToUTF16("Person 1"), entry_1->GetName());
283   entry_1->SetGAIAName(ASCIIToUTF16("Patt Smith"));
284   EXPECT_EQ(ASCIIToUTF16("Patt Smith"), entry_1->GetName());
285   entry_1->SetGAIAGivenName(ASCIIToUTF16("Patt"));
286   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
287 
288   // Set a custom profile name.
289   entry_1->SetIsUsingDefaultName(false);
290   entry_1->SetLocalProfileName(ASCIIToUTF16("Work"));
291   EXPECT_EQ(ASCIIToUTF16("Patt (Work)"), entry_1->GetName());
292 
293   // Set the profile name to be equal to GAIA name.
294   entry_1->SetLocalProfileName(ASCIIToUTF16("patt"));
295   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
296 
297   // Multiple profiles.
298   // Add another profile with the same GAIA name and a default profile name.
299   GetCache()->AddProfileToCache(
300       GetProfilePath("path_2"), ASCIIToUTF16("Person 2"), std::string(),
301       base::string16(), false, 0, std::string(), EmptyAccountId());
302   ProfileAttributesEntry* entry_2 = nullptr;
303   GetCache()->GetProfileAttributesWithPath(GetProfilePath("path_2"), &entry_2);
304   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
305   EXPECT_EQ(ASCIIToUTF16("Person 2"), entry_2->GetName());
306 
307   entry_1->SetLocalProfileName(ASCIIToUTF16("Work"));
308   EXPECT_EQ(ASCIIToUTF16("Patt (Work)"), entry_1->GetName());
309   EXPECT_EQ(ASCIIToUTF16("Person 2"), entry_2->GetName());
310 
311   // A second profile with a different GAIA name should not affect the first
312   // profile.
313   entry_2->SetGAIAGivenName(ASCIIToUTF16("Olly"));
314   EXPECT_EQ(ASCIIToUTF16("Patt (Work)"), entry_1->GetName());
315   EXPECT_EQ(ASCIIToUTF16("Olly"), entry_2->GetName());
316 
317   // Mark profile name as default.
318   entry_1->SetIsUsingDefaultName(true);
319   entry_1->SetLocalProfileName(ASCIIToUTF16("Person 1"));
320   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
321   EXPECT_EQ(ASCIIToUTF16("Olly"), entry_2->GetName());
322 
323   // Add a third profile with the same GAIA name as the first.
324   // The two profiles are marked as using default profile names.
325   GetCache()->AddProfileToCache(
326       GetProfilePath("path_3"), ASCIIToUTF16("Person 3"), std::string(),
327       base::string16(), false, 0, std::string(), EmptyAccountId());
328   ProfileAttributesEntry* entry_3 = nullptr;
329   GetCache()->GetProfileAttributesWithPath(GetProfilePath("path_3"), &entry_3);
330   entry_3->SetGAIAName(ASCIIToUTF16("Patt Smith"));
331   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
332   EXPECT_EQ(ASCIIToUTF16("Patt Smith"), entry_3->GetName());
333 
334   // Two profiles with same GAIA name and default profile name.
335   // Empty GAIA given name.
336   entry_3->SetGAIAName(ASCIIToUTF16("Patt"));
337   EXPECT_EQ(ASCIIToUTF16("Patt (Person 1)"), entry_1->GetName());
338   EXPECT_EQ(ASCIIToUTF16("Patt (Person 3)"), entry_3->GetName());
339   // Set GAIA given name.
340   entry_3->SetGAIAGivenName(ASCIIToUTF16("Patt"));
341   EXPECT_EQ(ASCIIToUTF16("Patt (Person 1)"), entry_1->GetName());
342   EXPECT_EQ(ASCIIToUTF16("Patt (Person 3)"), entry_3->GetName());
343 
344   // Customize the profile name for one of the two profiles.
345   entry_3->SetIsUsingDefaultName(false);
346   entry_3->SetLocalProfileName(ASCIIToUTF16("Personal"));
347   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
348   EXPECT_EQ(ASCIIToUTF16("Patt (Personal)"), entry_3->GetName());
349 
350   // Set one of the profile names to be equal to GAIA name, we should show
351   // the profile name even if it is Person n to clear ambiguity.
352   entry_3->SetLocalProfileName(ASCIIToUTF16("patt"));
353   EXPECT_EQ(ASCIIToUTF16("Patt (Person 1)"), entry_1->GetName());
354   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_3->GetName());
355 
356   // Never show the profile name if it is equal GAIA name.
357   entry_1->SetLocalProfileName(ASCIIToUTF16("Patt"));
358   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_1->GetName());
359   EXPECT_EQ(ASCIIToUTF16("Patt"), entry_3->GetName());
360   EXPECT_EQ(ASCIIToUTF16("Olly"), entry_2->GetName());
361 }
362 
TEST_F(ProfileInfoCacheTest,DeleteProfile)363 TEST_F(ProfileInfoCacheTest, DeleteProfile) {
364   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
365 
366   base::FilePath path_1 = GetProfilePath("path_1");
367   GetCache()->AddProfileToCache(path_1, ASCIIToUTF16("name_1"), std::string(),
368                                 base::string16(), false, 0, std::string(),
369                                 EmptyAccountId());
370   EXPECT_EQ(1u, GetCache()->GetNumberOfProfiles());
371 
372   base::FilePath path_2 = GetProfilePath("path_2");
373   base::string16 name_2 = ASCIIToUTF16("name_2");
374   GetCache()->AddProfileToCache(path_2, name_2, std::string(), base::string16(),
375                                 false, 0, std::string(), EmptyAccountId());
376   ProfileAttributesEntry* entry = nullptr;
377   GetCache()->GetProfileAttributesWithPath(path_2, &entry);
378   EXPECT_EQ(2u, GetCache()->GetNumberOfProfiles());
379 
380   GetCache()->DeleteProfileFromCache(path_1);
381   EXPECT_EQ(1u, GetCache()->GetNumberOfProfiles());
382   EXPECT_EQ(name_2, entry->GetName());
383 
384   GetCache()->DeleteProfileFromCache(path_2);
385   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
386 }
387 
TEST_F(ProfileInfoCacheTest,MutateProfile)388 TEST_F(ProfileInfoCacheTest, MutateProfile) {
389   base::FilePath profile_path_1 = GetProfilePath("path_1");
390   GetCache()->AddProfileToCache(profile_path_1, ASCIIToUTF16("name_1"),
391                                 std::string(), base::string16(), false, 0,
392                                 std::string(), EmptyAccountId());
393 
394   base::FilePath profile_path_2 = GetProfilePath("path_2");
395   GetCache()->AddProfileToCache(profile_path_2, ASCIIToUTF16("name_2"),
396                                 std::string(), base::string16(), false, 0,
397                                 std::string(), EmptyAccountId());
398   ProfileAttributesEntry* entry_1;
399   GetCache()->GetProfileAttributesWithPath(profile_path_1, &entry_1);
400   ProfileAttributesEntry* entry_2;
401   GetCache()->GetProfileAttributesWithPath(profile_path_2, &entry_2);
402 
403   base::string16 new_name = ASCIIToUTF16("new_name");
404   entry_2->SetLocalProfileName(new_name);
405   EXPECT_EQ(new_name, entry_2->GetName());
406   EXPECT_NE(new_name, entry_1->GetName());
407 
408   base::string16 new_user_name = ASCIIToUTF16("user_name");
409   std::string new_gaia_id = "12345";
410   entry_2->SetAuthInfo(new_gaia_id, new_user_name, true);
411   EXPECT_EQ(new_user_name, entry_2->GetUserName());
412   EXPECT_EQ(new_gaia_id, entry_2->GetGAIAId());
413   EXPECT_NE(new_user_name, entry_1->GetUserName());
414 
415   // Avatar icons not used on Android.
416 #if !defined(OS_ANDROID)
417   const size_t new_icon_index = 3;
418   GetCache()->SetAvatarIconOfProfileAtIndex(1, new_icon_index);
419   EXPECT_EQ(new_icon_index, GetCache()->GetAvatarIconIndexOfProfileAtIndex(1));
420 
421   const size_t wrong_icon_index = profiles::GetDefaultAvatarIconCount() + 1;
422   const size_t generic_icon_index = 0;
423   GetCache()->SetAvatarIconOfProfileAtIndex(1, wrong_icon_index);
424   EXPECT_EQ(generic_icon_index,
425             GetCache()->GetAvatarIconIndexOfProfileAtIndex(1));
426 #endif
427 }
428 
429 // Will be removed SOON with ProfileInfoCache tests.
TEST_F(ProfileInfoCacheTest,BackgroundModeStatus)430 TEST_F(ProfileInfoCacheTest, BackgroundModeStatus) {
431   base::FilePath path_1 = GetProfilePath("path_1");
432   base::FilePath path_2 = GetProfilePath("path_2");
433   GetCache()->AddProfileToCache(path_1, ASCIIToUTF16("name_1"), std::string(),
434                                 base::string16(), false, 0, std::string(),
435                                 EmptyAccountId());
436   GetCache()->AddProfileToCache(path_2, ASCIIToUTF16("name_2"), std::string(),
437                                 base::string16(), false, 0, std::string(),
438                                 EmptyAccountId());
439 
440   ProfileAttributesEntry* entry_1 = nullptr;
441   GetCache()->GetProfileAttributesWithPath(path_1, &entry_1);
442   ProfileAttributesEntry* entry_2 = nullptr;
443   GetCache()->GetProfileAttributesWithPath(path_2, &entry_2);
444   EXPECT_FALSE(entry_1->GetBackgroundStatus());
445   EXPECT_FALSE(entry_2->GetBackgroundStatus());
446 
447   entry_2->SetBackgroundStatus(true);
448 
449   EXPECT_FALSE(entry_1->GetBackgroundStatus());
450   EXPECT_TRUE(entry_2->GetBackgroundStatus());
451 
452   entry_1->SetBackgroundStatus(true);
453 
454   EXPECT_TRUE(entry_1->GetBackgroundStatus());
455   EXPECT_TRUE(entry_2->GetBackgroundStatus());
456 
457   entry_2->SetBackgroundStatus(false);
458 
459   EXPECT_TRUE(entry_1->GetBackgroundStatus());
460   EXPECT_FALSE(entry_2->GetBackgroundStatus());
461 }
462 
TEST_F(ProfileInfoCacheTest,GAIAPicture)463 TEST_F(ProfileInfoCacheTest, GAIAPicture) {
464   const int kDefaultAvatarIndex = 0;
465   const int kOtherAvatarIndex = 1;
466   const int kGaiaPictureSize = 256;  // Standard size of a Gaia account picture.
467   base::FilePath path_2 = GetProfilePath("path_2");
468   GetCache()->AddProfileToCache(GetProfilePath("path_1"),
469                                 ASCIIToUTF16("name_1"), std::string(),
470                                 base::string16(), false, kDefaultAvatarIndex,
471                                 std::string(), EmptyAccountId());
472   GetCache()->AddProfileToCache(path_2, ASCIIToUTF16("name_2"), std::string(),
473                                 base::string16(), false, kDefaultAvatarIndex,
474                                 std::string(), EmptyAccountId());
475   ProfileAttributesEntry* entry = nullptr;
476   GetCache()->GetProfileAttributesWithPath(path_2, &entry);
477 
478   // Sanity check.
479   EXPECT_EQ(NULL, GetCache()->GetGAIAPictureOfProfileAtIndex(0));
480   EXPECT_EQ(NULL, GetCache()->GetGAIAPictureOfProfileAtIndex(1));
481   EXPECT_FALSE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(0));
482   EXPECT_FALSE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(1));
483 
484   // The profile icon should be the default one.
485   EXPECT_TRUE(GetCache()->ProfileIsUsingDefaultAvatarAtIndex(0));
486   EXPECT_TRUE(GetCache()->ProfileIsUsingDefaultAvatarAtIndex(1));
487   size_t default_avatar_id =
488       GetDefaultAvatarIconResourceIDAtIndex(kDefaultAvatarIndex);
489   const gfx::Image& default_avatar_image(
490       ui::ResourceBundle::GetSharedInstance().GetImageNamed(default_avatar_id));
491   EXPECT_TRUE(
492       gfx::test::AreImagesEqual(default_avatar_image, entry->GetAvatarIcon()));
493 
494   // Set GAIA picture.
495   gfx::Image gaia_image(gfx::test::CreateImage(
496       kGaiaPictureSize, kGaiaPictureSize));
497   GetCache()->SetGAIAPictureOfProfileAtIndex(1, "GAIA_IMAGE_URL_WITH_SIZE_1",
498                                              gaia_image);
499   EXPECT_EQ(nullptr, GetCache()->GetGAIAPictureOfProfileAtIndex(0));
500   EXPECT_TRUE(gfx::test::AreImagesEqual(
501       gaia_image, *GetCache()->GetGAIAPictureOfProfileAtIndex(1)));
502   // Since we're still using the default avatar, the GAIA image should be
503   // preferred over the generic avatar image.
504   EXPECT_TRUE(GetCache()->ProfileIsUsingDefaultAvatarAtIndex(1));
505   EXPECT_TRUE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(1));
506   EXPECT_TRUE(gfx::test::AreImagesEqual(gaia_image, entry->GetAvatarIcon()));
507 
508   // Set a non-default avatar. This should be preferred over the GAIA image.
509   GetCache()->SetAvatarIconOfProfileAtIndex(1, kOtherAvatarIndex);
510   GetCache()->SetProfileIsUsingDefaultAvatarAtIndex(1, false);
511   EXPECT_FALSE(GetCache()->ProfileIsUsingDefaultAvatarAtIndex(1));
512   EXPECT_FALSE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(1));
513 // Avatar icons not used on Android.
514 #if !defined(OS_ANDROID)
515 
516   size_t other_avatar_id =
517       GetDefaultAvatarIconResourceIDAtIndex(kOtherAvatarIndex);
518   const gfx::Image& other_avatar_image(
519       ui::ResourceBundle::GetSharedInstance().GetImageNamed(other_avatar_id));
520   EXPECT_TRUE(
521       gfx::test::AreImagesEqual(other_avatar_image, entry->GetAvatarIcon()));
522 #endif  // !defined(OS_ANDROID)
523 
524   // Explicitly setting the GAIA picture should make it preferred again.
525   GetCache()->SetIsUsingGAIAPictureOfProfileAtIndex(1, true);
526   EXPECT_TRUE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(1));
527   EXPECT_TRUE(gfx::test::AreImagesEqual(
528       gaia_image, *GetCache()->GetGAIAPictureOfProfileAtIndex(1)));
529   EXPECT_TRUE(gfx::test::AreImagesEqual(gaia_image, entry->GetAvatarIcon()));
530 
531   // Clearing the IsUsingGAIAPicture flag should result in the generic image
532   // being used again.
533   GetCache()->SetIsUsingGAIAPictureOfProfileAtIndex(1, false);
534   EXPECT_FALSE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(1));
535   EXPECT_TRUE(gfx::test::AreImagesEqual(
536       gaia_image, *GetCache()->GetGAIAPictureOfProfileAtIndex(1)));
537 #if !defined(OS_ANDROID)
538   EXPECT_TRUE(
539       gfx::test::AreImagesEqual(other_avatar_image, entry->GetAvatarIcon()));
540 #endif
541 }
542 
TEST_F(ProfileInfoCacheTest,PersistGAIAPicture)543 TEST_F(ProfileInfoCacheTest, PersistGAIAPicture) {
544   GetCache()->AddProfileToCache(
545       GetProfilePath("path_1"), ASCIIToUTF16("name_1"), std::string(),
546       base::string16(), false, 0, std::string(), EmptyAccountId());
547   gfx::Image gaia_image(gfx::test::CreateImage());
548 
549   GetCache()->SetGAIAPictureOfProfileAtIndex(0, "GAIA_IMAGE_URL_WITH_SIZE_0",
550                                              gaia_image);
551 
552   // Make sure everything has completed, and the file has been written to disk.
553   content::RunAllTasksUntilIdle();
554 
555   EXPECT_EQ(
556       GetCache()->GetLastDownloadedGAIAPictureUrlWithSizeOfProfileAtIndex(0),
557       "GAIA_IMAGE_URL_WITH_SIZE_0");
558   EXPECT_TRUE(gfx::test::AreImagesEqual(
559       gaia_image, *GetCache()->GetGAIAPictureOfProfileAtIndex(0)));
560 
561   ResetCache();
562   // Try to get the GAIA picture. This should return NULL until the read from
563   // disk is done.
564   EXPECT_EQ(nullptr, GetCache()->GetGAIAPictureOfProfileAtIndex(0));
565   EXPECT_EQ(
566       GetCache()->GetLastDownloadedGAIAPictureUrlWithSizeOfProfileAtIndex(0),
567       "GAIA_IMAGE_URL_WITH_SIZE_0");
568   content::RunAllTasksUntilIdle();
569 
570   EXPECT_TRUE(gfx::test::AreImagesEqual(
571     gaia_image, *GetCache()->GetGAIAPictureOfProfileAtIndex(0)));
572 }
573 
574 #if BUILDFLAG(ENABLE_SUPERVISED_USERS)
TEST_F(ProfileInfoCacheTest,SetSupervisedUserId)575 TEST_F(ProfileInfoCacheTest, SetSupervisedUserId) {
576   base::FilePath profile_path = GetProfilePath("test");
577   GetCache()->AddProfileToCache(profile_path, ASCIIToUTF16("Test"),
578                                 std::string(), base::string16(), false, 0,
579                                 std::string(), EmptyAccountId());
580   ProfileAttributesEntry* entry = nullptr;
581   GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
582   EXPECT_FALSE(entry->IsSupervised());
583 
584   entry->SetSupervisedUserId(supervised_users::kChildAccountSUID);
585   EXPECT_TRUE(entry->IsSupervised());
586   EXPECT_EQ(supervised_users::kChildAccountSUID, entry->GetSupervisedUserId());
587 
588   ResetCache();
589   entry = nullptr;
590   GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
591   EXPECT_TRUE(entry->IsSupervised());
592 
593   entry->SetSupervisedUserId(std::string());
594   EXPECT_FALSE(entry->IsSupervised());
595   EXPECT_EQ("", entry->GetSupervisedUserId());
596 }
597 #endif  // BUILDFLAG(ENABLE_SUPERVISED_USERS)
598 
TEST_F(ProfileInfoCacheTest,EmptyGAIAInfo)599 TEST_F(ProfileInfoCacheTest, EmptyGAIAInfo) {
600   base::string16 profile_name = ASCIIToUTF16("name_1");
601   size_t id = GetDefaultAvatarIconResourceIDAtIndex(0);
602   const gfx::Image& profile_image(
603       ui::ResourceBundle::GetSharedInstance().GetImageNamed(id));
604 
605   base::FilePath profile_path = GetProfilePath("path_1");
606   GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
607                                 base::string16(), false, 0, std::string(),
608                                 EmptyAccountId());
609 
610   ProfileAttributesEntry* entry = nullptr;
611   GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
612 
613   gfx::Image gaia_image(gfx::test::CreateImage());
614   GetCache()->SetGAIAPictureOfProfileAtIndex(0, "GAIA_IMAGE_URL_WITH_SIZE_0",
615                                              gaia_image);
616 
617   // Make sure everything has completed, and the file has been written to disk.
618   content::RunAllTasksUntilIdle();
619 
620   // Set empty GAIA info.
621   entry->SetGAIAName(base::string16());
622   GetCache()->SetGAIAPictureOfProfileAtIndex(0, std::string(), gfx::Image());
623   GetCache()->SetIsUsingGAIAPictureOfProfileAtIndex(0, true);
624 
625   EXPECT_TRUE(GetCache()
626                   ->GetLastDownloadedGAIAPictureUrlWithSizeOfProfileAtIndex(0)
627                   .empty());
628 
629   // Verify that the profile name and picture are not empty.
630   EXPECT_EQ(profile_name, entry->GetName());
631   EXPECT_TRUE(gfx::test::AreImagesEqual(profile_image, entry->GetAvatarIcon()));
632 }
633 
634 #if BUILDFLAG(ENABLE_SUPERVISED_USERS)
TEST_F(ProfileInfoCacheTest,CreateSupervisedTestingProfile)635 TEST_F(ProfileInfoCacheTest, CreateSupervisedTestingProfile) {
636   base::FilePath path_1 =
637       testing_profile_manager_.CreateTestingProfile("default")->GetPath();
638   base::string16 supervised_user_name = ASCIIToUTF16("Supervised User");
639   base::FilePath path_2 =
640       testing_profile_manager_
641           .CreateTestingProfile(
642               "test1", std::unique_ptr<sync_preferences::PrefServiceSyncable>(),
643               supervised_user_name, 0, supervised_users::kChildAccountSUID,
644               TestingProfile::TestingFactories())
645           ->GetPath();
646   base::FilePath profile_path[] = {path_1, path_2};
647   for (const base::FilePath& path : profile_path) {
648     ProfileAttributesEntry* entry = nullptr;
649     GetCache()->GetProfileAttributesWithPath(path, &entry);
650     bool is_supervised = entry->GetName() == supervised_user_name;
651     EXPECT_EQ(is_supervised, entry->IsSupervised());
652     std::string supervised_user_id =
653         is_supervised ? supervised_users::kChildAccountSUID : "";
654     EXPECT_EQ(supervised_user_id, entry->GetSupervisedUserId());
655   }
656 
657   // Supervised profiles have a custom theme, which needs to be deleted on the
658   // FILE thread. Reset the profile manager now so everything is deleted while
659   // we still have a FILE thread.
660   TestingBrowserProcess::GetGlobal()->SetProfileManager(NULL);
661 }
662 #endif
663 
TEST_F(ProfileInfoCacheTest,AddStubProfile)664 TEST_F(ProfileInfoCacheTest, AddStubProfile) {
665   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
666 
667   // Add some profiles with and without a '.' in their paths.
668   const struct {
669     const char* profile_path;
670     const char* profile_name;
671   } kTestCases[] = {
672     { "path.test0", "name_0" },
673     { "path_test1", "name_1" },
674     { "path.test2", "name_2" },
675     { "path_test3", "name_3" },
676   };
677 
678   for (size_t i = 0; i < base::size(kTestCases); ++i) {
679     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
680     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
681 
682     GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
683                                   base::string16(), false, i, "",
684                                   EmptyAccountId());
685     ProfileAttributesEntry* entry = nullptr;
686     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
687     EXPECT_TRUE(entry);
688     EXPECT_EQ(profile_name, entry->GetName());
689   }
690 
691   ASSERT_EQ(4U, GetCache()->GetNumberOfProfiles());
692 
693   // Check that the profiles can be extracted from the local state.
694   std::vector<base::string16> names;
695   PrefService* local_state = g_browser_process->local_state();
696   const base::DictionaryValue* cache = local_state->GetDictionary(
697       prefs::kProfileInfoCache);
698   base::string16 name;
699   for (base::DictionaryValue::Iterator it(*cache); !it.IsAtEnd();
700        it.Advance()) {
701     const base::DictionaryValue* info = NULL;
702     it.value().GetAsDictionary(&info);
703     info->GetString("name", &name);
704     names.push_back(name);
705   }
706 
707   for (size_t i = 0; i < 4; i++)
708     ASSERT_FALSE(names[i].empty());
709 }
710 
TEST_F(ProfileInfoCacheTest,EntriesInAttributesStorage)711 TEST_F(ProfileInfoCacheTest, EntriesInAttributesStorage) {
712   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
713 
714   // Add some profiles with and without a '.' in their paths.
715   const struct {
716     const char* profile_path;
717     const char* profile_name;
718   } kTestCases[] = {
719     { "path.test0", "name_0" },
720     { "path_test1", "name_1" },
721     { "path.test2", "name_2" },
722     { "path_test3", "name_3" },
723   };
724 
725   // Profiles are added and removed using all combinations of the old and the
726   // new interfaces. The content of |profile_attributes_entries_| in
727   // ProfileAttributesStorage is checked after each insert and delete operation.
728 
729   // Add profiles.
730   for (size_t i = 0; i < base::size(kTestCases); ++i) {
731     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
732     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
733 
734     ASSERT_EQ(0u, GetCache()->profile_attributes_entries_.count(
735                       profile_path.value()));
736 
737     // Use ProfileInfoCache in profiles 0 and 2, and ProfileAttributesStorage in
738     // profiles 1 and 3.
739     if (i == 0 || i == 2) {
740       GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
741                                     base::string16(), false, i, "",
742                                     EmptyAccountId());
743     } else {
744       GetCache()->AddProfile(profile_path, profile_name, std::string(),
745                              base::string16(), false, i, "", EmptyAccountId());
746     }
747 
748     ASSERT_EQ(i + 1, GetCache()->GetNumberOfProfiles());
749     ASSERT_EQ(i + 1, GetCache()->profile_attributes_entries_.size());
750 
751     ASSERT_EQ(1u, GetCache()->profile_attributes_entries_.count(
752                       profile_path.value()));
753     // TODO(anthonyvd) : check that the entry in |profile_attributes_entries_|
754     // is null before GetProfileAttributesWithPath is run. Currently this is
755     // impossible to check because GetProfileAttributesWithPath is called during
756     // profile creation.
757 
758     ProfileAttributesEntry* entry = nullptr;
759     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
760     EXPECT_EQ(
761         entry,
762         GetCache()->profile_attributes_entries_[profile_path.value()].get());
763   }
764 
765   // Remove profiles.
766   for (size_t i = 0; i < base::size(kTestCases); ++i) {
767     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
768     ASSERT_EQ(1u, GetCache()->profile_attributes_entries_.count(
769                       profile_path.value()));
770 
771     // Use ProfileInfoCache in profiles 0 and 1, and ProfileAttributesStorage in
772     // profiles 2 and 3.
773     if (i == 0 || i == 1)
774       GetCache()->DeleteProfileFromCache(profile_path);
775     else
776       GetCache()->RemoveProfile(profile_path);
777 
778     ASSERT_EQ(0u, GetCache()->profile_attributes_entries_.count(
779                       profile_path.value()));
780 
781     ProfileAttributesEntry* entry = nullptr;
782     EXPECT_FALSE(GetCache()->GetProfileAttributesWithPath(profile_path,
783                                                           &entry));
784     ASSERT_EQ(0u, GetCache()->profile_attributes_entries_.count(
785                       profile_path.value()));
786   }
787 }
788 
789 #if !defined(OS_ANDROID) && !defined(OS_CHROMEOS)
TEST_F(ProfileInfoCacheTest,MigrateLegacyProfileNamesAndRecomputeIfNeeded)790 TEST_F(ProfileInfoCacheTest, MigrateLegacyProfileNamesAndRecomputeIfNeeded) {
791   EXPECT_EQ(0U, GetCache()->GetNumberOfProfiles());
792   // Mimick a pre-existing Directory with profiles that has legacy profile
793   // names.
794   const struct {
795     const char* profile_path;
796     const char* profile_name;
797     bool is_using_default_name;
798   } kTestCases[] = {
799       {"path_1", "Default Profile", true}, {"path_2", "First user", true},
800       {"path_3", "Lemonade", true},        {"path_4", "Batman", true},
801       {"path_5", "Batman", false},         {"path_6", "Person 2", true},
802       {"path_7", "Person 3", true},        {"path_8", "Person 1", true},
803       {"path_9", "Person 2", true},        {"path_10", "Person 1", true},
804       {"path_11", "Smith", false},         {"path_12", "Person 2", true}};
805 
806   ProfileAttributesEntry* entry = nullptr;
807   for (size_t i = 0; i < base::size(kTestCases); ++i) {
808     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
809     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
810     entry = nullptr;
811 
812     GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
813                                   base::string16(), false, i, "",
814                                   EmptyAccountId());
815     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
816     EXPECT_TRUE(entry);
817     entry->SetIsUsingDefaultName(kTestCases[i].is_using_default_name);
818   }
819 
820   EXPECT_EQ(12U, GetCache()->GetNumberOfProfiles());
821 
822   ResetCache();
823   ProfileInfoCache::SetLegacyProfileMigrationForTesting(true);
824   GetCache();
825   ProfileInfoCache::SetLegacyProfileMigrationForTesting(false);
826 
827   entry = nullptr;
828   GetCache()->GetProfileAttributesWithPath(
829       GetProfilePath(kTestCases[4].profile_path), &entry);
830   EXPECT_EQ(ASCIIToUTF16(kTestCases[4].profile_name), entry->GetName());
831   GetCache()->GetProfileAttributesWithPath(
832       GetProfilePath(kTestCases[10].profile_path), &entry);
833   EXPECT_EQ(ASCIIToUTF16(kTestCases[10].profile_name), entry->GetName());
834 
835   // Legacy profile names like "Default Profile" and "First user" should be
836   // migrated to "Person %n" type names, i.e. any permutation of "Person %n".
837   std::set<base::string16> expected_profile_names{
838       ASCIIToUTF16("Person 1"), ASCIIToUTF16("Person 2"),
839       ASCIIToUTF16("Person 3"), ASCIIToUTF16("Person 4"),
840       ASCIIToUTF16("Person 5"), ASCIIToUTF16("Person 6"),
841       ASCIIToUTF16("Person 7"), ASCIIToUTF16("Person 8"),
842       ASCIIToUTF16("Person 9"), ASCIIToUTF16("Person 10")};
843 
844   const char* profile_path[] = {
845       kTestCases[0].profile_path, kTestCases[1].profile_path,
846       kTestCases[2].profile_path, kTestCases[3].profile_path,
847       kTestCases[5].profile_path, kTestCases[6].profile_path,
848       kTestCases[7].profile_path, kTestCases[8].profile_path,
849       kTestCases[9].profile_path, kTestCases[11].profile_path};
850 
851   std::set<base::string16> actual_profile_names;
852   for (auto* path : profile_path) {
853     entry = nullptr;
854     GetCache()->GetProfileAttributesWithPath(GetProfilePath(path), &entry);
855     actual_profile_names.insert(entry->GetName());
856   }
857   EXPECT_EQ(actual_profile_names, expected_profile_names);
858 }
859 
TEST_F(ProfileInfoCacheTest,GetGaiaImageForAvatarMenu)860 TEST_F(ProfileInfoCacheTest, GetGaiaImageForAvatarMenu) {
861   // The TestingProfileManager's ProfileInfoCache doesn't download avatars.
862   ProfileInfoCache profile_info_cache(
863       g_browser_process->local_state(),
864       testing_profile_manager_.profile_manager()->user_data_dir());
865 
866   base::FilePath profile_path = GetProfilePath("path_1");
867 
868   GetCache()->AddProfileToCache(profile_path, ASCIIToUTF16("name_1"),
869                                 std::string(), base::string16(), false, 0,
870                                 std::string(), EmptyAccountId());
871 
872   gfx::Image gaia_image(gfx::test::CreateImage());
873   GetCache()->SetGAIAPictureOfProfileAtIndex(0, "GAIA_IMAGE_URL_WITH_SIZE_0",
874                                              gaia_image);
875 
876   // Make sure everything has completed, and the file has been written to disk.
877   content::RunAllTasksUntilIdle();
878 
879   // Make sure this profile is using GAIA picture.
880   EXPECT_TRUE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(0));
881 
882   ResetCache();
883 
884   // We need to explicitly set the GAIA usage flag after resetting the cache.
885   GetCache()->SetIsUsingGAIAPictureOfProfileAtIndex(0, true);
886   EXPECT_TRUE(GetCache()->IsUsingGAIAPictureOfProfileAtIndex(0));
887 
888   gfx::Image image_loaded;
889 
890   // Try to get the GAIA image. For the first time, it triggers an async image
891   // load from disk. The load status indicates the image is still being loaded.
892   constexpr int kArbitraryPreferredSize = 96;
893   EXPECT_EQ(AvatarMenu::ImageLoadStatus::LOADING,
894             AvatarMenu::GetImageForMenuButton(profile_path, &image_loaded,
895                                               kArbitraryPreferredSize));
896   EXPECT_FALSE(gfx::test::AreImagesEqual(gaia_image, image_loaded));
897 
898   // Wait until the async image load finishes.
899   content::RunAllTasksUntilIdle();
900 
901   // Since the GAIA image is loaded now, we can get it this time.
902   EXPECT_EQ(AvatarMenu::ImageLoadStatus::LOADED,
903             AvatarMenu::GetImageForMenuButton(profile_path, &image_loaded,
904                                               kArbitraryPreferredSize));
905   EXPECT_TRUE(gfx::test::AreImagesEqual(gaia_image, image_loaded));
906 }
907 #endif
908 
909 #if defined(OS_CHROMEOS) || defined(OS_ANDROID)
TEST_F(ProfileInfoCacheTest,DontMigrateLegacyProfileNamesWithoutNewAvatarMenu)910 TEST_F(ProfileInfoCacheTest,
911        DontMigrateLegacyProfileNamesWithoutNewAvatarMenu) {
912   EXPECT_EQ(0U, GetCache()->GetNumberOfProfiles());
913 
914   const struct {
915     const char* profile_path;
916     const char* profile_name;
917   } kTestCases[] = {{"path_1", "Default Profile"},
918                     {"path_2", "First user"},
919                     {"path_3", "Lemonade"},
920                     {"path_4", "Batman"}};
921 
922   for (size_t i = 0; i < base::size(kTestCases); ++i) {
923     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
924     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
925     ProfileAttributesEntry* entry = nullptr;
926     GetCache()->AddProfileToCache(profile_path, profile_name, std::string(),
927                                   base::string16(), false, i, "",
928                                   EmptyAccountId());
929     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
930     EXPECT_TRUE(entry);
931     entry->SetIsUsingDefaultName(true);
932   }
933   EXPECT_EQ(4U, GetCache()->GetNumberOfProfiles());
934 
935   ResetCache();
936 
937   // Profile names should have been preserved.
938   for (size_t i = 0; i < base::size(kTestCases); ++i) {
939     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
940     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
941     ProfileAttributesEntry* entry = nullptr;
942     GetCache()->GetProfileAttributesWithPath(profile_path, &entry);
943     EXPECT_TRUE(entry);
944     EXPECT_EQ(profile_name, entry->GetName());
945   }
946 }
947 #endif
948 
TEST_F(ProfileInfoCacheTest,RemoveProfileByAccountId)949 TEST_F(ProfileInfoCacheTest, RemoveProfileByAccountId) {
950   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
951   const struct {
952     const char* profile_path;
953     const char* profile_name;
954     AccountId account_id;
955     bool is_consented_primary_account;
956   } kTestCases[] = {
957       {"path_1", "name_1", AccountId::FromUserEmailGaiaId("email1", "111111"),
958        true},
959       {"path_2", "name_3", AccountId::FromUserEmailGaiaId("email2", "222222"),
960        true},
961       {"path_3", "name_3", AccountId::FromUserEmailGaiaId("email3", "333333"),
962        false},
963       {"path_4", "name_4", AccountId::FromUserEmailGaiaId("email4", "444444"),
964        false}};
965 
966   for (size_t i = 0; i < base::size(kTestCases); ++i) {
967     base::FilePath profile_path = GetProfilePath(kTestCases[i].profile_path);
968     base::string16 profile_name = ASCIIToUTF16(kTestCases[i].profile_name);
969     GetCache()->AddProfileToCache(
970         profile_path, profile_name, kTestCases[i].account_id.GetGaiaId(),
971         UTF8ToUTF16(kTestCases[i].account_id.GetUserEmail()),
972         kTestCases[i].is_consented_primary_account, 0, std::string(),
973         EmptyAccountId());
974     EXPECT_EQ(i + 1, GetCache()->GetNumberOfProfiles());
975   }
976 
977   GetCache()->RemoveProfileByAccountId(kTestCases[2].account_id);
978   EXPECT_EQ(3u, GetCache()->GetNumberOfProfiles());
979 
980   GetCache()->RemoveProfileByAccountId(kTestCases[0].account_id);
981   EXPECT_EQ(2u, GetCache()->GetNumberOfProfiles());
982 
983   // this profile is already deleted.
984   GetCache()->RemoveProfileByAccountId(kTestCases[2].account_id);
985   EXPECT_EQ(2u, GetCache()->GetNumberOfProfiles());
986 
987   // Remove profile by partial match
988   GetCache()->RemoveProfileByAccountId(
989       AccountId::FromUserEmail(kTestCases[1].account_id.GetUserEmail()));
990   EXPECT_EQ(1u, GetCache()->GetNumberOfProfiles());
991 
992   // Remove last profile
993   GetCache()->RemoveProfileByAccountId(kTestCases[3].account_id);
994   EXPECT_EQ(0u, GetCache()->GetNumberOfProfiles());
995 }
996