• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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/test/base/testing_profile.h"
6 
7 #include "build/build_config.h"
8 
9 #include "base/base_paths.h"
10 #include "base/command_line.h"
11 #include "base/file_util.h"
12 #include "base/message_loop/message_loop_proxy.h"
13 #include "base/path_service.h"
14 #include "base/prefs/testing_pref_store.h"
15 #include "base/run_loop.h"
16 #include "base/strings/string_number_conversions.h"
17 #include "chrome/browser/autocomplete/autocomplete_classifier.h"
18 #include "chrome/browser/bookmarks/bookmark_model_factory.h"
19 #include "chrome/browser/bookmarks/chrome_bookmark_client.h"
20 #include "chrome/browser/bookmarks/chrome_bookmark_client_factory.h"
21 #include "chrome/browser/browser_process.h"
22 #include "chrome/browser/chrome_notification_types.h"
23 #include "chrome/browser/content_settings/host_content_settings_map.h"
24 #include "chrome/browser/extensions/extension_service.h"
25 #include "chrome/browser/extensions/extension_special_storage_policy.h"
26 #include "chrome/browser/extensions/extension_system_factory.h"
27 #include "chrome/browser/extensions/test_extension_system.h"
28 #include "chrome/browser/favicon/favicon_service.h"
29 #include "chrome/browser/favicon/favicon_service_factory.h"
30 #include "chrome/browser/history/chrome_history_client.h"
31 #include "chrome/browser/history/chrome_history_client_factory.h"
32 #include "chrome/browser/history/history_backend.h"
33 #include "chrome/browser/history/history_db_task.h"
34 #include "chrome/browser/history/history_service.h"
35 #include "chrome/browser/history/history_service_factory.h"
36 #include "chrome/browser/history/top_sites.h"
37 #include "chrome/browser/history/web_history_service_factory.h"
38 #include "chrome/browser/net/pref_proxy_config_tracker.h"
39 #include "chrome/browser/net/proxy_service_factory.h"
40 #include "chrome/browser/notifications/desktop_notification_service.h"
41 #include "chrome/browser/notifications/desktop_notification_service_factory.h"
42 #include "chrome/browser/policy/profile_policy_connector.h"
43 #include "chrome/browser/policy/profile_policy_connector_factory.h"
44 #include "chrome/browser/prefs/browser_prefs.h"
45 #include "chrome/browser/prefs/pref_service_syncable.h"
46 #include "chrome/browser/prerender/prerender_manager.h"
47 #include "chrome/browser/profiles/chrome_browser_main_extra_parts_profiles.h"
48 #include "chrome/browser/profiles/profile_manager.h"
49 #include "chrome/browser/profiles/storage_partition_descriptor.h"
50 #include "chrome/browser/search_engines/template_url_fetcher_factory.h"
51 #include "chrome/browser/webdata/web_data_service.h"
52 #include "chrome/browser/webdata/web_data_service_factory.h"
53 #include "chrome/common/chrome_constants.h"
54 #include "chrome/common/chrome_switches.h"
55 #include "chrome/common/pref_names.h"
56 #include "chrome/common/url_constants.h"
57 #include "chrome/test/base/history_index_restore_observer.h"
58 #include "chrome/test/base/testing_pref_service_syncable.h"
59 #include "chrome/test/base/ui_test_utils.h"
60 #include "components/bookmarks/browser/bookmark_model.h"
61 #include "components/bookmarks/common/bookmark_constants.h"
62 #include "components/keyed_service/content/browser_context_dependency_manager.h"
63 #include "components/policy/core/common/policy_service.h"
64 #include "components/user_prefs/user_prefs.h"
65 #include "content/public/browser/browser_thread.h"
66 #include "content/public/browser/cookie_store_factory.h"
67 #include "content/public/browser/notification_service.h"
68 #include "content/public/browser/render_process_host.h"
69 #include "content/public/browser/storage_partition.h"
70 #include "content/public/test/mock_resource_context.h"
71 #include "content/public/test/test_utils.h"
72 #include "extensions/browser/extension_system.h"
73 #include "extensions/common/constants.h"
74 #include "net/cookies/cookie_monster.h"
75 #include "net/url_request/url_request_context.h"
76 #include "net/url_request/url_request_context_getter.h"
77 #include "net/url_request/url_request_test_util.h"
78 #include "testing/gmock/include/gmock/gmock.h"
79 
80 #if defined(ENABLE_CONFIGURATION_POLICY)
81 #include "chrome/browser/policy/schema_registry_service.h"
82 #include "chrome/browser/policy/schema_registry_service_factory.h"
83 #include "components/policy/core/common/configuration_policy_provider.h"
84 #include "components/policy/core/common/policy_service_impl.h"
85 #include "components/policy/core/common/schema.h"
86 #else
87 #include "components/policy/core/common/policy_service_stub.h"
88 #endif  // defined(ENABLE_CONFIGURATION_POLICY)
89 
90 #if defined(ENABLE_EXTENSIONS)
91 #include "chrome/browser/guest_view/guest_view_manager.h"
92 #endif
93 
94 #if defined(OS_ANDROID)
95 #include "chrome/browser/signin/android_profile_oauth2_token_service.h"
96 #endif
97 
98 #if defined(ENABLE_MANAGED_USERS)
99 #include "chrome/browser/supervised_user/supervised_user_settings_service.h"
100 #include "chrome/browser/supervised_user/supervised_user_settings_service_factory.h"
101 #endif
102 
103 using base::Time;
104 using content::BrowserThread;
105 using content::DownloadManagerDelegate;
106 using testing::NiceMock;
107 using testing::Return;
108 
109 namespace {
110 
111 // Task used to make sure history has finished processing a request. Intended
112 // for use with BlockUntilHistoryProcessesPendingRequests.
113 
114 class QuittingHistoryDBTask : public history::HistoryDBTask {
115  public:
QuittingHistoryDBTask()116   QuittingHistoryDBTask() {}
117 
RunOnDBThread(history::HistoryBackend * backend,history::HistoryDatabase * db)118   virtual bool RunOnDBThread(history::HistoryBackend* backend,
119                              history::HistoryDatabase* db) OVERRIDE {
120     return true;
121   }
122 
DoneRunOnMainThread()123   virtual void DoneRunOnMainThread() OVERRIDE {
124     base::MessageLoop::current()->Quit();
125   }
126 
127  private:
~QuittingHistoryDBTask()128   virtual ~QuittingHistoryDBTask() {}
129 
130   DISALLOW_COPY_AND_ASSIGN(QuittingHistoryDBTask);
131 };
132 
133 class TestExtensionURLRequestContext : public net::URLRequestContext {
134  public:
TestExtensionURLRequestContext()135   TestExtensionURLRequestContext() {
136     net::CookieMonster* cookie_monster =
137         content::CreateCookieStore(content::CookieStoreConfig())->
138             GetCookieMonster();
139     const char* schemes[] = {extensions::kExtensionScheme};
140     cookie_monster->SetCookieableSchemes(schemes, 1);
141     set_cookie_store(cookie_monster);
142   }
143 
~TestExtensionURLRequestContext()144   virtual ~TestExtensionURLRequestContext() {}
145 };
146 
147 class TestExtensionURLRequestContextGetter
148     : public net::URLRequestContextGetter {
149  public:
GetURLRequestContext()150   virtual net::URLRequestContext* GetURLRequestContext() OVERRIDE {
151     if (!context_.get())
152       context_.reset(new TestExtensionURLRequestContext());
153     return context_.get();
154   }
155   virtual scoped_refptr<base::SingleThreadTaskRunner>
GetNetworkTaskRunner() const156       GetNetworkTaskRunner() const OVERRIDE {
157     return BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO);
158   }
159 
160  protected:
~TestExtensionURLRequestContextGetter()161   virtual ~TestExtensionURLRequestContextGetter() {}
162 
163  private:
164   scoped_ptr<net::URLRequestContext> context_;
165 };
166 
167 #if defined(ENABLE_NOTIFICATIONS)
CreateTestDesktopNotificationService(content::BrowserContext * profile)168 KeyedService* CreateTestDesktopNotificationService(
169     content::BrowserContext* profile) {
170   return new DesktopNotificationService(static_cast<Profile*>(profile), NULL);
171 }
172 #endif
173 
174 }  // namespace
175 
176 // static
177 #if defined(OS_CHROMEOS)
178 // Must be kept in sync with
179 // ChromeBrowserMainPartsChromeos::PreEarlyInitialization.
180 const char TestingProfile::kTestUserProfileDir[] = "test-user";
181 #else
182 const char TestingProfile::kTestUserProfileDir[] = "Default";
183 #endif
184 
TestingProfile()185 TestingProfile::TestingProfile()
186     : start_time_(Time::Now()),
187       testing_prefs_(NULL),
188       incognito_(false),
189       force_incognito_(false),
190       original_profile_(NULL),
191       guest_session_(false),
192       last_session_exited_cleanly_(true),
193       browser_context_dependency_manager_(
194           BrowserContextDependencyManager::GetInstance()),
195       resource_context_(NULL),
196       delegate_(NULL) {
197   CreateTempProfileDir();
198   profile_path_ = temp_dir_.path();
199 
200   Init();
201   FinishInit();
202 }
203 
TestingProfile(const base::FilePath & path)204 TestingProfile::TestingProfile(const base::FilePath& path)
205     : start_time_(Time::Now()),
206       testing_prefs_(NULL),
207       incognito_(false),
208       force_incognito_(false),
209       original_profile_(NULL),
210       guest_session_(false),
211       last_session_exited_cleanly_(true),
212       profile_path_(path),
213       browser_context_dependency_manager_(
214           BrowserContextDependencyManager::GetInstance()),
215       resource_context_(NULL),
216       delegate_(NULL) {
217   Init();
218   FinishInit();
219 }
220 
TestingProfile(const base::FilePath & path,Delegate * delegate)221 TestingProfile::TestingProfile(const base::FilePath& path,
222                                Delegate* delegate)
223     : start_time_(Time::Now()),
224       testing_prefs_(NULL),
225       incognito_(false),
226       force_incognito_(false),
227       original_profile_(NULL),
228       guest_session_(false),
229       last_session_exited_cleanly_(true),
230       profile_path_(path),
231       browser_context_dependency_manager_(
232           BrowserContextDependencyManager::GetInstance()),
233       resource_context_(NULL),
234       delegate_(delegate) {
235   Init();
236   if (delegate_) {
237     base::MessageLoop::current()->PostTask(
238         FROM_HERE,
239         base::Bind(&TestingProfile::FinishInit, base::Unretained(this)));
240   } else {
241     FinishInit();
242   }
243 }
244 
TestingProfile(const base::FilePath & path,Delegate * delegate,scoped_refptr<ExtensionSpecialStoragePolicy> extension_policy,scoped_ptr<PrefServiceSyncable> prefs,bool incognito,bool guest_session,const std::string & supervised_user_id,scoped_ptr<policy::PolicyService> policy_service,const TestingFactories & factories)245 TestingProfile::TestingProfile(
246     const base::FilePath& path,
247     Delegate* delegate,
248     scoped_refptr<ExtensionSpecialStoragePolicy> extension_policy,
249     scoped_ptr<PrefServiceSyncable> prefs,
250     bool incognito,
251     bool guest_session,
252     const std::string& supervised_user_id,
253     scoped_ptr<policy::PolicyService> policy_service,
254     const TestingFactories& factories)
255     : start_time_(Time::Now()),
256       prefs_(prefs.release()),
257       testing_prefs_(NULL),
258       incognito_(incognito),
259       force_incognito_(false),
260       original_profile_(NULL),
261       guest_session_(guest_session),
262       supervised_user_id_(supervised_user_id),
263       last_session_exited_cleanly_(true),
264       extension_special_storage_policy_(extension_policy),
265       profile_path_(path),
266       browser_context_dependency_manager_(
267           BrowserContextDependencyManager::GetInstance()),
268       resource_context_(NULL),
269       delegate_(delegate),
270       policy_service_(policy_service.release()) {
271   // If no profile path was supplied, create one.
272   if (profile_path_.empty()) {
273     CreateTempProfileDir();
274     profile_path_ = temp_dir_.path();
275   }
276 
277   // Set any testing factories prior to initializing the services.
278   for (TestingFactories::const_iterator it = factories.begin();
279        it != factories.end(); ++it) {
280     it->first->SetTestingFactory(this, it->second);
281   }
282 
283   Init();
284   // If caller supplied a delegate, delay the FinishInit invocation until other
285   // tasks have run.
286   // TODO(atwilson): See if this is still required once we convert the current
287   // users of the constructor that takes a Delegate* param.
288   if (delegate_) {
289     base::MessageLoop::current()->PostTask(
290         FROM_HERE,
291         base::Bind(&TestingProfile::FinishInit, base::Unretained(this)));
292   } else {
293     FinishInit();
294   }
295 }
296 
CreateTempProfileDir()297 void TestingProfile::CreateTempProfileDir() {
298   if (!temp_dir_.CreateUniqueTempDir()) {
299     LOG(ERROR) << "Failed to create unique temporary directory.";
300 
301     // Fallback logic in case we fail to create unique temporary directory.
302     base::FilePath system_tmp_dir;
303     bool success = PathService::Get(base::DIR_TEMP, &system_tmp_dir);
304 
305     // We're severly screwed if we can't get the system temporary
306     // directory. Die now to avoid writing to the filesystem root
307     // or other bad places.
308     CHECK(success);
309 
310     base::FilePath fallback_dir(
311         system_tmp_dir.AppendASCII("TestingProfilePath"));
312     base::DeleteFile(fallback_dir, true);
313     base::CreateDirectory(fallback_dir);
314     if (!temp_dir_.Set(fallback_dir)) {
315       // That shouldn't happen, but if it does, try to recover.
316       LOG(ERROR) << "Failed to use a fallback temporary directory.";
317 
318       // We're screwed if this fails, see CHECK above.
319       CHECK(temp_dir_.Set(system_tmp_dir));
320     }
321   }
322 }
323 
Init()324 void TestingProfile::Init() {
325   // If threads have been initialized, we should be on the UI thread.
326   DCHECK(!content::BrowserThread::IsThreadInitialized(
327              content::BrowserThread::UI) ||
328          content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
329 
330 #if defined(OS_ANDROID)
331   // Make sure token service knows its running in tests.
332   AndroidProfileOAuth2TokenService::set_is_testing_profile();
333 #endif
334 
335   // Normally this would happen during browser startup, but for tests
336   // we need to trigger creation of Profile-related services.
337   ChromeBrowserMainExtraPartsProfiles::
338       EnsureBrowserContextKeyedServiceFactoriesBuilt();
339 
340   if (prefs_.get())
341     user_prefs::UserPrefs::Set(this, prefs_.get());
342   else
343     CreateTestingPrefService();
344 
345   if (!base::PathExists(profile_path_))
346     base::CreateDirectory(profile_path_);
347 
348   // TODO(joaodasilva): remove this once this PKS isn't created in ProfileImpl
349   // anymore, after converting the PrefService to a PKS. Until then it must
350   // be associated with a TestingProfile too.
351   if (!IsOffTheRecord())
352     CreateProfilePolicyConnector();
353 
354   extensions::ExtensionSystemFactory::GetInstance()->SetTestingFactory(
355       this, extensions::TestExtensionSystem::Build);
356 
357   // If no original profile was specified for this profile: register preferences
358   // even if this is an incognito profile - this allows tests to create a
359   // standalone incognito profile while still having prefs registered.
360   if (!IsOffTheRecord() || !original_profile_) {
361     user_prefs::PrefRegistrySyncable* pref_registry =
362         static_cast<user_prefs::PrefRegistrySyncable*>(
363             prefs_->DeprecatedGetPrefRegistry());
364     browser_context_dependency_manager_->
365         RegisterProfilePrefsForServices(this, pref_registry);
366   }
367 
368   browser_context_dependency_manager_->CreateBrowserContextServicesForTest(
369       this);
370 
371 #if defined(ENABLE_NOTIFICATIONS)
372   // Install profile keyed service factory hooks for dummy/test services
373   DesktopNotificationServiceFactory::GetInstance()->SetTestingFactory(
374       this, CreateTestDesktopNotificationService);
375 #endif
376 
377 #if defined(ENABLE_MANAGED_USERS)
378   SupervisedUserSettingsService* settings_service =
379       SupervisedUserSettingsServiceFactory::GetForProfile(this);
380   TestingPrefStore* store = new TestingPrefStore();
381   settings_service->Init(store);
382   store->SetInitializationCompleted();
383 #endif
384 
385   profile_name_ = "testing_profile";
386 }
387 
FinishInit()388 void TestingProfile::FinishInit() {
389   DCHECK(content::NotificationService::current());
390   content::NotificationService::current()->Notify(
391       chrome::NOTIFICATION_PROFILE_CREATED,
392       content::Source<Profile>(static_cast<Profile*>(this)),
393       content::NotificationService::NoDetails());
394 
395   ProfileManager* profile_manager = g_browser_process->profile_manager();
396   if (profile_manager)
397     profile_manager->InitProfileUserPrefs(this);
398 
399   if (delegate_)
400     delegate_->OnProfileCreated(this, true, false);
401 }
402 
~TestingProfile()403 TestingProfile::~TestingProfile() {
404   // Revert to non-incognito mode before shutdown.
405   force_incognito_ = false;
406 
407   // Any objects holding live URLFetchers should be deleted before teardown.
408   TemplateURLFetcherFactory::ShutdownForProfile(this);
409 
410   MaybeSendDestroyedNotification();
411 
412   browser_context_dependency_manager_->DestroyBrowserContextServices(this);
413 
414   if (host_content_settings_map_.get())
415     host_content_settings_map_->ShutdownOnUIThread();
416 
417   DestroyTopSites();
418 
419   if (pref_proxy_config_tracker_.get())
420     pref_proxy_config_tracker_->DetachFromPrefService();
421   // Failing a post == leaks == heapcheck failure. Make that an immediate test
422   // failure.
423   if (resource_context_) {
424     CHECK(BrowserThread::DeleteSoon(BrowserThread::IO, FROM_HERE,
425                                     resource_context_));
426     resource_context_ = NULL;
427     content::RunAllPendingInMessageLoop(BrowserThread::IO);
428   }
429 }
430 
BuildFaviconService(content::BrowserContext * profile)431 static KeyedService* BuildFaviconService(content::BrowserContext* profile) {
432   return new FaviconService(static_cast<Profile*>(profile));
433 }
434 
CreateFaviconService()435 void TestingProfile::CreateFaviconService() {
436   // It is up to the caller to create the history service if one is needed.
437   FaviconServiceFactory::GetInstance()->SetTestingFactory(
438       this, BuildFaviconService);
439 }
440 
BuildHistoryService(content::BrowserContext * context)441 static KeyedService* BuildHistoryService(content::BrowserContext* context) {
442   Profile* profile = static_cast<Profile*>(context);
443   return new HistoryService(ChromeHistoryClientFactory::GetForProfile(profile),
444                             profile);
445 }
446 
CreateHistoryService(bool delete_file,bool no_db)447 bool TestingProfile::CreateHistoryService(bool delete_file, bool no_db) {
448   DestroyHistoryService();
449   if (delete_file) {
450     base::FilePath path = GetPath();
451     path = path.Append(chrome::kHistoryFilename);
452     if (!base::DeleteFile(path, false) || base::PathExists(path))
453       return false;
454   }
455   // This will create and init the history service.
456   HistoryService* history_service = static_cast<HistoryService*>(
457       HistoryServiceFactory::GetInstance()->SetTestingFactoryAndUse(
458           this, BuildHistoryService));
459   if (!history_service->Init(this->GetPath(), no_db)) {
460     HistoryServiceFactory::GetInstance()->SetTestingFactoryAndUse(this, NULL);
461   }
462   // Disable WebHistoryService by default, since it makes network requests.
463   WebHistoryServiceFactory::GetInstance()->SetTestingFactory(this, NULL);
464   return true;
465 }
466 
DestroyHistoryService()467 void TestingProfile::DestroyHistoryService() {
468   HistoryService* history_service =
469       HistoryServiceFactory::GetForProfileWithoutCreating(this);
470   if (!history_service)
471     return;
472 
473   history_service->ClearCachedDataForContextID(0);
474   history_service->SetOnBackendDestroyTask(base::MessageLoop::QuitClosure());
475   history_service->Cleanup();
476   HistoryServiceFactory::ShutdownForProfile(this);
477 
478   // Wait for the backend class to terminate before deleting the files and
479   // moving to the next test. Note: if this never terminates, somebody is
480   // probably leaking a reference to the history backend, so it never calls
481   // our destroy task.
482   base::MessageLoop::current()->Run();
483 
484   // Make sure we don't have any event pending that could disrupt the next
485   // test.
486   base::MessageLoop::current()->PostTask(FROM_HERE,
487                                          base::MessageLoop::QuitClosure());
488   base::MessageLoop::current()->Run();
489 }
490 
CreateTopSites()491 void TestingProfile::CreateTopSites() {
492   DestroyTopSites();
493   top_sites_ = history::TopSites::Create(
494       this, GetPath().Append(chrome::kTopSitesFilename));
495 }
496 
DestroyTopSites()497 void TestingProfile::DestroyTopSites() {
498   if (top_sites_.get()) {
499     top_sites_->Shutdown();
500     top_sites_ = NULL;
501     // TopSitesImpl::Shutdown schedules some tasks (from TopSitesBackend) that
502     // need to be run to properly shutdown. Run all pending tasks now. This is
503     // normally handled by browser_process shutdown.
504     if (base::MessageLoop::current())
505       base::MessageLoop::current()->RunUntilIdle();
506   }
507 }
508 
BuildBookmarkModel(content::BrowserContext * context)509 static KeyedService* BuildBookmarkModel(content::BrowserContext* context) {
510   Profile* profile = static_cast<Profile*>(context);
511   ChromeBookmarkClient* bookmark_client =
512       ChromeBookmarkClientFactory::GetForProfile(profile);
513   BookmarkModel* bookmark_model = new BookmarkModel(bookmark_client, false);
514   bookmark_client->Init(bookmark_model);
515   bookmark_model->Load(profile->GetPrefs(),
516                        profile->GetPrefs()->GetString(prefs::kAcceptLanguages),
517                        profile->GetPath(),
518                        profile->GetIOTaskRunner(),
519                        content::BrowserThread::GetMessageLoopProxyForThread(
520                            content::BrowserThread::UI));
521   return bookmark_model;
522 }
523 
BuildChromeBookmarkClient(content::BrowserContext * context)524 static KeyedService* BuildChromeBookmarkClient(
525     content::BrowserContext* context) {
526   return new ChromeBookmarkClient(static_cast<Profile*>(context));
527 }
528 
BuildChromeHistoryClient(content::BrowserContext * context)529 static KeyedService* BuildChromeHistoryClient(
530     content::BrowserContext* context) {
531   Profile* profile = static_cast<Profile*>(context);
532   return new ChromeHistoryClient(BookmarkModelFactory::GetForProfile(profile));
533 }
534 
CreateBookmarkModel(bool delete_file)535 void TestingProfile::CreateBookmarkModel(bool delete_file) {
536   if (delete_file) {
537     base::FilePath path = GetPath().Append(bookmarks::kBookmarksFileName);
538     base::DeleteFile(path, false);
539   }
540   ChromeHistoryClientFactory::GetInstance()->SetTestingFactory(
541       this, BuildChromeHistoryClient);
542   ChromeBookmarkClientFactory::GetInstance()->SetTestingFactory(
543       this, BuildChromeBookmarkClient);
544   // This creates the BookmarkModel.
545   ignore_result(BookmarkModelFactory::GetInstance()->SetTestingFactoryAndUse(
546       this, BuildBookmarkModel));
547 }
548 
BuildWebDataService(content::BrowserContext * profile)549 static KeyedService* BuildWebDataService(content::BrowserContext* profile) {
550   return new WebDataServiceWrapper(static_cast<Profile*>(profile));
551 }
552 
CreateWebDataService()553 void TestingProfile::CreateWebDataService() {
554   WebDataServiceFactory::GetInstance()->SetTestingFactory(
555       this, BuildWebDataService);
556 }
557 
BlockUntilHistoryIndexIsRefreshed()558 void TestingProfile::BlockUntilHistoryIndexIsRefreshed() {
559   // Only get the history service if it actually exists since the caller of the
560   // test should explicitly call CreateHistoryService to build it.
561   HistoryService* history_service =
562       HistoryServiceFactory::GetForProfileWithoutCreating(this);
563   DCHECK(history_service);
564   history::InMemoryURLIndex* index = history_service->InMemoryIndex();
565   if (!index || index->restored())
566     return;
567   base::RunLoop run_loop;
568   HistoryIndexRestoreObserver observer(
569       content::GetQuitTaskForRunLoop(&run_loop));
570   index->set_restore_cache_observer(&observer);
571   run_loop.Run();
572   index->set_restore_cache_observer(NULL);
573   DCHECK(index->restored());
574 }
575 
576 // TODO(phajdan.jr): Doesn't this hang if Top Sites are already loaded?
BlockUntilTopSitesLoaded()577 void TestingProfile::BlockUntilTopSitesLoaded() {
578   content::WindowedNotificationObserver top_sites_loaded_observer(
579       chrome::NOTIFICATION_TOP_SITES_LOADED,
580       content::NotificationService::AllSources());
581   top_sites_loaded_observer.Wait();
582 }
583 
SetGuestSession(bool guest)584 void TestingProfile::SetGuestSession(bool guest) {
585   guest_session_ = guest;
586 }
587 
GetPath() const588 base::FilePath TestingProfile::GetPath() const {
589   return profile_path_;
590 }
591 
GetIOTaskRunner()592 scoped_refptr<base::SequencedTaskRunner> TestingProfile::GetIOTaskRunner() {
593   return base::MessageLoop::current()->message_loop_proxy();
594 }
595 
GetTestingPrefService()596 TestingPrefServiceSyncable* TestingProfile::GetTestingPrefService() {
597   if (!prefs_.get())
598     CreateTestingPrefService();
599   DCHECK(testing_prefs_);
600   return testing_prefs_;
601 }
602 
AsTestingProfile()603 TestingProfile* TestingProfile::AsTestingProfile() {
604   return this;
605 }
606 
GetProfileName()607 std::string TestingProfile::GetProfileName() {
608   return profile_name_;
609 }
610 
GetProfileType() const611 Profile::ProfileType TestingProfile::GetProfileType() const {
612   if (guest_session_)
613     return GUEST_PROFILE;
614   if (force_incognito_ || incognito_)
615     return INCOGNITO_PROFILE;
616   return REGULAR_PROFILE;
617 }
618 
IsOffTheRecord() const619 bool TestingProfile::IsOffTheRecord() const {
620   return force_incognito_ || incognito_;
621 }
622 
SetOffTheRecordProfile(scoped_ptr<Profile> profile)623 void TestingProfile::SetOffTheRecordProfile(scoped_ptr<Profile> profile) {
624   DCHECK(!IsOffTheRecord());
625   incognito_profile_ = profile.Pass();
626 }
627 
SetOriginalProfile(Profile * profile)628 void TestingProfile::SetOriginalProfile(Profile* profile) {
629   DCHECK(IsOffTheRecord());
630   original_profile_ = profile;
631 }
632 
GetOffTheRecordProfile()633 Profile* TestingProfile::GetOffTheRecordProfile() {
634   if (IsOffTheRecord())
635     return this;
636   if (!incognito_profile_) {
637     TestingProfile::Builder builder;
638     builder.SetIncognito();
639     scoped_ptr<TestingProfile> incognito_test_profile(builder.Build());
640     incognito_test_profile->SetOriginalProfile(this);
641     SetOffTheRecordProfile(incognito_test_profile.PassAs<Profile>());
642   }
643   return incognito_profile_.get();
644 }
645 
HasOffTheRecordProfile()646 bool TestingProfile::HasOffTheRecordProfile() {
647   return incognito_profile_.get() != NULL;
648 }
649 
GetOriginalProfile()650 Profile* TestingProfile::GetOriginalProfile() {
651   if (original_profile_)
652     return original_profile_;
653   return this;
654 }
655 
IsSupervised()656 bool TestingProfile::IsSupervised() {
657   return !supervised_user_id_.empty();
658 }
659 
GetExtensionService()660 ExtensionService* TestingProfile::GetExtensionService() {
661   return extensions::ExtensionSystem::Get(this)->extension_service();
662 }
663 
SetExtensionSpecialStoragePolicy(ExtensionSpecialStoragePolicy * extension_special_storage_policy)664 void TestingProfile::SetExtensionSpecialStoragePolicy(
665     ExtensionSpecialStoragePolicy* extension_special_storage_policy) {
666   extension_special_storage_policy_ = extension_special_storage_policy;
667 }
668 
669 ExtensionSpecialStoragePolicy*
GetExtensionSpecialStoragePolicy()670 TestingProfile::GetExtensionSpecialStoragePolicy() {
671   if (!extension_special_storage_policy_.get())
672     extension_special_storage_policy_ = new ExtensionSpecialStoragePolicy(NULL);
673   return extension_special_storage_policy_.get();
674 }
675 
GetCookieMonster()676 net::CookieMonster* TestingProfile::GetCookieMonster() {
677   if (!GetRequestContext())
678     return NULL;
679   return GetRequestContext()->GetURLRequestContext()->cookie_store()->
680       GetCookieMonster();
681 }
682 
CreateTestingPrefService()683 void TestingProfile::CreateTestingPrefService() {
684   DCHECK(!prefs_.get());
685   testing_prefs_ = new TestingPrefServiceSyncable();
686   prefs_.reset(testing_prefs_);
687   user_prefs::UserPrefs::Set(this, prefs_.get());
688   chrome::RegisterUserProfilePrefs(testing_prefs_->registry());
689 }
690 
CreateProfilePolicyConnector()691 void TestingProfile::CreateProfilePolicyConnector() {
692 #if defined(ENABLE_CONFIGURATION_POLICY)
693   schema_registry_service_ =
694       policy::SchemaRegistryServiceFactory::CreateForContext(
695           this, policy::Schema(), NULL);
696   CHECK_EQ(schema_registry_service_.get(),
697            policy::SchemaRegistryServiceFactory::GetForContext(this));
698 #endif  // defined(ENABLE_CONFIGURATION_POLICY)
699 
700 if (!policy_service_) {
701 #if defined(ENABLE_CONFIGURATION_POLICY)
702     std::vector<policy::ConfigurationPolicyProvider*> providers;
703     policy_service_.reset(new policy::PolicyServiceImpl(providers));
704 #else
705     policy_service_.reset(new policy::PolicyServiceStub());
706 #endif
707   }
708   profile_policy_connector_.reset(new policy::ProfilePolicyConnector());
709   profile_policy_connector_->InitForTesting(policy_service_.Pass());
710   policy::ProfilePolicyConnectorFactory::GetInstance()->SetServiceForTesting(
711       this, profile_policy_connector_.get());
712   CHECK_EQ(profile_policy_connector_.get(),
713            policy::ProfilePolicyConnectorFactory::GetForProfile(this));
714 }
715 
GetPrefs()716 PrefService* TestingProfile::GetPrefs() {
717   if (!prefs_.get()) {
718     CreateTestingPrefService();
719   }
720   return prefs_.get();
721 }
722 
GetTopSites()723 history::TopSites* TestingProfile::GetTopSites() {
724   return top_sites_.get();
725 }
726 
GetTopSitesWithoutCreating()727 history::TopSites* TestingProfile::GetTopSitesWithoutCreating() {
728   return top_sites_.get();
729 }
730 
GetDownloadManagerDelegate()731 DownloadManagerDelegate* TestingProfile::GetDownloadManagerDelegate() {
732   return NULL;
733 }
734 
GetRequestContext()735 net::URLRequestContextGetter* TestingProfile::GetRequestContext() {
736   return GetDefaultStoragePartition(this)->GetURLRequestContext();
737 }
738 
CreateRequestContext(content::ProtocolHandlerMap * protocol_handlers,content::URLRequestInterceptorScopedVector request_interceptors)739 net::URLRequestContextGetter* TestingProfile::CreateRequestContext(
740     content::ProtocolHandlerMap* protocol_handlers,
741     content::URLRequestInterceptorScopedVector request_interceptors) {
742   return new net::TestURLRequestContextGetter(
743             BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO));
744 }
745 
GetRequestContextForRenderProcess(int renderer_child_id)746 net::URLRequestContextGetter* TestingProfile::GetRequestContextForRenderProcess(
747     int renderer_child_id) {
748   content::RenderProcessHost* rph = content::RenderProcessHost::FromID(
749       renderer_child_id);
750   return rph->GetStoragePartition()->GetURLRequestContext();
751 }
752 
GetMediaRequestContext()753 net::URLRequestContextGetter* TestingProfile::GetMediaRequestContext() {
754   return NULL;
755 }
756 
757 net::URLRequestContextGetter*
GetMediaRequestContextForRenderProcess(int renderer_child_id)758 TestingProfile::GetMediaRequestContextForRenderProcess(
759     int renderer_child_id) {
760   return NULL;
761 }
762 
763 net::URLRequestContextGetter*
GetMediaRequestContextForStoragePartition(const base::FilePath & partition_path,bool in_memory)764 TestingProfile::GetMediaRequestContextForStoragePartition(
765     const base::FilePath& partition_path,
766     bool in_memory) {
767   return NULL;
768 }
769 
GetRequestContextForExtensions()770 net::URLRequestContextGetter* TestingProfile::GetRequestContextForExtensions() {
771   if (!extensions_request_context_.get())
772     extensions_request_context_ = new TestExtensionURLRequestContextGetter();
773   return extensions_request_context_.get();
774 }
775 
GetSSLConfigService()776 net::SSLConfigService* TestingProfile::GetSSLConfigService() {
777   if (!GetRequestContext())
778     return NULL;
779   return GetRequestContext()->GetURLRequestContext()->ssl_config_service();
780 }
781 
782 net::URLRequestContextGetter*
CreateRequestContextForStoragePartition(const base::FilePath & partition_path,bool in_memory,content::ProtocolHandlerMap * protocol_handlers,content::URLRequestInterceptorScopedVector request_interceptors)783 TestingProfile::CreateRequestContextForStoragePartition(
784     const base::FilePath& partition_path,
785     bool in_memory,
786     content::ProtocolHandlerMap* protocol_handlers,
787     content::URLRequestInterceptorScopedVector request_interceptors) {
788   // We don't test storage partitions here yet, so returning the same dummy
789   // context is sufficient for now.
790   return GetRequestContext();
791 }
792 
GetResourceContext()793 content::ResourceContext* TestingProfile::GetResourceContext() {
794   if (!resource_context_)
795     resource_context_ = new content::MockResourceContext();
796   return resource_context_;
797 }
798 
GetHostContentSettingsMap()799 HostContentSettingsMap* TestingProfile::GetHostContentSettingsMap() {
800   if (!host_content_settings_map_.get()) {
801     host_content_settings_map_ = new HostContentSettingsMap(GetPrefs(), false);
802 #if defined(ENABLE_EXTENSIONS)
803     ExtensionService* extension_service = GetExtensionService();
804     if (extension_service)
805       host_content_settings_map_->RegisterExtensionService(extension_service);
806 #endif
807   }
808   return host_content_settings_map_.get();
809 }
810 
GetGuestManager()811 content::BrowserPluginGuestManager* TestingProfile::GetGuestManager() {
812 #if defined(ENABLE_EXTENSIONS)
813   return GuestViewManager::FromBrowserContext(this);
814 #else
815   return NULL;
816 #endif
817 }
818 
GetPushMessagingService()819 content::PushMessagingService* TestingProfile::GetPushMessagingService() {
820   return NULL;
821 }
822 
IsSameProfile(Profile * p)823 bool TestingProfile::IsSameProfile(Profile *p) {
824   return this == p;
825 }
826 
GetStartTime() const827 base::Time TestingProfile::GetStartTime() const {
828   return start_time_;
829 }
830 
last_selected_directory()831 base::FilePath TestingProfile::last_selected_directory() {
832   return last_selected_directory_;
833 }
834 
set_last_selected_directory(const base::FilePath & path)835 void TestingProfile::set_last_selected_directory(const base::FilePath& path) {
836   last_selected_directory_ = path;
837 }
838 
GetProxyConfigTracker()839 PrefProxyConfigTracker* TestingProfile::GetProxyConfigTracker() {
840   if (!pref_proxy_config_tracker_.get()) {
841     // TestingProfile is used in unit tests, where local state is not available.
842     pref_proxy_config_tracker_.reset(
843         ProxyServiceFactory::CreatePrefProxyConfigTrackerOfProfile(GetPrefs(),
844                                                                    NULL));
845   }
846   return pref_proxy_config_tracker_.get();
847 }
848 
BlockUntilHistoryProcessesPendingRequests()849 void TestingProfile::BlockUntilHistoryProcessesPendingRequests() {
850   HistoryService* history_service =
851       HistoryServiceFactory::GetForProfile(this, Profile::EXPLICIT_ACCESS);
852   DCHECK(history_service);
853   DCHECK(base::MessageLoop::current());
854 
855   CancelableRequestConsumer consumer;
856   history_service->ScheduleDBTask(new QuittingHistoryDBTask(), &consumer);
857   base::MessageLoop::current()->Run();
858 }
859 
GetNetworkPredictor()860 chrome_browser_net::Predictor* TestingProfile::GetNetworkPredictor() {
861   return NULL;
862 }
863 
GetDevToolsNetworkController()864 DevToolsNetworkController* TestingProfile::GetDevToolsNetworkController() {
865   return NULL;
866 }
867 
ClearNetworkingHistorySince(base::Time time,const base::Closure & completion)868 void TestingProfile::ClearNetworkingHistorySince(
869     base::Time time,
870     const base::Closure& completion) {
871   if (!completion.is_null()) {
872     BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, completion);
873   }
874 }
875 
ClearDomainReliabilityMonitor(domain_reliability::DomainReliabilityClearMode mode,const base::Closure & completion)876 void TestingProfile::ClearDomainReliabilityMonitor(
877     domain_reliability::DomainReliabilityClearMode mode,
878     const base::Closure& completion) {
879   if (!completion.is_null()) {
880     BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, completion);
881   }
882 }
883 
GetHomePage()884 GURL TestingProfile::GetHomePage() {
885   return GURL(chrome::kChromeUINewTabURL);
886 }
887 
GetOffTheRecordPrefs()888 PrefService* TestingProfile::GetOffTheRecordPrefs() {
889   return NULL;
890 }
891 
GetSpecialStoragePolicy()892 quota::SpecialStoragePolicy* TestingProfile::GetSpecialStoragePolicy() {
893   return GetExtensionSpecialStoragePolicy();
894 }
895 
WasCreatedByVersionOrLater(const std::string & version)896 bool TestingProfile::WasCreatedByVersionOrLater(const std::string& version) {
897   return true;
898 }
899 
IsGuestSession() const900 bool TestingProfile::IsGuestSession() const {
901   return guest_session_;
902 }
903 
GetLastSessionExitType()904 Profile::ExitType TestingProfile::GetLastSessionExitType() {
905   return last_session_exited_cleanly_ ? EXIT_NORMAL : EXIT_CRASHED;
906 }
907 
Builder()908 TestingProfile::Builder::Builder()
909     : build_called_(false),
910       delegate_(NULL),
911       incognito_(false),
912       guest_session_(false) {
913 }
914 
~Builder()915 TestingProfile::Builder::~Builder() {
916 }
917 
SetPath(const base::FilePath & path)918 void TestingProfile::Builder::SetPath(const base::FilePath& path) {
919   path_ = path;
920 }
921 
SetDelegate(Delegate * delegate)922 void TestingProfile::Builder::SetDelegate(Delegate* delegate) {
923   delegate_ = delegate;
924 }
925 
SetExtensionSpecialStoragePolicy(scoped_refptr<ExtensionSpecialStoragePolicy> policy)926 void TestingProfile::Builder::SetExtensionSpecialStoragePolicy(
927     scoped_refptr<ExtensionSpecialStoragePolicy> policy) {
928   extension_policy_ = policy;
929 }
930 
SetPrefService(scoped_ptr<PrefServiceSyncable> prefs)931 void TestingProfile::Builder::SetPrefService(
932     scoped_ptr<PrefServiceSyncable> prefs) {
933   pref_service_ = prefs.Pass();
934 }
935 
SetIncognito()936 void TestingProfile::Builder::SetIncognito() {
937   incognito_ = true;
938 }
939 
SetGuestSession()940 void TestingProfile::Builder::SetGuestSession() {
941   guest_session_ = true;
942 }
943 
SetSupervisedUserId(const std::string & supervised_user_id)944 void TestingProfile::Builder::SetSupervisedUserId(
945     const std::string& supervised_user_id) {
946   supervised_user_id_ = supervised_user_id;
947 }
948 
SetPolicyService(scoped_ptr<policy::PolicyService> policy_service)949 void TestingProfile::Builder::SetPolicyService(
950     scoped_ptr<policy::PolicyService> policy_service) {
951   policy_service_ = policy_service.Pass();
952 }
953 
AddTestingFactory(BrowserContextKeyedServiceFactory * service_factory,BrowserContextKeyedServiceFactory::TestingFactoryFunction callback)954 void TestingProfile::Builder::AddTestingFactory(
955     BrowserContextKeyedServiceFactory* service_factory,
956     BrowserContextKeyedServiceFactory::TestingFactoryFunction callback) {
957   testing_factories_.push_back(std::make_pair(service_factory, callback));
958 }
959 
Build()960 scoped_ptr<TestingProfile> TestingProfile::Builder::Build() {
961   DCHECK(!build_called_);
962   build_called_ = true;
963 
964   return scoped_ptr<TestingProfile>(new TestingProfile(
965       path_,
966       delegate_,
967       extension_policy_,
968       pref_service_.Pass(),
969       incognito_,
970       guest_session_,
971       supervised_user_id_,
972       policy_service_.Pass(),
973       testing_factories_));
974 }
975